unframer 2.7.7 → 2.7.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +5 -1
- package/dist/babel-plugin-imports.d.ts +21 -0
- package/dist/babel-plugin-imports.d.ts.map +1 -0
- package/dist/babel-plugin-imports.js +375 -0
- package/dist/babel-plugin-imports.js.map +1 -0
- package/dist/cli.d.ts.map +1 -1
- package/dist/cli.js +2 -11
- package/dist/cli.js.map +1 -1
- package/dist/css.d.ts.map +1 -1
- package/dist/css.js +4 -3
- package/dist/css.js.map +1 -1
- package/dist/exporter.d.ts.map +1 -1
- package/dist/exporter.js +55 -29
- package/dist/exporter.js.map +1 -1
- package/dist/framer.d.ts.map +1 -1
- package/dist/framer.js +26 -1788
- package/dist/framer.js.map +1 -1
- package/dist/renamer.d.ts +12 -0
- package/dist/renamer.d.ts.map +1 -0
- package/dist/renamer.js +169 -0
- package/dist/renamer.js.map +1 -0
- package/esm/babel-plugin-imports.d.ts +21 -0
- package/esm/babel-plugin-imports.d.ts.map +1 -0
- package/esm/babel-plugin-imports.js +344 -0
- package/esm/babel-plugin-imports.js.map +1 -0
- package/esm/cli.d.ts.map +1 -1
- package/esm/cli.js +2 -11
- package/esm/cli.js.map +1 -1
- package/esm/css.d.ts.map +1 -1
- package/esm/css.js +3 -2
- package/esm/css.js.map +1 -1
- package/esm/exporter.d.ts.map +1 -1
- package/esm/exporter.js +53 -27
- package/esm/exporter.js.map +1 -1
- package/esm/framer.d.ts.map +1 -1
- package/esm/framer.js +27 -1788
- package/esm/framer.js.map +1 -1
- package/esm/renamer.d.ts +12 -0
- package/esm/renamer.d.ts.map +1 -0
- package/esm/renamer.js +140 -0
- package/esm/renamer.js.map +1 -0
- package/package.json +5 -4
- package/src/babel-plugin-imports.ts +441 -0
- package/src/cli.tsx +2 -12
- package/src/css.ts +3 -2
- package/src/exporter.ts +62 -28
- package/src/framer.js +25 -1827
- package/src/renamer.ts +184 -0
package/esm/renamer.d.ts
ADDED
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { Scope } from '@babel/traverse';
|
|
2
|
+
import * as t from '@babel/types';
|
|
3
|
+
import { NodePath } from '@babel/core';
|
|
4
|
+
export default class BatchRenamer {
|
|
5
|
+
constructor(scope: Scope, map: Map<string, string>);
|
|
6
|
+
map: Map<string, string>;
|
|
7
|
+
scope: Scope;
|
|
8
|
+
maybeConvertFromExportDeclaration(parentDeclar: NodePath): void;
|
|
9
|
+
maybeConvertFromClassFunctionExpression(path: NodePath): NodePath<t.Node>;
|
|
10
|
+
rename(): void;
|
|
11
|
+
}
|
|
12
|
+
//# sourceMappingURL=renamer.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"renamer.d.ts","sourceRoot":"","sources":["../src/renamer.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,iBAAiB,CAAA;AAI5C,OAAO,KAAK,CAAC,MAAM,cAAc,CAAA;AAEjC,OAAO,EAAE,QAAQ,EAAW,MAAM,aAAa,CAAA;AAgF/C,MAAM,CAAC,OAAO,OAAO,YAAY;gBACjB,KAAK,EAAE,KAAK,EAAE,GAAG,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC;IAK1C,GAAG,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,CAAA;IAExB,KAAK,EAAE,KAAK,CAAA;IAEpB,iCAAiC,CAAC,YAAY,EAAE,QAAQ;IAyBxD,uCAAuC,CAAC,IAAI,EAAE,QAAQ;IAItD,MAAM;CAwDT"}
|
package/esm/renamer.js
ADDED
|
@@ -0,0 +1,140 @@
|
|
|
1
|
+
// original https://github.com/babel/babel/blob/9c77558234c87b9220604fbc1519089e2d6334e2/packages/babel-traverse/src/scope/lib/renamer.ts#L61
|
|
2
|
+
import splitExportDeclaration from '@babel/helper-split-export-declaration';
|
|
3
|
+
import { visitors } from '@babel/traverse';
|
|
4
|
+
import { traverseNode } from '@babel/traverse/lib/traverse-node';
|
|
5
|
+
import * as t from '@babel/types';
|
|
6
|
+
import { logger } from './utils';
|
|
7
|
+
const renameVisitor = {
|
|
8
|
+
ReferencedIdentifier({ node }, state) {
|
|
9
|
+
for (let [oldName, newName] of state.map) {
|
|
10
|
+
// console.log(node.name, oldName, newName)
|
|
11
|
+
if (node.name === oldName) {
|
|
12
|
+
node.name = newName;
|
|
13
|
+
}
|
|
14
|
+
}
|
|
15
|
+
},
|
|
16
|
+
// Scope(path, state) {
|
|
17
|
+
// if (
|
|
18
|
+
// !path.scope.bindingIdentifierEquals(
|
|
19
|
+
// state.oldName,
|
|
20
|
+
// state.binding.identifier,
|
|
21
|
+
// )
|
|
22
|
+
// ) {
|
|
23
|
+
// path.skip()
|
|
24
|
+
// if (path.isMethod()) {
|
|
25
|
+
// requeueComputedKeyAndDecorators(path)
|
|
26
|
+
// }
|
|
27
|
+
// }
|
|
28
|
+
// },
|
|
29
|
+
ObjectProperty({ node, scope }, state) {
|
|
30
|
+
var _a;
|
|
31
|
+
const { name } = node.key;
|
|
32
|
+
if (node.shorthand &&
|
|
33
|
+
// In destructuring the identifier is already renamed by the
|
|
34
|
+
// AssignmentExpression|Declaration|VariableDeclarator visitor,
|
|
35
|
+
// while in object literals it's renamed later by the
|
|
36
|
+
// ReferencedIdentifier visitor.
|
|
37
|
+
// (name === state.oldName || name === state.newName) &&
|
|
38
|
+
(state.map.has(name) || inverseMap(state.map).has(name)) &&
|
|
39
|
+
// Ignore shadowed bindings
|
|
40
|
+
[...state.map.keys()].some((oldName) => state.scope.getBindingIdentifier(oldName) ===
|
|
41
|
+
scope.getBindingIdentifier(name))) {
|
|
42
|
+
node.shorthand = false;
|
|
43
|
+
if ((_a = node.extra) === null || _a === void 0 ? void 0 : _a.shorthand)
|
|
44
|
+
node.extra.shorthand = false;
|
|
45
|
+
}
|
|
46
|
+
},
|
|
47
|
+
// @ts-ignore
|
|
48
|
+
'AssignmentExpression|Declaration|VariableDeclarator'(path, state) {
|
|
49
|
+
if (path.isVariableDeclaration())
|
|
50
|
+
return;
|
|
51
|
+
const ids = path.getOuterBindingIdentifiers();
|
|
52
|
+
for (const name in ids) {
|
|
53
|
+
for (let [oldName, newName] of state.map) {
|
|
54
|
+
// console.log(name, oldName, newName)
|
|
55
|
+
if (name === oldName)
|
|
56
|
+
ids[name].name = newName;
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
},
|
|
60
|
+
};
|
|
61
|
+
let cache = new WeakMap();
|
|
62
|
+
function inverseMap(map) {
|
|
63
|
+
if (cache.has(map))
|
|
64
|
+
return cache.get(map);
|
|
65
|
+
const inverse = new Map();
|
|
66
|
+
for (let [key, value] of map) {
|
|
67
|
+
inverse.set(value, key);
|
|
68
|
+
}
|
|
69
|
+
cache.set(map, inverse);
|
|
70
|
+
return inverse;
|
|
71
|
+
}
|
|
72
|
+
export default class BatchRenamer {
|
|
73
|
+
constructor(scope, map) {
|
|
74
|
+
this.map = map;
|
|
75
|
+
this.scope = scope;
|
|
76
|
+
}
|
|
77
|
+
maybeConvertFromExportDeclaration(parentDeclar) {
|
|
78
|
+
const maybeExportDeclar = parentDeclar.parentPath;
|
|
79
|
+
if (!(maybeExportDeclar === null || maybeExportDeclar === void 0 ? void 0 : maybeExportDeclar.isExportDeclaration())) {
|
|
80
|
+
return;
|
|
81
|
+
}
|
|
82
|
+
if (maybeExportDeclar.isExportDefaultDeclaration()) {
|
|
83
|
+
const { declaration } = maybeExportDeclar.node;
|
|
84
|
+
if (t.isDeclaration(declaration) && !declaration.id) {
|
|
85
|
+
return;
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
if (maybeExportDeclar.isExportAllDeclaration()) {
|
|
89
|
+
return;
|
|
90
|
+
}
|
|
91
|
+
splitExportDeclaration(maybeExportDeclar);
|
|
92
|
+
}
|
|
93
|
+
maybeConvertFromClassFunctionExpression(path) {
|
|
94
|
+
return path;
|
|
95
|
+
}
|
|
96
|
+
rename( /* Babel 7 - block?: t.Pattern | t.Scopable */) {
|
|
97
|
+
const { scope, map } = this;
|
|
98
|
+
for (let binding of [...map.keys()].map((name) => scope.getBinding(name))) {
|
|
99
|
+
if (!binding) {
|
|
100
|
+
continue;
|
|
101
|
+
}
|
|
102
|
+
const path = binding.path;
|
|
103
|
+
const parentDeclar = path.find((path) => path.isDeclaration() ||
|
|
104
|
+
path.isFunctionExpression() ||
|
|
105
|
+
path.isClassExpression());
|
|
106
|
+
if (parentDeclar) {
|
|
107
|
+
const bindingIds = parentDeclar.getOuterBindingIdentifiers();
|
|
108
|
+
const oldNames = Object.keys(bindingIds);
|
|
109
|
+
for (let oldName of oldNames) {
|
|
110
|
+
const binding = scope.getBinding(oldName);
|
|
111
|
+
if (binding && bindingIds[oldName] === binding.identifier) {
|
|
112
|
+
// When we are renaming an exported identifier, we need to ensure that
|
|
113
|
+
// the exported binding keeps the old name.
|
|
114
|
+
this.maybeConvertFromExportDeclaration(parentDeclar);
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
traverseNode(scope.block, visitors.explode(renameVisitor), scope, this, scope.path,
|
|
120
|
+
// When blockToTraverse is a SwitchStatement, the discriminant
|
|
121
|
+
// is not part of the current scope and thus should be skipped.
|
|
122
|
+
{ discriminant: true });
|
|
123
|
+
for (let [oldName, newName] of map) {
|
|
124
|
+
if (oldName === newName)
|
|
125
|
+
continue;
|
|
126
|
+
if (!arguments[0]) {
|
|
127
|
+
scope.removeOwnBinding(oldName);
|
|
128
|
+
const binding = scope.getBinding(oldName);
|
|
129
|
+
if (binding) {
|
|
130
|
+
binding.identifier.name = newName;
|
|
131
|
+
scope.bindings[newName] = binding;
|
|
132
|
+
}
|
|
133
|
+
else {
|
|
134
|
+
logger.log(`binding not found for ${oldName}`);
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
//# sourceMappingURL=renamer.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"renamer.js","sourceRoot":"","sources":["../src/renamer.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "unframer",
|
|
3
|
-
"version": "2.7.
|
|
3
|
+
"version": "2.7.8",
|
|
4
4
|
"description": "Import Framer components directly in your React app, type safe and customizable",
|
|
5
5
|
"sideEffects": false,
|
|
6
6
|
"repository": "https://github.com/remorses/unframer",
|
|
@@ -41,7 +41,6 @@
|
|
|
41
41
|
"dependencies": {
|
|
42
42
|
"async-sema": "^3.1.1",
|
|
43
43
|
"cac": "^6.7.14",
|
|
44
|
-
"dedent": "^1.5.3",
|
|
45
44
|
"dprint-node": "^1.0.8",
|
|
46
45
|
"esbuild": "^0.24.0",
|
|
47
46
|
"esbuild-plugins-node-modules-polyfill": "^1.6.8",
|
|
@@ -49,12 +48,14 @@
|
|
|
49
48
|
"find-up": "^5.0.0",
|
|
50
49
|
"fs-extra": "^11.2.0",
|
|
51
50
|
"json5": "^2.2.3",
|
|
51
|
+
"just-kebab-case": "^4.2.0",
|
|
52
52
|
"marked": "^15.0.3",
|
|
53
53
|
"marked-terminal": "^7.2.1",
|
|
54
54
|
"nanospinner": "^1.2.0",
|
|
55
55
|
"native-fetch": "^4.0.2",
|
|
56
56
|
"picocolors": "^1.0.1",
|
|
57
|
-
"real-framer-motion": "npm:framer-motion@11.2.10"
|
|
57
|
+
"real-framer-motion": "npm:framer-motion@11.2.10",
|
|
58
|
+
"string-dedent": "^3.0.1"
|
|
58
59
|
},
|
|
59
60
|
"devDependencies": {
|
|
60
61
|
"@babel/core": "^7.24.9",
|
|
@@ -70,7 +71,7 @@
|
|
|
70
71
|
"@types/fs-extra": "^11.0.4",
|
|
71
72
|
"@types/node": "^22.7.4",
|
|
72
73
|
"@types/react": "^18.3.12",
|
|
73
|
-
"@xmorse/deployment-utils": "^0.2.
|
|
74
|
+
"@xmorse/deployment-utils": "^0.2.19",
|
|
74
75
|
"concurrently": "^8.2.2",
|
|
75
76
|
"openai": "^4.52.7",
|
|
76
77
|
"posthtml": "^0.16.6",
|
|
@@ -0,0 +1,441 @@
|
|
|
1
|
+
import * as BabelTypes from '@babel/types'
|
|
2
|
+
|
|
3
|
+
import { PluginObj } from '@babel/core'
|
|
4
|
+
import { ImportDeclaration, ImportSpecifier, Identifier } from '@babel/types'
|
|
5
|
+
import BatchRenamer from './renamer'
|
|
6
|
+
import { logger } from './utils'
|
|
7
|
+
|
|
8
|
+
export function babelPluginDeduplicateImports({
|
|
9
|
+
types: t,
|
|
10
|
+
}: {
|
|
11
|
+
types: typeof BabelTypes
|
|
12
|
+
}): PluginObj {
|
|
13
|
+
const importAliasMap = new Map<
|
|
14
|
+
string,
|
|
15
|
+
Map<
|
|
16
|
+
string,
|
|
17
|
+
{ consolidated: string; importName; path: ImportSpecifier; source }
|
|
18
|
+
>
|
|
19
|
+
>()
|
|
20
|
+
|
|
21
|
+
function addImport({
|
|
22
|
+
source,
|
|
23
|
+
local,
|
|
24
|
+
consolidated,
|
|
25
|
+
importName,
|
|
26
|
+
path,
|
|
27
|
+
}: {
|
|
28
|
+
source: string
|
|
29
|
+
local: string
|
|
30
|
+
consolidated: string
|
|
31
|
+
importName: string
|
|
32
|
+
path
|
|
33
|
+
}) {
|
|
34
|
+
if (!importAliasMap.has(source)) {
|
|
35
|
+
importAliasMap.set(source, new Map())
|
|
36
|
+
}
|
|
37
|
+
importAliasMap
|
|
38
|
+
.get(source)
|
|
39
|
+
?.set(local, { consolidated, importName, path, source })
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
function getConsolidatedName({ source, importName, defaultOne }) {
|
|
43
|
+
const allSpecifiers = [...importAliasMap.values()].flatMap((x) => [
|
|
44
|
+
...x.values(),
|
|
45
|
+
])
|
|
46
|
+
const first = allSpecifiers.find((x) => {
|
|
47
|
+
if (importName === 'default' || importName === 'namespace') {
|
|
48
|
+
if (source !== x.source) {
|
|
49
|
+
return false
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
return x.importName === importName
|
|
53
|
+
})
|
|
54
|
+
return first?.consolidated || defaultOne
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
return {
|
|
58
|
+
visitor: {
|
|
59
|
+
ImportDeclaration(path) {
|
|
60
|
+
const source = path.node.source.value
|
|
61
|
+
|
|
62
|
+
path.node.specifiers.forEach((specifier) => {
|
|
63
|
+
if (
|
|
64
|
+
t.isImportSpecifier(specifier) &&
|
|
65
|
+
BabelTypes.isIdentifier(specifier.imported)
|
|
66
|
+
) {
|
|
67
|
+
const importName = specifier.imported.name
|
|
68
|
+
|
|
69
|
+
const consolidatedName = getConsolidatedName({
|
|
70
|
+
source,
|
|
71
|
+
importName,
|
|
72
|
+
defaultOne: specifier.local.name,
|
|
73
|
+
})
|
|
74
|
+
addImport({
|
|
75
|
+
source,
|
|
76
|
+
local: specifier.local.name,
|
|
77
|
+
importName,
|
|
78
|
+
consolidated: consolidatedName,
|
|
79
|
+
path,
|
|
80
|
+
})
|
|
81
|
+
} else if (t.isImportDefaultSpecifier(specifier)) {
|
|
82
|
+
const importName = 'default'
|
|
83
|
+
|
|
84
|
+
const consolidatedName = getConsolidatedName({
|
|
85
|
+
source,
|
|
86
|
+
importName,
|
|
87
|
+
defaultOne: specifier.local.name,
|
|
88
|
+
})
|
|
89
|
+
addImport({
|
|
90
|
+
source,
|
|
91
|
+
local: specifier.local.name,
|
|
92
|
+
importName,
|
|
93
|
+
consolidated: consolidatedName,
|
|
94
|
+
path,
|
|
95
|
+
})
|
|
96
|
+
} else if (t.isImportNamespaceSpecifier(specifier)) {
|
|
97
|
+
const importName = 'namespace'
|
|
98
|
+
|
|
99
|
+
const consolidatedName = getConsolidatedName({
|
|
100
|
+
source,
|
|
101
|
+
importName,
|
|
102
|
+
defaultOne: specifier.local.name,
|
|
103
|
+
})
|
|
104
|
+
addImport({
|
|
105
|
+
source,
|
|
106
|
+
local: specifier.local.name,
|
|
107
|
+
importName,
|
|
108
|
+
consolidated: consolidatedName,
|
|
109
|
+
path,
|
|
110
|
+
})
|
|
111
|
+
}
|
|
112
|
+
})
|
|
113
|
+
|
|
114
|
+
// Remove the current import declaration to later add the consolidated one
|
|
115
|
+
// path.remove()
|
|
116
|
+
},
|
|
117
|
+
Program: {
|
|
118
|
+
exit(path) {
|
|
119
|
+
console.log(`renaming imports...`)
|
|
120
|
+
for (const [source, modMap] of importAliasMap) {
|
|
121
|
+
// rename import names to consolidated names
|
|
122
|
+
for (let [local, { consolidated, path: p }] of modMap) {
|
|
123
|
+
logger.log(
|
|
124
|
+
`renaming ${local} to ${consolidated}...`,
|
|
125
|
+
)
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
const map = new Map<string, string>(
|
|
130
|
+
[...importAliasMap.values()].flatMap((x) => {
|
|
131
|
+
return [...x.entries()]
|
|
132
|
+
.map(([prev, x]) => {
|
|
133
|
+
if (prev === x.consolidated) {
|
|
134
|
+
return
|
|
135
|
+
}
|
|
136
|
+
return [prev, x.consolidated]
|
|
137
|
+
})
|
|
138
|
+
.filter((x) => x !== undefined) as Array<
|
|
139
|
+
[string, string]
|
|
140
|
+
>
|
|
141
|
+
}),
|
|
142
|
+
)
|
|
143
|
+
// console.log([...map.entries()])
|
|
144
|
+
const renamer = new BatchRenamer(path.scope, map)
|
|
145
|
+
renamer.rename()
|
|
146
|
+
|
|
147
|
+
const importDecs = path.node.body.filter((node) =>
|
|
148
|
+
t.isImportDeclaration(node),
|
|
149
|
+
) as ImportDeclaration[]
|
|
150
|
+
|
|
151
|
+
const definedImports = new Set<string>()
|
|
152
|
+
const later = [] as Function[]
|
|
153
|
+
console.log(`removing duplicates...`)
|
|
154
|
+
for (let importDec of importDecs) {
|
|
155
|
+
const source = importDec.source.value
|
|
156
|
+
|
|
157
|
+
const specifiers = importDec.specifiers
|
|
158
|
+
for (let specifier of specifiers) {
|
|
159
|
+
if (
|
|
160
|
+
!BabelTypes.isImportSpecifier(specifier) &&
|
|
161
|
+
!BabelTypes.isImportDefaultSpecifier(
|
|
162
|
+
specifier,
|
|
163
|
+
) &&
|
|
164
|
+
!BabelTypes.isImportNamespaceSpecifier(
|
|
165
|
+
specifier,
|
|
166
|
+
)
|
|
167
|
+
) {
|
|
168
|
+
continue
|
|
169
|
+
}
|
|
170
|
+
let importKey = ''
|
|
171
|
+
if (
|
|
172
|
+
BabelTypes.isImportDefaultSpecifier(specifier)
|
|
173
|
+
) {
|
|
174
|
+
importKey = source + 'default'
|
|
175
|
+
} else if (
|
|
176
|
+
BabelTypes.isImportNamespaceSpecifier(specifier)
|
|
177
|
+
) {
|
|
178
|
+
importKey = source + 'namespace'
|
|
179
|
+
} else {
|
|
180
|
+
if (
|
|
181
|
+
!BabelTypes.isIdentifier(specifier.imported)
|
|
182
|
+
) {
|
|
183
|
+
continue
|
|
184
|
+
}
|
|
185
|
+
importKey = specifier.imported.name
|
|
186
|
+
}
|
|
187
|
+
|
|
188
|
+
if (definedImports.has(importKey)) {
|
|
189
|
+
later.push(() => {
|
|
190
|
+
console.log(
|
|
191
|
+
`removing ${importKey} from ${source}...`,
|
|
192
|
+
)
|
|
193
|
+
|
|
194
|
+
importDec.specifiers =
|
|
195
|
+
importDec.specifiers.filter(
|
|
196
|
+
(x) => x !== specifier,
|
|
197
|
+
)
|
|
198
|
+
if (!importDec.specifiers.length) {
|
|
199
|
+
const index = path.node.body.findIndex(
|
|
200
|
+
(x) => x === importDec,
|
|
201
|
+
)
|
|
202
|
+
path.node.body.splice(index, 1)
|
|
203
|
+
}
|
|
204
|
+
})
|
|
205
|
+
}
|
|
206
|
+
definedImports.add(importKey)
|
|
207
|
+
}
|
|
208
|
+
}
|
|
209
|
+
for (let fn of later) {
|
|
210
|
+
fn()
|
|
211
|
+
}
|
|
212
|
+
},
|
|
213
|
+
},
|
|
214
|
+
// Identifier(path) {
|
|
215
|
+
// const name = path.node.name
|
|
216
|
+
// const binding = path.scope.getBinding(name)
|
|
217
|
+
|
|
218
|
+
// if (binding && t.isImportSpecifier(binding.path.node)) {
|
|
219
|
+
// const source = (binding.path.parent as ImportDeclaration)
|
|
220
|
+
// .source.value
|
|
221
|
+
// const localName = getLocalImportName(source, name)
|
|
222
|
+
|
|
223
|
+
// if (localName && localName !== name) {
|
|
224
|
+
// path.node.name = localName
|
|
225
|
+
// }
|
|
226
|
+
// }
|
|
227
|
+
// },
|
|
228
|
+
},
|
|
229
|
+
}
|
|
230
|
+
}
|
|
231
|
+
|
|
232
|
+
export function babelPluginRenameExports({
|
|
233
|
+
map,
|
|
234
|
+
}: {
|
|
235
|
+
map: Map<string, string>
|
|
236
|
+
}) {
|
|
237
|
+
return {
|
|
238
|
+
name: 'rename-exports',
|
|
239
|
+
visitor: {
|
|
240
|
+
ExportNamedDeclaration(path) {
|
|
241
|
+
const { specifiers, declaration } = path.node
|
|
242
|
+
// Handle export specifiers like: export { something as oldName }
|
|
243
|
+
for (const specifier of specifiers) {
|
|
244
|
+
if (!BabelTypes.isExportSpecifier(specifier)) continue
|
|
245
|
+
const exported = specifier.exported
|
|
246
|
+
if (!BabelTypes.isIdentifier(exported)) continue
|
|
247
|
+
const oldName = exported.name
|
|
248
|
+
const newName = map.get(oldName)
|
|
249
|
+
if (newName) {
|
|
250
|
+
exported.name = newName
|
|
251
|
+
}
|
|
252
|
+
}
|
|
253
|
+
// Handle function declarations like: export function oldName1() {}
|
|
254
|
+
if (BabelTypes.isFunctionDeclaration(declaration)) {
|
|
255
|
+
const oldName = declaration.id?.name
|
|
256
|
+
if (oldName) {
|
|
257
|
+
const newName = map.get(oldName)
|
|
258
|
+
if (newName && declaration?.id) {
|
|
259
|
+
declaration.id.name = newName
|
|
260
|
+
}
|
|
261
|
+
}
|
|
262
|
+
}
|
|
263
|
+
},
|
|
264
|
+
ExportDefaultDeclaration(path) {
|
|
265
|
+
const { declaration } = path.node
|
|
266
|
+
if (BabelTypes.isIdentifier(declaration)) {
|
|
267
|
+
const oldName = declaration.name
|
|
268
|
+
const newName = map.get(oldName)
|
|
269
|
+
if (newName) {
|
|
270
|
+
declaration.name = newName
|
|
271
|
+
}
|
|
272
|
+
}
|
|
273
|
+
},
|
|
274
|
+
},
|
|
275
|
+
}
|
|
276
|
+
}
|
|
277
|
+
|
|
278
|
+
// Set of types that don't need expression containers
|
|
279
|
+
const noContainerTypes = new Set([
|
|
280
|
+
'JSXElement',
|
|
281
|
+
// 'StringLiteral',
|
|
282
|
+
'NumericLiteral',
|
|
283
|
+
])
|
|
284
|
+
|
|
285
|
+
export function babelPluginJsxTransform() {
|
|
286
|
+
return {
|
|
287
|
+
name: 'jsx-transform',
|
|
288
|
+
visitor: {
|
|
289
|
+
CallExpression(path) {
|
|
290
|
+
// Check if it's a _jsx or _jsxs call
|
|
291
|
+
if (
|
|
292
|
+
!path.node.callee ||
|
|
293
|
+
!path.node.callee.name?.startsWith('_jsx')
|
|
294
|
+
) {
|
|
295
|
+
return
|
|
296
|
+
}
|
|
297
|
+
|
|
298
|
+
// Remove /* @__PURE__ */ comments
|
|
299
|
+
if (path.node.leadingComments) {
|
|
300
|
+
path.node.leadingComments =
|
|
301
|
+
path.node.leadingComments.filter(
|
|
302
|
+
(comment) => !comment.value.includes('@__PURE__'),
|
|
303
|
+
)
|
|
304
|
+
}
|
|
305
|
+
|
|
306
|
+
const [elementArg, propsArg] = path.node.arguments
|
|
307
|
+
|
|
308
|
+
// Get the element type name
|
|
309
|
+
let elementName = ''
|
|
310
|
+
if (elementArg.type === 'MemberExpression') {
|
|
311
|
+
elementName = `${elementArg.object.name}.${elementArg.property.name}`
|
|
312
|
+
} else if (elementArg.type === 'StringLiteral') {
|
|
313
|
+
elementName = elementArg.value
|
|
314
|
+
} else if (elementArg.type === 'Identifier') {
|
|
315
|
+
elementName = elementArg.name
|
|
316
|
+
} else {
|
|
317
|
+
// Skip if we can't determine element name
|
|
318
|
+
return
|
|
319
|
+
}
|
|
320
|
+
|
|
321
|
+
// Convert to JSX element
|
|
322
|
+
const jsxElement: BabelTypes.JSXElement = {
|
|
323
|
+
type: 'JSXElement',
|
|
324
|
+
openingElement: {
|
|
325
|
+
type: 'JSXOpeningElement',
|
|
326
|
+
name: {
|
|
327
|
+
type: 'JSXIdentifier',
|
|
328
|
+
name: elementName,
|
|
329
|
+
},
|
|
330
|
+
attributes: [],
|
|
331
|
+
selfClosing: !propsArg.properties.find(
|
|
332
|
+
(p) => p.key?.name === 'children',
|
|
333
|
+
),
|
|
334
|
+
},
|
|
335
|
+
closingElement: propsArg.properties.find(
|
|
336
|
+
(p) => p.key?.name === 'children',
|
|
337
|
+
)
|
|
338
|
+
? {
|
|
339
|
+
type: 'JSXClosingElement',
|
|
340
|
+
name: {
|
|
341
|
+
type: 'JSXIdentifier',
|
|
342
|
+
name: elementName,
|
|
343
|
+
},
|
|
344
|
+
}
|
|
345
|
+
: null,
|
|
346
|
+
children: [],
|
|
347
|
+
}
|
|
348
|
+
|
|
349
|
+
// Add attributes
|
|
350
|
+
if (propsArg && propsArg.properties) {
|
|
351
|
+
propsArg.properties.forEach((prop) => {
|
|
352
|
+
if (prop.type === 'SpreadElement') {
|
|
353
|
+
jsxElement.openingElement.attributes.push({
|
|
354
|
+
type: 'JSXSpreadAttribute',
|
|
355
|
+
argument: prop.argument,
|
|
356
|
+
})
|
|
357
|
+
} else if (prop.key?.name === 'children') {
|
|
358
|
+
if (prop.value.type === 'ArrayExpression') {
|
|
359
|
+
jsxElement.children = prop.value.elements.map(
|
|
360
|
+
(element) => {
|
|
361
|
+
if (
|
|
362
|
+
noContainerTypes.has(
|
|
363
|
+
element.type,
|
|
364
|
+
) ||
|
|
365
|
+
(element.type ===
|
|
366
|
+
'CallExpression' &&
|
|
367
|
+
element.callee?.name?.startsWith(
|
|
368
|
+
'_jsx',
|
|
369
|
+
))
|
|
370
|
+
) {
|
|
371
|
+
return element
|
|
372
|
+
}
|
|
373
|
+
return {
|
|
374
|
+
type: 'JSXExpressionContainer',
|
|
375
|
+
expression: element,
|
|
376
|
+
}
|
|
377
|
+
},
|
|
378
|
+
)
|
|
379
|
+
} else {
|
|
380
|
+
if (
|
|
381
|
+
noContainerTypes.has(prop.value.type) ||
|
|
382
|
+
(prop.value.type === 'CallExpression' &&
|
|
383
|
+
prop.value.callee?.name?.startsWith(
|
|
384
|
+
'_jsx',
|
|
385
|
+
))
|
|
386
|
+
) {
|
|
387
|
+
jsxElement.children = [prop.value]
|
|
388
|
+
} else {
|
|
389
|
+
jsxElement.children = [
|
|
390
|
+
{
|
|
391
|
+
type: 'JSXExpressionContainer',
|
|
392
|
+
expression: prop.value,
|
|
393
|
+
},
|
|
394
|
+
]
|
|
395
|
+
}
|
|
396
|
+
}
|
|
397
|
+
} else {
|
|
398
|
+
let attrName = prop.key?.name
|
|
399
|
+
if (
|
|
400
|
+
!attrName &&
|
|
401
|
+
prop.key?.type === 'StringLiteral'
|
|
402
|
+
) {
|
|
403
|
+
attrName = prop.key.value
|
|
404
|
+
}
|
|
405
|
+
if (!attrName) {
|
|
406
|
+
console.log(
|
|
407
|
+
`no prop.key?.name for ${JSON.stringify(
|
|
408
|
+
prop,
|
|
409
|
+
)}`,
|
|
410
|
+
)
|
|
411
|
+
return
|
|
412
|
+
}
|
|
413
|
+
|
|
414
|
+
jsxElement.openingElement.attributes.push({
|
|
415
|
+
type: 'JSXAttribute',
|
|
416
|
+
name: {
|
|
417
|
+
type: 'JSXIdentifier',
|
|
418
|
+
name: attrName,
|
|
419
|
+
},
|
|
420
|
+
value: {
|
|
421
|
+
type: 'JSXExpressionContainer',
|
|
422
|
+
expression: prop.value,
|
|
423
|
+
},
|
|
424
|
+
})
|
|
425
|
+
}
|
|
426
|
+
})
|
|
427
|
+
}
|
|
428
|
+
|
|
429
|
+
path.replaceWith(jsxElement)
|
|
430
|
+
},
|
|
431
|
+
},
|
|
432
|
+
}
|
|
433
|
+
}
|
|
434
|
+
|
|
435
|
+
function jsonStringifyWithMaps(map) {
|
|
436
|
+
return JSON.stringify(
|
|
437
|
+
[...map],
|
|
438
|
+
(key, value) => (value instanceof Map ? [...value] : value),
|
|
439
|
+
2,
|
|
440
|
+
)
|
|
441
|
+
}
|
package/src/cli.tsx
CHANGED
|
@@ -9,19 +9,12 @@ import path, { basename } from 'path'
|
|
|
9
9
|
import { BreakpointSizes } from './css.js'
|
|
10
10
|
import { logger } from './utils.js'
|
|
11
11
|
const configNames = ['unframer.config.json', 'unframer.json']
|
|
12
|
+
import kebabCase from 'just-kebab-case'
|
|
12
13
|
|
|
13
14
|
export const cli = cac('unframer')
|
|
14
15
|
|
|
15
16
|
let defaultOutDir = 'framer'
|
|
16
17
|
|
|
17
|
-
function nameToFolder(name: string) {
|
|
18
|
-
return name
|
|
19
|
-
.replace(/[^a-zA-Z0-9]/g, '-') // Replace non-alphanumeric with dash
|
|
20
|
-
.replace(/-+/g, '-') // Replace multiple dashes with single dash
|
|
21
|
-
.replace(/^-|-$/g, '') // Remove leading/trailing dashes
|
|
22
|
-
.toLowerCase()
|
|
23
|
-
}
|
|
24
|
-
|
|
25
18
|
cli.command('[projectId]', 'Run unframer with optional project ID')
|
|
26
19
|
.option('--outDir <dir>', 'Output directory', { default: defaultOutDir })
|
|
27
20
|
.action(async function main(projectId, options) {
|
|
@@ -46,10 +39,7 @@ cli.command('[projectId]', 'Run unframer with optional project ID')
|
|
|
46
39
|
config: {
|
|
47
40
|
outDir,
|
|
48
41
|
components: Object.fromEntries(
|
|
49
|
-
data.components.map((c) => [
|
|
50
|
-
nameToFolder(c.name),
|
|
51
|
-
c.url,
|
|
52
|
-
]),
|
|
42
|
+
data.components.map((c) => [kebabCase(c.name), c.url]),
|
|
53
43
|
),
|
|
54
44
|
tokens: data.colorStyles,
|
|
55
45
|
framerWebPages: data.framerWebPages || [],
|