@cluerise/tools 3.0.0

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.
@@ -0,0 +1,149 @@
1
+ import FileSystem from "fs/promises";
2
+ import { z, ZodError } from "zod";
3
+ import ChildProcess from "child_process";
4
+ import "eslint";
5
+ import "glob";
6
+ import "prettier";
7
+ import loadCommitlintConfig from "@commitlint/load";
8
+ const enginesSchema = z.object({
9
+ node: z.string()
10
+ });
11
+ const repositoryObjectSchema = z.object({
12
+ type: z.string(),
13
+ url: z.string(),
14
+ directory: z.ostring()
15
+ });
16
+ const repositorySchema = z.union([z.string(), repositoryObjectSchema]);
17
+ z.object({
18
+ name: z.string(),
19
+ version: z.string(),
20
+ description: z.string(),
21
+ engines: enginesSchema.optional(),
22
+ repository: repositorySchema.optional()
23
+ });
24
+ const runMain = (main2) => {
25
+ main2(process.argv.slice(2)).then((exitCode) => {
26
+ process.exit(exitCode);
27
+ }).catch((error) => {
28
+ console.error(error);
29
+ process.exit(1);
30
+ });
31
+ };
32
+ const capitalize = (value) => {
33
+ const [firstLetter] = value;
34
+ if (!firstLetter) {
35
+ return value;
36
+ }
37
+ return `${firstLetter.toUpperCase()}${value.slice(1)}`;
38
+ };
39
+ const StringUtils = {
40
+ capitalize
41
+ };
42
+ const getBranchName = () => ChildProcess.execSync("git symbolic-ref --short HEAD").toString().trim();
43
+ const isRebasing = () => {
44
+ try {
45
+ ChildProcess.execSync("ls `git rev-parse --git-dir` | grep rebase");
46
+ return true;
47
+ } catch {
48
+ return false;
49
+ }
50
+ };
51
+ const GitCommands = {
52
+ getBranchName,
53
+ isRebasing
54
+ };
55
+ z.union([z.literal("all"), z.literal("code")]);
56
+ const stringifySemanticCommitMessagePrefix = ({ type, scope }) => `${type}${scope ? `(${scope})` : ""}`;
57
+ const startsWithSemanticCommitMessagePrefix = (message, prefix) => message.startsWith(stringifySemanticCommitMessagePrefix(prefix));
58
+ const createSemanticCommitMessage = (prefix, message) => {
59
+ const [subject, ...comments] = message.split("\n#");
60
+ let commitMessage = stringifySemanticCommitMessagePrefix(prefix) + ": ";
61
+ if (subject) {
62
+ commitMessage += StringUtils.capitalize(subject);
63
+ }
64
+ if (comments.length > 0) {
65
+ commitMessage += "\n\n#" + comments.join("\n#");
66
+ }
67
+ return commitMessage;
68
+ };
69
+ const isValidEnumValue = async (ruleName, value) => {
70
+ const { rules } = await loadCommitlintConfig();
71
+ const rule = rules[ruleName];
72
+ if (!rule) {
73
+ return true;
74
+ }
75
+ const [_severity, _condition, values] = rule;
76
+ if (!values) {
77
+ return true;
78
+ }
79
+ return values.includes(value);
80
+ };
81
+ const isValidType = (type) => isValidEnumValue("type-enum", type);
82
+ const isValidScope = (scope) => isValidEnumValue("scope-enum", scope);
83
+ const CommitLintConfig = {
84
+ isValidType,
85
+ isValidScope
86
+ };
87
+ const parseSemanticBranchName = async (name) => {
88
+ const [typeValue, scopeValue] = name.split("-");
89
+ if (!typeValue || !await CommitLintConfig.isValidType(typeValue)) {
90
+ throw new Error("Invalid commit type in branch name");
91
+ }
92
+ const type = typeValue.toLowerCase();
93
+ const scope = scopeValue && await CommitLintConfig.isValidScope(scopeValue) ? scopeValue.toLowerCase() : null;
94
+ return {
95
+ type,
96
+ scope
97
+ };
98
+ };
99
+ const parseSemanticCommitMessage = (message) => {
100
+ const firstColonPosition = message.search(":");
101
+ const prefix = message.slice(0, firstColonPosition).trim();
102
+ const content = message.slice(firstColonPosition + 1).trim();
103
+ return { prefix, content };
104
+ };
105
+ const formatSemanticCommitMessage = (message) => {
106
+ const { prefix, content } = parseSemanticCommitMessage(message);
107
+ if (!prefix || !content) {
108
+ return message;
109
+ }
110
+ return `${prefix}: ${StringUtils.capitalize(content)}`;
111
+ };
112
+ const CommitLintCommands = {
113
+ createSemanticCommitMessage,
114
+ parseSemanticBranchName,
115
+ formatSemanticCommitMessage,
116
+ startsWithSemanticCommitMessagePrefix
117
+ };
118
+ const commitMessagePathArgSchema = z.string();
119
+ const parseCreateCommitMessageArgs = ([commitMessagePathArg]) => {
120
+ const commitMessagePath = commitMessagePathArgSchema.parse(commitMessagePathArg);
121
+ return {
122
+ commitMessagePath
123
+ };
124
+ };
125
+ const main = async (args) => {
126
+ try {
127
+ if (GitCommands.isRebasing()) {
128
+ return 0;
129
+ }
130
+ const { commitMessagePath } = parseCreateCommitMessageArgs(args);
131
+ const commitMessage = (await FileSystem.readFile(commitMessagePath)).toString();
132
+ const branchName = GitCommands.getBranchName();
133
+ const commitMessagePrefix = await CommitLintCommands.parseSemanticBranchName(branchName);
134
+ if (!CommitLintCommands.startsWithSemanticCommitMessagePrefix(commitMessage, commitMessagePrefix)) {
135
+ const nextCommitMessage = CommitLintCommands.createSemanticCommitMessage(commitMessagePrefix, commitMessage);
136
+ await FileSystem.writeFile(commitMessagePath, nextCommitMessage);
137
+ }
138
+ } catch (error) {
139
+ if (error instanceof ZodError) {
140
+ console.warn("Invalid commit message path");
141
+ }
142
+ if (error instanceof Error) {
143
+ console.warn(error.message);
144
+ }
145
+ console.warn(error);
146
+ }
147
+ return 0;
148
+ };
149
+ runMain(main);
@@ -0,0 +1,130 @@
1
+ import FileSystem from "fs/promises";
2
+ import { z, ZodError } from "zod";
3
+ import "eslint";
4
+ import "glob";
5
+ import "prettier";
6
+ import loadCommitlintConfig from "@commitlint/load";
7
+ const enginesSchema = z.object({
8
+ node: z.string()
9
+ });
10
+ const repositoryObjectSchema = z.object({
11
+ type: z.string(),
12
+ url: z.string(),
13
+ directory: z.ostring()
14
+ });
15
+ const repositorySchema = z.union([z.string(), repositoryObjectSchema]);
16
+ z.object({
17
+ name: z.string(),
18
+ version: z.string(),
19
+ description: z.string(),
20
+ engines: enginesSchema.optional(),
21
+ repository: repositorySchema.optional()
22
+ });
23
+ const runMain = (main2) => {
24
+ main2(process.argv.slice(2)).then((exitCode) => {
25
+ process.exit(exitCode);
26
+ }).catch((error) => {
27
+ console.error(error);
28
+ process.exit(1);
29
+ });
30
+ };
31
+ const capitalize = (value) => {
32
+ const [firstLetter] = value;
33
+ if (!firstLetter) {
34
+ return value;
35
+ }
36
+ return `${firstLetter.toUpperCase()}${value.slice(1)}`;
37
+ };
38
+ const StringUtils = {
39
+ capitalize
40
+ };
41
+ z.union([z.literal("all"), z.literal("code")]);
42
+ const stringifySemanticCommitMessagePrefix = ({ type, scope }) => `${type}${scope ? `(${scope})` : ""}`;
43
+ const startsWithSemanticCommitMessagePrefix = (message, prefix) => message.startsWith(stringifySemanticCommitMessagePrefix(prefix));
44
+ const createSemanticCommitMessage = (prefix, message) => {
45
+ const [subject, ...comments] = message.split("\n#");
46
+ let commitMessage = stringifySemanticCommitMessagePrefix(prefix) + ": ";
47
+ if (subject) {
48
+ commitMessage += StringUtils.capitalize(subject);
49
+ }
50
+ if (comments.length > 0) {
51
+ commitMessage += "\n\n#" + comments.join("\n#");
52
+ }
53
+ return commitMessage;
54
+ };
55
+ const isValidEnumValue = async (ruleName, value) => {
56
+ const { rules } = await loadCommitlintConfig();
57
+ const rule = rules[ruleName];
58
+ if (!rule) {
59
+ return true;
60
+ }
61
+ const [_severity, _condition, values] = rule;
62
+ if (!values) {
63
+ return true;
64
+ }
65
+ return values.includes(value);
66
+ };
67
+ const isValidType = (type) => isValidEnumValue("type-enum", type);
68
+ const isValidScope = (scope) => isValidEnumValue("scope-enum", scope);
69
+ const CommitLintConfig = {
70
+ isValidType,
71
+ isValidScope
72
+ };
73
+ const parseSemanticBranchName = async (name) => {
74
+ const [typeValue, scopeValue] = name.split("-");
75
+ if (!typeValue || !await CommitLintConfig.isValidType(typeValue)) {
76
+ throw new Error("Invalid commit type in branch name");
77
+ }
78
+ const type = typeValue.toLowerCase();
79
+ const scope = scopeValue && await CommitLintConfig.isValidScope(scopeValue) ? scopeValue.toLowerCase() : null;
80
+ return {
81
+ type,
82
+ scope
83
+ };
84
+ };
85
+ const parseSemanticCommitMessage = (message) => {
86
+ const firstColonPosition = message.search(":");
87
+ const prefix = message.slice(0, firstColonPosition).trim();
88
+ const content = message.slice(firstColonPosition + 1).trim();
89
+ return { prefix, content };
90
+ };
91
+ const formatSemanticCommitMessage = (message) => {
92
+ const { prefix, content } = parseSemanticCommitMessage(message);
93
+ if (!prefix || !content) {
94
+ return message;
95
+ }
96
+ return `${prefix}: ${StringUtils.capitalize(content)}`;
97
+ };
98
+ const CommitLintCommands = {
99
+ createSemanticCommitMessage,
100
+ parseSemanticBranchName,
101
+ formatSemanticCommitMessage,
102
+ startsWithSemanticCommitMessagePrefix
103
+ };
104
+ const commitMessagePathArgSchema = z.string();
105
+ const parseFormatCommitMessageArgs = ([commitMessagePathArg]) => {
106
+ const commitMessagePath = commitMessagePathArgSchema.parse(commitMessagePathArg);
107
+ return {
108
+ commitMessagePath
109
+ };
110
+ };
111
+ const main = async (args) => {
112
+ try {
113
+ const { commitMessagePath } = parseFormatCommitMessageArgs(args);
114
+ const commitMessage = (await FileSystem.readFile(commitMessagePath)).toString();
115
+ const formattedCommitMessage = CommitLintCommands.formatSemanticCommitMessage(commitMessage);
116
+ if (formattedCommitMessage !== commitMessage) {
117
+ await FileSystem.writeFile(commitMessagePath, formattedCommitMessage);
118
+ }
119
+ } catch (error) {
120
+ if (error instanceof ZodError) {
121
+ console.warn("Invalid commit message path");
122
+ }
123
+ if (error instanceof Error) {
124
+ console.warn(error.message);
125
+ }
126
+ console.warn(error);
127
+ }
128
+ return 0;
129
+ };
130
+ runMain(main);
@@ -0,0 +1,386 @@
1
+ import { z, ZodError } from "zod";
2
+ import FileSystem from "fs/promises";
3
+ import Path from "path";
4
+ import ChildProcess from "child_process";
5
+ import { ESLint } from "eslint";
6
+ import { glob } from "glob";
7
+ import * as Prettier from "prettier";
8
+ import "@commitlint/load";
9
+ class ParseGitRepositoryError extends Error {
10
+ }
11
+ const gitProviderOrigins = {
12
+ github: "https://github.com"
13
+ };
14
+ const gitProviderNames = Object.keys(gitProviderOrigins);
15
+ const isGitProviderName = (name) => gitProviderNames.includes(name);
16
+ const parseRepositoryUrl = (urlString) => {
17
+ const urlValue = urlString.includes(":") ? urlString : `https://${urlString}`;
18
+ const url = new URL(urlValue);
19
+ const scheme = url.protocol.slice(0, -1);
20
+ if (isGitProviderName(scheme)) {
21
+ const [owner, repositoryName] = url.pathname.split("/");
22
+ if (!owner || !repositoryName) {
23
+ throw new ParseGitRepositoryError("Unknown owner or repositoryName");
24
+ }
25
+ return {
26
+ origin: gitProviderOrigins[scheme],
27
+ owner,
28
+ repositoryName
29
+ };
30
+ }
31
+ if (scheme === "https") {
32
+ const [, owner, repositoryName] = url.pathname.split("/");
33
+ if (!owner || !repositoryName) {
34
+ throw new ParseGitRepositoryError("Unknown owner or repositoryName");
35
+ }
36
+ return {
37
+ origin: url.origin,
38
+ owner,
39
+ repositoryName: repositoryName.endsWith(".git") ? repositoryName.slice(0, -4) : repositoryName
40
+ };
41
+ }
42
+ throw new ParseGitRepositoryError("Unsupported repository URL");
43
+ };
44
+ const parsePackageJsonRepository = (repository) => {
45
+ if (typeof repository === "string") {
46
+ return parseRepositoryUrl(repository);
47
+ }
48
+ return parseRepositoryUrl(repository.url);
49
+ };
50
+ const enginesSchema = z.object({
51
+ node: z.string()
52
+ });
53
+ const repositoryObjectSchema = z.object({
54
+ type: z.string(),
55
+ url: z.string(),
56
+ directory: z.ostring()
57
+ });
58
+ const repositorySchema = z.union([z.string(), repositoryObjectSchema]);
59
+ const packageJsonSchema = z.object({
60
+ name: z.string(),
61
+ version: z.string(),
62
+ description: z.string(),
63
+ engines: enginesSchema.optional(),
64
+ repository: repositorySchema.optional()
65
+ });
66
+ const readPackageJson = async () => {
67
+ const packageJsonData = await FileSystem.readFile("package.json", { encoding: "utf8" });
68
+ const packageJson = JSON.parse(packageJsonData);
69
+ const parseResult = packageJsonSchema.safeParse(packageJson);
70
+ if (!parseResult.success) {
71
+ throw parseResult.error;
72
+ }
73
+ return packageJson;
74
+ };
75
+ const CoreCommands = {
76
+ readPackageJson,
77
+ parsePackageJsonRepository
78
+ };
79
+ const runMain = (main2) => {
80
+ main2(process.argv.slice(2)).then((exitCode) => {
81
+ process.exit(exitCode);
82
+ }).catch((error) => {
83
+ console.error(error);
84
+ process.exit(1);
85
+ });
86
+ };
87
+ const createResultMessage = (exitCode) => {
88
+ if (exitCode === null) {
89
+ return "Done";
90
+ }
91
+ return exitCode === 0 ? "OK" : "Failed";
92
+ };
93
+ const createStatusConsole = (command) => ({
94
+ printBegin: (arg) => console.info(`${command} ${arg}...`),
95
+ printEnd: (arg, exitCode = null) => console.info(`${command} ${arg}... ${createResultMessage(exitCode)}`)
96
+ });
97
+ const packageName = "@cluerise/tools";
98
+ const rootAppDirectory = `./node_modules/${packageName}`;
99
+ const toolsConfigPackage = `${packageName}/dist/configs`;
100
+ const toolsConfigDirectory = `${rootAppDirectory}/dist/configs`;
101
+ const AppConfig = {
102
+ toolsConfigPackage,
103
+ toolsConfigDirectory
104
+ };
105
+ const copyFile = async (sourceDirectory, filePath, destinationFilePath) => {
106
+ const sourcePath = Path.resolve(sourceDirectory, filePath);
107
+ const destinationPath = Path.resolve(process.cwd(), destinationFilePath ?? filePath);
108
+ await FileSystem.mkdir(Path.dirname(destinationPath), { recursive: true });
109
+ return FileSystem.copyFile(sourcePath, destinationPath);
110
+ };
111
+ const createFile = async (path, content) => {
112
+ const destinationPath = Path.resolve(process.cwd(), path);
113
+ await FileSystem.mkdir(Path.dirname(destinationPath), { recursive: true });
114
+ return FileSystem.writeFile(destinationPath, content);
115
+ };
116
+ const ConfigCommands = {
117
+ copyFile,
118
+ createFile
119
+ };
120
+ const commitlintConfigName = "commitlint.config";
121
+ const commitlintConfigPath = `${commitlintConfigName}.ts`;
122
+ const initCommitlint = async ({ configPackage }) => {
123
+ const configContent = `export { default } from '${configPackage}/${commitlintConfigName}';
124
+ `;
125
+ await ConfigCommands.createFile(commitlintConfigPath, configContent);
126
+ };
127
+ const editorConfigPath = ".editorconfig";
128
+ const initEditorConfig = async ({ configDirectory }) => {
129
+ await ConfigCommands.copyFile(configDirectory, editorConfigPath);
130
+ };
131
+ const eslintConfigPath = ".eslintrc.cjs";
132
+ const eslintIgnorePath = ".eslintignore";
133
+ const initEslint = async ({ configDirectory }) => {
134
+ const configContent = `module.exports = {
135
+ extends: '${configDirectory}/${eslintConfigPath}'
136
+ };
137
+ `;
138
+ await ConfigCommands.createFile(eslintConfigPath, configContent);
139
+ await ConfigCommands.copyFile(configDirectory, eslintIgnorePath);
140
+ };
141
+ const sourceGitignorePath = "_gitignore";
142
+ const destinationGitignorePath = ".gitignore";
143
+ const gitHookDirectory = "hooks";
144
+ const gitHookPaths = [
145
+ Path.join(gitHookDirectory, "commit-msg"),
146
+ Path.join(gitHookDirectory, "post-commit"),
147
+ Path.join(gitHookDirectory, "pre-commit"),
148
+ Path.join(gitHookDirectory, "prepare-commit-msg")
149
+ ];
150
+ const initGit = async ({ configDirectory }) => {
151
+ await ConfigCommands.copyFile(configDirectory, sourceGitignorePath, destinationGitignorePath);
152
+ await Promise.all(gitHookPaths.map((gitHookPath) => ConfigCommands.copyFile(configDirectory, gitHookPath)));
153
+ };
154
+ const lintStagedConfigPath = "lint-staged.config.js";
155
+ const initLintStaged = async ({ configPackage }) => {
156
+ const configContent = `export { default } from '${configPackage}/${lintStagedConfigPath}';
157
+ `;
158
+ await ConfigCommands.createFile(lintStagedConfigPath, configContent);
159
+ };
160
+ const sourceNpmrcPath = "_npmrc";
161
+ const destinationNpmrcPath = ".npmrc";
162
+ const initNpm = async ({ configDirectory }) => {
163
+ await ConfigCommands.copyFile(configDirectory, sourceNpmrcPath, destinationNpmrcPath);
164
+ };
165
+ const nvmrcPath = ".nvmrc";
166
+ const initNvm = async ({ configDirectory }) => {
167
+ await ConfigCommands.copyFile(configDirectory, nvmrcPath);
168
+ };
169
+ const prettierConfigPath = "prettier.config.js";
170
+ const initPrettier = async ({ configPackage }) => {
171
+ const configContent = `export { default } from '${configPackage}/${prettierConfigPath}';
172
+ `;
173
+ await ConfigCommands.createFile(prettierConfigPath, configContent);
174
+ };
175
+ const releaseConfigPath = "release.config.js";
176
+ const defaultReleaseConfigParams = {
177
+ host: "<host>",
178
+ owner: "<owner>",
179
+ repository: "<repository>"
180
+ };
181
+ const getReleaseConfigParams = async () => {
182
+ try {
183
+ const { repository } = await CoreCommands.readPackageJson();
184
+ if (!repository) {
185
+ return defaultReleaseConfigParams;
186
+ }
187
+ const { origin, owner, repositoryName } = CoreCommands.parsePackageJsonRepository(repository);
188
+ return {
189
+ host: origin,
190
+ owner,
191
+ repository: repositoryName
192
+ };
193
+ } catch {
194
+ return defaultReleaseConfigParams;
195
+ }
196
+ };
197
+ const initRelease = async ({ configPackage }) => {
198
+ const releaseConfigParams = await getReleaseConfigParams();
199
+ const configContent = `import { createReleaseConfig } from '${configPackage}/${releaseConfigPath}';
200
+
201
+ export default createReleaseConfig(${JSON.stringify(releaseConfigParams, null, 2)});
202
+ `;
203
+ await ConfigCommands.createFile(releaseConfigPath, configContent);
204
+ };
205
+ const typescriptConfigPath = "tsconfig.json";
206
+ const initTypescript = async ({ configDirectory }) => {
207
+ const configContent = `{
208
+ "extends": "${configDirectory}/${typescriptConfigPath}",
209
+ "compilerOptions": {
210
+ "baseUrl": "./"
211
+ }
212
+ }
213
+ `;
214
+ await ConfigCommands.createFile(typescriptConfigPath, configContent);
215
+ };
216
+ const vscodeSettingsPath = Path.join(".vscode", "settings.json");
217
+ const initVscode = async () => {
218
+ const configContent = `{
219
+ "prettier.ignorePath": "node_modules/@cluerise/tools/dist/configs/.prettierignore",
220
+ "typescript.tsdk": "node_modules/typescript/lib"
221
+ }
222
+ `;
223
+ await ConfigCommands.createFile(vscodeSettingsPath, configContent);
224
+ };
225
+ const toolInitializers = {
226
+ commitlint: initCommitlint,
227
+ editorconfig: initEditorConfig,
228
+ eslint: initEslint,
229
+ git: initGit,
230
+ "lint-staged": initLintStaged,
231
+ npm: initNpm,
232
+ nvm: initNvm,
233
+ prettier: initPrettier,
234
+ release: initRelease,
235
+ typescript: initTypescript,
236
+ vscode: initVscode
237
+ };
238
+ const toolInitializerNames = Object.keys(toolInitializers);
239
+ const toolNameSchema = z.union([
240
+ z.literal("commitlint"),
241
+ z.literal("editorconfig"),
242
+ z.literal("eslint"),
243
+ z.literal("git"),
244
+ z.literal("lint-staged"),
245
+ z.literal("npm"),
246
+ z.literal("nvm"),
247
+ z.literal("prettier"),
248
+ z.literal("release"),
249
+ z.literal("typescript"),
250
+ z.literal("vscode")
251
+ ]);
252
+ const initializingConsole = createStatusConsole("Initializing");
253
+ const initTool = async (name, params) => {
254
+ const toolInitializer = toolInitializers[name];
255
+ if (!toolInitializer) {
256
+ throw new Error(`Tool "${name}" is not supported.`);
257
+ }
258
+ initializingConsole.printBegin(name);
259
+ await toolInitializer(params);
260
+ initializingConsole.printEnd(name);
261
+ };
262
+ const initAllTools = async (params) => {
263
+ for (const name of toolInitializerNames) {
264
+ await initTool(name, params);
265
+ }
266
+ };
267
+ const InitCommands = {
268
+ initAllTools,
269
+ initTool
270
+ };
271
+ const lintCommit = (args) => {
272
+ const { status } = ChildProcess.spawnSync("commitlint", args, { stdio: "inherit" });
273
+ return status ?? 0;
274
+ };
275
+ z.union([z.literal("all"), z.literal("code")]);
276
+ const scopePatterns = {
277
+ all: ["**"],
278
+ code: ["src/**"]
279
+ };
280
+ const scopeShortcuts = Object.keys(scopePatterns);
281
+ const isScopeShortcut = (scope) => scopeShortcuts.includes(scope);
282
+ const resolveScope = (scope) => {
283
+ if (Array.isArray(scope)) {
284
+ return scope;
285
+ }
286
+ if (isScopeShortcut(scope)) {
287
+ return scopePatterns[scope];
288
+ }
289
+ return [scope];
290
+ };
291
+ const formatWithPrettier = async (patterns) => {
292
+ const eslint = new ESLint();
293
+ const configPath = await Prettier.resolveConfigFile();
294
+ if (!configPath) {
295
+ return false;
296
+ }
297
+ const config = await Prettier.resolveConfig(configPath);
298
+ if (!config) {
299
+ return false;
300
+ }
301
+ const paths = await glob(patterns, {
302
+ nodir: true,
303
+ ignore: "node_modules/**"
304
+ });
305
+ await Promise.all(
306
+ paths.map(async (path) => {
307
+ if (await eslint.isPathIgnored(path)) {
308
+ return;
309
+ }
310
+ const prevContent = (await FileSystem.readFile(path)).toString();
311
+ const nextContent = await Prettier.format(prevContent, {
312
+ ...config,
313
+ filepath: path
314
+ });
315
+ await FileSystem.writeFile(path, nextContent);
316
+ })
317
+ );
318
+ };
319
+ const lintFiles = async (scope, options) => {
320
+ const patterns = resolveScope(scope);
321
+ if (options == null ? void 0 : options.fix) {
322
+ await formatWithPrettier(patterns);
323
+ }
324
+ const eslint = new ESLint({
325
+ fix: options == null ? void 0 : options.fix
326
+ });
327
+ const results = await eslint.lintFiles(patterns);
328
+ const problemCount = results.reduce((sum, result) => sum + result.errorCount + result.warningCount, 0);
329
+ if (options == null ? void 0 : options.fix) {
330
+ await ESLint.outputFixes(results);
331
+ }
332
+ if (problemCount > 0) {
333
+ const formatter = await eslint.loadFormatter("stylish");
334
+ const resultText = formatter.format(results);
335
+ console.error(resultText);
336
+ const errorMessage = `Linting failed with ${problemCount} problem${problemCount === 1 ? "" : "s"}.`;
337
+ throw new Error(errorMessage);
338
+ }
339
+ };
340
+ const lintStaged = (args) => {
341
+ const { status } = ChildProcess.spawnSync("lint-staged", args, { stdio: "inherit" });
342
+ return status ?? 0;
343
+ };
344
+ const LintCommands = {
345
+ lintFiles,
346
+ lintCommit,
347
+ lintStaged
348
+ };
349
+ const toolNameArgSchema = z.union([z.literal("all"), toolNameSchema]);
350
+ const parseInitArgs = ([nameArg]) => {
351
+ const name = toolNameArgSchema.parse(nameArg);
352
+ return {
353
+ name
354
+ };
355
+ };
356
+ const toolInitializerParams = {
357
+ configDirectory: AppConfig.toolsConfigDirectory,
358
+ configPackage: AppConfig.toolsConfigPackage
359
+ };
360
+ const main = async (args) => {
361
+ try {
362
+ const { name } = parseInitArgs(args);
363
+ if (name === "all") {
364
+ await InitCommands.initAllTools(toolInitializerParams);
365
+ } else {
366
+ await InitCommands.initTool(name, toolInitializerParams);
367
+ }
368
+ await LintCommands.lintFiles("all", { fix: true });
369
+ return 0;
370
+ } catch (error) {
371
+ if (error instanceof ZodError) {
372
+ const firstIssue = error.issues[0];
373
+ if ((firstIssue == null ? void 0 : firstIssue.code) === "invalid_union") {
374
+ console.error("Invalid tool name");
375
+ return 1;
376
+ }
377
+ }
378
+ if (error instanceof Error) {
379
+ console.error(error.message);
380
+ return 1;
381
+ }
382
+ console.error(error);
383
+ return 1;
384
+ }
385
+ };
386
+ runMain(main);