@react-spectrum/codemods 1.2.1 → 1.2.3
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/dist/index.js +12 -10
- package/dist/s1-to-s2/src/codemods/codemod.js +33 -17
- package/dist/s1-to-s2/src/codemods/components/ActionGroup/transform.js +34 -11
- package/dist/s1-to-s2/src/codemods/components/Avatar/transform.js +5 -1
- package/dist/s1-to-s2/src/codemods/components/ContextualHelpTrigger/transform.js +1 -1
- package/dist/s1-to-s2/src/codemods/components/DialogContainer/transform.js +3 -4
- package/dist/s1-to-s2/src/codemods/components/DialogTrigger/transform.js +33 -11
- package/dist/s1-to-s2/src/codemods/components/Item/transform.js +28 -7
- package/dist/s1-to-s2/src/codemods/components/Link/transform.js +6 -4
- package/dist/s1-to-s2/src/codemods/components/Row/transform.js +12 -5
- package/dist/s1-to-s2/src/codemods/components/Section/transform.js +12 -3
- package/dist/s1-to-s2/src/codemods/components/TableView/transform.js +36 -19
- package/dist/s1-to-s2/src/codemods/components/Tabs/transform.js +25 -9
- package/dist/s1-to-s2/src/codemods/icons/iconMap.js +319 -1276
- package/dist/s1-to-s2/src/codemods/shared/dimensions.js +5 -32
- package/dist/s1-to-s2/src/codemods/shared/styleProps.js +55 -19
- package/dist/s1-to-s2/src/codemods/shared/transforms.js +130 -67
- package/dist/s1-to-s2/src/codemods/shared/unsafeStyle.js +102 -48
- package/dist/s1-to-s2/src/codemods/shared/utils.js +31 -28
- package/dist/s1-to-s2/src/getComponents.js +8 -8
- package/dist/s1-to-s2/src/index.js +10 -6
- package/dist/s1-to-s2/src/utils/installPackage.js +5 -1
- package/dist/s1-to-s2/src/utils/waitForKeypress.js +1 -1
- package/dist/test-utils-rc-update/src/codemod.js +236 -0
- package/dist/test-utils-rc-update/src/index.js +13 -0
- package/dist/use-monopackages/src/codemod.js +25 -27
- package/dist/use-subpaths/src/codemod.js +11 -5
- package/dist/use-subpaths/src/specifiers.js +3 -1
- package/package.json +24 -22
|
@@ -98,39 +98,11 @@ const dimensions = {
|
|
|
98
98
|
'single-line-width': 192 // size-2400
|
|
99
99
|
};
|
|
100
100
|
const spacingValues = [
|
|
101
|
-
0,
|
|
102
|
-
|
|
103
|
-
8,
|
|
104
|
-
12,
|
|
105
|
-
16,
|
|
106
|
-
20,
|
|
107
|
-
24,
|
|
108
|
-
28,
|
|
109
|
-
32,
|
|
110
|
-
36,
|
|
111
|
-
40,
|
|
112
|
-
44,
|
|
113
|
-
48,
|
|
114
|
-
56,
|
|
115
|
-
64,
|
|
116
|
-
80,
|
|
117
|
-
96,
|
|
118
|
-
112,
|
|
119
|
-
128,
|
|
120
|
-
144,
|
|
121
|
-
160,
|
|
122
|
-
176,
|
|
123
|
-
192,
|
|
124
|
-
208,
|
|
125
|
-
224,
|
|
126
|
-
240,
|
|
127
|
-
256,
|
|
128
|
-
288,
|
|
129
|
-
320,
|
|
130
|
-
384
|
|
101
|
+
0, 4, 8, 12, 16, 20, 24, 28, 32, 36, 40, 44, 48, 56, 64, 80, 96, 112, 128, 144, 160, 176, 192,
|
|
102
|
+
208, 224, 240, 256, 288, 320, 384
|
|
131
103
|
];
|
|
132
104
|
const sizing = {
|
|
133
|
-
|
|
105
|
+
auto: 'auto',
|
|
134
106
|
'100vh': 'screen',
|
|
135
107
|
'min-content': 'min',
|
|
136
108
|
'max-content': 'max',
|
|
@@ -180,7 +152,8 @@ function convertDimension(value, type) {
|
|
|
180
152
|
return `[${pixelValue}px]`;
|
|
181
153
|
}
|
|
182
154
|
function convertGridTrack(value, toPixels = false) {
|
|
183
|
-
if (typeof value === 'string' &&
|
|
155
|
+
if (typeof value === 'string' &&
|
|
156
|
+
/^max-content|min-content|minmax|auto|fit-content|repeat|\d+fr/.test(value)) {
|
|
184
157
|
return value;
|
|
185
158
|
}
|
|
186
159
|
else {
|
|
@@ -158,7 +158,9 @@ function getStylePropValue(prop, value, element, colorVersion, condition = '') {
|
|
|
158
158
|
// return [mappedProp, customProp, [[customProp, value]]];
|
|
159
159
|
return null;
|
|
160
160
|
case 'flex':
|
|
161
|
-
if (value.type === 'BooleanLiteral' ||
|
|
161
|
+
if (value.type === 'BooleanLiteral' ||
|
|
162
|
+
value.type === 'StringLiteral' ||
|
|
163
|
+
value.type === 'NumericLiteral') {
|
|
162
164
|
let val = value.value;
|
|
163
165
|
if (val === true) {
|
|
164
166
|
val = 1;
|
|
@@ -257,16 +259,24 @@ function getStylePropValue(prop, value, element, colorVersion, condition = '') {
|
|
|
257
259
|
break;
|
|
258
260
|
case 'areas':
|
|
259
261
|
if (element === 'Grid') {
|
|
260
|
-
if (value.type === 'ArrayExpression' &&
|
|
262
|
+
if (value.type === 'ArrayExpression' &&
|
|
263
|
+
value.elements.every(e => e?.type === 'StringLiteral')) {
|
|
261
264
|
return {
|
|
262
|
-
macroValues: [
|
|
265
|
+
macroValues: [
|
|
266
|
+
{
|
|
267
|
+
key: mappedProp,
|
|
268
|
+
value: value.elements.map(e => e?.type === 'StringLiteral' && e.value)
|
|
269
|
+
}
|
|
270
|
+
]
|
|
263
271
|
};
|
|
264
272
|
}
|
|
265
273
|
else if (value.type === 'ObjectExpression') {
|
|
266
274
|
return getResponsiveValue(prop, value, element, colorVersion);
|
|
267
275
|
}
|
|
268
276
|
else {
|
|
269
|
-
let val = t.callExpression(t.memberExpression(t.callExpression(t.memberExpression(value, t.identifier('map')), [
|
|
277
|
+
let val = t.callExpression(t.memberExpression(t.callExpression(t.memberExpression(value, t.identifier('map')), [
|
|
278
|
+
t.arrowFunctionExpression([t.identifier('v')], t.templateLiteral([t.templateElement({ raw: '"' }, false), t.templateElement({ raw: '"' }, true)], [t.identifier('v')]))
|
|
279
|
+
]), t.identifier('join')), [t.stringLiteral('')]);
|
|
270
280
|
return {
|
|
271
281
|
macroValues: [],
|
|
272
282
|
dynamicValues: [{ key: mappedProp, value: val }]
|
|
@@ -285,16 +295,20 @@ function getStylePropValue(prop, value, element, colorVersion, condition = '') {
|
|
|
285
295
|
else if (value.type === 'ArrayExpression') {
|
|
286
296
|
let values = [];
|
|
287
297
|
for (let element of value.elements) {
|
|
298
|
+
// oxlint-disable-next-line max-depth
|
|
288
299
|
if (element?.type === 'StringLiteral' || element?.type === 'NumericLiteral') {
|
|
289
300
|
values.push((0, dimensions_1.convertGridTrack)(element.value));
|
|
290
301
|
}
|
|
291
302
|
else if (element?.type === 'CallExpression') {
|
|
292
303
|
// TODO: match to import using scope
|
|
304
|
+
// oxlint-disable-next-line max-depth
|
|
293
305
|
if (element.callee.type === 'Identifier' &&
|
|
294
306
|
element.callee.name === 'minmax' &&
|
|
295
307
|
element.arguments.length === 2 &&
|
|
296
|
-
(element.arguments[0].type === 'StringLiteral' ||
|
|
297
|
-
|
|
308
|
+
(element.arguments[0].type === 'StringLiteral' ||
|
|
309
|
+
element.arguments[0].type === 'NumericLiteral') &&
|
|
310
|
+
(element.arguments[1].type === 'StringLiteral' ||
|
|
311
|
+
element.arguments[1].type === 'NumericLiteral')) {
|
|
298
312
|
// TODO: use theme value somehow?
|
|
299
313
|
let min = (0, dimensions_1.convertGridTrack)(element.arguments[0].value, true);
|
|
300
314
|
let max = (0, dimensions_1.convertGridTrack)(element.arguments[1].value, true);
|
|
@@ -348,6 +362,7 @@ function getStylePropValue(prop, value, element, colorVersion, condition = '') {
|
|
|
348
362
|
if (prop === 'padding' && value.type === 'StringLiteral' && /\s/.test(value.value)) {
|
|
349
363
|
// Check if it has multiple whitespace-separated values
|
|
350
364
|
let expansions = expandSpaceShorthand(prop, value.value, dimensions_1.convertDimension);
|
|
365
|
+
// oxlint-disable-next-line max-depth
|
|
351
366
|
if (!expansions) {
|
|
352
367
|
return null;
|
|
353
368
|
}
|
|
@@ -481,12 +496,15 @@ function getResponsiveValue(prop, value, element, colorVersion) {
|
|
|
481
496
|
let res = {};
|
|
482
497
|
let custom = [];
|
|
483
498
|
for (let property of value.properties) {
|
|
484
|
-
if (property.type === 'ObjectProperty' &&
|
|
499
|
+
if (property.type === 'ObjectProperty' &&
|
|
500
|
+
property.key.type === 'Identifier' &&
|
|
501
|
+
property.key.name in breakpoints) {
|
|
485
502
|
let propertyValue = (0, utils_1.getPropValue)(property.value);
|
|
486
503
|
if (propertyValue && propertyValue.type !== 'ObjectExpression') {
|
|
487
504
|
let val = getStylePropValue(prop, propertyValue, element, colorVersion, property.key.name);
|
|
488
505
|
if (val && val.macroValues) {
|
|
489
|
-
res[breakpoints[property.key.name]] =
|
|
506
|
+
res[breakpoints[property.key.name]] =
|
|
507
|
+
val.macroValues[0].value;
|
|
490
508
|
}
|
|
491
509
|
if (val && val.dynamicValues) {
|
|
492
510
|
custom.push(...val.dynamicValues);
|
|
@@ -498,10 +516,12 @@ function getResponsiveValue(prop, value, element, colorVersion) {
|
|
|
498
516
|
return null;
|
|
499
517
|
}
|
|
500
518
|
return {
|
|
501
|
-
macroValues: [
|
|
519
|
+
macroValues: [
|
|
520
|
+
{
|
|
502
521
|
key: prop,
|
|
503
522
|
value: res
|
|
504
|
-
}
|
|
523
|
+
}
|
|
524
|
+
],
|
|
505
525
|
dynamicValues: custom
|
|
506
526
|
};
|
|
507
527
|
}
|
|
@@ -596,9 +616,9 @@ function expandSpaceShorthand(prop, rawValue, convertFn) {
|
|
|
596
616
|
}
|
|
597
617
|
}
|
|
598
618
|
function transformStyleProps(path, element) {
|
|
599
|
-
let macroValues = new Map;
|
|
600
|
-
let dynamicValues = new Map;
|
|
601
|
-
let conditions = new Map;
|
|
619
|
+
let macroValues = new Map();
|
|
620
|
+
let dynamicValues = new Map();
|
|
621
|
+
let conditions = new Map();
|
|
602
622
|
let isDOMElement = element === 'Flex' || element === 'Grid' || element === 'View' || element === 'Well';
|
|
603
623
|
if (element === 'Flex') {
|
|
604
624
|
macroValues.set('display', 'flex');
|
|
@@ -650,11 +670,13 @@ function transformStyleProps(path, element) {
|
|
|
650
670
|
macroValues.set(val.key, val.value);
|
|
651
671
|
}
|
|
652
672
|
if (value.dynamicValues) {
|
|
673
|
+
// oxlint-disable-next-line max-depth
|
|
653
674
|
for (let val of value.dynamicValues) {
|
|
654
675
|
dynamicValues.set(val.key, val.value);
|
|
655
676
|
}
|
|
656
677
|
}
|
|
657
678
|
if (value.conditions) {
|
|
679
|
+
// oxlint-disable-next-line max-depth
|
|
658
680
|
for (let val of value.conditions) {
|
|
659
681
|
conditions.set(val.key, val.value);
|
|
660
682
|
}
|
|
@@ -688,9 +710,15 @@ function transformStyleProps(path, element) {
|
|
|
688
710
|
return t.arrayExpression(v.map(v => valueToAST(v)));
|
|
689
711
|
}
|
|
690
712
|
else if (typeof v === 'object') {
|
|
691
|
-
if ('default' in v &&
|
|
713
|
+
if ('default' in v &&
|
|
714
|
+
typeof v.default === 'string' &&
|
|
715
|
+
'dark' in v &&
|
|
716
|
+
typeof v.dark === 'string') {
|
|
692
717
|
usedLightDark = true;
|
|
693
|
-
return t.callExpression(t.identifier('lightDark'), [
|
|
718
|
+
return t.callExpression(t.identifier('lightDark'), [
|
|
719
|
+
t.stringLiteral(v.default),
|
|
720
|
+
t.stringLiteral(v.dark)
|
|
721
|
+
]);
|
|
694
722
|
}
|
|
695
723
|
return t.objectExpression(Object.entries(v).map(([k, v]) => t.objectProperty(t.identifier(k), valueToAST(v))));
|
|
696
724
|
}
|
|
@@ -712,17 +740,25 @@ function transformStyleProps(path, element) {
|
|
|
712
740
|
}))
|
|
713
741
|
]);
|
|
714
742
|
if (conditions.size) {
|
|
715
|
-
macroCall = t.callExpression(macroCall, [
|
|
743
|
+
macroCall = t.callExpression(macroCall, [
|
|
744
|
+
t.objectExpression([...conditions].map(([k, v]) => t.objectProperty(t.identifier(k), v, false, v.type === 'Identifier' && v.name === k)))
|
|
745
|
+
]);
|
|
716
746
|
}
|
|
717
747
|
if (classNameAttribute?.isJSXAttribute()) {
|
|
718
|
-
classNameAttribute
|
|
748
|
+
classNameAttribute
|
|
749
|
+
.get('value')
|
|
750
|
+
.replaceWith(t.jsxExpressionContainer(t.binaryExpression('+', (0, utils_1.getPropValue)(classNameAttribute.node.value), macroCall)));
|
|
719
751
|
}
|
|
720
752
|
else {
|
|
721
|
-
path
|
|
753
|
+
path
|
|
754
|
+
.get('openingElement')
|
|
755
|
+
.pushContainer('attributes', t.jsxAttribute(t.jsxIdentifier(isDOMElement ? 'className' : 'styles'), t.jsxExpressionContainer(macroCall)));
|
|
722
756
|
}
|
|
723
757
|
}
|
|
724
758
|
if (dynamicValues.size) {
|
|
725
|
-
path
|
|
759
|
+
path
|
|
760
|
+
.get('openingElement')
|
|
761
|
+
.pushContainer('attributes', t.jsxAttribute(t.jsxIdentifier('style'), t.jsxExpressionContainer(t.objectExpression([...dynamicValues].map(([key, value]) => t.objectProperty(key.startsWith('--') ? t.stringLiteral(key) : t.identifier(key), value))))));
|
|
726
762
|
}
|
|
727
763
|
return { hasMacros, usedLightDark };
|
|
728
764
|
}
|
|
@@ -65,10 +65,12 @@ let availableComponents = (0, getComponents_1.getComponents)();
|
|
|
65
65
|
*/
|
|
66
66
|
function updatePropNameAndValue(path, options) {
|
|
67
67
|
const { oldPropName, oldPropValue, newPropName, newPropValue } = options;
|
|
68
|
-
let attrPath = path
|
|
68
|
+
let attrPath = path
|
|
69
|
+
.get('openingElement')
|
|
70
|
+
.get('attributes')
|
|
71
|
+
.find(attr => t.isJSXAttribute(attr.node) && attr.node.name.name === oldPropName);
|
|
69
72
|
if (attrPath && t.isJSXAttribute(attrPath.node) && attrPath.node.name.name === oldPropName) {
|
|
70
|
-
if (t.isStringLiteral(attrPath.node.value) &&
|
|
71
|
-
attrPath.node.value.value === oldPropValue) {
|
|
73
|
+
if (t.isStringLiteral(attrPath.node.value) && attrPath.node.value.value === oldPropValue) {
|
|
72
74
|
// Update old prop name to new prop name
|
|
73
75
|
attrPath.node.name.name = newPropName;
|
|
74
76
|
// If prop value is a string and matches the old value, replace it with the new value
|
|
@@ -86,8 +88,11 @@ function updatePropNameAndValue(path, options) {
|
|
|
86
88
|
}
|
|
87
89
|
else if (t.isJSXExpressionContainer(attrPath.node.value)) {
|
|
88
90
|
if (t.isIdentifier(attrPath.node.value.expression)) {
|
|
91
|
+
if (
|
|
89
92
|
// @ts-ignore
|
|
90
|
-
|
|
93
|
+
attrPath.node.comments &&
|
|
94
|
+
// @ts-ignore
|
|
95
|
+
[...attrPath.node.comments].some(comment => comment.value.includes('could not be automatically'))) {
|
|
91
96
|
return;
|
|
92
97
|
}
|
|
93
98
|
(0, utils_1.addComment)(attrPath.node, ` TODO(S2-upgrade): Prop ${oldPropName} could not be automatically updated because ${attrPath.node.value.expression.name} could not be followed.`);
|
|
@@ -96,8 +101,7 @@ function updatePropNameAndValue(path, options) {
|
|
|
96
101
|
// If prop value is an expression, traverse to find a string literal that matches the old and replace it with the new value
|
|
97
102
|
attrPath.traverse({
|
|
98
103
|
StringLiteral(stringPath) {
|
|
99
|
-
if (t.isStringLiteral(stringPath.node) &&
|
|
100
|
-
stringPath.node.value === oldPropValue) {
|
|
104
|
+
if (t.isStringLiteral(stringPath.node) && stringPath.node.value === oldPropValue) {
|
|
101
105
|
// Update old prop name to new prop name
|
|
102
106
|
attrPath.node.name.name = newPropName;
|
|
103
107
|
if (typeof newPropValue === 'string') {
|
|
@@ -126,8 +130,13 @@ function updatePropNameAndValue(path, options) {
|
|
|
126
130
|
*/
|
|
127
131
|
function updatePropValueAndAddNewPropName(path, options) {
|
|
128
132
|
const { oldPropName, oldPropValue, newPropName, newPropValue, additionalPropName, additionalPropValue } = options;
|
|
129
|
-
let attrPath = path
|
|
130
|
-
|
|
133
|
+
let attrPath = path
|
|
134
|
+
.get('openingElement')
|
|
135
|
+
.get('attributes')
|
|
136
|
+
.find(attr => t.isJSXAttribute(attr.node) && attr.node.name.name === oldPropName);
|
|
137
|
+
if (attrPath &&
|
|
138
|
+
t.isStringLiteral(attrPath.node.value) &&
|
|
139
|
+
attrPath.node.value.value === oldPropValue) {
|
|
131
140
|
// Update old prop name to new prop name
|
|
132
141
|
attrPath.node.name.name = newPropName;
|
|
133
142
|
// If prop value is a string and matches the old value, replace it with the new value
|
|
@@ -145,8 +154,7 @@ function updatePropValueAndAddNewPropName(path, options) {
|
|
|
145
154
|
// If prop value is an expression, traverse to find a string literal that matches the old and replace it with the new value
|
|
146
155
|
attrPath.traverse({
|
|
147
156
|
StringLiteral(stringPath) {
|
|
148
|
-
if (t.isStringLiteral(stringPath.node) &&
|
|
149
|
-
stringPath.node.value === oldPropValue) {
|
|
157
|
+
if (t.isStringLiteral(stringPath.node) && stringPath.node.value === oldPropValue) {
|
|
150
158
|
// Update old prop name to new prop name
|
|
151
159
|
attrPath.node.name.name = newPropName;
|
|
152
160
|
if (typeof newPropValue === 'string') {
|
|
@@ -171,7 +179,10 @@ function updatePropValueAndAddNewPropName(path, options) {
|
|
|
171
179
|
*/
|
|
172
180
|
function updatePropName(path, options) {
|
|
173
181
|
const { oldPropName, newPropName, comment } = options;
|
|
174
|
-
let attrPath = path
|
|
182
|
+
let attrPath = path
|
|
183
|
+
.get('openingElement')
|
|
184
|
+
.get('attributes')
|
|
185
|
+
.find(attr => t.isJSXAttribute(attr.node) && attr.node.name.name === oldPropName);
|
|
175
186
|
if (attrPath && t.isJSXAttribute(attrPath.node) && attrPath.node.name.name === oldPropName) {
|
|
176
187
|
attrPath.node.name.name = newPropName;
|
|
177
188
|
if (comment) {
|
|
@@ -187,7 +198,10 @@ function updatePropName(path, options) {
|
|
|
187
198
|
*/
|
|
188
199
|
function removeProp(path, options) {
|
|
189
200
|
const { propName, propValue } = options;
|
|
190
|
-
let attrPath = path
|
|
201
|
+
let attrPath = path
|
|
202
|
+
.get('openingElement')
|
|
203
|
+
.get('attributes')
|
|
204
|
+
.find(attr => t.isJSXAttribute(attr.node) && attr.node.name.name === propName);
|
|
191
205
|
if (attrPath && t.isJSXAttribute(attrPath.node) && attrPath.node.name.name === propName) {
|
|
192
206
|
if (propValue) {
|
|
193
207
|
// If prop value is provided, remove prop only if it matches the value
|
|
@@ -196,9 +210,12 @@ function removeProp(path, options) {
|
|
|
196
210
|
}
|
|
197
211
|
else if (t.isJSXExpressionContainer(attrPath.node.value)) {
|
|
198
212
|
if (t.isIdentifier(attrPath.node.value.expression)) {
|
|
199
|
-
// @ts-ignore
|
|
200
213
|
// eslint-disable-next-line max-depth
|
|
201
|
-
if (
|
|
214
|
+
if (
|
|
215
|
+
// @ts-ignore
|
|
216
|
+
attrPath.node.comments &&
|
|
217
|
+
// @ts-ignore
|
|
218
|
+
[...attrPath.node.comments].some(comment => comment.value.includes('could not be automatically'))) {
|
|
202
219
|
return;
|
|
203
220
|
}
|
|
204
221
|
(0, utils_1.addComment)(attrPath.node, ` TODO(S2-upgrade): Prop ${propName} could not be automatically removed because ${attrPath.node.value.expression.name} could not be followed.`);
|
|
@@ -206,8 +223,7 @@ function removeProp(path, options) {
|
|
|
206
223
|
else {
|
|
207
224
|
attrPath.traverse({
|
|
208
225
|
StringLiteral(stringPath) {
|
|
209
|
-
if (t.isStringLiteral(stringPath.node) &&
|
|
210
|
-
stringPath.node.value === propValue) {
|
|
226
|
+
if (t.isStringLiteral(stringPath.node) && stringPath.node.value === propValue) {
|
|
211
227
|
// Invalid prop value was found inside expression.
|
|
212
228
|
(0, utils_1.addComment)(attrPath.node, ` TODO(S2-upgrade): ${propName}="${propValue}" is no longer supported. You'll need to update this manually.`);
|
|
213
229
|
}
|
|
@@ -230,7 +246,10 @@ function removeProp(path, options) {
|
|
|
230
246
|
*/
|
|
231
247
|
function commentOutProp(path, options) {
|
|
232
248
|
const { propName, propValue } = options;
|
|
233
|
-
let attrPath = path
|
|
249
|
+
let attrPath = path
|
|
250
|
+
.get('openingElement')
|
|
251
|
+
.get('attributes')
|
|
252
|
+
.find(attr => t.isJSXAttribute(attr.node) && attr.node.name.name === propName);
|
|
234
253
|
if (attrPath && t.isJSXAttribute(attrPath.node) && attrPath.node.name.name === propName) {
|
|
235
254
|
if (propValue) {
|
|
236
255
|
// If prop value is provided, comment out prop only if it matches the value
|
|
@@ -241,8 +260,7 @@ function commentOutProp(path, options) {
|
|
|
241
260
|
else {
|
|
242
261
|
attrPath.traverse({
|
|
243
262
|
StringLiteral(stringPath) {
|
|
244
|
-
if (t.isStringLiteral(stringPath.node) &&
|
|
245
|
-
stringPath.node.value === propValue) {
|
|
263
|
+
if (t.isStringLiteral(stringPath.node) && stringPath.node.value === propValue) {
|
|
246
264
|
(0, utils_1.addComment)(attrPath.parentPath.node, ` TODO(S2-upgrade): ${propName}="${propValue}" has not been implemented yet.`);
|
|
247
265
|
attrPath.remove();
|
|
248
266
|
}
|
|
@@ -274,13 +292,16 @@ function addCommentToElement(path, options) {
|
|
|
274
292
|
*/
|
|
275
293
|
function updateComponentIfPropPresent(path, options) {
|
|
276
294
|
const { newComponentName, propName } = options;
|
|
277
|
-
let attrPath = path
|
|
295
|
+
let attrPath = path
|
|
296
|
+
.get('openingElement')
|
|
297
|
+
.get('attributes')
|
|
298
|
+
.find(attr => t.isJSXAttribute(attr.node) && attr.node.name.name === propName);
|
|
278
299
|
if (attrPath && t.isJSXAttribute(attrPath.node) && attrPath.node.name.name === propName) {
|
|
279
|
-
let node = attrPath.findParent(
|
|
300
|
+
let node = attrPath.findParent(p => t.isJSXElement(p.node))?.node;
|
|
280
301
|
if (node && t.isJSXElement(node)) {
|
|
281
302
|
let localName = newComponentName;
|
|
282
303
|
if (availableComponents.has(newComponentName)) {
|
|
283
|
-
let program = path.findParent(
|
|
304
|
+
let program = path.findParent(p => t.isProgram(p.node));
|
|
284
305
|
localName = (0, utils_1.addComponentImport)(program, newComponentName);
|
|
285
306
|
}
|
|
286
307
|
node.openingElement.name = t.jsxIdentifier(localName);
|
|
@@ -293,12 +314,12 @@ function updateComponentIfPropPresent(path, options) {
|
|
|
293
314
|
/**
|
|
294
315
|
* Remove render props, and move usage to a child component.
|
|
295
316
|
*
|
|
296
|
-
* Example:
|
|
297
|
-
*
|
|
317
|
+
* Example: - DialogTrigger: Update children to remove render props usage, and note that `close`
|
|
318
|
+
* export function moved from `DialogTrigger` to `Dialog`.
|
|
298
319
|
*/
|
|
299
320
|
function moveRenderPropsToChild(path, options) {
|
|
300
321
|
const { newChildComponentName } = options;
|
|
301
|
-
const renderFunctionIndex = path.node.children.findIndex(
|
|
322
|
+
const renderFunctionIndex = path.node.children.findIndex(child => t.isJSXExpressionContainer(child) &&
|
|
302
323
|
t.isArrowFunctionExpression(child.expression) &&
|
|
303
324
|
t.isJSXElement(child.expression.body) &&
|
|
304
325
|
t.isJSXIdentifier(child.expression.body.openingElement.name));
|
|
@@ -317,7 +338,7 @@ function moveRenderPropsToChild(path, options) {
|
|
|
317
338
|
const dialogElement = renderFunction.expression.body;
|
|
318
339
|
const originalParam = renderFunction.expression.params[0];
|
|
319
340
|
if (!t.isIdentifier(originalParam)) {
|
|
320
|
-
(0, utils_1.addComment)(path.node.children[renderFunctionIndex],
|
|
341
|
+
(0, utils_1.addComment)(path.node.children[renderFunctionIndex], " TODO(S2-upgrade): Could not automatically move the render props. You'll need to update this manually.");
|
|
321
342
|
return;
|
|
322
343
|
}
|
|
323
344
|
const paramName = originalParam.name;
|
|
@@ -326,7 +347,7 @@ function moveRenderPropsToChild(path, options) {
|
|
|
326
347
|
]);
|
|
327
348
|
const newRenderFunction = t.jsxExpressionContainer(t.arrowFunctionExpression([objectPattern], t.jsxFragment(t.jsxOpeningFragment(), t.jsxClosingFragment(), dialogElement.children)));
|
|
328
349
|
let removedOnDismiss = false;
|
|
329
|
-
const attributes = dialogElement.openingElement.attributes.filter(
|
|
350
|
+
const attributes = dialogElement.openingElement.attributes.filter(attr => {
|
|
330
351
|
if (t.isJSXAttribute(attr) && attr.name.name === 'onDismiss') {
|
|
331
352
|
removedOnDismiss = true;
|
|
332
353
|
return false;
|
|
@@ -349,11 +370,23 @@ function updateComponentWithinCollection(path, options) {
|
|
|
349
370
|
const { parentComponentName, newComponentName } = options;
|
|
350
371
|
// Collections currently implemented.
|
|
351
372
|
// TODO: Add 'ActionGroup', 'ListBox' once implemented
|
|
352
|
-
const collectionItemParents = new Set([
|
|
353
|
-
|
|
354
|
-
|
|
373
|
+
const collectionItemParents = new Set([
|
|
374
|
+
'Menu',
|
|
375
|
+
'ActionMenu',
|
|
376
|
+
'TagGroup',
|
|
377
|
+
'Breadcrumbs',
|
|
378
|
+
'Picker',
|
|
379
|
+
'ComboBox',
|
|
380
|
+
'ListBox',
|
|
381
|
+
'ListView',
|
|
382
|
+
'TabList',
|
|
383
|
+
'TabPanels',
|
|
384
|
+
'Collection',
|
|
385
|
+
'ContextualHelpTrigger'
|
|
386
|
+
]);
|
|
387
|
+
if (t.isJSXElement(path.node) && t.isJSXIdentifier(path.node.openingElement.name)) {
|
|
355
388
|
// Find closest parent collection component
|
|
356
|
-
let closestParentCollection = path.findParent(
|
|
389
|
+
let closestParentCollection = path.findParent(p => t.isJSXElement(p.node) &&
|
|
357
390
|
t.isJSXIdentifier(p.node.openingElement.name) &&
|
|
358
391
|
collectionItemParents.has((0, utils_1.getName)(path, p.node.openingElement.name)));
|
|
359
392
|
if (closestParentCollection &&
|
|
@@ -364,7 +397,7 @@ function updateComponentWithinCollection(path, options) {
|
|
|
364
397
|
updateKeyToId(path);
|
|
365
398
|
let localName = newComponentName;
|
|
366
399
|
if (availableComponents.has(newComponentName)) {
|
|
367
|
-
let program = path.findParent(
|
|
400
|
+
let program = path.findParent(p => t.isProgram(p.node));
|
|
368
401
|
localName = (0, utils_1.addComponentImport)(program, newComponentName);
|
|
369
402
|
}
|
|
370
403
|
let newNode = t.jsxElement(t.jsxOpeningElement(t.jsxIdentifier(localName), path.node.openingElement.attributes), t.jsxClosingElement(t.jsxIdentifier(localName)), path.node.children);
|
|
@@ -378,23 +411,44 @@ function updateComponentWithinCollection(path, options) {
|
|
|
378
411
|
* Example: If they're declaring declaring Items somewhere above the collection.
|
|
379
412
|
*/
|
|
380
413
|
function commentIfParentCollectionNotDetected(path) {
|
|
381
|
-
const collectionItemParents = new Set([
|
|
414
|
+
const collectionItemParents = new Set([
|
|
415
|
+
'Menu',
|
|
416
|
+
'ActionMenu',
|
|
417
|
+
'TagGroup',
|
|
418
|
+
'Breadcrumbs',
|
|
419
|
+
'Picker',
|
|
420
|
+
'ComboBox',
|
|
421
|
+
'ListBox',
|
|
422
|
+
'TabList',
|
|
423
|
+
'TabPanels',
|
|
424
|
+
'ActionGroup',
|
|
425
|
+
'ActionButtonGroup',
|
|
426
|
+
'ToggleButtonGroup',
|
|
427
|
+
'ListBox',
|
|
428
|
+
'ListView',
|
|
429
|
+
'Collection',
|
|
430
|
+
'SearchAutocomplete',
|
|
431
|
+
'Accordion',
|
|
432
|
+
'ActionBar',
|
|
433
|
+
'StepList',
|
|
434
|
+
'ContextualHelpTrigger'
|
|
435
|
+
]);
|
|
382
436
|
if (t.isJSXElement(path.node)) {
|
|
383
437
|
// Find closest parent collection component
|
|
384
|
-
let closestParentCollection = path.findParent(
|
|
438
|
+
let closestParentCollection = path.findParent(p => t.isJSXElement(p.node) &&
|
|
385
439
|
t.isJSXIdentifier(p.node.openingElement.name) &&
|
|
386
440
|
collectionItemParents.has((0, utils_1.getName)(path, p.node.openingElement.name)));
|
|
387
441
|
if (!closestParentCollection) {
|
|
388
442
|
// If we couldn't find a parent collection parent, leave a comment for them to check manually
|
|
389
|
-
(0, utils_1.addComment)(path.node,
|
|
443
|
+
(0, utils_1.addComment)(path.node, " TODO(S2-upgrade): Couldn't automatically detect what type of collection component this is rendered in. You'll need to update this manually.");
|
|
390
444
|
}
|
|
391
445
|
}
|
|
392
446
|
}
|
|
393
447
|
/**
|
|
394
448
|
* If within a component, moves prop to new child component.
|
|
395
449
|
*
|
|
396
|
-
* Example:
|
|
397
|
-
*
|
|
450
|
+
* Example: - Section: If within `Menu`, move `title` prop string to be a child of new `Heading`
|
|
451
|
+
* within a `Header`.
|
|
398
452
|
*/
|
|
399
453
|
function movePropToNewChildComponentName(path, options) {
|
|
400
454
|
const { parentComponentName, childComponentName, propName, newChildComponentName } = options;
|
|
@@ -406,17 +460,16 @@ function movePropToNewChildComponentName(path, options) {
|
|
|
406
460
|
(0, utils_1.getName)(path, path.parentPath.node.openingElement.name) === parentComponentName) {
|
|
407
461
|
let propValue;
|
|
408
462
|
let localName = newChildComponentName;
|
|
409
|
-
path.node.openingElement.attributes =
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
});
|
|
463
|
+
path.node.openingElement.attributes = path.node.openingElement.attributes.filter(attr => {
|
|
464
|
+
if (t.isJSXAttribute(attr) && attr.name.name === propName) {
|
|
465
|
+
propValue = attr.value;
|
|
466
|
+
return false;
|
|
467
|
+
}
|
|
468
|
+
return true;
|
|
469
|
+
});
|
|
417
470
|
if (propValue) {
|
|
418
471
|
if (availableComponents.has(newChildComponentName)) {
|
|
419
|
-
let program = path.findParent(
|
|
472
|
+
let program = path.findParent(p => t.isProgram(p.node));
|
|
420
473
|
localName = (0, utils_1.addComponentImport)(program, newChildComponentName);
|
|
421
474
|
}
|
|
422
475
|
path.node.children.unshift(t.jsxElement(t.jsxOpeningElement(t.jsxIdentifier(localName), []), t.jsxClosingElement(t.jsxIdentifier(localName)), [t.isStringLiteral(propValue) ? t.jsxText(propValue.value) : propValue]));
|
|
@@ -463,7 +516,9 @@ function movePropToChildComponent(path, options) {
|
|
|
463
516
|
if (!propAttr) {
|
|
464
517
|
return;
|
|
465
518
|
}
|
|
466
|
-
let childPath = path
|
|
519
|
+
let childPath = path
|
|
520
|
+
.get('children')
|
|
521
|
+
.find(child => child.isJSXElement() &&
|
|
467
522
|
t.isJSXIdentifier(child.node.openingElement.name) &&
|
|
468
523
|
(0, utils_1.getName)(path, child.node.openingElement.name) === childComponentName);
|
|
469
524
|
if (!childPath?.isJSXElement()) {
|
|
@@ -485,7 +540,7 @@ function updateToNewComponentName(path, options) {
|
|
|
485
540
|
const { newComponentName } = options;
|
|
486
541
|
let localName = newComponentName;
|
|
487
542
|
if (availableComponents.has(newComponentName)) {
|
|
488
|
-
let program = path.findParent(
|
|
543
|
+
let program = path.findParent(p => t.isProgram(p.node));
|
|
489
544
|
localName = (0, utils_1.addComponentImport)(program, newComponentName);
|
|
490
545
|
}
|
|
491
546
|
path.node.openingElement.name = t.jsxIdentifier(localName);
|
|
@@ -494,11 +549,11 @@ function updateToNewComponentName(path, options) {
|
|
|
494
549
|
}
|
|
495
550
|
}
|
|
496
551
|
const conversions = {
|
|
497
|
-
|
|
498
|
-
|
|
499
|
-
|
|
500
|
-
|
|
501
|
-
|
|
552
|
+
cm: 37.8,
|
|
553
|
+
mm: 3.78,
|
|
554
|
+
in: 96,
|
|
555
|
+
pt: 1.33,
|
|
556
|
+
pc: 16
|
|
502
557
|
};
|
|
503
558
|
/**
|
|
504
559
|
* Updates prop to use pixel value instead.
|
|
@@ -508,7 +563,10 @@ const conversions = {
|
|
|
508
563
|
*/
|
|
509
564
|
function convertDimensionValueToPx(path, options) {
|
|
510
565
|
const { propName } = options;
|
|
511
|
-
let attrPath = path
|
|
566
|
+
let attrPath = path
|
|
567
|
+
.get('openingElement')
|
|
568
|
+
.get('attributes')
|
|
569
|
+
.find(attr => t.isJSXAttribute(attr.node) && attr.node.name.name === propName);
|
|
512
570
|
if (attrPath && t.isJSXAttribute(attrPath.node) && attrPath.node.name.name === propName) {
|
|
513
571
|
if (t.isStringLiteral(attrPath.node.value)) {
|
|
514
572
|
try {
|
|
@@ -518,10 +576,10 @@ function convertDimensionValueToPx(path, options) {
|
|
|
518
576
|
}
|
|
519
577
|
else if (value && typeof value === 'string') {
|
|
520
578
|
// eslint-disable-next-line max-depth
|
|
521
|
-
if (
|
|
579
|
+
if (/%|vw|vh|auto|ex|ch|rem|vmin|vmax/.test(value)) {
|
|
522
580
|
(0, utils_1.addComment)(attrPath.node, ' TODO(S2-upgrade): Unable to convert CSS unit to a pixel value');
|
|
523
581
|
}
|
|
524
|
-
else if (
|
|
582
|
+
else if (/cm|mm|in|pt|pc/.test(value)) {
|
|
525
583
|
let unit = value.replace(/\[|\]|\d+/g, '');
|
|
526
584
|
let conversion = conversions[unit];
|
|
527
585
|
value = Number(value.replace(/\[|\]|cm|mm|in|pt|pc/g, ''));
|
|
@@ -531,7 +589,7 @@ function convertDimensionValueToPx(path, options) {
|
|
|
531
589
|
attrPath.node.value = t.jsxExpressionContainer(t.numericLiteral(pixelValue));
|
|
532
590
|
}
|
|
533
591
|
}
|
|
534
|
-
else if (
|
|
592
|
+
else if (/px/.test(value)) {
|
|
535
593
|
let pixelValue = Number(value.replace(/\[|\]|px/g, ''));
|
|
536
594
|
// eslint-disable-next-line max-depth
|
|
537
595
|
if (!isNaN(pixelValue)) {
|
|
@@ -577,13 +635,20 @@ function updatePlacementToSingleValue(path, options) {
|
|
|
577
635
|
'end top',
|
|
578
636
|
'end bottom'
|
|
579
637
|
]);
|
|
580
|
-
let elementPath = childComponentName
|
|
581
|
-
path
|
|
638
|
+
let elementPath = childComponentName
|
|
639
|
+
? path
|
|
640
|
+
.get('children')
|
|
641
|
+
.find(child => t.isJSXElement(child.node) &&
|
|
582
642
|
t.isJSXIdentifier(child.node.openingElement.name) &&
|
|
583
|
-
(0, utils_1.getName)(path, child.node.openingElement.name) === childComponentName)
|
|
584
|
-
|
|
643
|
+
(0, utils_1.getName)(path, child.node.openingElement.name) === childComponentName)
|
|
644
|
+
: path;
|
|
645
|
+
let attrPath = elementPath
|
|
646
|
+
.get('openingElement')
|
|
647
|
+
.get('attributes')
|
|
648
|
+
.find(attr => t.isJSXAttribute(attr.node) && attr.node.name.name === propToUpdateName);
|
|
585
649
|
if (attrPath && t.isJSXAttribute(attrPath.node) && attrPath.node.name.name === propToUpdateName) {
|
|
586
|
-
if (t.isStringLiteral(attrPath.node.value) &&
|
|
650
|
+
if (t.isStringLiteral(attrPath.node.value) &&
|
|
651
|
+
doublePlacementValues.has(attrPath.node.value.value)) {
|
|
587
652
|
attrPath.replaceWith(t.jsxAttribute(t.jsxIdentifier(propToUpdateName), t.stringLiteral(attrPath.node.value.value.split(' ')[0])));
|
|
588
653
|
return;
|
|
589
654
|
}
|
|
@@ -621,9 +686,8 @@ function removeComponentIfWithinParent(path, options) {
|
|
|
621
686
|
*/
|
|
622
687
|
function updateKeyToId(path) {
|
|
623
688
|
let attributes = path.node.openingElement.attributes;
|
|
624
|
-
let keyProp = attributes.find(
|
|
625
|
-
if (keyProp &&
|
|
626
|
-
t.isJSXAttribute(keyProp)) {
|
|
689
|
+
let keyProp = attributes.find(attr => t.isJSXAttribute(attr) && attr.name.name === 'key');
|
|
690
|
+
if (keyProp && t.isJSXAttribute(keyProp)) {
|
|
627
691
|
// Update key prop to be id
|
|
628
692
|
keyProp.name = t.jsxIdentifier('id');
|
|
629
693
|
}
|
|
@@ -634,8 +698,7 @@ function updateKeyToId(path) {
|
|
|
634
698
|
path.parentPath.parentPath.node.callee.property.type === 'Identifier' &&
|
|
635
699
|
path.parentPath.parentPath.node.callee.property.name === 'map') {
|
|
636
700
|
// If Array.map is used, keep the key prop
|
|
637
|
-
if (keyProp &&
|
|
638
|
-
t.isJSXAttribute(keyProp)) {
|
|
701
|
+
if (keyProp && t.isJSXAttribute(keyProp)) {
|
|
639
702
|
let newKeyProp = t.jsxAttribute(t.jsxIdentifier('key'), keyProp.value);
|
|
640
703
|
attributes.push(newKeyProp);
|
|
641
704
|
}
|