1 | #!/usr/bin/env node
|
2 |
|
3 |
|
4 |
|
5 |
|
6 |
|
7 |
|
8 |
|
9 |
|
10 | 'use strict';
|
11 |
|
12 | const Runner = require('../src/Runner.js');
|
13 |
|
14 | const fs = require('fs');
|
15 | const path = require('path');
|
16 | const pkg = require('../package.json');
|
17 | const parser = require('../src/argsParser')
|
18 | .options({
|
19 | transform: {
|
20 | display_index: 15,
|
21 | abbr: 't',
|
22 | default: './transform.js',
|
23 | help: 'path to the transform file. Can be either a local path or url',
|
24 | metavar: 'FILE',
|
25 | required: true
|
26 | },
|
27 | cpus: {
|
28 | display_index: 1,
|
29 | abbr: 'c',
|
30 | help: 'start at most N child processes to process source files',
|
31 | defaultHelp: 'max(all - 1, 1)',
|
32 | metavar: 'N',
|
33 | process: Number,
|
34 | },
|
35 | verbose: {
|
36 | display_index: 16,
|
37 | abbr: 'v',
|
38 | choices: [0, 1, 2],
|
39 | default: 0,
|
40 | help: 'show more information about the transform process',
|
41 | metavar: 'N',
|
42 | process: Number,
|
43 | },
|
44 | dry: {
|
45 | display_index: 2,
|
46 | abbr: 'd',
|
47 | flag: true,
|
48 | default: false,
|
49 | help: 'dry run (no changes are made to files)'
|
50 | },
|
51 | print: {
|
52 | display_index: 11,
|
53 | abbr: 'p',
|
54 | flag: true,
|
55 | default: false,
|
56 | help: 'print transformed files to stdout, useful for development'
|
57 | },
|
58 | babel: {
|
59 | display_index: 0,
|
60 | flag: true,
|
61 | default: true,
|
62 | help: 'apply babeljs to the transform file'
|
63 | },
|
64 | extensions: {
|
65 | display_index: 3,
|
66 | default: 'js',
|
67 | help: 'transform files with these file extensions (comma separated list)',
|
68 | metavar: 'EXT',
|
69 | },
|
70 | ignorePattern: {
|
71 | display_index: 7,
|
72 | full: 'ignore-pattern',
|
73 | list: true,
|
74 | help: 'ignore files that match a provided glob expression',
|
75 | metavar: 'GLOB',
|
76 | },
|
77 | ignoreConfig: {
|
78 | display_index: 6,
|
79 | full: 'ignore-config',
|
80 | list: true,
|
81 | help: 'ignore files if they match patterns sourced from a configuration file (e.g. a .gitignore)',
|
82 | metavar: 'FILE'
|
83 | },
|
84 | gitignore: {
|
85 | display_index: 8,
|
86 | flag: true,
|
87 | default: false,
|
88 | help: 'adds entries the current directory\'s .gitignore file',
|
89 | },
|
90 | runInBand: {
|
91 | display_index: 12,
|
92 | flag: true,
|
93 | default: false,
|
94 | full: 'run-in-band',
|
95 | help: 'run serially in the current process'
|
96 | },
|
97 | silent: {
|
98 | display_index: 13,
|
99 | abbr: 's',
|
100 | flag: true,
|
101 | default: false,
|
102 | help: 'do not write to stdout or stderr'
|
103 | },
|
104 | parser: {
|
105 | display_index: 9,
|
106 | choices: ['babel', 'babylon', 'flow', 'ts', 'tsx'],
|
107 | default: 'babel',
|
108 | help: 'the parser to use for parsing the source files'
|
109 | },
|
110 | parserConfig: {
|
111 | display_index: 10,
|
112 | full: 'parser-config',
|
113 | help: 'path to a JSON file containing a custom parser configuration for flow or babylon',
|
114 | metavar: 'FILE',
|
115 | process: file => JSON.parse(fs.readFileSync(file)),
|
116 | },
|
117 | failOnError: {
|
118 | display_index: 4,
|
119 | flag: true,
|
120 | help: 'Return a non-zero code when there are errors',
|
121 | full: 'fail-on-error',
|
122 | default: false,
|
123 | },
|
124 | version: {
|
125 | display_index: 17,
|
126 | help: 'print version and exit',
|
127 | callback: function() {
|
128 | const requirePackage = require('../utils/requirePackage');
|
129 | return [
|
130 | `jscodeshift: ${pkg.version}`,
|
131 | ` - babel: ${require('babel-core').version}`,
|
132 | ` - babylon: ${requirePackage('@babel/parser').version}`,
|
133 | ` - flow: ${requirePackage('flow-parser').version}`,
|
134 | ` - recast: ${requirePackage('recast').version}\n`,
|
135 | ].join('\n');
|
136 | },
|
137 | },
|
138 | stdin: {
|
139 | display_index: 14,
|
140 | help: 'read file/directory list from stdin',
|
141 | flag: true,
|
142 | default: false,
|
143 | },
|
144 | });
|
145 |
|
146 | let options, positionalArguments;
|
147 | try {
|
148 | ({options, positionalArguments} = parser.parse());
|
149 | if (positionalArguments.length === 0 && !options.stdin) {
|
150 | process.stderr.write(
|
151 | 'Error: You have to provide at least one file/directory to transform.' +
|
152 | '\n\n---\n\n' +
|
153 | parser.getHelpText()
|
154 | );
|
155 | process.exit(1);
|
156 | }
|
157 | } catch(e) {
|
158 | const exitCode = e.exitCode === undefined ? 1 : e.exitCode;
|
159 | (exitCode ? process.stderr : process.stdout).write(e.message);
|
160 | process.exit(exitCode);
|
161 | }
|
162 | function run(paths, options) {
|
163 | Runner.run(
|
164 | /^https?/.test(options.transform) ? options.transform : path.resolve(options.transform),
|
165 | paths,
|
166 | options
|
167 | );
|
168 | }
|
169 |
|
170 | if (options.stdin) {
|
171 | let buffer = '';
|
172 | process.stdin.on('data', data => buffer += data);
|
173 | process.stdin.on('end', () => run(buffer.split('\n'), options));
|
174 | } else {
|
175 | run(positionalArguments, options);
|
176 | }
|