@dhzh/eslint-config 1.26.0 → 1.27.1

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,269 @@
1
+ import process from "node:process";
2
+ import * as p from "@clack/prompts";
3
+ import c, { green } from "ansis";
4
+ import { cac } from "cac";
5
+ import fsp from "node:fs/promises";
6
+ import path from "node:path";
7
+ import fs from "node:fs";
8
+ //#region package.json
9
+ var version = "1.27.1";
10
+ var devDependencies = {
11
+ "@eslint/config-inspector": "^2.0.0",
12
+ "@prettier/plugin-xml": "^3.4.2",
13
+ "@types/eslint-plugin-tailwindcss": "^3.17.0",
14
+ "@types/node": "^24.12.2",
15
+ "@typescript-eslint/types": "^8.59.0",
16
+ "bumpp": "^11.0.1",
17
+ "bundle-require": "^5.1.0",
18
+ "eslint": "^10.2.1",
19
+ "eslint-typegen": "^2.3.1",
20
+ "lint-staged": "^16.4.0",
21
+ "simple-git-hooks": "^2.13.1",
22
+ "tailwindcss": "^4.2.4",
23
+ "tsdown": "^0.21.10",
24
+ "tsx": "^4.21.0",
25
+ "typescript": "^6.0.3"
26
+ };
27
+ //#endregion
28
+ //#region src/cli/stages/update-package-json.ts
29
+ async function ensureScript(scripts, name, command) {
30
+ if (scripts[name] == null) {
31
+ scripts[name] = command;
32
+ return;
33
+ }
34
+ if (scripts[name] === command) return;
35
+ const shouldOverride = await p.confirm({
36
+ message: `Script "${name}" already exists as "${String(scripts[name])}". Replace it with "${command}"?`,
37
+ initialValue: true
38
+ });
39
+ if (p.isCancel(shouldOverride)) {
40
+ p.cancel("Operation cancelled");
41
+ throw new Error("Operation cancelled");
42
+ }
43
+ if (shouldOverride) scripts[name] = command;
44
+ }
45
+ async function updatePackageJson() {
46
+ const cwd = process.cwd();
47
+ const pathPackageJSON = path.join(cwd, "package.json");
48
+ p.log.step(c.cyan`Bumping @dhzh/eslint-config to v${version}`);
49
+ const pkgContent = await fsp.readFile(pathPackageJSON, "utf8");
50
+ const pkg = JSON.parse(pkgContent);
51
+ pkg.devDependencies ??= {};
52
+ pkg.devDependencies["@dhzh/eslint-config"] = `^${version}`;
53
+ pkg.devDependencies.eslint ??= devDependencies.eslint;
54
+ pkg.scripts ??= {};
55
+ await ensureScript(pkg.scripts, "lint", "eslint");
56
+ await ensureScript(pkg.scripts, "lint-fix", "eslint --fix .");
57
+ await fsp.writeFile(pathPackageJSON, JSON.stringify(pkg, null, 2));
58
+ p.log.success(c.green`Changes wrote to package.json`);
59
+ }
60
+ //#endregion
61
+ //#region src/cli/constants.ts
62
+ const vscodeSettingsString = `
63
+ // Entry
64
+ "eslint.format.enable": true,
65
+ "eslint.ignoreUntitled": true,
66
+ "eslint.enable": true,
67
+
68
+ // Disable the default formatter, use eslint instead
69
+ "prettier.enable": false,
70
+
71
+ // Auto fix
72
+ "editor.codeActionsOnSave": {
73
+ "source.fixAll.eslint": "explicit",
74
+ "source.organizeImports": "never"
75
+ },
76
+
77
+ // Silent the stylistic rules in you IDE, but still auto fix them
78
+ // "eslint.rules.customizations": [
79
+ // { "rule": "style/*", "severity": "off", "fixable": true },
80
+ // { "rule": "format/*", "severity": "off", "fixable": true },
81
+ // { "rule": "*-indent", "severity": "off", "fixable": true },
82
+ // { "rule": "*-spacing", "severity": "off", "fixable": true },
83
+ // { "rule": "*-spaces", "severity": "off", "fixable": true },
84
+ // { "rule": "*-order", "severity": "off", "fixable": true },
85
+ // { "rule": "*-dangle", "severity": "off", "fixable": true },
86
+ // { "rule": "*-newline", "severity": "off", "fixable": true },
87
+ // { "rule": "*quotes", "severity": "off", "fixable": true },
88
+ // { "rule": "*semi", "severity": "off", "fixable": true }
89
+ // ],
90
+
91
+ // Enable eslint for all supported languages
92
+ "eslint.validate": [
93
+ "javascript",
94
+ "javascriptreact",
95
+ "typescript",
96
+ "typescriptreact",
97
+ "html",
98
+ "json",
99
+ "json5",
100
+ "jsonc",
101
+ "yaml",
102
+ "toml",
103
+ "xml",
104
+ "css",
105
+ "less",
106
+ "scss",
107
+ "pcss",
108
+ "postcss",
109
+ "gql",
110
+ "graphql",
111
+ "vue"
112
+ ],
113
+
114
+ // Enable eslint as the default formatter
115
+ "[javascript]": {
116
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
117
+ },
118
+ "[javascriptreact]": {
119
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
120
+ },
121
+ "[typescript]": {
122
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
123
+ },
124
+ "[typescriptreact]": {
125
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
126
+ },
127
+ "[html]": {
128
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
129
+ },
130
+ "[json]": {
131
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
132
+ },
133
+ "[jsonc]": {
134
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
135
+ },
136
+ "[yaml]": {
137
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
138
+ },
139
+ "[toml]": {
140
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
141
+ },
142
+ "[xml]": {
143
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
144
+ },
145
+ "[css]": {
146
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
147
+ },
148
+ "[less]": {
149
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
150
+ },
151
+ "[scss]": {
152
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
153
+ },
154
+ "[pcss]": {
155
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
156
+ },
157
+ "[postcss]": {
158
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
159
+ },
160
+ "[gql]": {
161
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
162
+ },
163
+ "[graphql]": {
164
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
165
+ },
166
+ "[vue]": {
167
+ "editor.defaultFormatter": "dbaeumer.vscode-eslint"
168
+ }
169
+ `;
170
+ const eslintConfigContent = (options) => `import { defineConfig } from '@dhzh/eslint-config';
171
+
172
+ export default defineConfig(${options.hasNest ? `{
173
+ configs: {
174
+ json: {
175
+ packageJsonRequireType: false,
176
+ },
177
+ },
178
+ }` : ""});
179
+ `;
180
+ const npmignoreString = `# If these files (ESLint flat config files) are not included in .npmignore,
181
+ # they will be published, and importing devDependencies in published files will trigger \`n/no-unpublished-import\` errors.
182
+ eslint.config.js
183
+ eslint.config.mjs
184
+ `;
185
+ //#endregion
186
+ //#region src/cli/stages/update-eslint-config.ts
187
+ async function updateEslintConfig(options) {
188
+ const cwd = process.cwd();
189
+ const pathPackageJSON = path.join(cwd, "package.json");
190
+ const pkgContent = await fsp.readFile(pathPackageJSON, "utf8");
191
+ const configFileName = JSON.parse(pkgContent).type === "module" ? "eslint.config.js" : "eslint.config.mjs";
192
+ const pathFlatConfig = path.join(cwd, configFileName);
193
+ await fsp.writeFile(pathFlatConfig, eslintConfigContent(options));
194
+ p.log.success(c.green`Created ${configFileName}`);
195
+ }
196
+ //#endregion
197
+ //#region src/cli/stages/update-npmignore.ts
198
+ async function updateNpmignore() {
199
+ const cwd = process.cwd();
200
+ const npmignoreFileName = ".npmignore";
201
+ const npmignoreFilePath = path.join(cwd, npmignoreFileName);
202
+ let action = "Created";
203
+ try {
204
+ await fsp.access(npmignoreFilePath);
205
+ const trimmedContent = (await fsp.readFile(npmignoreFilePath, "utf8")).trimEnd();
206
+ await fsp.writeFile(npmignoreFilePath, `${trimmedContent}\n${npmignoreString}`);
207
+ action = "Updated";
208
+ } catch {
209
+ await fsp.writeFile(npmignoreFilePath, npmignoreString);
210
+ }
211
+ p.log.success(c.green`${action} ${npmignoreFileName}`);
212
+ }
213
+ //#endregion
214
+ //#region src/cli/stages/update-vscode-settings.ts
215
+ async function updateVscodeSettings() {
216
+ const cwd = process.cwd();
217
+ const dotVscodePath = path.join(cwd, ".vscode");
218
+ const settingsPath = path.join(dotVscodePath, "settings.json");
219
+ if (!fs.existsSync(dotVscodePath)) await fsp.mkdir(dotVscodePath, { recursive: true });
220
+ if (fs.existsSync(settingsPath)) {
221
+ let settingsContent = await fsp.readFile(settingsPath, "utf8");
222
+ settingsContent = settingsContent.trim().replace(/\s*\}$/, "");
223
+ settingsContent += settingsContent.endsWith(",") || settingsContent.endsWith("{") ? "" : ",";
224
+ settingsContent += `${vscodeSettingsString}}\n`;
225
+ await fsp.writeFile(settingsPath, settingsContent, "utf8");
226
+ p.log.success(green`Updated .vscode/settings.json`);
227
+ } else {
228
+ await fsp.writeFile(settingsPath, `{${vscodeSettingsString}}\n`, "utf8");
229
+ p.log.success(green`Created .vscode/settings.json`);
230
+ }
231
+ }
232
+ //#endregion
233
+ //#region src/cli/run.ts
234
+ async function run(options) {
235
+ await updatePackageJson();
236
+ await updateEslintConfig(options);
237
+ await updateNpmignore();
238
+ await updateVscodeSettings();
239
+ p.log.success(c.green`Setup completed`);
240
+ p.outro(`Now you can update the dependencies by run ${c.blue("pnpm i")} and run ${c.blue("eslint --fix")}\n`);
241
+ }
242
+ //#endregion
243
+ //#region src/cli/index.ts
244
+ const cli = cac("@dhzh/eslint-config");
245
+ cli.command("", "Run the initialization or migration").action(async () => {
246
+ console.log("\n");
247
+ p.intro(`${c.green`@dhzh/eslint-config `}${c.dim`v${version}`}`);
248
+ const options = { hasNest: false };
249
+ const hasNest = await p.confirm({
250
+ message: "Is NestJS a part of the current project?",
251
+ initialValue: false
252
+ });
253
+ if (p.isCancel(hasNest)) {
254
+ p.cancel("Operation cancelled");
255
+ throw new Error("Operation cancelled");
256
+ } else options.hasNest = hasNest;
257
+ try {
258
+ await run(options);
259
+ } catch (error) {
260
+ p.log.error(c.inverse.red(" Failed to migrate "));
261
+ p.log.error(c.red`✘ ${String(error)}`);
262
+ throw error;
263
+ }
264
+ });
265
+ cli.help();
266
+ cli.version(version);
267
+ cli.parse();
268
+ //#endregion
269
+ export {};