UNPKG

3.53 kBJavaScriptView Raw
1#!/usr/bin/env node
2
3import fs from 'fs'
4import path from 'path'
5import { fileURLToPath } from 'url'
6
7import cmdline from 'commander'
8import debug from 'debug'
9import supportsColor from 'supports-color'
10
11import lintStaged from '../lib/index.js'
12import { CONFIG_STDIN_ERROR } from '../lib/messages.js'
13
14// Force colors for packages that depend on https://www.npmjs.com/package/supports-color
15if (supportsColor.stdout) {
16 process.env.FORCE_COLOR = supportsColor.stdout.level.toString()
17}
18
19// Do not terminate main Listr process on SIGINT
20process.on('SIGINT', () => {})
21
22const packageJsonPath = path.join(fileURLToPath(import.meta.url), '../../package.json')
23const packageJson = JSON.parse(fs.readFileSync(packageJsonPath))
24const version = packageJson.version
25
26cmdline
27 .version(version)
28 .option('--allow-empty', 'allow empty commits when tasks revert all staged changes', false)
29 .option(
30 '-p, --concurrent <number|boolean>',
31 'the number of tasks to run concurrently, or false for serial',
32 true
33 )
34 .option('-c, --config [path]', 'path to configuration file, or - to read from stdin')
35 .option('--cwd [path]', 'run all tasks in specific directory, instead of the current')
36 .option('-d, --debug', 'print additional debug information', false)
37 .option('--no-stash', 'disable the backup stash, and do not revert in case of errors', false)
38 .option('-q, --quiet', 'disable lint-staged’s own console output', false)
39 .option('-r, --relative', 'pass relative filepaths to tasks', false)
40 .option('-x, --shell [path]', 'skip parsing of tasks for better shell support', false)
41 .option(
42 '-v, --verbose',
43 'show task output even when tasks succeed; by default only failed output is shown',
44 false
45 )
46 .parse(process.argv)
47
48const cmdlineOptions = cmdline.opts()
49
50if (cmdlineOptions.debug) {
51 debug.enable('lint-staged*')
52}
53
54const debugLog = debug('lint-staged:bin')
55debugLog('Running `lint-staged@%s`', version)
56
57/**
58 * Get the maximum length of a command-line argument string based on current platform
59 *
60 * https://serverfault.com/questions/69430/what-is-the-maximum-length-of-a-command-line-in-mac-os-x
61 * https://support.microsoft.com/en-us/help/830473/command-prompt-cmd-exe-command-line-string-limitation
62 * https://unix.stackexchange.com/a/120652
63 */
64const getMaxArgLength = () => {
65 switch (process.platform) {
66 case 'darwin':
67 return 262144
68 case 'win32':
69 return 8191
70 default:
71 return 131072
72 }
73}
74
75const options = {
76 allowEmpty: !!cmdlineOptions.allowEmpty,
77 concurrent: JSON.parse(cmdlineOptions.concurrent),
78 configPath: cmdlineOptions.config,
79 cwd: cmdlineOptions.cwd,
80 debug: !!cmdlineOptions.debug,
81 maxArgLength: getMaxArgLength() / 2,
82 quiet: !!cmdlineOptions.quiet,
83 relative: !!cmdlineOptions.relative,
84 shell: cmdlineOptions.shell /* Either a boolean or a string pointing to the shell */,
85 stash: !!cmdlineOptions.stash, // commander inverts `no-<x>` flags to `!x`
86 verbose: !!cmdlineOptions.verbose,
87}
88
89debugLog('Options parsed from command-line:', options)
90
91if (options.configPath === '-') {
92 delete options.configPath
93 try {
94 options.config = fs.readFileSync(process.stdin.fd, 'utf8').toString().trim()
95 } catch {
96 console.error(CONFIG_STDIN_ERROR)
97 process.exit(1)
98 }
99
100 try {
101 options.config = JSON.parse(options.config)
102 } catch {
103 // Let config parsing complain if it's not JSON
104 }
105}
106
107lintStaged(options)
108 .then((passed) => {
109 process.exitCode = passed ? 0 : 1
110 })
111 .catch(() => {
112 process.exitCode = 1
113 })