-
Notifications
You must be signed in to change notification settings - Fork 1
/
index.js
389 lines (344 loc) · 9.64 KB
/
index.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
#! /usr/bin/env node
var prompts = require("prompts");
const { nextVersions } = require("./next-versions");
const fs = require("fs");
const path = require("path");
const semver = require("semver");
const chalk = require("chalk");
var shell = require("shelljs");
var exec = shell.exec;
const projectWorkingDirectory = process.cwd();
/// test script
// exec(
// `node /Users/suraj/Sites/projects/nativebase-codemod/node_modules/.bin/jscodeshift --ignore-pattern="**/node_modules/**" --extensions="js,jsx,ts,tsx" --parser="tsx" -t /Users/suraj/Sites/projects/nativebase-codemod/transformer.js /Users/suraj/Sites/projects/nativebase-codemod/test`,
// { silent: false },
// (err, stdout) => {
// console.log("hello here");
// if (err) {
// console.log("Error: ", err);
// }
// console.log(stdout);
// }
// );
//
///
///
///
///
const commandLineArgs = require("command-line-args");
const optionDefinitions = [
{ name: "verbose", alias: "v", type: Boolean },
{ name: "experimental-inline-props", alias: "e", type: Boolean },
];
let options = {};
try {
options = commandLineArgs(optionDefinitions);
} catch (err) {
console.log(chalk.red(err.message));
process.exit(0);
}
const silent = options.verbose ? false : true;
const experimentalInlineProps = options["experimental-inline-props"]
? true
: false;
async function getCurrentVersion() {
return new Promise((resolve, reject) => {
exec(
`npx npm ls native-base`,
{ cwd: projectWorkingDirectory, silent: silent },
(err, stdout) => {
if (err) {
reject(err);
}
const output = stdout.trim();
const currentVersion = output.slice(output.lastIndexOf("@") + 1);
resolve(currentVersion);
}
);
});
}
async function updateNativeBaseVersion(packageManager, nextVersion) {
return new Promise((resolve, reject) => {
if (packageManager === "yarn") {
//
const yarnAddCommand = `yarn add native-base@${nextVersion}`;
exec(
yarnAddCommand,
{ cwd: projectWorkingDirectory, silent: false },
(err, stdout) => {
if (err) {
console.log(err);
console.log(
`\n${chalk.yellow(`${chalk.bold(yarnAddCommand)} failed!`)}`
);
reject(err);
}
// console.log(stdout);
resolve();
}
);
} else {
//
const npmInstallCommand = `npm install native-base@${nextVersion}`;
exec(
npmInstallCommand,
{ cwd: projectWorkingDirectory, silent: false },
(err, stdout) => {
if (err) {
console.log(
`\n${chalk.yellow(`${chalk.bold(npmInstallCommand)} failed!`)}`
);
return;
}
// console.log(stdout);
resolve();
}
);
}
});
}
async function updateFiles(srcPath) {
return new Promise((resolve, reject) => {
const runCommand = `node ${path.join(
__dirname,
"node_modules/.bin/jscodeshift"
)}`;
const runCommandProduction = `npx jscodeshift`;
const options = `--ignore-pattern="**/node_modules/**" --extensions="js,jsx,ts,tsx" --parser="tsx"`;
let transformerPath;
if (!experimentalInlineProps) {
transformerPath = path.join(__dirname, "extend-theme-transformer-v3.js");
} else {
transformerPath = path.join(__dirname, "transformer.js");
}
const transformCommand =
runCommandProduction +
" " +
options +
" -t " +
transformerPath +
" " +
srcPath;
// console.log(transformCommand, experimentalInlineProps, "hello transform");
exec(transformCommand, { silent: silent }, (err, stdout) => {
if (err) {
console.log("Error: ", err);
reject(err);
}
resolve();
});
});
}
function printSuccessMessage(nextVersion) {
fs.readFile(path.join(__dirname, "temp.txt"), (err, data) => {
if (err) {
console.error(err);
return;
}
console.log(
chalk.bold(`native-base upgraded to ` + chalk.green(nextVersion))
);
console.log(chalk.bold("\nModified files: "));
console.log(chalk.cyan(data.toString()));
console.log(
chalk.yellow(
`\nIt is recommended for you to verify the changes made to these files by the codemod. Happy coding!`
)
);
});
}
function getNextUpgradableVersion(currentVersion) {
return nextVersions[currentVersion];
}
function cleanTemp() {
fs.writeFile(path.join(__dirname, "temp.txt"), "", (err) => {
if (err) {
console.error(err);
return;
}
});
}
async function checkGitAvailable() {
return new Promise((resolve, reject) => {
exec(
`git rev-parse --is-inside-work-tree`,
{ cwd: projectWorkingDirectory, silent: silent },
(err, stdout) => {
if (err) {
reject();
}
resolve(true);
}
);
});
//git rev-parse --is-inside-work-tree
}
// main
async function fetchUserCurrentVersion() {
const response = await prompts({
type: "text",
name: "value",
message: `Enter your native-base version (e.g, ${chalk.gray("3.0.7")})`,
initial: "",
});
if (
!response.value ||
!semver.valid(response.value) // '1.2.3'
) {
console.log(chalk.red(`Invalid version! Please try again!`));
process.exit(0);
// return fetchUserCurrentVersion();
} else {
return response.value;
}
}
async function isValidSrcPath(srcPath) {
if (fs.existsSync(path.join(projectWorkingDirectory, srcPath))) {
return true;
} else {
console.log(chalk.red("Invalid path!"));
return false;
}
}
async function getSrcPath() {
let validSrcPath;
let srcPath;
while (!validSrcPath) {
const response = await prompts({
type: "text",
name: "value",
message: `Relative path to your source folder (${chalk.yellow(
"node_modules will be ignored"
)}) (e.g, ${chalk.gray("src/")}, ${chalk.gray(".")})`,
initial: "",
});
if (response.value === undefined) {
process.exit(0);
}
srcPath = response.value;
validSrcPath = await isValidSrcPath(srcPath);
}
return srcPath;
}
function printVersion() {
if (!silent) {
var pjson = require("./package.json");
console.log(chalk.green(" ............................"));
console.log(chalk.green(` name: ${pjson.name}`));
console.log(chalk.green(` version: ${pjson.version}`));
console.log(chalk.green(" ............................"));
console.log(chalk.green("\n"));
}
}
try {
(async () => {
cleanTemp();
printVersion();
let currentVersion;
let gitAvailable = false;
try {
currentVersion = await getCurrentVersion();
} catch (err) {
console.log(
chalk.red(`Failed to fetch your current version of native-base!`)
);
currentVersion = await fetchUserCurrentVersion();
}
try {
gitAvailable = await checkGitAvailable();
} catch (err) {
//
}
const nextVersion = getNextUpgradableVersion(currentVersion);
if (!gitAvailable) {
console.log(
chalk.yellow(
`We couldn't find a git repository in your project directory.\nIt's recommended to back up your project before proceeding.`
)
);
} else {
console.log(
chalk.yellow(
`It's recommended to commit all your changes before proceeding, so you can revert the changes made by this command if necessary.`
)
);
}
const continueResponse = await prompts({
type: "confirm",
name: "value",
message: `Do you want continue?`,
initial: true,
});
if (!continueResponse.value) {
process.exit(0);
}
console.log(chalk.bold(`Current Version: `) + chalk.green(currentVersion));
if (!nextVersion) {
console.warn(
chalk.yellow(`No codemod available to for v${currentVersion}`)
);
const response = await prompts({
type: "confirm",
name: "value",
message: `Do you want to upgrade native-base to latest version?`,
initial: true,
});
if (response.value === true) {
const packageManager = await prompts({
type: "select",
name: "value",
message: "Update native-base using ",
choices: [
{
title: "yarn",
value: "yarn",
},
{ title: "npm", value: "npm" },
],
initial: 0,
});
await updateNativeBaseVersion(packageManager.value, "latest");
}
process.exit(0);
}
const updgradableVersions = [];
const response = await prompts({
type: "confirm",
name: "value",
message: `Upgrade to ${chalk.cyan(
nextVersion
)} using codemod, Can you confirm?`,
initial: true,
});
if (response.value === true) {
const packageManager = await prompts({
type: "select",
name: "value",
message: "Update native-base using ",
choices: [
{
title: "yarn",
value: "yarn",
},
{ title: "npm", value: "npm" },
],
initial: 0,
});
// check for src path
const srcPath = await getSrcPath();
try {
await updateNativeBaseVersion(packageManager.value, nextVersion);
console.log(chalk.greenBright(`Modifying files...`));
await updateFiles(path.join(projectWorkingDirectory, srcPath));
} catch (err) {
console.log(chalk.red("\nUnable to run codemod!"));
process.exit(1);
}
printSuccessMessage(nextVersion);
}
})();
} catch (err) {
console.log(chalk.red(err));
console.log(chalk.red("\nUnable to run codemod!"));
process.exit(1);
}