From 1ab8963f527024cb7c7882e90e6ee38f3d12d291 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=EA=B0=95=EB=8F=99=EC=9C=A4=20=28Donny=29?= Date: Fri, 8 Dec 2023 14:14:38 +0900 Subject: [PATCH 1/3] Add types --- crates/swc_ecma_ast/src/expr.rs | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/crates/swc_ecma_ast/src/expr.rs b/crates/swc_ecma_ast/src/expr.rs index a4638348b768..b60f600cd416 100644 --- a/crates/swc_ecma_ast/src/expr.rs +++ b/crates/swc_ecma_ast/src/expr.rs @@ -378,6 +378,27 @@ pub struct ObjectLit { pub props: Vec, } +impl ObjectLit { + /// See [ImportWith] for details. + pub fn as_import_with(&self) -> ImportWith {} +} + +/// According to the current spec `with` of [crate::ImportDecl] can only have +/// strings or idents as keys, can't be nested, can only have string literals as +/// values: + +#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash, EqIgnoreSpan)] +pub struct ImportWith { + pub span: Span, + pub values: Vec, +} + +#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash, EqIgnoreSpan)] +pub struct ImportWithItem { + pub key: Ident, + pub value: Str, +} + impl Take for ObjectLit { fn dummy() -> Self { ObjectLit { From 982906a906a79214d89c8cf6d7d8c0845b7e5198 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=EA=B0=95=EB=8F=99=EC=9C=A4=20=28Donny=29?= Date: Fri, 8 Dec 2023 14:19:20 +0900 Subject: [PATCH 2/3] `as_import_with` --- crates/swc_ecma_ast/src/expr.rs | 52 ++++++++++++++++++++++++++++++--- 1 file changed, 48 insertions(+), 4 deletions(-) diff --git a/crates/swc_ecma_ast/src/expr.rs b/crates/swc_ecma_ast/src/expr.rs index b60f600cd416..8caa67bdcf2c 100644 --- a/crates/swc_ecma_ast/src/expr.rs +++ b/crates/swc_ecma_ast/src/expr.rs @@ -24,7 +24,7 @@ use crate::{ TsAsExpr, TsConstAssertion, TsInstantiation, TsNonNullExpr, TsSatisfiesExpr, TsTypeAnn, TsTypeAssertion, TsTypeParamDecl, TsTypeParamInstantiation, }, - ComputedPropName, Id, Invalid, + ComputedPropName, Id, Invalid, PropName, Str, }; #[ast_node(no_clone)] @@ -380,20 +380,64 @@ pub struct ObjectLit { impl ObjectLit { /// See [ImportWith] for details. - pub fn as_import_with(&self) -> ImportWith {} + /// + /// Returns [None] if this is not a valid for `with` of [crate::ImportDecl]. + pub fn as_import_with(&self) -> Option { + let mut values = vec![]; + for prop in &self.props { + match prop { + PropOrSpread::Spread(..) => return None, + PropOrSpread::Prop(prop) => match &**prop { + Prop::KeyValue(kv) => { + let key = match &kv.key { + PropName::Ident(i) => i.clone(), + PropName::Str(s) => Ident::new(s.value.clone(), s.span), + _ => return None, + }; + + values.push(ImportWithItem { + key, + value: match &*kv.value { + Expr::Lit(Lit::Str(s)) => s.clone(), + _ => return None, + }, + }); + } + _ => return None, + }, + } + } + + Some(ImportWith { + span: self.span, + values, + }) + } } /// According to the current spec `with` of [crate::ImportDecl] can only have /// strings or idents as keys, can't be nested, can only have string literals as /// values: -#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash, EqIgnoreSpan)] +#[derive(Debug, Clone, PartialEq, Eq, Hash, EqIgnoreSpan)] pub struct ImportWith { pub span: Span, pub values: Vec, } -#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash, EqIgnoreSpan)] +impl ImportWith { + pub fn get(&self, key: &str) -> Option<&Str> { + self.values.iter().find_map(|item| { + if item.key.sym == key { + Some(&item.value) + } else { + None + } + }) + } +} + +#[derive(Debug, Clone, PartialEq, Eq, Hash, EqIgnoreSpan)] pub struct ImportWithItem { pub key: Ident, pub value: Str, From 01955ad4e878878d52c7c0f7ad3aeeaf5d5a9b55 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=EA=B0=95=EB=8F=99=EC=9C=A4=20=28Donny=29?= Date: Fri, 8 Dec 2023 14:21:47 +0900 Subject: [PATCH 3/3] From impl --- crates/swc_ecma_ast/src/expr.rs | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/crates/swc_ecma_ast/src/expr.rs b/crates/swc_ecma_ast/src/expr.rs index 8caa67bdcf2c..e88373230639 100644 --- a/crates/swc_ecma_ast/src/expr.rs +++ b/crates/swc_ecma_ast/src/expr.rs @@ -24,7 +24,7 @@ use crate::{ TsAsExpr, TsConstAssertion, TsInstantiation, TsNonNullExpr, TsSatisfiesExpr, TsTypeAnn, TsTypeAssertion, TsTypeParamDecl, TsTypeParamInstantiation, }, - ComputedPropName, Id, Invalid, PropName, Str, + ComputedPropName, Id, Invalid, KeyValueProp, PropName, Str, }; #[ast_node(no_clone)] @@ -415,6 +415,24 @@ impl ObjectLit { } } +impl From for ObjectLit { + fn from(v: ImportWith) -> Self { + ObjectLit { + span: v.span, + props: v + .values + .into_iter() + .map(|item| { + PropOrSpread::Prop(Box::new(Prop::KeyValue(KeyValueProp { + key: PropName::Ident(item.key), + value: Box::new(Expr::Lit(Lit::Str(item.value))), + }))) + }) + .collect(), + } + } +} + /// According to the current spec `with` of [crate::ImportDecl] can only have /// strings or idents as keys, can't be nested, can only have string literals as /// values: