Skip to content

Commit

Permalink
feat: extract other jsx types to variable
Browse files Browse the repository at this point in the history
  • Loading branch information
j4k0xb committed Dec 22, 2023
1 parent e1aff38 commit ac17bd7
Show file tree
Hide file tree
Showing 2 changed files with 21 additions and 8 deletions.
23 changes: 15 additions & 8 deletions packages/webcrack/src/transforms/jsx-new.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,14 +28,12 @@ export default {
m.identifier(),
false,
);

const type = m.capture(
m.or(
m.identifier(), // jsx(Component, ...)
m.stringLiteral(), // jsx('div', ...)
deepIdentifierMemberExpression, // jsx(Component.SubComponent, ...)
),
const convertibleName = m.or(
m.identifier(), // jsx(Component, ...)
m.stringLiteral(), // jsx('div', ...)
deepIdentifierMemberExpression, // jsx(Component.SubComponent, ...)
);
const type = m.capture(m.anyExpression());
const fragmentType = constMemberExpression('React', 'Fragment');
const props = m.capture(m.objectExpression());
const key = m.capture(m.anyExpression());
Expand All @@ -52,7 +50,16 @@ export default {
exit(path) {
if (!jsxMatcher.match(path.node)) return;

let name = convertType(type.current!);
let name: t.Node;
if (convertibleName.match(type.current!)) {
name = convertType(type.current);
} else {
name = t.jsxIdentifier(path.scope.generateUid('Component'));
const componentVar = t.variableDeclaration('const', [
t.variableDeclarator(t.identifier(name.name), type.current),
]);
path.getStatementParent()?.insertBefore(componentVar);
}
const isFragment = fragmentType.match(type.current);

// rename component to avoid conflict with built-in html tags
Expand Down
6 changes: 6 additions & 0 deletions packages/webcrack/test/jsx-new.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,12 @@ test('deeply nested member expression type', () =>
'<components.list.TodoList />;',
));

test('any other expression type', () =>
expectJS('jsx(r ? "a" : "div", {});').toMatchInlineSnapshot(`
const _Component = r ? "a" : "div";
<_Component />;
`));

test('rename component with conflicting name', () =>
expectJS('function a(){} jsx(a, {});').toMatchInlineSnapshot(`
function _Component() {}
Expand Down

0 comments on commit ac17bd7

Please sign in to comment.