1#![cfg_attr(docsrs, feature(doc_cfg))]
2#![deny(unreachable_patterns)]
3#![deny(missing_copy_implementations)]
4#![deny(trivial_casts)]
5#![deny(trivial_numeric_casts)]
6#![deny(unreachable_pub)]
7#![deny(clippy::all)]
8#![allow(clippy::enum_variant_names)]
9#![allow(clippy::clone_on_copy)]
10#![recursion_limit = "1024"]
11
12pub use num_bigint::BigInt as BigIntValue;
13#[cfg(feature = "serde")]
14use serde::{Deserialize, Serialize};
15use swc_common::{ast_node, pass::Either, util::take::Take, EqIgnoreSpan, Span};
16
17pub use self::{
18 class::{
19 AutoAccessor, Class, ClassMember, ClassMethod, ClassProp, Constructor, Decorator, Key,
20 MethodKind, PrivateMethod, PrivateProp, StaticBlock,
21 },
22 decl::{ClassDecl, Decl, FnDecl, UsingDecl, VarDecl, VarDeclKind, VarDeclarator},
23 expr::*,
24 function::{Function, Param, ParamOrTsParamProp},
25 ident::{
26 unsafe_id, unsafe_id_from_ident, BindingIdent, EsReserved, Id, Ident, IdentName,
27 PrivateName, UnsafeId,
28 },
29 jsx::{
30 JSXAttr, JSXAttrName, JSXAttrOrSpread, JSXAttrValue, JSXClosingElement, JSXClosingFragment,
31 JSXElement, JSXElementChild, JSXElementName, JSXEmptyExpr, JSXExpr, JSXExprContainer,
32 JSXFragment, JSXMemberExpr, JSXNamespacedName, JSXObject, JSXOpeningElement,
33 JSXOpeningFragment, JSXSpreadChild, JSXText,
34 },
35 list::ListFormat,
36 lit::{BigInt, Bool, Lit, Null, Number, Regex, Str},
37 module::{Module, ModuleItem, Program, Script},
38 module_decl::{
39 DefaultDecl, ExportAll, ExportDecl, ExportDefaultDecl, ExportDefaultExpr,
40 ExportDefaultSpecifier, ExportNamedSpecifier, ExportNamespaceSpecifier, ExportSpecifier,
41 ImportDecl, ImportDefaultSpecifier, ImportNamedSpecifier, ImportPhase, ImportSpecifier,
42 ImportStarAsSpecifier, ModuleDecl, ModuleExportName, NamedExport,
43 },
44 operators::{AssignOp, BinaryOp, UnaryOp, UpdateOp},
45 pat::{
46 ArrayPat, AssignPat, AssignPatProp, KeyValuePatProp, ObjectPat, ObjectPatProp, Pat, RestPat,
47 },
48 prop::{
49 AssignProp, ComputedPropName, GetterProp, KeyValueProp, MethodProp, Prop, PropName,
50 SetterProp,
51 },
52 source_map::{SourceMapperExt, SpanExt},
53 stmt::{
54 BlockStmt, BreakStmt, CatchClause, ContinueStmt, DebuggerStmt, DoWhileStmt, EmptyStmt,
55 ExprStmt, ForHead, ForInStmt, ForOfStmt, ForStmt, IfStmt, LabeledStmt, ReturnStmt, Stmt,
56 SwitchCase, SwitchStmt, ThrowStmt, TryStmt, VarDeclOrExpr, WhileStmt, WithStmt,
57 },
58 typescript::{
59 Accessibility, TruePlusMinus, TsArrayType, TsAsExpr, TsCallSignatureDecl,
60 TsConditionalType, TsConstAssertion, TsConstructSignatureDecl, TsConstructorType,
61 TsEntityName, TsEnumDecl, TsEnumMember, TsEnumMemberId, TsExportAssignment,
62 TsExprWithTypeArgs, TsExternalModuleRef, TsFnOrConstructorType, TsFnParam, TsFnType,
63 TsGetterSignature, TsImportCallOptions, TsImportEqualsDecl, TsImportType, TsIndexSignature,
64 TsIndexedAccessType, TsInferType, TsInstantiation, TsInterfaceBody, TsInterfaceDecl,
65 TsIntersectionType, TsKeywordType, TsKeywordTypeKind, TsLit, TsLitType, TsMappedType,
66 TsMethodSignature, TsModuleBlock, TsModuleDecl, TsModuleName, TsModuleRef, TsNamespaceBody,
67 TsNamespaceDecl, TsNamespaceExportDecl, TsNonNullExpr, TsOptionalType, TsParamProp,
68 TsParamPropParam, TsParenthesizedType, TsPropertySignature, TsQualifiedName, TsRestType,
69 TsSatisfiesExpr, TsSetterSignature, TsThisType, TsThisTypeOrIdent, TsTplLitType,
70 TsTupleElement, TsTupleType, TsType, TsTypeAliasDecl, TsTypeAnn, TsTypeAssertion,
71 TsTypeElement, TsTypeLit, TsTypeOperator, TsTypeOperatorOp, TsTypeParam, TsTypeParamDecl,
72 TsTypeParamInstantiation, TsTypePredicate, TsTypeQuery, TsTypeQueryExpr, TsTypeRef,
73 TsUnionOrIntersectionType, TsUnionType,
74 },
75};
76
77#[macro_use]
78mod macros;
79mod class;
80mod decl;
81mod expr;
82mod function;
83mod ident;
84mod jsx;
85mod list;
86mod lit;
87mod module;
88mod module_decl;
89mod operators;
90mod pat;
91mod prop;
92mod source_map;
93mod stmt;
94mod typescript;
95
96pub trait Pass {
106 fn process(&mut self, program: &mut Program);
107}
108
109impl<P> Pass for Option<P>
111where
112 P: Pass,
113{
114 #[inline(always)]
115 fn process(&mut self, program: &mut Program) {
116 if let Some(pass) = self {
117 pass.process(program);
118 }
119 }
120}
121
122impl<P: ?Sized> Pass for Box<P>
123where
124 P: Pass,
125{
126 #[inline(always)]
127 fn process(&mut self, program: &mut Program) {
128 (**self).process(program);
129 }
130}
131
132impl<P: ?Sized> Pass for &'_ mut P
133where
134 P: Pass,
135{
136 #[inline(always)]
137 fn process(&mut self, program: &mut Program) {
138 (**self).process(program);
139 }
140}
141
142impl<L, R> Pass for Either<L, R>
143where
144 L: Pass,
145 R: Pass,
146{
147 #[inline]
148 fn process(&mut self, program: &mut Program) {
149 match self {
150 Either::Left(l) => l.process(program),
151 Either::Right(r) => r.process(program),
152 }
153 }
154}
155
156impl<P> Pass for swc_visit::Optional<P>
157where
158 P: Pass,
159{
160 #[inline]
161 fn process(&mut self, program: &mut Program) {
162 if self.enabled {
163 self.visitor.process(program);
164 }
165 }
166}
167
168impl<P> Pass for swc_visit::Repeat<P>
169where
170 P: Pass + swc_visit::Repeated,
171{
172 #[inline]
173 fn process(&mut self, program: &mut Program) {
174 loop {
175 self.pass.reset();
176 self.pass.process(program);
177
178 if !self.pass.changed() {
179 break;
180 }
181 }
182 }
183}
184
185impl Program {
186 #[inline(always)]
187 pub fn mutate<P>(&mut self, mut pass: P)
188 where
189 P: Pass,
190 {
191 pass.process(self);
192 }
193
194 #[inline(always)]
195 pub fn apply<P>(mut self, mut pass: P) -> Self
196 where
197 P: Pass,
198 {
199 pass.process(&mut self);
200 self
201 }
202}
203
204macro_rules! impl_pass_for_tuple {
205 (
206 [$idx:tt, $name:ident], $([$idx_rest:tt, $name_rest:ident]),*
207 ) => {
208 impl<$name, $($name_rest),*> Pass for ($name, $($name_rest),*)
209 where
210 $name: Pass,
211 $($name_rest: Pass),*
212 {
213 #[inline]
214 fn process(&mut self, program: &mut Program) {
215 self.$idx.process(program);
216
217 $(
218 self.$idx_rest.process(program);
219 )*
220
221 }
222 }
223 };
224}
225
226impl_pass_for_tuple!([0, A], [1, B]);
227impl_pass_for_tuple!([0, A], [1, B], [2, C]);
228impl_pass_for_tuple!([0, A], [1, B], [2, C], [3, D]);
229impl_pass_for_tuple!([0, A], [1, B], [2, C], [3, D], [4, E]);
230impl_pass_for_tuple!([0, A], [1, B], [2, C], [3, D], [4, E], [5, F]);
231impl_pass_for_tuple!([0, A], [1, B], [2, C], [3, D], [4, E], [5, F], [6, G]);
232impl_pass_for_tuple!(
233 [0, A],
234 [1, B],
235 [2, C],
236 [3, D],
237 [4, E],
238 [5, F],
239 [6, G],
240 [7, H]
241);
242impl_pass_for_tuple!(
243 [0, A],
244 [1, B],
245 [2, C],
246 [3, D],
247 [4, E],
248 [5, F],
249 [6, G],
250 [7, H],
251 [8, I]
252);
253impl_pass_for_tuple!(
254 [0, A],
255 [1, B],
256 [2, C],
257 [3, D],
258 [4, E],
259 [5, F],
260 [6, G],
261 [7, H],
262 [8, I],
263 [9, J]
264);
265impl_pass_for_tuple!(
266 [0, A],
267 [1, B],
268 [2, C],
269 [3, D],
270 [4, E],
271 [5, F],
272 [6, G],
273 [7, H],
274 [8, I],
275 [9, J],
276 [10, K]
277);
278impl_pass_for_tuple!(
279 [0, A],
280 [1, B],
281 [2, C],
282 [3, D],
283 [4, E],
284 [5, F],
285 [6, G],
286 [7, H],
287 [8, I],
288 [9, J],
289 [10, K],
290 [11, L]
291);
292impl_pass_for_tuple!(
293 [0, A],
294 [1, B],
295 [2, C],
296 [3, D],
297 [4, E],
298 [5, F],
299 [6, G],
300 [7, H],
301 [8, I],
302 [9, J],
303 [10, K],
304 [11, L],
305 [12, M]
306);
307
308#[inline(always)]
309pub fn noop_pass() -> impl Pass {
310 fn noop(_: &mut Program) {}
311
312 fn_pass(noop)
313}
314
315#[inline(always)]
316pub fn fn_pass(f: impl FnMut(&mut Program)) -> impl Pass {
317 FnPass { f }
318}
319
320struct FnPass<F> {
321 f: F,
322}
323
324impl<F> Pass for FnPass<F>
325where
326 F: FnMut(&mut Program),
327{
328 fn process(&mut self, program: &mut Program) {
329 (self.f)(program);
330 }
331}
332
333#[ast_node("Invalid")]
335#[derive(Eq, Default, Hash, Copy, EqIgnoreSpan)]
336#[cfg_attr(feature = "arbitrary", derive(arbitrary::Arbitrary))]
337#[cfg_attr(feature = "shrink-to-fit", derive(shrink_to_fit::ShrinkToFit))]
338pub struct Invalid {
339 pub span: Span,
340}
341
342impl Take for Invalid {
343 fn dummy() -> Self {
344 Invalid::default()
345 }
346}
347
348#[derive(Debug, Default, Clone, Copy, PartialOrd, Ord, PartialEq, Eq, Hash)]
351#[cfg_attr(feature = "serde", derive(Serialize))]
352#[cfg_attr(feature = "serde", serde(rename_all = "lowercase"))]
353pub enum EsVersion {
354 Es3,
355 #[default]
356 Es5,
357 Es2015,
358 Es2016,
359 Es2017,
360 Es2018,
361 Es2019,
362 Es2020,
363 Es2021,
364 Es2022,
365 Es2023,
366 Es2024,
367 EsNext,
368}
369
370#[cfg(feature = "serde")]
371impl<'de> Deserialize<'de> for EsVersion {
372 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
373 where
374 D: serde::Deserializer<'de>,
375 {
376 use serde::de::Error;
377
378 let s = String::deserialize(deserializer)?;
379 match s.to_lowercase().as_str() {
380 "es3" => Ok(EsVersion::Es3),
381 "es5" => Ok(EsVersion::Es5),
382 "es2015" | "es6" => Ok(EsVersion::Es2015),
383 "es2016" => Ok(EsVersion::Es2016),
384 "es2017" => Ok(EsVersion::Es2017),
385 "es2018" => Ok(EsVersion::Es2018),
386 "es2019" => Ok(EsVersion::Es2019),
387 "es2020" => Ok(EsVersion::Es2020),
388 "es2021" => Ok(EsVersion::Es2021),
389 "es2022" => Ok(EsVersion::Es2022),
390 "es2023" => Ok(EsVersion::Es2023),
391 "es2024" => Ok(EsVersion::Es2024),
392 "esnext" => Ok(EsVersion::EsNext),
393 _ => Err(D::Error::custom(format!("Unknown ES version: {s}"))),
394 }
395 }
396}
397
398impl EsVersion {
399 pub const fn latest() -> Self {
400 EsVersion::EsNext
401 }
402}
403
404#[cfg(feature = "rkyv-impl")]
410#[doc(hidden)]
411pub use self::{
412 class::{
413 ArchivedAutoAccessor, ArchivedClass, ArchivedClassMember, ArchivedClassMethod,
414 ArchivedClassProp, ArchivedConstructor, ArchivedDecorator, ArchivedKey, ArchivedMethodKind,
415 ArchivedPrivateMethod, ArchivedPrivateProp, ArchivedStaticBlock,
416 },
417 decl::{
418 ArchivedClassDecl, ArchivedDecl, ArchivedFnDecl, ArchivedUsingDecl, ArchivedVarDecl,
419 ArchivedVarDeclKind, ArchivedVarDeclarator,
420 },
421 expr::{
422 ArchivedArrayLit, ArchivedArrowExpr, ArchivedAssignExpr, ArchivedAssignTarget,
423 ArchivedAwaitExpr, ArchivedBinExpr, ArchivedBlockStmtOrExpr, ArchivedCallExpr,
424 ArchivedCallee, ArchivedClassExpr, ArchivedCondExpr, ArchivedExpr, ArchivedExprOrSpread,
425 ArchivedFnExpr, ArchivedImport, ArchivedMemberExpr, ArchivedMemberProp,
426 ArchivedMetaPropExpr, ArchivedMetaPropKind, ArchivedNewExpr, ArchivedObjectLit,
427 ArchivedOptCall, ArchivedOptChainBase, ArchivedOptChainExpr, ArchivedParenExpr,
428 ArchivedPropOrSpread, ArchivedSeqExpr, ArchivedSpreadElement, ArchivedSuper,
429 ArchivedSuperProp, ArchivedSuperPropExpr, ArchivedTaggedTpl, ArchivedThisExpr, ArchivedTpl,
430 ArchivedTplElement, ArchivedUnaryExpr, ArchivedUpdateExpr, ArchivedYieldExpr,
431 },
432 function::{ArchivedFunction, ArchivedParam, ArchivedParamOrTsParamProp},
433 ident::{ArchivedBindingIdent, ArchivedIdent, ArchivedIdentName, ArchivedPrivateName},
434 jsx::{
435 ArchivedJSXAttr, ArchivedJSXAttrName, ArchivedJSXAttrOrSpread, ArchivedJSXAttrValue,
436 ArchivedJSXClosingElement, ArchivedJSXClosingFragment, ArchivedJSXElement,
437 ArchivedJSXElementChild, ArchivedJSXElementName, ArchivedJSXEmptyExpr, ArchivedJSXExpr,
438 ArchivedJSXExprContainer, ArchivedJSXFragment, ArchivedJSXMemberExpr,
439 ArchivedJSXNamespacedName, ArchivedJSXObject, ArchivedJSXOpeningElement,
440 ArchivedJSXOpeningFragment, ArchivedJSXSpreadChild, ArchivedJSXText,
441 },
442 lit::{
443 ArchivedBigInt, ArchivedBool, ArchivedLit, ArchivedNull, ArchivedNumber, ArchivedRegex,
444 ArchivedStr,
445 },
446 module::{ArchivedModule, ArchivedModuleItem, ArchivedProgram, ArchivedScript},
447 module_decl::{
448 ArchivedDefaultDecl, ArchivedExportAll, ArchivedExportDecl, ArchivedExportDefaultDecl,
449 ArchivedExportDefaultExpr, ArchivedExportDefaultSpecifier, ArchivedExportNamedSpecifier,
450 ArchivedExportNamespaceSpecifier, ArchivedExportSpecifier, ArchivedImportDecl,
451 ArchivedImportDefaultSpecifier, ArchivedImportNamedSpecifier, ArchivedImportSpecifier,
452 ArchivedImportStarAsSpecifier, ArchivedModuleDecl, ArchivedModuleExportName,
453 ArchivedNamedExport,
454 },
455 operators::{ArchivedAssignOp, ArchivedBinaryOp, ArchivedUnaryOp, ArchivedUpdateOp},
456 pat::{
457 ArchivedArrayPat, ArchivedAssignPat, ArchivedAssignPatProp, ArchivedKeyValuePatProp,
458 ArchivedObjectPat, ArchivedObjectPatProp, ArchivedPat, ArchivedRestPat,
459 },
460 prop::{
461 ArchivedAssignProp, ArchivedComputedPropName, ArchivedGetterProp, ArchivedKeyValueProp,
462 ArchivedMethodProp, ArchivedProp, ArchivedPropName, ArchivedSetterProp,
463 },
464 stmt::{
465 ArchivedBlockStmt, ArchivedBreakStmt, ArchivedCatchClause, ArchivedContinueStmt,
466 ArchivedDebuggerStmt, ArchivedDoWhileStmt, ArchivedEmptyStmt, ArchivedExprStmt,
467 ArchivedForHead, ArchivedForInStmt, ArchivedForOfStmt, ArchivedForStmt, ArchivedIfStmt,
468 ArchivedLabeledStmt, ArchivedReturnStmt, ArchivedStmt, ArchivedSwitchCase,
469 ArchivedSwitchStmt, ArchivedThrowStmt, ArchivedTryStmt, ArchivedVarDeclOrExpr,
470 ArchivedWhileStmt, ArchivedWithStmt,
471 },
472 typescript::{
473 ArchivedAccessibility, ArchivedTruePlusMinus, ArchivedTsArrayType, ArchivedTsAsExpr,
474 ArchivedTsCallSignatureDecl, ArchivedTsConditionalType, ArchivedTsConstAssertion,
475 ArchivedTsConstructSignatureDecl, ArchivedTsConstructorType, ArchivedTsEntityName,
476 ArchivedTsEnumDecl, ArchivedTsEnumMember, ArchivedTsEnumMemberId,
477 ArchivedTsExportAssignment, ArchivedTsExprWithTypeArgs, ArchivedTsExternalModuleRef,
478 ArchivedTsFnOrConstructorType, ArchivedTsFnParam, ArchivedTsFnType,
479 ArchivedTsGetterSignature, ArchivedTsImportEqualsDecl, ArchivedTsImportType,
480 ArchivedTsIndexSignature, ArchivedTsIndexedAccessType, ArchivedTsInferType,
481 ArchivedTsInstantiation, ArchivedTsInterfaceBody, ArchivedTsInterfaceDecl,
482 ArchivedTsIntersectionType, ArchivedTsKeywordType, ArchivedTsKeywordTypeKind,
483 ArchivedTsLit, ArchivedTsLitType, ArchivedTsMappedType, ArchivedTsMethodSignature,
484 ArchivedTsModuleBlock, ArchivedTsModuleDecl, ArchivedTsModuleName, ArchivedTsModuleRef,
485 ArchivedTsNamespaceBody, ArchivedTsNamespaceDecl, ArchivedTsNamespaceExportDecl,
486 ArchivedTsNonNullExpr, ArchivedTsOptionalType, ArchivedTsParamProp,
487 ArchivedTsParamPropParam, ArchivedTsParenthesizedType, ArchivedTsPropertySignature,
488 ArchivedTsQualifiedName, ArchivedTsRestType, ArchivedTsSatisfiesExpr,
489 ArchivedTsSetterSignature, ArchivedTsThisType, ArchivedTsThisTypeOrIdent,
490 ArchivedTsTplLitType, ArchivedTsTupleElement, ArchivedTsTupleType, ArchivedTsType,
491 ArchivedTsTypeAliasDecl, ArchivedTsTypeAnn, ArchivedTsTypeAssertion, ArchivedTsTypeElement,
492 ArchivedTsTypeLit, ArchivedTsTypeOperator, ArchivedTsTypeOperatorOp, ArchivedTsTypeParam,
493 ArchivedTsTypeParamDecl, ArchivedTsTypeParamInstantiation, ArchivedTsTypePredicate,
494 ArchivedTsTypeQuery, ArchivedTsTypeQueryExpr, ArchivedTsTypeRef,
495 ArchivedTsUnionOrIntersectionType, ArchivedTsUnionType,
496 },
497};