mirror of
https://github.com/danbulant/oxc
synced 2026-05-25 04:42:10 +00:00
feat(transformer/react): handle babel 8 breaking removed-options (#1489)
1. removed options react jsx 2. Passed 4 test cases.
This commit is contained in:
parent
f06f0f2078
commit
b6393f052f
6 changed files with 42 additions and 16 deletions
|
|
@ -94,7 +94,7 @@ impl<'a> Transformer<'a> {
|
||||||
es2015_shorthand_properties: ShorthandProperties::new(Rc::clone(&ast), &options),
|
es2015_shorthand_properties: ShorthandProperties::new(Rc::clone(&ast), &options),
|
||||||
es2015_template_literals: TemplateLiterals::new(Rc::clone(&ast), &options),
|
es2015_template_literals: TemplateLiterals::new(Rc::clone(&ast), &options),
|
||||||
es3_property_literal: PropertyLiteral::new(Rc::clone(&ast ), &options),
|
es3_property_literal: PropertyLiteral::new(Rc::clone(&ast ), &options),
|
||||||
react_jsx: options.react_jsx.map(|options| ReactJsx::new(Rc::clone(&ast), ctx.clone(), options)),
|
react_jsx: ReactJsx::new(Rc::clone(&ast), ctx.clone(), options)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -24,6 +24,7 @@ pub struct TransformOptions {
|
||||||
pub sticky_regex: bool,
|
pub sticky_regex: bool,
|
||||||
pub template_literals: bool,
|
pub template_literals: bool,
|
||||||
pub property_literals: bool,
|
pub property_literals: bool,
|
||||||
|
pub babel_8_breaking: Option<bool>,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// See <https://www.typescriptlang.org/tsconfig#target>
|
/// See <https://www.typescriptlang.org/tsconfig#target>
|
||||||
|
|
|
||||||
|
|
@ -15,7 +15,7 @@ use oxc_syntax::{
|
||||||
};
|
};
|
||||||
|
|
||||||
pub use self::options::{ReactJsxOptions, ReactJsxRuntime};
|
pub use self::options::{ReactJsxOptions, ReactJsxRuntime};
|
||||||
use crate::context::TransformerCtx;
|
use crate::{context::TransformerCtx, TransformOptions};
|
||||||
|
|
||||||
#[derive(Debug, Error, Diagnostic)]
|
#[derive(Debug, Error, Diagnostic)]
|
||||||
#[error("pragma and pragmaFrag cannot be set when runtime is automatic.")]
|
#[error("pragma and pragmaFrag cannot be set when runtime is automatic.")]
|
||||||
|
|
@ -59,6 +59,7 @@ pub struct ReactJsx<'a> {
|
||||||
import_create_element: bool,
|
import_create_element: bool,
|
||||||
require_jsx_runtime: bool,
|
require_jsx_runtime: bool,
|
||||||
jsx_runtime_importer: Atom,
|
jsx_runtime_importer: Atom,
|
||||||
|
pub babel_8_breaking: Option<bool>,
|
||||||
}
|
}
|
||||||
|
|
||||||
enum JSXElementOrFragment<'a, 'b> {
|
enum JSXElementOrFragment<'a, 'b> {
|
||||||
|
|
@ -100,21 +101,35 @@ impl<'a, 'b> JSXElementOrFragment<'a, 'b> {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a> ReactJsx<'a> {
|
impl<'a> ReactJsx<'a> {
|
||||||
pub fn new(ast: Rc<AstBuilder<'a>>, ctx: TransformerCtx<'a>, options: ReactJsxOptions) -> Self {
|
pub fn new(
|
||||||
|
ast: Rc<AstBuilder<'a>>,
|
||||||
|
mut ctx: TransformerCtx<'a>,
|
||||||
|
options: TransformOptions,
|
||||||
|
) -> Option<Self> {
|
||||||
let imports = ast.new_vec();
|
let imports = ast.new_vec();
|
||||||
let options = options.with_comments(&ctx.semantic());
|
let jsx_options = options.react_jsx?.with_comments(&ctx.semantic());
|
||||||
|
if options.babel_8_breaking == Some(true) {
|
||||||
|
if jsx_options.use_built_ins.is_some() {
|
||||||
|
ctx.error(miette::Error::msg("@babel/plugin-transform-react-jsx: Since \"useBuiltIns\" is removed in Babel 8, you can remove it from the config."));
|
||||||
|
return None;
|
||||||
|
}
|
||||||
|
|
||||||
|
if jsx_options.use_spread.is_some() {
|
||||||
|
ctx.error(miette::Error::msg("@babel/plugin-transform-react-jsx: Since Babel 8, an inline object with spread elements is always used, and the \"useSpread\" option is no longer available. Please remove it from your config."));
|
||||||
|
return None;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
let jsx_runtime_importer =
|
let jsx_runtime_importer =
|
||||||
if options.import_source == "react" || options.runtime.is_classic() {
|
if jsx_options.import_source == "react" || jsx_options.runtime.is_classic() {
|
||||||
Atom::new_inline("react/jsx-runtime")
|
Atom::new_inline("react/jsx-runtime")
|
||||||
} else {
|
} else {
|
||||||
Atom::from(format!("{}/jsx-runtime", options.import_source))
|
Atom::from(format!("{}/jsx-runtime", jsx_options.import_source))
|
||||||
};
|
};
|
||||||
|
Some(Self {
|
||||||
Self {
|
|
||||||
ast,
|
ast,
|
||||||
ctx,
|
ctx,
|
||||||
options,
|
options: jsx_options,
|
||||||
imports,
|
imports,
|
||||||
jsx_runtime_importer,
|
jsx_runtime_importer,
|
||||||
require_jsx_runtime: false,
|
require_jsx_runtime: false,
|
||||||
|
|
@ -122,7 +137,8 @@ impl<'a> ReactJsx<'a> {
|
||||||
import_jsxs: false,
|
import_jsxs: false,
|
||||||
import_fragment: false,
|
import_fragment: false,
|
||||||
import_create_element: false,
|
import_create_element: false,
|
||||||
}
|
babel_8_breaking: options.babel_8_breaking,
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn transform_expression(&mut self, expr: &mut Expression<'a>) {
|
pub fn transform_expression(&mut self, expr: &mut Expression<'a>) {
|
||||||
|
|
|
||||||
|
|
@ -7,6 +7,7 @@ use serde::Deserialize;
|
||||||
#[serde(rename_all = "camelCase")]
|
#[serde(rename_all = "camelCase")]
|
||||||
pub struct ReactJsxOptions {
|
pub struct ReactJsxOptions {
|
||||||
/// Decides which runtime to use.
|
/// Decides which runtime to use.
|
||||||
|
#[serde(default)]
|
||||||
pub runtime: ReactJsxRuntime,
|
pub runtime: ReactJsxRuntime,
|
||||||
/// Toggles whether or not to throw an error if an XML namespaced tag name is used. e.g. `<f:image />`
|
/// Toggles whether or not to throw an error if an XML namespaced tag name is used. e.g. `<f:image />`
|
||||||
/// Though the JSX spec allows this, it is disabled by default since React's JSX does not currently have support for it.
|
/// Though the JSX spec allows this, it is disabled by default since React's JSX does not currently have support for it.
|
||||||
|
|
@ -25,6 +26,15 @@ pub struct ReactJsxOptions {
|
||||||
/// Replace the component used when compiling JSX fragments. It should be a valid JSX tag name. default to `React.Fragment`
|
/// Replace the component used when compiling JSX fragments. It should be a valid JSX tag name. default to `React.Fragment`
|
||||||
#[serde(default = "default_pragma_frag")]
|
#[serde(default = "default_pragma_frag")]
|
||||||
pub pragma_frag: Cow<'static, str>,
|
pub pragma_frag: Cow<'static, str>,
|
||||||
|
|
||||||
|
/// When spreading props, use Object.assign directly instead of Babel's extend helper.
|
||||||
|
/// Use `Some<T>` instead of `bool` because we want to know if user set this field explicitly,
|
||||||
|
/// which used for creating warning, https://github.com/oxc-project/oxc/blob/c3e2098c04d8916cb812bdd16d2026bb430ac25f/crates/oxc_transformer/src/react_jsx/mod.rs#L111-L114
|
||||||
|
pub use_built_ins: Option<bool>,
|
||||||
|
/// When spreading props, use inline object with spread elements directly instead of Babel's extend helper or Object.assign.
|
||||||
|
/// Use `Some<T>` instead of `bool` because we want to know if user set this field explicitly,
|
||||||
|
/// which used for creating warning, https://github.com/oxc-project/oxc/blob/c3e2098c04d8916cb812bdd16d2026bb430ac25f/crates/oxc_transformer/src/react_jsx/mod.rs#L111-L114
|
||||||
|
pub use_spread: Option<bool>,
|
||||||
}
|
}
|
||||||
|
|
||||||
fn default_throw_if_namespace() -> bool {
|
fn default_throw_if_namespace() -> bool {
|
||||||
|
|
@ -51,6 +61,8 @@ impl Default for ReactJsxOptions {
|
||||||
import_source: default_import_source(),
|
import_source: default_import_source(),
|
||||||
pragma: default_pragma(),
|
pragma: default_pragma(),
|
||||||
pragma_frag: default_pragma_frag(),
|
pragma_frag: default_pragma_frag(),
|
||||||
|
use_built_ins: None,
|
||||||
|
use_spread: None,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,4 @@
|
||||||
Passed: 265/1081
|
Passed: 269/1081
|
||||||
|
|
||||||
# All Passed:
|
# All Passed:
|
||||||
* babel-plugin-transform-numeric-separator
|
* babel-plugin-transform-numeric-separator
|
||||||
|
|
@ -844,7 +844,7 @@ Passed: 265/1081
|
||||||
* regression/11061/input.mjs
|
* regression/11061/input.mjs
|
||||||
* variable-declaration/non-null-in-optional-chain/input.ts
|
* variable-declaration/non-null-in-optional-chain/input.ts
|
||||||
|
|
||||||
# babel-plugin-transform-react-jsx (139/156)
|
# babel-plugin-transform-react-jsx (143/156)
|
||||||
* autoImport/after-polyfills-compiled-to-cjs/input.mjs
|
* autoImport/after-polyfills-compiled-to-cjs/input.mjs
|
||||||
* autoImport/complicated-scope-module/input.js
|
* autoImport/complicated-scope-module/input.js
|
||||||
* react/arrow-functions/input.js
|
* react/arrow-functions/input.js
|
||||||
|
|
@ -855,10 +855,6 @@ Passed: 265/1081
|
||||||
* react-automatic/should-throw-when-filter-is-specified/input.js
|
* react-automatic/should-throw-when-filter-is-specified/input.js
|
||||||
* regression/issue-12478-automatic/input.js
|
* regression/issue-12478-automatic/input.js
|
||||||
* regression/issue-12478-classic/input.js
|
* regression/issue-12478-classic/input.js
|
||||||
* removed-options/invalid-use-builtins-false/input.js
|
|
||||||
* removed-options/invalid-use-builtins-true/input.js
|
|
||||||
* removed-options/invalid-use-spread-false/input.js
|
|
||||||
* removed-options/invalid-use-spread-true/input.js
|
|
||||||
* runtime/invalid-runtime/input.js
|
* runtime/invalid-runtime/input.js
|
||||||
* spread-transform/transform-to-babel-extend/input.js
|
* spread-transform/transform-to-babel-extend/input.js
|
||||||
* spread-transform/transform-to-object-assign/input.js
|
* spread-transform/transform-to-object-assign/input.js
|
||||||
|
|
|
||||||
|
|
@ -88,6 +88,7 @@ pub trait TestCase {
|
||||||
let options = self.options();
|
let options = self.options();
|
||||||
TransformOptions {
|
TransformOptions {
|
||||||
target: TransformTarget::ESNext,
|
target: TransformTarget::ESNext,
|
||||||
|
babel_8_breaking: options.babel_8_breaking,
|
||||||
react_jsx: options
|
react_jsx: options
|
||||||
.get_plugin("transform-react-jsx")
|
.get_plugin("transform-react-jsx")
|
||||||
.map(get_options::<ReactJsxOptions>),
|
.map(get_options::<ReactJsxOptions>),
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue