@configjs/cli 1.1.16 → 1.1.18

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.
Files changed (34) hide show
  1. package/dist/{angular-command-XN26G6L3.js → angular-command-EOREU45Q.js} +8 -8
  2. package/dist/{angular-installer-FY43HE72.js → angular-installer-TKZDPFLD.js} +9 -1
  3. package/dist/angular-setup-QDTWXOB4.js +30 -0
  4. package/dist/check-KAPRT4FM.js +168 -0
  5. package/dist/{chunk-JYWGJJ4M.js → chunk-D7IWYKUX.js} +476 -28
  6. package/dist/chunk-EDCNW4UO.js +92 -0
  7. package/dist/{chunk-TN27AX4L.js → chunk-FJLN62L4.js} +797 -18
  8. package/dist/{chunk-FIB2J36N.js → chunk-HI7RYD6W.js} +161 -36
  9. package/dist/{chunk-NYCK4R4K.js → chunk-RIJNUJDC.js} +361 -96
  10. package/dist/chunk-V2IBYLVH.js +932 -0
  11. package/dist/chunk-VN4XTFDK.js +315 -0
  12. package/dist/{chunk-UKEHW2LH.js → chunk-Y4XYC7QV.js} +17 -3
  13. package/dist/cli.js +31 -21
  14. package/dist/{installed-D6CUYQM5.js → installed-QMJZIZNC.js} +4 -4
  15. package/dist/{list-VZDUWV5O.js → list-5T6VDDAO.js} +4 -4
  16. package/dist/{nextjs-command-WKKOAY7I.js → nextjs-command-C6PM7A5C.js} +8 -9
  17. package/dist/{nextjs-installer-2ZC5IWJ6.js → nextjs-installer-OFY5BQC4.js} +9 -2
  18. package/dist/{nextjs-setup-DYOFF72S.js → nextjs-setup-JIKPIJCX.js} +21 -9
  19. package/dist/{react-command-2T6IOTHB.js → react-command-JMK6VM4Q.js} +8 -9
  20. package/dist/{remove-ZY3MLPGN.js → remove-4ZNQR6ZR.js} +4 -4
  21. package/dist/{svelte-command-B2DNNQ5Z.js → svelte-command-YUSD55NO.js} +8 -8
  22. package/dist/svelte-installer-UP3KDZSY.js +105 -0
  23. package/dist/{svelte-setup-FWXLXJAC.js → svelte-setup-33E46IBT.js} +16 -5
  24. package/dist/{vite-installer-Y6VMFHIM.js → vite-installer-EE2LE76G.js} +9 -2
  25. package/dist/{vite-setup-JRELX6K2.js → vite-setup-VO5BOI46.js} +16 -4
  26. package/dist/{vue-command-IOTC32AI.js → vue-command-3CYWLLFQ.js} +8 -9
  27. package/dist/{vue-installer-DGBBVF6F.js → vue-installer-LEGLVD77.js} +9 -2
  28. package/dist/{vue-setup-G44DLT2U.js → vue-setup-FK5QT7AY.js} +16 -4
  29. package/package.json +12 -4
  30. package/dist/angular-setup-Z6TCKNBG.js +0 -18
  31. package/dist/check-KNGZSCMM.js +0 -131
  32. package/dist/chunk-6GV4NKUX.js +0 -122
  33. package/dist/chunk-QPEUT7QG.js +0 -157
  34. package/dist/svelte-installer-EOSC3EP3.js +0 -65
@@ -0,0 +1,315 @@
1
+ // src/utils/logger.ts
2
+ import pc from "chalk";
3
+ var Logger = class {
4
+ level = 1 /* INFO */;
5
+ setLevel(level) {
6
+ this.level = level;
7
+ }
8
+ debug(message, ...args) {
9
+ if (this.level <= 0 /* DEBUG */) {
10
+ console.log(pc.gray(`[DEBUG] ${message}`), ...args);
11
+ }
12
+ }
13
+ info(message, ...args) {
14
+ if (this.level <= 1 /* INFO */) {
15
+ console.log(pc.cyan(`\u2139 ${message}`), ...args);
16
+ }
17
+ }
18
+ success(message, ...args) {
19
+ if (this.level <= 1 /* INFO */) {
20
+ console.log(pc.green(`\u2713 ${message}`), ...args);
21
+ }
22
+ }
23
+ warn(message, ...args) {
24
+ if (this.level <= 2 /* WARN */) {
25
+ console.warn(pc.yellow(`\u26A0\uFE0F ${message}`), ...args);
26
+ }
27
+ }
28
+ error(message, ...args) {
29
+ if (this.level <= 3 /* ERROR */) {
30
+ console.error(pc.red(`\u2716 ${message}`), ...args);
31
+ }
32
+ }
33
+ header(message) {
34
+ if (this.level <= 1 /* INFO */) {
35
+ console.log();
36
+ console.log(pc.bold(pc.magenta(`\u25C6 ${message}`)));
37
+ console.log();
38
+ }
39
+ }
40
+ section(title) {
41
+ if (this.level <= 1 /* INFO */) {
42
+ console.log();
43
+ console.log(pc.bold(pc.cyan(`\u25B8 ${title}`)));
44
+ }
45
+ }
46
+ item(message, color = "gray") {
47
+ if (this.level <= 1 /* INFO */) {
48
+ const colorFn = pc[color];
49
+ console.log(colorFn(` \u2022 ${message}`));
50
+ }
51
+ }
52
+ dim(message) {
53
+ if (this.level <= 1 /* INFO */) {
54
+ console.log(pc.gray(` ${message}`));
55
+ }
56
+ }
57
+ step(message) {
58
+ if (this.level <= 1 /* INFO */) {
59
+ console.log(pc.cyan(`
60
+ \u2192 ${message}`));
61
+ }
62
+ }
63
+ box(title, content) {
64
+ if (this.level <= 1 /* INFO */) {
65
+ const maxLength = Math.max(
66
+ title.length,
67
+ ...content.map((line) => line.length)
68
+ );
69
+ const border = "\u2500".repeat(maxLength + 4);
70
+ console.log(pc.cyan(`\u250C${border}\u2510`));
71
+ console.log(pc.cyan(`\u2502 ${title.padEnd(maxLength)} \u2502`));
72
+ console.log(pc.cyan(`\u251C${border}\u2524`));
73
+ content.forEach((line) => {
74
+ console.log(pc.cyan(`\u2502 ${line.padEnd(maxLength)} \u2502`));
75
+ });
76
+ console.log(pc.cyan(`\u2514${border}\u2518`));
77
+ }
78
+ }
79
+ };
80
+ var logger = new Logger();
81
+
82
+ // src/utils/logger-provider.ts
83
+ var NoOpLogger = class {
84
+ debug() {
85
+ }
86
+ info() {
87
+ }
88
+ warn() {
89
+ }
90
+ error() {
91
+ }
92
+ success() {
93
+ }
94
+ header() {
95
+ }
96
+ section() {
97
+ }
98
+ item() {
99
+ }
100
+ dim() {
101
+ }
102
+ step() {
103
+ }
104
+ box() {
105
+ }
106
+ };
107
+ var ScrubbingLogger = class {
108
+ constructor(innerLogger) {
109
+ this.innerLogger = innerLogger;
110
+ }
111
+ scrubMessage(message) {
112
+ return scrubSensitiveData(message);
113
+ }
114
+ scrubArgs(args) {
115
+ return args.map((arg) => {
116
+ if (typeof arg === "string") {
117
+ return this.scrubMessage(arg);
118
+ }
119
+ if (typeof arg === "object" && arg !== null) {
120
+ try {
121
+ const json = JSON.stringify(arg);
122
+ const scrubbed = this.scrubMessage(json);
123
+ return JSON.parse(scrubbed);
124
+ } catch {
125
+ return arg;
126
+ }
127
+ }
128
+ return arg;
129
+ });
130
+ }
131
+ debug(message, ...args) {
132
+ this.innerLogger.debug(this.scrubMessage(message), ...this.scrubArgs(args));
133
+ }
134
+ info(message, ...args) {
135
+ this.innerLogger.info(this.scrubMessage(message), ...this.scrubArgs(args));
136
+ }
137
+ warn(message, ...args) {
138
+ this.innerLogger.warn(this.scrubMessage(message), ...this.scrubArgs(args));
139
+ }
140
+ error(message, ...args) {
141
+ this.innerLogger.error(this.scrubMessage(message), ...this.scrubArgs(args));
142
+ }
143
+ success(message, ...args) {
144
+ this.innerLogger.success(
145
+ this.scrubMessage(message),
146
+ ...this.scrubArgs(args)
147
+ );
148
+ }
149
+ header(message) {
150
+ this.innerLogger.header(this.scrubMessage(message));
151
+ }
152
+ section(title) {
153
+ this.innerLogger.section(this.scrubMessage(title));
154
+ }
155
+ item(message, color) {
156
+ this.innerLogger.item(this.scrubMessage(message), color);
157
+ }
158
+ dim(message) {
159
+ this.innerLogger.dim(this.scrubMessage(message));
160
+ }
161
+ step(message) {
162
+ this.innerLogger.step(this.scrubMessage(message));
163
+ }
164
+ box(title, content) {
165
+ this.innerLogger.box(
166
+ this.scrubMessage(title),
167
+ content.map((line) => this.scrubMessage(line))
168
+ );
169
+ }
170
+ };
171
+ var LoggerProvider = class {
172
+ currentLogger = new NoOpLogger();
173
+ /**
174
+ * Get the current logger instance
175
+ * CLI commands should use the real logger
176
+ * Core modules should use whatever is provided
177
+ */
178
+ getLogger() {
179
+ return this.currentLogger;
180
+ }
181
+ /**
182
+ * Set the active logger (typically called by CLI)
183
+ * Automatically wraps with ScrubbingLogger for credential redaction (SEC-003)
184
+ * @param newLogger - The logger instance to use
185
+ */
186
+ setLogger(newLogger) {
187
+ this.currentLogger = new ScrubbingLogger(newLogger);
188
+ }
189
+ /**
190
+ * Enable CLI logging (use the real logger)
191
+ * Wraps with ScrubbingLogger for automatic credential redaction (SEC-003)
192
+ */
193
+ enableCLILogging() {
194
+ this.currentLogger = new ScrubbingLogger(logger);
195
+ }
196
+ /**
197
+ * Disable logging (use no-op logger)
198
+ */
199
+ disableLogging() {
200
+ this.currentLogger = new NoOpLogger();
201
+ }
202
+ /**
203
+ * Set the log level for the real logger
204
+ */
205
+ setLogLevel(level) {
206
+ if (this.currentLogger instanceof ScrubbingLogger) {
207
+ logger.setLevel(level);
208
+ } else if (this.currentLogger === logger) {
209
+ logger.setLevel(level);
210
+ }
211
+ }
212
+ };
213
+ var SENSITIVE_PATTERNS = [
214
+ {
215
+ pattern: /npm_token\s*=\s*\S+/gi,
216
+ replacement: "npm_token=[REDACTED]",
217
+ description: "NPM authentication tokens"
218
+ },
219
+ {
220
+ pattern: /npm_auth_token\s*=\s*\S+/gi,
221
+ replacement: "npm_auth_token=[REDACTED]",
222
+ description: "NPM authentication tokens"
223
+ },
224
+ {
225
+ pattern: /--token\s*=\s*\S+/gi,
226
+ replacement: "--token=[REDACTED]",
227
+ description: "Generic token flag"
228
+ },
229
+ {
230
+ pattern: /--auth-token\s*=\s*\S+/gi,
231
+ replacement: "--auth-token=[REDACTED]",
232
+ description: "Generic auth token flag"
233
+ },
234
+ {
235
+ pattern: /registry\s*=\s*https?:\/\/[^\s]+/gi,
236
+ replacement: "registry=[REDACTED]",
237
+ description: "Registry URLs with or without --"
238
+ },
239
+ {
240
+ pattern: /https?:\/\/[^@\s]+@[^\s]+/g,
241
+ replacement: "https://[REDACTED]@[REDACTED]",
242
+ description: "URLs with embedded credentials (user:pass@host)"
243
+ },
244
+ {
245
+ pattern: /--proxy\s*=\s*\S+/gi,
246
+ replacement: "--proxy=[REDACTED]",
247
+ description: "Proxy URLs which might contain credentials"
248
+ },
249
+ {
250
+ pattern: /AWS_SECRET_ACCESS_KEY\s*=\s*\S+/gi,
251
+ replacement: "AWS_SECRET_ACCESS_KEY=[REDACTED]",
252
+ description: "AWS secret access keys"
253
+ },
254
+ {
255
+ pattern: /AWS_ACCESS_KEY_ID\s*=\s*\S+/gi,
256
+ replacement: "AWS_ACCESS_KEY_ID=[REDACTED]",
257
+ description: "AWS access key IDs (partial redaction)"
258
+ },
259
+ {
260
+ pattern: /github_token\s*=\s*\S+/gi,
261
+ replacement: "github_token=[REDACTED]",
262
+ description: "GitHub personal access tokens"
263
+ },
264
+ {
265
+ pattern: /GIT_TOKEN\s*=\s*\S+/gi,
266
+ replacement: "GIT_TOKEN=[REDACTED]",
267
+ description: "Git tokens"
268
+ },
269
+ {
270
+ pattern: /Bearer\s+\S+/gi,
271
+ replacement: "Bearer [REDACTED]",
272
+ description: "Bearer tokens in Authorization headers"
273
+ },
274
+ {
275
+ pattern: /Authorization:\s*\S+\s+\S+/gi,
276
+ replacement: "Authorization: [REDACTED]",
277
+ description: "Authorization headers"
278
+ },
279
+ // Generic token patterns - match common token formats
280
+ {
281
+ pattern: /\bghp_[A-Za-z0-9_]{20,}/g,
282
+ replacement: "[REDACTED]",
283
+ description: "GitHub personal access tokens (ghp_ prefix)"
284
+ },
285
+ {
286
+ pattern: /\bghu_[A-Za-z0-9_]{20,}/g,
287
+ replacement: "[REDACTED]",
288
+ description: "GitHub user tokens (ghu_ prefix)"
289
+ },
290
+ {
291
+ pattern: /\bnpm_[A-Za-z0-9_]{20,}/g,
292
+ replacement: "[REDACTED]",
293
+ description: "NPM tokens (generic npm_ prefix)"
294
+ }
295
+ ];
296
+ function scrubSensitiveData(message) {
297
+ let scrubbed = message;
298
+ for (const { pattern, replacement } of SENSITIVE_PATTERNS) {
299
+ scrubbed = scrubbed.replace(pattern, replacement);
300
+ }
301
+ return scrubbed;
302
+ }
303
+ var loggerProvider = new LoggerProvider();
304
+ function getModuleLogger() {
305
+ return loggerProvider.getLogger();
306
+ }
307
+ function initializeCLILogging() {
308
+ loggerProvider.enableCLILogging();
309
+ }
310
+
311
+ export {
312
+ logger,
313
+ getModuleLogger,
314
+ initializeCLILogging
315
+ };
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  detectPackageManager
3
- } from "./chunk-6GV4NKUX.js";
3
+ } from "./chunk-V2IBYLVH.js";
4
4
  import {
5
5
  checkPathExists,
6
6
  createDefaultFsAdapter,
@@ -8,10 +8,10 @@ import {
8
8
  readPackageJson,
9
9
  readTsConfig,
10
10
  writeFileContent
11
- } from "./chunk-FIB2J36N.js";
11
+ } from "./chunk-HI7RYD6W.js";
12
12
  import {
13
13
  getModuleLogger
14
- } from "./chunk-QPEUT7QG.js";
14
+ } from "./chunk-VN4XTFDK.js";
15
15
 
16
16
  // src/core/plugin-tracker.ts
17
17
  import { join } from "path";
@@ -200,6 +200,17 @@ var PluginTracker = class {
200
200
  import { resolve, join as join2 } from "path";
201
201
  import { platform, version } from "process";
202
202
  var detectionCache = /* @__PURE__ */ new Map();
203
+ var IGNORED_DIRS = /* @__PURE__ */ new Set([
204
+ "node_modules",
205
+ ".git",
206
+ ".next",
207
+ "dist",
208
+ "build",
209
+ "coverage",
210
+ ".nuxt",
211
+ ".vite",
212
+ "out"
213
+ ]);
203
214
  var DetectionError = class extends Error {
204
215
  constructor(message, context) {
205
216
  super(message);
@@ -410,6 +421,9 @@ async function detectVueApi(projectRoot, srcDir, fsAdapter) {
410
421
  async function findVueFiles(dir) {
411
422
  const entries = await adapter.readdir(dir);
412
423
  for (const entryName of entries) {
424
+ if (IGNORED_DIRS.has(entryName)) {
425
+ continue;
426
+ }
413
427
  const fullPath = join2(dir, entryName);
414
428
  const stat = await adapter.stat(fullPath);
415
429
  if (stat.isDirectory()) {
package/dist/cli.js CHANGED
@@ -1,14 +1,15 @@
1
1
  #!/usr/bin/env node
2
2
  import {
3
- initializeCLILogging
4
- } from "./chunk-QPEUT7QG.js";
3
+ initializeCLILogging,
4
+ logger
5
+ } from "./chunk-VN4XTFDK.js";
5
6
  import "./chunk-QGM4M3NI.js";
6
7
 
7
8
  // src/cli.ts
8
9
  import { Command } from "commander";
9
10
 
10
11
  // package.json
11
- var version = "1.1.16";
12
+ var version = "1.1.18";
12
13
 
13
14
  // src/cli.ts
14
15
  initializeCLILogging();
@@ -17,11 +18,12 @@ program.name("confjs").description("Configure your frontend stack, instantly").v
17
18
  program.command("react").description("Configure a React project").option("-y, --yes", "Accept all defaults").option("-d, --dry-run", "Simulate without writing to disk").option("-s, --silent", "Non-interactive mode").option("--debug", "Enable debug logs").option("-c, --config <file>", "Use configuration file").option("-f, --force", "Force installation (overwrite configs)").option("--no-install", "Generate configs only, skip package installation").action(
18
19
  async (options) => {
19
20
  try {
20
- const { ReactCommand } = await import("./react-command-2T6IOTHB.js");
21
+ const { ReactCommand } = await import("./react-command-JMK6VM4Q.js");
21
22
  const command = new ReactCommand();
22
23
  await command.execute(options);
23
24
  } catch (error) {
24
- console.error("Error:", error);
25
+ const errorMessage = error instanceof Error ? error.message : String(error);
26
+ logger.error(`\u274C React configuration failed: ${errorMessage}`);
25
27
  process.exit(1);
26
28
  }
27
29
  }
@@ -29,11 +31,12 @@ program.command("react").description("Configure a React project").option("-y, --
29
31
  program.command("nextjs").description("Configure a Next.js project").option("-y, --yes", "Accept all defaults").option("-d, --dry-run", "Simulate without writing to disk").option("-s, --silent", "Non-interactive mode").option("--debug", "Enable debug logs").option("-c, --config <file>", "Use configuration file").option("-f, --force", "Force installation (overwrite configs)").option("--no-install", "Generate configs only, skip package installation").action(
30
32
  async (options) => {
31
33
  try {
32
- const { NextjsCommand } = await import("./nextjs-command-WKKOAY7I.js");
34
+ const { NextjsCommand } = await import("./nextjs-command-C6PM7A5C.js");
33
35
  const command = new NextjsCommand();
34
36
  await command.execute(options);
35
37
  } catch (error) {
36
- console.error("Error:", error);
38
+ const errorMessage = error instanceof Error ? error.message : String(error);
39
+ logger.error(`\u274C Next.js configuration failed: ${errorMessage}`);
37
40
  process.exit(1);
38
41
  }
39
42
  }
@@ -41,11 +44,12 @@ program.command("nextjs").description("Configure a Next.js project").option("-y,
41
44
  program.command("vue").description("Configure a Vue.js project").option("-y, --yes", "Accept all defaults").option("-d, --dry-run", "Simulate without writing to disk").option("-s, --silent", "Non-interactive mode").option("--debug", "Enable debug logs").option("-c, --config <file>", "Use configuration file").option("-f, --force", "Force installation (overwrite configs)").option("--no-install", "Generate configs only, skip package installation").action(
42
45
  async (options) => {
43
46
  try {
44
- const { VueCommand } = await import("./vue-command-IOTC32AI.js");
47
+ const { VueCommand } = await import("./vue-command-3CYWLLFQ.js");
45
48
  const command = new VueCommand();
46
49
  await command.execute(options);
47
50
  } catch (error) {
48
- console.error("Error:", error);
51
+ const errorMessage = error instanceof Error ? error.message : String(error);
52
+ logger.error(`\u274C Vue configuration failed: ${errorMessage}`);
49
53
  process.exit(1);
50
54
  }
51
55
  }
@@ -53,11 +57,12 @@ program.command("vue").description("Configure a Vue.js project").option("-y, --y
53
57
  program.command("svelte").description("Configure a Svelte project").option("-y, --yes", "Accept all defaults").option("-d, --dry-run", "Simulate without writing to disk").option("-s, --silent", "Non-interactive mode").option("--debug", "Enable debug logs").option("-c, --config <file>", "Use configuration file").option("-f, --force", "Force installation (overwrite configs)").option("--no-install", "Generate configs only, skip package installation").action(
54
58
  async (options) => {
55
59
  try {
56
- const { SvelteCommand } = await import("./svelte-command-B2DNNQ5Z.js");
60
+ const { SvelteCommand } = await import("./svelte-command-YUSD55NO.js");
57
61
  const command = new SvelteCommand();
58
62
  await command.execute(options);
59
63
  } catch (error) {
60
- console.error("Error:", error);
64
+ const errorMessage = error instanceof Error ? error.message : String(error);
65
+ logger.error(`\u274C Svelte configuration failed: ${errorMessage}`);
61
66
  process.exit(1);
62
67
  }
63
68
  }
@@ -65,48 +70,53 @@ program.command("svelte").description("Configure a Svelte project").option("-y,
65
70
  program.command("angular").description("Configure an Angular project").option("-y, --yes", "Accept all defaults").option("-d, --dry-run", "Simulate without writing to disk").option("-s, --silent", "Non-interactive mode").option("--debug", "Enable debug logs").option("-c, --config <file>", "Use configuration file").option("-f, --force", "Force installation (overwrite configs)").option("--no-install", "Generate configs only, skip package installation").action(
66
71
  async (options) => {
67
72
  try {
68
- const { AngularCommand } = await import("./angular-command-XN26G6L3.js");
73
+ const { AngularCommand } = await import("./angular-command-EOREU45Q.js");
69
74
  const command = new AngularCommand();
70
75
  await command.execute(options);
71
76
  } catch (error) {
72
- console.error("Error:", error);
77
+ const errorMessage = error instanceof Error ? error.message : String(error);
78
+ logger.error(`\u274C Angular configuration failed: ${errorMessage}`);
73
79
  process.exit(1);
74
80
  }
75
81
  }
76
82
  );
77
83
  program.command("list").description("List available libraries").option("-c, --category <category>", "Filter by category").action(async (options) => {
78
84
  try {
79
- const { listLibraries } = await import("./list-VZDUWV5O.js");
85
+ const { listLibraries } = await import("./list-5T6VDDAO.js");
80
86
  listLibraries(options);
81
87
  } catch (error) {
82
- console.error("Error:", error);
88
+ const errorMessage = error instanceof Error ? error.message : String(error);
89
+ logger.error(`\u274C Failed to list libraries: ${errorMessage}`);
83
90
  process.exit(1);
84
91
  }
85
92
  });
86
93
  program.command("check").description("Check compatibility without installing").option("-c, --config <file>", "Configuration file to check").action(async (options) => {
87
94
  try {
88
- const { checkCompatibility } = await import("./check-KNGZSCMM.js");
95
+ const { checkCompatibility } = await import("./check-KAPRT4FM.js");
89
96
  await checkCompatibility(options);
90
97
  } catch (error) {
91
- console.error("Error:", error);
98
+ const errorMessage = error instanceof Error ? error.message : String(error);
99
+ logger.error(`\u274C Compatibility check failed: ${errorMessage}`);
92
100
  process.exit(1);
93
101
  }
94
102
  });
95
103
  program.command("installed").description("List installed plugins").action(async () => {
96
104
  try {
97
- const { installedCommand } = await import("./installed-D6CUYQM5.js");
105
+ const { installedCommand } = await import("./installed-QMJZIZNC.js");
98
106
  await installedCommand();
99
107
  } catch (error) {
100
- console.error("Error:", error);
108
+ const errorMessage = error instanceof Error ? error.message : String(error);
109
+ logger.error(`\u274C Failed to list installed plugins: ${errorMessage}`);
101
110
  process.exit(1);
102
111
  }
103
112
  });
104
113
  program.command("remove <plugin>").description("Remove an installed plugin").action(async (plugin) => {
105
114
  try {
106
- const { removeCommand } = await import("./remove-ZY3MLPGN.js");
115
+ const { removeCommand } = await import("./remove-4ZNQR6ZR.js");
107
116
  await removeCommand(plugin);
108
117
  } catch (error) {
109
- console.error("Error:", error);
118
+ const errorMessage = error instanceof Error ? error.message : String(error);
119
+ logger.error(`\u274C Failed to remove plugin '${plugin}': ${errorMessage}`);
110
120
  process.exit(1);
111
121
  }
112
122
  });
@@ -1,12 +1,12 @@
1
1
  import {
2
2
  PluginTracker,
3
3
  detectContext
4
- } from "./chunk-UKEHW2LH.js";
5
- import "./chunk-6GV4NKUX.js";
6
- import "./chunk-FIB2J36N.js";
4
+ } from "./chunk-Y4XYC7QV.js";
5
+ import "./chunk-V2IBYLVH.js";
6
+ import "./chunk-HI7RYD6W.js";
7
7
  import {
8
8
  logger
9
- } from "./chunk-QPEUT7QG.js";
9
+ } from "./chunk-VN4XTFDK.js";
10
10
  import "./chunk-QGM4M3NI.js";
11
11
 
12
12
  // src/cli/commands/installed.ts
@@ -1,9 +1,9 @@
1
1
  import {
2
2
  pluginRegistry
3
- } from "./chunk-JYWGJJ4M.js";
4
- import "./chunk-6GV4NKUX.js";
5
- import "./chunk-FIB2J36N.js";
6
- import "./chunk-QPEUT7QG.js";
3
+ } from "./chunk-D7IWYKUX.js";
4
+ import "./chunk-V2IBYLVH.js";
5
+ import "./chunk-HI7RYD6W.js";
6
+ import "./chunk-VN4XTFDK.js";
7
7
  import "./chunk-QGM4M3NI.js";
8
8
 
9
9
  // src/cli/commands/list.ts
@@ -1,24 +1,24 @@
1
1
  import {
2
2
  BaseFrameworkCommand,
3
3
  getFrameworkMetadata
4
- } from "./chunk-TN27AX4L.js";
5
- import "./chunk-NYCK4R4K.js";
6
- import "./chunk-JYWGJJ4M.js";
4
+ } from "./chunk-FJLN62L4.js";
5
+ import "./chunk-RIJNUJDC.js";
6
+ import "./chunk-D7IWYKUX.js";
7
7
  import {
8
8
  DetectionError,
9
9
  detectContext
10
- } from "./chunk-UKEHW2LH.js";
11
- import "./chunk-6GV4NKUX.js";
10
+ } from "./chunk-Y4XYC7QV.js";
11
+ import "./chunk-V2IBYLVH.js";
12
12
  import "./chunk-KAMPBTFG.js";
13
- import "./chunk-FIB2J36N.js";
14
- import "./chunk-QPEUT7QG.js";
13
+ import "./chunk-HI7RYD6W.js";
14
+ import "./chunk-VN4XTFDK.js";
15
15
  import {
16
16
  getTranslations
17
17
  } from "./chunk-L4GX22RG.js";
18
18
  import "./chunk-QGM4M3NI.js";
19
19
 
20
20
  // src/cli/commands/nextjs-command.ts
21
- import pc from "picocolors";
21
+ import pc from "chalk";
22
22
  var NextjsCommand = class extends BaseFrameworkCommand {
23
23
  getFramework() {
24
24
  return "nextjs";
@@ -47,7 +47,6 @@ var NextjsCommand = class extends BaseFrameworkCommand {
47
47
  projectRoot,
48
48
  language
49
49
  );
50
- process.chdir(newProjectPath);
51
50
  projectRoot = newProjectPath;
52
51
  console.log();
53
52
  return await detectContext(projectRoot);
@@ -1,9 +1,9 @@
1
1
  import {
2
2
  checkPathExists
3
- } from "./chunk-FIB2J36N.js";
3
+ } from "./chunk-HI7RYD6W.js";
4
4
  import {
5
5
  logger
6
- } from "./chunk-QPEUT7QG.js";
6
+ } from "./chunk-VN4XTFDK.js";
7
7
  import {
8
8
  getTranslations
9
9
  } from "./chunk-L4GX22RG.js";
@@ -12,6 +12,10 @@ import "./chunk-QGM4M3NI.js";
12
12
  // src/cli/utils/nextjs-installer.ts
13
13
  import { resolve } from "path";
14
14
  import { execa } from "execa";
15
+ function validateProjectName(name) {
16
+ if (!/^[a-zA-Z0-9._-]+$/.test(name)) return false;
17
+ return !name.includes("..") && !name.includes("/") && !name.includes("\\");
18
+ }
15
19
  async function createNextjsProject(options, currentDir, language) {
16
20
  const t = getTranslations(language);
17
21
  const {
@@ -23,6 +27,9 @@ async function createNextjsProject(options, currentDir, language) {
23
27
  appRouter,
24
28
  importAlias
25
29
  } = options;
30
+ if (!validateProjectName(projectName)) {
31
+ throw new Error(`Invalid project name: ${projectName}`);
32
+ }
26
33
  const projectPath = resolve(currentDir, projectName);
27
34
  if (await checkPathExists(projectPath)) {
28
35
  throw new Error(t.nextjs.folderExists(projectName));
@@ -1,3 +1,8 @@
1
+ import {
2
+ getValidationErrorMessage,
3
+ nextjsSetupSchema,
4
+ validateInput
5
+ } from "./chunk-EDCNW4UO.js";
1
6
  import {
2
7
  getTranslations
3
8
  } from "./chunk-L4GX22RG.js";
@@ -5,6 +10,7 @@ import "./chunk-QGM4M3NI.js";
5
10
 
6
11
  // src/cli/prompts/nextjs-setup.ts
7
12
  import inquirer from "inquirer";
13
+ import pc from "chalk";
8
14
  async function promptNextjsSetup(language) {
9
15
  const t = getTranslations(language);
10
16
  const answers = await inquirer.prompt([
@@ -85,15 +91,21 @@ async function promptNextjsSetup(language) {
85
91
  if (!answers.shouldCreate) {
86
92
  return null;
87
93
  }
88
- return {
89
- projectName: answers.projectName.trim(),
90
- typescript: answers.typescript,
91
- eslint: answers.eslint,
92
- tailwind: answers.tailwind,
93
- srcDir: answers.srcDir,
94
- appRouter: answers.appRouter,
95
- importAlias: answers.importAlias.trim()
96
- };
94
+ try {
95
+ const validated = validateInput(nextjsSetupSchema, {
96
+ projectName: answers.projectName.trim(),
97
+ typescript: answers.typescript,
98
+ eslint: answers.eslint,
99
+ tailwind: answers.tailwind,
100
+ srcDir: answers.srcDir,
101
+ appRouter: answers.appRouter,
102
+ importAlias: answers.importAlias.trim()
103
+ });
104
+ return validated;
105
+ } catch (error) {
106
+ console.error(pc.red(`\u274C ${getValidationErrorMessage(error)}`));
107
+ throw error;
108
+ }
97
109
  }
98
110
  export {
99
111
  promptNextjsSetup