diff --git a/crates/binding/src/config.rs b/crates/binding/src/config.rs index f602d10..ea7589a 100644 --- a/crates/binding/src/config.rs +++ b/crates/binding/src/config.rs @@ -125,7 +125,13 @@ impl TryFrom for Config { fn try_from(val: JsConfig) -> Result { let expand_props = match val.expand_props { Some(raw) => match raw { - Either::A(b) => ExpandProps::Bool(b), + Either::A(b) => { + if b { + ExpandProps::End + } else { + ExpandProps::None + } + } Either::B(s) => match s.as_str() { "start" => ExpandProps::Start, "end" => ExpandProps::End, @@ -142,8 +148,8 @@ impl TryFrom for Config { }); let svg_props = match val.svg_props { - Some(raw) => Some(raw.0), - None => None, + Some(raw) => raw.0, + None => vec![], }; let jsx_runtime = match val.jsx_runtime { @@ -184,21 +190,21 @@ impl TryFrom for Config { }; Ok(Self { - r#ref: val.r#ref, - title_prop: val.title_prop, - desc_prop: val.desc_prop, + r#ref: val.r#ref.unwrap_or(false), + title_prop: val.title_prop.unwrap_or(false), + desc_prop: val.desc_prop.unwrap_or(false), expand_props, - dimensions: val.dimensions, + dimensions: val.dimensions.unwrap_or(true), icon, - native: val.native, + native: val.native.unwrap_or(false), svg_props, - typescript: val.typescript, - memo: val.memo, + typescript: val.typescript.unwrap_or(false), + memo: val.memo.unwrap_or(false), replace_attr_values, - jsx_runtime: Some(jsx_runtime), + jsx_runtime, jsx_runtime_import, named_export, - export_type: Some(export_type), + export_type, }) } } diff --git a/crates/binding/src/lib.rs b/crates/binding/src/lib.rs index 21271b0..fb24632 100644 --- a/crates/binding/src/lib.rs +++ b/crates/binding/src/lib.rs @@ -13,7 +13,7 @@ use state::JsState; use svgr_rs::{transform, Config}; pub struct TransformTask { - code: String, + code: Option, config: Option, state: Option, } @@ -23,12 +23,13 @@ impl Task for TransformTask { type JsValue = JsString; fn compute(&mut self) -> Result { - let config: Config = match self.config.clone() { + let config: Config = match self.config.take() { Some(val) => val.try_into()?, None => Config::default(), }; - let state = self.state.clone().map(|s| s.into()).unwrap_or_default(); - match transform(self.code.clone(), config, state) { + let state = self.state.take().map(|s| s.into()).unwrap_or_default(); + let code = self.code.take().unwrap(); + match transform(code, config, state) { Ok(result) => napi::Result::Ok(result), Err(reason) => napi::Result::Err(napi::Error::from_reason(reason.to_string())), } @@ -46,7 +47,7 @@ pub fn transform_node( state: Option, ) -> AsyncTask { AsyncTask::new(TransformTask { - code, + code: Some(code), config, state, }) diff --git a/crates/core/src/add_jsx_attribute.rs b/crates/core/src/add_jsx_attribute.rs index 10a17ac..68b307b 100644 --- a/crates/core/src/add_jsx_attribute.rs +++ b/crates/core/src/add_jsx_attribute.rs @@ -30,15 +30,12 @@ impl Visitor { pub fn new(config: &core::config::Config) -> Self { let mut attributes = Vec::new(); - if let Some(svg_props) = &config.svg_props { - for SvgProp { key, value } in svg_props { - let attr = svg_prop_to_attr(key, value); - attributes.push(attr); - } + for SvgProp { key, value } in &config.svg_props { + let attr = svg_prop_to_attr(key, value); + attributes.push(attr); } - let r#ref = config.r#ref.unwrap_or(false); - if r#ref { + if config.r#ref { attributes.push(Attribute { name: "ref".to_string(), value: Some("ref".to_string()), @@ -47,8 +44,7 @@ impl Visitor { }); } - let title_prop = config.title_prop.unwrap_or(false); - if title_prop { + if config.title_prop { attributes.push(Attribute { name: "aria-labelledby".to_string(), value: Some("titleId".to_string()), @@ -57,8 +53,7 @@ impl Visitor { }); } - let desc_prop = config.desc_prop.unwrap_or(false); - if desc_prop { + if config.desc_prop { attributes.push(Attribute { name: "aria-describedby".to_string(), value: Some("descId".to_string()), @@ -67,16 +62,13 @@ impl Visitor { }); } - let expand_props = match config.expand_props { - core::config::ExpandProps::Bool(b) => b, - _ => true, - }; - let position = match config.expand_props { - core::config::ExpandProps::Start => Some(AttributePosition::Start), - core::config::ExpandProps::End => Some(AttributePosition::End), - _ => None, - }; + let expand_props = !matches!(config.expand_props, core::config::ExpandProps::None); if expand_props { + let position = match config.expand_props { + core::config::ExpandProps::Start => Some(AttributePosition::Start), + core::config::ExpandProps::End => Some(AttributePosition::End), + core::config::ExpandProps::None => None, + }; attributes.push(Attribute { name: "props".to_string(), spread: true, diff --git a/crates/core/src/core/config.rs b/crates/core/src/core/config.rs index c878c9e..1aabd40 100644 --- a/crates/core/src/core/config.rs +++ b/crates/core/src/core/config.rs @@ -15,14 +15,15 @@ impl Default for Icon { #[derive(Debug, Clone, Default)] pub enum ExpandProps { - Bool(bool), + None, Start, #[default] End, } -#[derive(Debug, Clone)] +#[derive(Debug, Clone, Default)] pub enum JSXRuntime { + #[default] Classic, ClassicPreact, Automatic, @@ -36,9 +37,10 @@ pub struct JSXRuntimeImport { pub specifiers: Option>, } -#[derive(Debug, Clone)] +#[derive(Debug, Clone, Default)] pub enum ExportType { Named, + #[default] Default, } @@ -52,15 +54,15 @@ pub struct SvgProp { #[derive(Debug, Clone)] pub struct Config { /// Setting this to `true` will forward ref to the root SVG tag. - pub r#ref: Option, + pub r#ref: bool, /// Add title tag via title property. /// If title_prop is set to true and no title is provided at render time, this will fallback to an existing title element in the svg if exists. - pub title_prop: Option, + pub title_prop: bool, /// Add desc tag via desc property. /// If desc_prop is set to true and no description is provided at render time, this will fallback to an existing desc element in the svg if exists. - pub desc_prop: Option, + pub desc_prop: bool, /// All properties given to component will be forwarded on SVG tag. /// Possible values: "start", "end" or false. @@ -68,7 +70,7 @@ pub struct Config { /// Keep `width` and `height` attributes from the root SVG tag. /// Removal is guaranteed if `dimensions: false`, unlike the `remove_dimensions: true` SVGO plugin option which also generates a `viewBox` from the dimensions if no `viewBox` is present. - pub dimensions: Option, + pub dimensions: bool, /// Replace SVG `width` and `height` by a custom value. /// If value is omitted, it uses `1em` in order to make SVG size inherits from text size. @@ -76,16 +78,16 @@ pub struct Config { /// Modify all SVG nodes with uppercase and use a specific template with `react-native-svg` imports. /// All unsupported nodes will be removed. - pub native: Option, + pub native: bool, /// Add props to the root SVG tag. - pub svg_props: Option>, + pub svg_props: Vec, /// Generates `.tsx` files with TypeScript typings. - pub typescript: Option, + pub typescript: bool, /// Setting this to `true` will wrap the exported component in `React.memo`. - pub memo: Option, + pub memo: bool, /// Replace an attribute value by an other. /// The main usage of this option is to change an icon color to "currentColor" in order to inherit from text color. @@ -95,7 +97,7 @@ pub struct Config { /// * "classic": adds `import * as React from 'react'` on the top of file /// * "automatic": do not add anything /// * "classic-preact": adds `import { h } from 'preact'` on the top of file - pub jsx_runtime: Option, + pub jsx_runtime: JSXRuntime, /// Specify a custom JSX runtime source to use. Allows to customize the import added at the top of generated file. pub jsx_runtime_import: Option, @@ -104,27 +106,27 @@ pub struct Config { pub named_export: String, /// If you prefer named export in any case, you may set the `export_type` option to `named`. - pub export_type: Option, + pub export_type: ExportType, } impl Default for Config { fn default() -> Self { Self { - r#ref: Default::default(), - title_prop: Default::default(), - desc_prop: Default::default(), - expand_props: Default::default(), - dimensions: Default::default(), - icon: Default::default(), - native: Default::default(), - svg_props: Default::default(), - typescript: Default::default(), - memo: Default::default(), - replace_attr_values: Default::default(), - jsx_runtime: Default::default(), + r#ref: false, + title_prop: false, + desc_prop: false, + expand_props: ExpandProps::End, + dimensions: true, + icon: None, + native: false, + svg_props: vec![], + typescript: false, + memo: false, + replace_attr_values: None, + jsx_runtime: JSXRuntime::Classic, jsx_runtime_import: Default::default(), named_export: "ReactComponent".to_string(), - export_type: Default::default(), + export_type: ExportType::Default, } } } diff --git a/crates/core/src/lib.rs b/crates/core/src/lib.rs index 5e355f3..8bd0f8e 100644 --- a/crates/core/src/lib.rs +++ b/crates/core/src/lib.rs @@ -77,8 +77,7 @@ pub fn transform(code: String, config: Config, state: State) -> Result false, _ => true, }; - let dimensions = config.dimensions.unwrap_or(true); - let m = if icon && dimensions { + let m = if icon && config.dimensions { m.fold_with(&mut as_folder(svg_em_dimensions::Visitor::new(&config))) } else { m @@ -91,8 +90,7 @@ pub fn transform(code: String, config: Config, state: State) -> Result Result Result Self { let mut attributes = vec!["version".to_string()]; - let dimensions = config.dimensions.unwrap_or(true); - if !dimensions { + if !config.dimensions { attributes.push("width".to_string()); attributes.push("height".to_string()); } diff --git a/crates/core/src/svg_em_dimensions.rs b/crates/core/src/svg_em_dimensions.rs index 8c19083..7dcc2f4 100644 --- a/crates/core/src/svg_em_dimensions.rs +++ b/crates/core/src/svg_em_dimensions.rs @@ -36,8 +36,7 @@ impl Visitor { width = Some(Size::Num(n)); } core::config::Icon::Bool(_) => { - let native = config.native.unwrap_or(false); - if native { + if config.native { height = Some(Size::Num(24.0)); width = Some(Size::Num(24.0)); } else { diff --git a/crates/core/src/transform_svg_component/mod.rs b/crates/core/src/transform_svg_component/mod.rs index d5c7f03..a583eca 100644 --- a/crates/core/src/transform_svg_component/mod.rs +++ b/crates/core/src/transform_svg_component/mod.rs @@ -6,27 +6,16 @@ use crate::{core, SvgrError}; mod variables; fn get_variables_options(config: &core::config::Config) -> variables::Options { - let expand_props = match config.expand_props { - core::config::ExpandProps::Bool(b) => Some(variables::ExpandProps::Bool(b)), - core::config::ExpandProps::Start => Some(variables::ExpandProps::Start), - core::config::ExpandProps::End => Some(variables::ExpandProps::End), - }; - - let export_type = match config.export_type { - Some(core::config::ExportType::Named) => variables::ExportType::Named, - _ => variables::ExportType::Default, - }; - let mut opts = variables::Options { - typescript: config.typescript.unwrap_or(false), - title_prop: config.title_prop.unwrap_or(false), - desc_prop: config.desc_prop.unwrap_or(false), - expand_props, - r#ref: config.r#ref.unwrap_or(false), - native: config.native.unwrap_or(false), - memo: config.memo.unwrap_or(false), + typescript: config.typescript, + title_prop: config.title_prop, + desc_prop: config.desc_prop, + expand_props: config.expand_props.clone(), + r#ref: config.r#ref, + native: config.native, + memo: config.memo, named_export: Some(config.named_export.clone()), - export_type, + export_type: config.export_type.clone(), ..Default::default() }; @@ -36,12 +25,7 @@ fn get_variables_options(config: &core::config::Config) -> variables::Options { return opts; } - let jsx_runtime = config - .jsx_runtime - .clone() - .unwrap_or(core::config::JSXRuntime::Classic); - - match jsx_runtime { + match &config.jsx_runtime { core::config::JSXRuntime::Classic => { opts.jsx_runtime = variables::JSXRuntime::Classic; opts.import_source = Some("react".to_string()); @@ -190,7 +174,7 @@ mod tests { test_code(input, config, state, js); let mut config = config.clone(); - config.typescript = Some(true); + config.typescript = true; test_code(input, &config, state, ts); } @@ -199,7 +183,7 @@ mod tests { test_js_n_ts( r#""#, &core::config::Config { - expand_props: core::config::ExpandProps::Bool(false), + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -221,8 +205,8 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - native: Some(true), - expand_props: core::config::ExpandProps::Bool(false), + native: true, + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -246,8 +230,8 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - r#ref: Some(true), - expand_props: core::config::ExpandProps::Bool(false), + r#ref: true, + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -274,8 +258,8 @@ export default ForwardRef; test_js_n_ts( r#""#, &core::config::Config { - title_prop: Some(true), - expand_props: core::config::ExpandProps::Bool(false), + title_prop: true, + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -301,8 +285,8 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - title_prop: Some(true), - expand_props: core::config::ExpandProps::Bool(true), + title_prop: true, + expand_props: core::config::ExpandProps::End, ..Default::default() }, &core::state::InternalConfig { @@ -329,8 +313,8 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - desc_prop: Some(true), - expand_props: core::config::ExpandProps::Bool(false), + desc_prop: true, + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -356,8 +340,8 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - expand_props: core::config::ExpandProps::Bool(true), - desc_prop: Some(true), + expand_props: core::config::ExpandProps::End, + desc_prop: true, ..Default::default() }, &core::state::InternalConfig { @@ -384,9 +368,9 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - title_prop: Some(true), - desc_prop: Some(true), - expand_props: core::config::ExpandProps::Bool(false), + title_prop: true, + desc_prop: true, + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -415,9 +399,9 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - expand_props: core::config::ExpandProps::Bool(true), - title_prop: Some(true), - desc_prop: Some(true), + expand_props: core::config::ExpandProps::End, + title_prop: true, + desc_prop: true, ..Default::default() }, &core::state::InternalConfig { @@ -446,7 +430,7 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - expand_props: core::config::ExpandProps::Bool(true), + expand_props: core::config::ExpandProps::End, ..Default::default() }, &core::state::InternalConfig { @@ -470,8 +454,8 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - expand_props: core::config::ExpandProps::Bool(true), - r#ref: Some(true), + expand_props: core::config::ExpandProps::End, + r#ref: true, ..Default::default() }, &core::state::InternalConfig { @@ -498,9 +482,9 @@ export default ForwardRef; test_js_n_ts( r#""#, &core::config::Config { - native: Some(true), - r#ref: Some(true), - expand_props: core::config::ExpandProps::Bool(false), + native: true, + r#ref: true, + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -529,8 +513,8 @@ export default ForwardRef; test_js_n_ts( r#""#, &core::config::Config { - native: Some(true), - expand_props: core::config::ExpandProps::Bool(true), + native: true, + expand_props: core::config::ExpandProps::End, ..Default::default() }, &core::state::InternalConfig { @@ -556,9 +540,9 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - native: Some(true), - expand_props: core::config::ExpandProps::Bool(true), - r#ref: Some(true), + native: true, + expand_props: core::config::ExpandProps::End, + r#ref: true, ..Default::default() }, &core::state::InternalConfig { @@ -587,8 +571,8 @@ export default ForwardRef; test_js_n_ts( r#""#, &core::config::Config { - memo: Some(true), - expand_props: core::config::ExpandProps::Bool(false), + memo: true, + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -615,9 +599,9 @@ export default Memo; test_js_n_ts( r#""#, &core::config::Config { - memo: Some(true), - r#ref: Some(true), - expand_props: core::config::ExpandProps::Bool(false), + memo: true, + r#ref: true, + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -647,7 +631,7 @@ export default Memo; r#""#, &core::config::Config { named_export: "Component".to_string(), - expand_props: core::config::ExpandProps::Bool(false), + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -684,8 +668,8 @@ export default img; r#""#, &core::config::Config { named_export: "ReactComponent".to_string(), - export_type: Some(core::config::ExportType::Named), - expand_props: core::config::ExpandProps::Bool(false), + export_type: core::config::ExportType::Named, + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -710,8 +694,8 @@ export { SvgComponent as ReactComponent }; test_js_n_ts( r#""#, &core::config::Config { - jsx_runtime: Some(core::config::JSXRuntime::Automatic), - expand_props: core::config::ExpandProps::Bool(false), + jsx_runtime: core::config::JSXRuntime::Automatic, + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -731,8 +715,8 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - jsx_runtime: Some(core::config::JSXRuntime::Classic), - expand_props: core::config::ExpandProps::Bool(false), + jsx_runtime: core::config::JSXRuntime::Classic, + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -754,13 +738,13 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - jsx_runtime: Some(core::config::JSXRuntime::Classic), + jsx_runtime: core::config::JSXRuntime::Classic, jsx_runtime_import: Some(core::config::JSXRuntimeImport { specifiers: Some(vec!["h".to_string()]), source: "preact".to_string(), ..Default::default() }), - expand_props: core::config::ExpandProps::Bool(false), + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -782,13 +766,13 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - jsx_runtime: Some(core::config::JSXRuntime::Classic), + jsx_runtime: core::config::JSXRuntime::Classic, jsx_runtime_import: Some(core::config::JSXRuntimeImport { namespace: Some("Preact".to_string()), source: "preact".to_string(), ..Default::default() }), - expand_props: core::config::ExpandProps::Bool(false), + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -810,13 +794,13 @@ export default SvgComponent; test_js_n_ts( r#""#, &core::config::Config { - jsx_runtime: Some(core::config::JSXRuntime::Classic), + jsx_runtime: core::config::JSXRuntime::Classic, jsx_runtime_import: Some(core::config::JSXRuntimeImport { default_specifier: Some("h".to_string()), source: "hyperapp-jsx-pragma".to_string(), ..Default::default() }), - expand_props: core::config::ExpandProps::Bool(false), + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { @@ -841,12 +825,12 @@ export default SvgComponent; test_code( r#""#, &core::config::Config { - jsx_runtime: Some(core::config::JSXRuntime::Classic), + jsx_runtime: core::config::JSXRuntime::Classic, jsx_runtime_import: Some(core::config::JSXRuntimeImport { source: "preact".to_string(), ..Default::default() }), - expand_props: core::config::ExpandProps::Bool(false), + expand_props: core::config::ExpandProps::None, ..Default::default() }, &core::state::InternalConfig { diff --git a/crates/core/src/transform_svg_component/variables.rs b/crates/core/src/transform_svg_component/variables.rs index 304b3c2..f456318 100644 --- a/crates/core/src/transform_svg_component/variables.rs +++ b/crates/core/src/transform_svg_component/variables.rs @@ -8,7 +8,7 @@ use swc_core::{ }; use super::core; -use crate::SvgrError; +use crate::{ExpandProps, ExportType, SvgrError}; pub struct TemplateVariables { #[allow(dead_code)] @@ -27,25 +27,12 @@ pub enum JSXRuntime { Classic, } -pub enum ExpandProps { - Bool(bool), - Start, - End, -} - -#[derive(Default)] -pub enum ExportType { - #[default] - Default, - Named, -} - #[derive(Default)] pub struct Options { pub typescript: bool, pub title_prop: bool, pub desc_prop: bool, - pub expand_props: Option, + pub expand_props: ExpandProps, pub r#ref: bool, // pub template: Option>, pub native: bool, @@ -165,11 +152,7 @@ pub fn get_variables( props.push(Pat::Object(prop)); } - let need_expand_props = match opts.expand_props { - None => false, - Some(ExpandProps::Bool(expand_props)) => expand_props, - _ => true, - }; + let need_expand_props = !matches!(opts.expand_props, ExpandProps::None); if need_expand_props { let existing = if !props.is_empty() { if let Pat::Object(ref mut object_pat) = props[0] {