lynxprompt 0.3.1 → 0.4.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.
package/dist/index.js CHANGED
@@ -200,12 +200,7 @@ async function loginCommand() {
200
200
  pollSpinner.succeed("Authentication successful!");
201
201
  setToken(result.token);
202
202
  setUser(result.user);
203
- console.log();
204
- console.log(chalk.green(`\u2705 Logged in as ${chalk.bold(result.user.email)}`));
205
- console.log(chalk.gray(` Plan: ${result.user.plan}`));
206
- console.log(chalk.gray(` Token stored securely in config`));
207
- console.log();
208
- console.log(chalk.cyan("You're ready to use LynxPrompt CLI!"));
203
+ displayWelcome(result.user);
209
204
  return;
210
205
  }
211
206
  if (result.status === "expired") {
@@ -259,6 +254,53 @@ async function tryOpenBrowser(url) {
259
254
  function sleep(ms) {
260
255
  return new Promise((resolve) => setTimeout(resolve, ms));
261
256
  }
257
+ function displayWelcome(user) {
258
+ const plan = user.plan?.toUpperCase() || "FREE";
259
+ const name = user.name || user.email.split("@")[0];
260
+ const planConfig = {
261
+ FREE: { color: chalk.gray, emoji: "\u{1F193}", badge: "Free" },
262
+ PRO: { color: chalk.cyan, emoji: "\u26A1", badge: "Pro" },
263
+ MAX: { color: chalk.magenta, emoji: "\u{1F680}", badge: "Max" },
264
+ TEAMS: { color: chalk.yellow, emoji: "\u{1F465}", badge: "Teams" }
265
+ };
266
+ const config2 = planConfig[plan] || planConfig.FREE;
267
+ console.log();
268
+ console.log(chalk.bold("\u250C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2510"));
269
+ console.log(chalk.bold("\u2502") + " " + chalk.bold("\u2502"));
270
+ console.log(chalk.bold("\u2502") + chalk.green.bold(` ${config2.emoji} Welcome to LynxPrompt CLI!`) + " " + chalk.bold("\u2502"));
271
+ console.log(chalk.bold("\u2502") + " " + chalk.bold("\u2502"));
272
+ console.log(chalk.bold("\u2502") + ` ${chalk.white("User:")} ${chalk.bold(name.padEnd(38))}` + chalk.bold("\u2502"));
273
+ console.log(chalk.bold("\u2502") + ` ${chalk.white("Plan:")} ${config2.color(config2.badge.padEnd(38))}` + chalk.bold("\u2502"));
274
+ console.log(chalk.bold("\u2502") + " " + chalk.bold("\u2502"));
275
+ console.log(chalk.bold("\u2514\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2518"));
276
+ console.log();
277
+ console.log(chalk.bold("\u{1F4CB} Your CLI Capabilities:"));
278
+ console.log();
279
+ console.log(chalk.green(" \u2713") + " " + chalk.white("lynxprompt init") + chalk.gray(" - Generate config files"));
280
+ console.log(chalk.green(" \u2713") + " " + chalk.white("lynxprompt wizard") + chalk.gray(" - Interactive wizard"));
281
+ console.log(chalk.green(" \u2713") + " " + chalk.white("lynxprompt list") + chalk.gray(" - List your blueprints"));
282
+ console.log(chalk.green(" \u2713") + " " + chalk.white("lynxprompt pull <id>") + chalk.gray(" - Download blueprints"));
283
+ console.log(chalk.green(" \u2713") + " " + chalk.white("lynxprompt push") + chalk.gray(" - Upload blueprints to marketplace"));
284
+ console.log(chalk.green(" \u2713") + " " + chalk.white("lynxprompt link") + chalk.gray(" - Link project to blueprint"));
285
+ console.log(chalk.green(" \u2713") + " " + chalk.white("lynxprompt sync") + chalk.gray(" - Sync linked blueprints"));
286
+ console.log(chalk.green(" \u2713") + " " + chalk.white("lynxprompt diff") + chalk.gray(" - Compare local vs remote"));
287
+ if (plan === "PRO" || plan === "MAX" || plan === "TEAMS") {
288
+ console.log();
289
+ console.log(chalk.cyan(" \u26A1") + " " + chalk.white("Advanced wizards") + chalk.gray(" - More customization options"));
290
+ console.log(chalk.cyan(" \u26A1") + " " + chalk.white("Sell blueprints") + chalk.gray(" - Monetize your configurations"));
291
+ }
292
+ if (plan === "MAX" || plan === "TEAMS") {
293
+ console.log(chalk.magenta(" \u{1F680}") + " " + chalk.white("All paid blueprints") + chalk.gray(" - Access premium content"));
294
+ console.log(chalk.magenta(" \u{1F680}") + " " + chalk.white("Priority support") + chalk.gray(" - Get help faster"));
295
+ }
296
+ if (plan === "TEAMS") {
297
+ console.log(chalk.yellow(" \u{1F465}") + " " + chalk.white("Team blueprints") + chalk.gray(" - Share with your team"));
298
+ console.log(chalk.yellow(" \u{1F465}") + " " + chalk.white("SSO integration") + chalk.gray(" - Enterprise authentication"));
299
+ }
300
+ console.log();
301
+ console.log(chalk.gray("Token stored securely. Run ") + chalk.cyan("lynxprompt --help") + chalk.gray(" to see all commands."));
302
+ console.log();
303
+ }
262
304
 
263
305
  // src/commands/logout.ts
264
306
  import chalk2 from "chalk";
@@ -1974,7 +2016,17 @@ var PLATFORM_FILES = {
1974
2016
  claude: "CLAUDE.md",
1975
2017
  copilot: ".github/copilot-instructions.md",
1976
2018
  windsurf: ".windsurfrules",
1977
- zed: ".zed/instructions.md"
2019
+ zed: ".zed/instructions.md",
2020
+ aider: ".aider.conf.yml",
2021
+ cline: ".clinerules",
2022
+ continue: ".continue/rules.md",
2023
+ cody: ".cody/rules.md",
2024
+ amazonq: ".amazonq/rules/project.md",
2025
+ tabnine: ".tabnine.yaml",
2026
+ supermaven: ".supermaven/rules.md",
2027
+ codegpt: ".codegpt/rules.md",
2028
+ void: ".void/rules.md",
2029
+ goose: ".goosehints"
1978
2030
  };
1979
2031
  var PERSONA_DESCRIPTIONS = {
1980
2032
  backend: "a senior backend developer specializing in APIs, databases, and microservices architecture",
@@ -1995,6 +2047,8 @@ var STACK_NAMES = {
1995
2047
  ruby: "Ruby",
1996
2048
  php: "PHP",
1997
2049
  swift: "Swift",
2050
+ kotlin: "Kotlin",
2051
+ cpp: "C/C++",
1998
2052
  react: "React",
1999
2053
  nextjs: "Next.js",
2000
2054
  vue: "Vue.js",
@@ -2007,10 +2061,44 @@ var STACK_NAMES = {
2007
2061
  spring: "Spring Boot",
2008
2062
  rails: "Ruby on Rails",
2009
2063
  laravel: "Laravel",
2064
+ nestjs: "NestJS",
2065
+ vite: "Vite",
2066
+ "react-native": "React Native",
2067
+ postgresql: "PostgreSQL",
2068
+ mysql: "MySQL",
2069
+ mongodb: "MongoDB",
2070
+ redis: "Redis",
2071
+ sqlite: "SQLite",
2072
+ supabase: "Supabase",
2073
+ firebase: "Firebase",
2010
2074
  prisma: "Prisma",
2011
2075
  tailwind: "Tailwind CSS",
2012
2076
  fastify: "Fastify"
2013
2077
  };
2078
+ var NAMING_DESCRIPTIONS = {
2079
+ language_default: "follow idiomatic conventions for the primary language",
2080
+ camelCase: "use camelCase for variables and functions",
2081
+ snake_case: "use snake_case for variables and functions",
2082
+ PascalCase: "use PascalCase for classes and types",
2083
+ "kebab-case": "use kebab-case for file names and CSS classes"
2084
+ };
2085
+ var AI_BEHAVIOR_DESCRIPTIONS = {
2086
+ explain_changes: "Always explain what changes you're making and why before implementing them",
2087
+ preserve_style: "Preserve and follow the existing code style in the project",
2088
+ minimal_changes: "Make minimal, focused changes - avoid unnecessary refactoring",
2089
+ no_comments: "Avoid adding unnecessary comments; code should be self-documenting",
2090
+ prefer_simple: "Prefer simpler solutions over clever ones",
2091
+ test_first: "Write tests before implementing new functionality (TDD)",
2092
+ no_console: "Remove console.log/print statements before committing",
2093
+ type_strict: "Be strict with types - avoid any/Any/Object types"
2094
+ };
2095
+ var IMPORTANT_FILES_PATHS = {
2096
+ readme: "README.md",
2097
+ package: "package.json or pyproject.toml",
2098
+ tsconfig: "tsconfig.json or similar config",
2099
+ architecture: "ARCHITECTURE.md",
2100
+ contributing: "CONTRIBUTING.md"
2101
+ };
2014
2102
  var BOUNDARIES = {
2015
2103
  conservative: {
2016
2104
  always: ["Read any file in the project", "Run lint and format commands"],
@@ -2069,6 +2157,12 @@ var BOUNDARIES = {
2069
2157
  ]
2070
2158
  }
2071
2159
  };
2160
+ var TEST_LEVEL_DESCRIPTIONS = {
2161
+ smoke: "Quick sanity checks for critical paths",
2162
+ unit: "Unit tests for individual functions and components",
2163
+ integration: "Integration tests for component interactions",
2164
+ e2e: "End-to-end tests for full user flows"
2165
+ };
2072
2166
  function generateConfig(options) {
2073
2167
  const files = {};
2074
2168
  for (const platform of options.platforms) {
@@ -2082,8 +2176,12 @@ function generateConfig(options) {
2082
2176
  function generateFileContent(options, platform) {
2083
2177
  const sections = [];
2084
2178
  const isMdc = platform === "cursor";
2085
- const isPlainText = platform === "windsurf";
2086
- const isMarkdown = !isMdc && !isPlainText;
2179
+ const isYaml = platform === "aider" || platform === "tabnine";
2180
+ const isPlainText = platform === "windsurf" || platform === "cline" || platform === "goose";
2181
+ const isMarkdown = !isMdc && !isYaml && !isPlainText;
2182
+ if (isYaml) {
2183
+ return generateYamlConfig(options, platform);
2184
+ }
2087
2185
  if (isMdc) {
2088
2186
  sections.push("---");
2089
2187
  sections.push(`description: "${options.name} - AI coding rules"`);
@@ -2098,6 +2196,23 @@ function generateFileContent(options, platform) {
2098
2196
  sections.push(`# ${options.name} - AI Assistant Configuration`);
2099
2197
  sections.push("");
2100
2198
  }
2199
+ if (options.projectType) {
2200
+ const typeContexts = {
2201
+ work: "This is a professional/enterprise project. Follow strict procedures and maintain high code quality.",
2202
+ leisure: "This is a personal/hobby project. Feel free to be more experimental and creative.",
2203
+ opensource: "This is an open-source project. Consider community guidelines and contribution standards.",
2204
+ learning: "This is an educational project. Explain concepts and be patient with learning-focused approaches."
2205
+ };
2206
+ if (typeContexts[options.projectType]) {
2207
+ if (isMarkdown || isMdc) {
2208
+ sections.push(`> **Project Context:** ${typeContexts[options.projectType]}`);
2209
+ sections.push("");
2210
+ } else {
2211
+ sections.push(`Project Context: ${typeContexts[options.projectType]}`);
2212
+ sections.push("");
2213
+ }
2214
+ }
2215
+ }
2101
2216
  const personaDesc = PERSONA_DESCRIPTIONS[options.persona] || options.persona;
2102
2217
  if (isMarkdown || isMdc) {
2103
2218
  sections.push("## Persona");
@@ -2128,7 +2243,25 @@ function generateFileContent(options, platform) {
2128
2243
  }
2129
2244
  sections.push("");
2130
2245
  }
2131
- const hasCommands = Object.values(options.commands).some(Boolean);
2246
+ if (options.repoHost || options.license || options.conventionalCommits) {
2247
+ if (isMarkdown || isMdc) {
2248
+ sections.push("## Repository");
2249
+ sections.push("");
2250
+ if (options.repoHost) {
2251
+ sections.push(`- **Host:** ${options.repoHost.charAt(0).toUpperCase() + options.repoHost.slice(1)}`);
2252
+ }
2253
+ if (options.license && options.license !== "none") {
2254
+ sections.push(`- **License:** ${options.license.toUpperCase()}`);
2255
+ }
2256
+ if (options.conventionalCommits) {
2257
+ sections.push("- **Commits:** Follow [Conventional Commits](https://conventionalcommits.org) format");
2258
+ }
2259
+ sections.push("");
2260
+ }
2261
+ }
2262
+ const hasCommands = options.commands && Object.values(options.commands).some(
2263
+ (v) => Array.isArray(v) ? v.length > 0 : Boolean(v)
2264
+ );
2132
2265
  if (hasCommands) {
2133
2266
  if (isMarkdown || isMdc) {
2134
2267
  sections.push("## Commands");
@@ -2139,24 +2272,68 @@ function generateFileContent(options, platform) {
2139
2272
  } else {
2140
2273
  sections.push("Commands:");
2141
2274
  }
2142
- if (options.commands.build) {
2143
- sections.push(isMarkdown || isMdc ? `# Build: ${options.commands.build}` : `- Build: ${options.commands.build}`);
2275
+ const cmdCategories = ["build", "test", "lint", "dev", "custom"];
2276
+ for (const cat of cmdCategories) {
2277
+ const cmd = options.commands[cat];
2278
+ if (cmd) {
2279
+ const cmds = Array.isArray(cmd) ? cmd : [cmd];
2280
+ for (const c of cmds) {
2281
+ if (c) {
2282
+ const label = cat.charAt(0).toUpperCase() + cat.slice(1);
2283
+ sections.push(isMarkdown || isMdc ? `# ${label}: ${c}` : `- ${label}: ${c}`);
2284
+ }
2285
+ }
2286
+ }
2144
2287
  }
2145
- if (options.commands.test) {
2146
- sections.push(isMarkdown || isMdc ? `# Test: ${options.commands.test}` : `- Test: ${options.commands.test}`);
2288
+ if (isMarkdown || isMdc) {
2289
+ sections.push("```");
2147
2290
  }
2148
- if (options.commands.lint) {
2149
- sections.push(isMarkdown || isMdc ? `# Lint: ${options.commands.lint}` : `- Lint: ${options.commands.lint}`);
2291
+ sections.push("");
2292
+ }
2293
+ if (options.aiBehavior && options.aiBehavior.length > 0) {
2294
+ if (isMarkdown || isMdc) {
2295
+ sections.push("## AI Behavior Rules");
2296
+ sections.push("");
2297
+ for (const rule of options.aiBehavior) {
2298
+ const desc = AI_BEHAVIOR_DESCRIPTIONS[rule];
2299
+ if (desc) {
2300
+ sections.push(`- ${desc}`);
2301
+ }
2302
+ }
2303
+ sections.push("");
2150
2304
  }
2151
- if (options.commands.dev) {
2152
- sections.push(isMarkdown || isMdc ? `# Dev: ${options.commands.dev}` : `- Dev: ${options.commands.dev}`);
2305
+ }
2306
+ if (options.importantFiles && options.importantFiles.length > 0) {
2307
+ if (isMarkdown || isMdc) {
2308
+ sections.push("## Important Files to Read");
2309
+ sections.push("");
2310
+ sections.push("Always read these files first to understand the project context:");
2311
+ sections.push("");
2312
+ for (const file of options.importantFiles) {
2313
+ const path2 = IMPORTANT_FILES_PATHS[file];
2314
+ if (path2) {
2315
+ sections.push(`- \`${path2}\``);
2316
+ }
2317
+ }
2318
+ sections.push("");
2153
2319
  }
2320
+ }
2321
+ if (options.selfImprove) {
2154
2322
  if (isMarkdown || isMdc) {
2155
- sections.push("```");
2323
+ sections.push("## Self-Improving Blueprint");
2324
+ sections.push("");
2325
+ sections.push("> **Auto-update enabled:** As you work on this project, track patterns and update this configuration file to better reflect the project's conventions and preferences.");
2326
+ sections.push("");
2156
2327
  }
2157
- sections.push("");
2158
2328
  }
2159
- const boundaries = BOUNDARIES[options.boundaries];
2329
+ let boundaries = BOUNDARIES[options.boundaries];
2330
+ if (options.boundaryNever?.length || options.boundaryAsk?.length) {
2331
+ boundaries = {
2332
+ ...boundaries,
2333
+ never: options.boundaryNever?.length ? options.boundaryNever : boundaries.never,
2334
+ askFirst: options.boundaryAsk?.length ? options.boundaryAsk : boundaries.askFirst
2335
+ };
2336
+ }
2160
2337
  if (boundaries) {
2161
2338
  if (isMarkdown || isMdc) {
2162
2339
  sections.push("## Boundaries");
@@ -2201,6 +2378,27 @@ function generateFileContent(options, platform) {
2201
2378
  if (isMarkdown || isMdc) {
2202
2379
  sections.push("## Code Style");
2203
2380
  sections.push("");
2381
+ if (options.namingConvention) {
2382
+ const namingDesc = NAMING_DESCRIPTIONS[options.namingConvention];
2383
+ if (namingDesc) {
2384
+ sections.push(`- **Naming:** ${namingDesc}`);
2385
+ }
2386
+ }
2387
+ if (options.errorHandling) {
2388
+ const errorStyles = {
2389
+ try_catch: "Use try/catch blocks for error handling",
2390
+ result_types: "Use Result/Either types for error handling",
2391
+ error_codes: "Use error codes with proper documentation",
2392
+ exceptions: "Use custom exception classes"
2393
+ };
2394
+ if (errorStyles[options.errorHandling]) {
2395
+ sections.push(`- **Errors:** ${errorStyles[options.errorHandling]}`);
2396
+ }
2397
+ }
2398
+ if (options.styleNotes) {
2399
+ sections.push(`- **Notes:** ${options.styleNotes}`);
2400
+ }
2401
+ sections.push("");
2204
2402
  sections.push("Follow these conventions:");
2205
2403
  sections.push("");
2206
2404
  if (options.stack.includes("typescript") || options.stack.includes("javascript")) {
@@ -2234,6 +2432,49 @@ function generateFileContent(options, platform) {
2234
2432
  sections.push("- Keep functions focused and testable");
2235
2433
  sections.push("");
2236
2434
  }
2435
+ if (options.testLevels?.length || options.testFrameworks?.length || options.coverageTarget) {
2436
+ if (isMarkdown || isMdc) {
2437
+ sections.push("## Testing Strategy");
2438
+ sections.push("");
2439
+ if (options.testLevels?.length) {
2440
+ sections.push("### Test Levels");
2441
+ sections.push("");
2442
+ for (const level of options.testLevels) {
2443
+ const desc = TEST_LEVEL_DESCRIPTIONS[level];
2444
+ if (desc) {
2445
+ sections.push(`- **${level.charAt(0).toUpperCase() + level.slice(1)}:** ${desc}`);
2446
+ }
2447
+ }
2448
+ sections.push("");
2449
+ }
2450
+ if (options.testFrameworks?.length) {
2451
+ sections.push("### Frameworks");
2452
+ sections.push("");
2453
+ sections.push(`Use: ${options.testFrameworks.join(", ")}`);
2454
+ sections.push("");
2455
+ }
2456
+ if (options.coverageTarget) {
2457
+ sections.push(`### Coverage Target: ${options.coverageTarget}%`);
2458
+ sections.push("");
2459
+ }
2460
+ if (options.testNotes) {
2461
+ sections.push(`**Notes:** ${options.testNotes}`);
2462
+ sections.push("");
2463
+ }
2464
+ }
2465
+ }
2466
+ if (options.extraNotes) {
2467
+ if (isMarkdown || isMdc) {
2468
+ sections.push("## Additional Notes");
2469
+ sections.push("");
2470
+ sections.push(options.extraNotes);
2471
+ sections.push("");
2472
+ } else {
2473
+ sections.push("Additional Notes:");
2474
+ sections.push(options.extraNotes);
2475
+ sections.push("");
2476
+ }
2477
+ }
2237
2478
  if (isMarkdown || isMdc) {
2238
2479
  sections.push("---");
2239
2480
  sections.push("");
@@ -2241,37 +2482,90 @@ function generateFileContent(options, platform) {
2241
2482
  }
2242
2483
  return sections.join("\n");
2243
2484
  }
2485
+ function generateYamlConfig(options, platform) {
2486
+ const lines = [];
2487
+ if (platform === "aider") {
2488
+ lines.push("# Aider configuration");
2489
+ lines.push(`# Project: ${options.name}`);
2490
+ lines.push("");
2491
+ lines.push("# Model settings");
2492
+ lines.push("model: gpt-4");
2493
+ lines.push("");
2494
+ lines.push("# Code style");
2495
+ if (options.stack.includes("typescript") || options.stack.includes("javascript")) {
2496
+ lines.push("auto-lint: true");
2497
+ }
2498
+ lines.push("");
2499
+ lines.push("# Custom instructions");
2500
+ lines.push("read:");
2501
+ lines.push(" - README.md");
2502
+ if (options.importantFiles?.includes("architecture")) {
2503
+ lines.push(" - ARCHITECTURE.md");
2504
+ }
2505
+ } else if (platform === "tabnine") {
2506
+ lines.push("# Tabnine configuration");
2507
+ lines.push(`# Project: ${options.name}`);
2508
+ lines.push("");
2509
+ lines.push("version: 1.0.0");
2510
+ lines.push("");
2511
+ lines.push("project:");
2512
+ lines.push(` name: ${options.name}`);
2513
+ if (options.description) {
2514
+ lines.push(` description: "${options.description}"`);
2515
+ }
2516
+ lines.push("");
2517
+ lines.push("context:");
2518
+ lines.push(" include:");
2519
+ lines.push(' - "**/*.ts"');
2520
+ lines.push(' - "**/*.js"');
2521
+ lines.push(' - "**/*.py"');
2522
+ }
2523
+ lines.push("");
2524
+ lines.push(`# Generated by LynxPrompt CLI`);
2525
+ return lines.join("\n");
2526
+ }
2244
2527
 
2245
2528
  // src/commands/wizard.ts
2529
+ var WIZARD_STEPS = [
2530
+ { id: "format", title: "Output Format", icon: "\u{1F4E4}", tier: "basic" },
2531
+ { id: "project", title: "Project Basics", icon: "\u2728", tier: "basic" },
2532
+ { id: "tech", title: "Tech Stack", icon: "\u{1F4BB}", tier: "basic" },
2533
+ { id: "repo", title: "Repository Setup", icon: "\u{1F500}", tier: "basic" },
2534
+ { id: "commands", title: "Commands", icon: "\u{1F4CB}", tier: "intermediate" },
2535
+ { id: "code_style", title: "Code Style", icon: "\u{1FA84}", tier: "intermediate" },
2536
+ { id: "ai", title: "AI Behavior", icon: "\u{1F9E0}", tier: "basic" },
2537
+ { id: "boundaries", title: "Boundaries", icon: "\u{1F6E1}\uFE0F", tier: "advanced" },
2538
+ { id: "testing", title: "Testing Strategy", icon: "\u{1F9EA}", tier: "advanced" },
2539
+ { id: "static", title: "Static Files", icon: "\u{1F4C4}", tier: "advanced" },
2540
+ { id: "extra", title: "Final Details", icon: "\u{1F4AC}", tier: "basic" }
2541
+ ];
2542
+ var ALL_PLATFORMS = [
2543
+ { id: "agents", name: "Universal (AGENTS.md)", file: "AGENTS.md", icon: "\u{1F310}", note: "Works with all AI-enabled IDEs" },
2544
+ { id: "cursor", name: "Cursor", file: ".cursor/rules/", icon: "\u26A1", note: "Native project rules format" },
2545
+ { id: "claude", name: "Claude Code", file: "CLAUDE.md", icon: "\u{1F9E0}", note: "Also works with Cursor" },
2546
+ { id: "copilot", name: "GitHub Copilot", file: ".github/copilot-instructions.md", icon: "\u{1F419}", note: "VS Code & JetBrains" },
2547
+ { id: "windsurf", name: "Windsurf", file: ".windsurfrules", icon: "\u{1F3C4}", note: "Codeium IDE" },
2548
+ { id: "zed", name: "Zed", file: ".zed/instructions.md", icon: "\u26A1", note: "Zed editor" },
2549
+ { id: "aider", name: "Aider", file: ".aider.conf.yml", icon: "\u{1F916}", note: "CLI AI pair programming" },
2550
+ { id: "cline", name: "Cline", file: ".clinerules", icon: "\u{1F527}", note: "VS Code extension" },
2551
+ { id: "continue", name: "Continue", file: ".continue/config.json", icon: "\u27A1\uFE0F", note: "Open-source autopilot" },
2552
+ { id: "cody", name: "Sourcegraph Cody", file: ".cody/config.json", icon: "\u{1F50D}", note: "Context-aware AI" },
2553
+ { id: "amazonq", name: "Amazon Q", file: ".amazonq/rules/", icon: "\u{1F4E6}", note: "AWS AI assistant" },
2554
+ { id: "tabnine", name: "Tabnine", file: ".tabnine.yaml", icon: "\u{1F4DD}", note: "AI code completion" },
2555
+ { id: "supermaven", name: "Supermaven", file: ".supermaven/config.json", icon: "\u{1F9B8}", note: "Fast AI completions" },
2556
+ { id: "codegpt", name: "CodeGPT", file: ".codegpt/config.json", icon: "\u{1F4AC}", note: "VS Code AI assistant" },
2557
+ { id: "void", name: "Void", file: ".void/config.json", icon: "\u{1F573}\uFE0F", note: "Open-source Cursor alt" },
2558
+ { id: "goose", name: "Goose", file: ".goosehints", icon: "\u{1FABF}", note: "Block AI agent" }
2559
+ ];
2246
2560
  var OUTPUT_FORMATS = [
2247
- {
2248
- title: "\u{1F310} AGENTS.md",
2249
- value: "agents",
2250
- description: "Universal format - Claude, Copilot, Aider, & more",
2251
- recommended: true
2252
- },
2253
- {
2254
- title: "\u{1F5B1}\uFE0F Cursor",
2255
- value: "cursor",
2256
- description: ".cursor/rules/ with MDC format"
2257
- },
2258
- {
2259
- title: "\u{1F30A} Windsurf",
2260
- value: "windsurf",
2261
- description: ".windsurfrules configuration"
2262
- },
2263
- {
2264
- title: "\u{1F916} Claude Code",
2265
- value: "claude",
2266
- description: "CLAUDE.md for Claude AI"
2267
- },
2268
- {
2269
- title: "\u{1F4E6} Multiple",
2270
- value: "multiple",
2271
- description: "Generate for multiple AI editors"
2272
- }
2561
+ { title: "\u{1F310} AGENTS.md (Universal)", value: "agents", description: "Works with Claude, Copilot, Aider, Devin & more", recommended: true },
2562
+ { title: "\u26A1 Cursor", value: "cursor", description: ".cursor/rules/ native format" },
2563
+ { title: "\u{1F9E0} Claude Code", value: "claude", description: "CLAUDE.md format" },
2564
+ { title: "\u{1F419} GitHub Copilot", value: "copilot", description: ".github/copilot-instructions.md" },
2565
+ { title: "\u{1F3C4} Windsurf", value: "windsurf", description: ".windsurfrules configuration" },
2566
+ { title: "\u{1F4E6} Multiple platforms...", value: "multiple", description: "Select from 16+ supported AI editors" }
2273
2567
  ];
2274
- var TECH_STACKS = [
2568
+ var LANGUAGES = [
2275
2569
  { title: "\u{1F537} TypeScript", value: "typescript" },
2276
2570
  { title: "\u{1F7E1} JavaScript", value: "javascript" },
2277
2571
  { title: "\u{1F40D} Python", value: "python" },
@@ -2281,7 +2575,9 @@ var TECH_STACKS = [
2281
2575
  { title: "\u{1F49C} C#/.NET", value: "csharp" },
2282
2576
  { title: "\u{1F48E} Ruby", value: "ruby" },
2283
2577
  { title: "\u{1F418} PHP", value: "php" },
2284
- { title: "\u{1F34E} Swift", value: "swift" }
2578
+ { title: "\u{1F34E} Swift", value: "swift" },
2579
+ { title: "\u{1F536} Kotlin", value: "kotlin" },
2580
+ { title: "\u2B1B C/C++", value: "cpp" }
2285
2581
  ];
2286
2582
  var FRAMEWORKS = [
2287
2583
  { title: "\u269B\uFE0F React", value: "react" },
@@ -2300,23 +2596,133 @@ var FRAMEWORKS = [
2300
2596
  { title: "\u26A1 Vite", value: "vite" },
2301
2597
  { title: "\u{1F4F1} React Native", value: "react-native" }
2302
2598
  ];
2303
- var PLATFORMS = [
2304
- { title: "\u{1F310} AGENTS.md (Universal)", value: "agents", filename: "AGENTS.md" },
2305
- { title: "\u{1F5B1}\uFE0F Cursor", value: "cursor", filename: ".cursor/rules/project.mdc" },
2306
- { title: "\u{1F916} Claude Code", value: "claude", filename: "CLAUDE.md" },
2307
- { title: "\u{1F419} GitHub Copilot", value: "copilot", filename: ".github/copilot-instructions.md" },
2308
- { title: "\u{1F30A} Windsurf", value: "windsurf", filename: ".windsurfrules" },
2309
- { title: "\u26A1 Zed", value: "zed", filename: ".zed/instructions.md" },
2310
- { title: "\u{1F916} Cline", value: "cline", filename: ".clinerules" }
2599
+ var DATABASES = [
2600
+ { title: "\u{1F418} PostgreSQL", value: "postgresql" },
2601
+ { title: "\u{1F42C} MySQL", value: "mysql" },
2602
+ { title: "\u{1F343} MongoDB", value: "mongodb" },
2603
+ { title: "\u{1F534} Redis", value: "redis" },
2604
+ { title: "\u{1F4CA} SQLite", value: "sqlite" },
2605
+ { title: "\u2601\uFE0F Supabase", value: "supabase" },
2606
+ { title: "\u{1F525} Firebase", value: "firebase" },
2607
+ { title: "\u{1F4C2} Prisma", value: "prisma" }
2608
+ ];
2609
+ var REPO_HOSTS = [
2610
+ { id: "github", label: "GitHub", icon: "\u{1F419}" },
2611
+ { id: "gitlab", label: "GitLab", icon: "\u{1F98A}" },
2612
+ { id: "bitbucket", label: "Bitbucket", icon: "\u{1FAA3}" },
2613
+ { id: "gitea", label: "Gitea", icon: "\u{1F375}" },
2614
+ { id: "azure", label: "Azure DevOps", icon: "\u2601\uFE0F" },
2615
+ { id: "other", label: "Other", icon: "\u{1F4E6}" }
2616
+ ];
2617
+ var LICENSES = [
2618
+ { id: "mit", label: "MIT" },
2619
+ { id: "apache-2.0", label: "Apache 2.0" },
2620
+ { id: "gpl-3.0", label: "GPL 3.0" },
2621
+ { id: "lgpl-3.0", label: "LGPL 3.0" },
2622
+ { id: "agpl-3.0", label: "AGPL 3.0" },
2623
+ { id: "bsd-3", label: "BSD 3-Clause" },
2624
+ { id: "mpl-2.0", label: "MPL 2.0" },
2625
+ { id: "unlicense", label: "Unlicense" },
2626
+ { id: "none", label: "None / Proprietary" }
2627
+ ];
2628
+ var COMMON_COMMANDS = {
2629
+ build: [
2630
+ "npm run build",
2631
+ "pnpm build",
2632
+ "yarn build",
2633
+ "bun run build",
2634
+ "next build",
2635
+ "vite build",
2636
+ "tsc",
2637
+ "tsc --noEmit",
2638
+ "go build",
2639
+ "cargo build",
2640
+ "cargo build --release",
2641
+ "mvn package",
2642
+ "gradle build",
2643
+ "dotnet build",
2644
+ "docker build -t app .",
2645
+ "docker compose build"
2646
+ ],
2647
+ test: [
2648
+ "npm test",
2649
+ "pnpm test",
2650
+ "yarn test",
2651
+ "bun test",
2652
+ "vitest",
2653
+ "vitest run",
2654
+ "jest",
2655
+ "jest --coverage",
2656
+ "pytest",
2657
+ "pytest --cov",
2658
+ "go test ./...",
2659
+ "cargo test",
2660
+ "mvn test",
2661
+ "gradle test",
2662
+ "playwright test",
2663
+ "cypress run"
2664
+ ],
2665
+ lint: [
2666
+ "npm run lint",
2667
+ "pnpm lint",
2668
+ "eslint .",
2669
+ "eslint . --fix",
2670
+ "prettier --check .",
2671
+ "prettier --write .",
2672
+ "ruff check",
2673
+ "ruff format",
2674
+ "black .",
2675
+ "flake8",
2676
+ "golangci-lint run",
2677
+ "cargo clippy",
2678
+ "rubocop"
2679
+ ],
2680
+ dev: [
2681
+ "npm run dev",
2682
+ "pnpm dev",
2683
+ "yarn dev",
2684
+ "bun run dev",
2685
+ "next dev",
2686
+ "vite",
2687
+ "vite dev",
2688
+ "uvicorn main:app --reload",
2689
+ "flask run",
2690
+ "rails server",
2691
+ "go run .",
2692
+ "cargo run",
2693
+ "dotnet run"
2694
+ ]
2695
+ };
2696
+ var NAMING_CONVENTIONS = [
2697
+ { id: "language_default", label: "Follow language conventions", desc: "Use idiomatic style" },
2698
+ { id: "camelCase", label: "camelCase", desc: "JavaScript, TypeScript, Java" },
2699
+ { id: "snake_case", label: "snake_case", desc: "Python, Ruby, Rust, Go" },
2700
+ { id: "PascalCase", label: "PascalCase", desc: "C#, .NET classes" },
2701
+ { id: "kebab-case", label: "kebab-case", desc: "CSS, HTML, URLs" }
2702
+ ];
2703
+ var ERROR_PATTERNS = [
2704
+ { id: "try_catch", label: "try/catch blocks" },
2705
+ { id: "result_types", label: "Result/Either types" },
2706
+ { id: "error_codes", label: "Error codes" },
2707
+ { id: "exceptions", label: "Custom exceptions" },
2708
+ { id: "other", label: "Other" }
2311
2709
  ];
2312
- var PERSONAS = [
2313
- { title: "\u{1F9D1}\u200D\u{1F4BB} Full-Stack Developer", value: "fullstack", description: "Complete application development" },
2314
- { title: "\u2699\uFE0F Backend Developer", value: "backend", description: "APIs, databases, services" },
2315
- { title: "\u{1F3A8} Frontend Developer", value: "frontend", description: "UI, components, styling" },
2316
- { title: "\u{1F680} DevOps Engineer", value: "devops", description: "Infrastructure, CI/CD" },
2317
- { title: "\u{1F4CA} Data Engineer", value: "data", description: "Pipelines, ETL, analytics" },
2318
- { title: "\u{1F512} Security Engineer", value: "security", description: "Secure code, auditing" },
2319
- { title: "\u270F\uFE0F Custom...", value: "custom", description: "Define your own" }
2710
+ var AI_BEHAVIOR_RULES = [
2711
+ { id: "explain_changes", label: "Explain changes before making them", recommended: true },
2712
+ { id: "preserve_style", label: "Preserve existing code style", recommended: true },
2713
+ { id: "minimal_changes", label: "Make minimal, focused changes", recommended: true },
2714
+ { id: "no_comments", label: "Avoid adding unnecessary comments", recommended: false },
2715
+ { id: "prefer_simple", label: "Prefer simpler solutions", recommended: true },
2716
+ { id: "test_first", label: "Write tests before implementation", recommended: false },
2717
+ { id: "no_console", label: "Remove console.log/print before committing", recommended: false },
2718
+ { id: "type_strict", label: "Be strict with types (no any/Any)", recommended: false }
2719
+ ];
2720
+ var IMPORTANT_FILES = [
2721
+ { id: "readme", label: "README.md", icon: "\u{1F4D6}" },
2722
+ { id: "package", label: "package.json / pyproject.toml", icon: "\u{1F4E6}" },
2723
+ { id: "tsconfig", label: "tsconfig.json / config files", icon: "\u2699\uFE0F" },
2724
+ { id: "architecture", label: "ARCHITECTURE.md", icon: "\u{1F3D7}\uFE0F" },
2725
+ { id: "contributing", label: "CONTRIBUTING.md", icon: "\u{1F91D}" }
2320
2726
  ];
2321
2727
  var BOUNDARY_PRESETS = [
2322
2728
  {
@@ -2344,11 +2750,79 @@ var BOUNDARY_PRESETS = [
2344
2750
  never: ["Modify .env", "Access external APIs without confirmation"]
2345
2751
  }
2346
2752
  ];
2347
- function showStep(current, total, title) {
2348
- const progress = "\u25CF".repeat(current) + "\u25CB".repeat(total - current);
2349
- console.log();
2350
- console.log(chalk8.cyan(` ${progress} Step ${current}/${total}: ${title}`));
2351
- console.log();
2753
+ var BOUNDARY_OPTIONS = [
2754
+ "Delete files",
2755
+ "Create new files",
2756
+ "Rename/move files",
2757
+ "Rewrite large sections",
2758
+ "Refactor architecture",
2759
+ "Change dependencies",
2760
+ "Modify database schema",
2761
+ "Update API contracts",
2762
+ "Touch CI pipelines",
2763
+ "Modify Docker config",
2764
+ "Change environment vars",
2765
+ "Update docs automatically",
2766
+ "Edit README",
2767
+ "Handle secrets/credentials",
2768
+ "Modify auth logic",
2769
+ "Delete failing tests",
2770
+ "Skip tests temporarily"
2771
+ ];
2772
+ var TEST_FRAMEWORKS = [
2773
+ "jest",
2774
+ "vitest",
2775
+ "mocha",
2776
+ "ava",
2777
+ "tap",
2778
+ "pytest",
2779
+ "unittest",
2780
+ "nose2",
2781
+ "go test",
2782
+ "testify",
2783
+ "cargo test",
2784
+ "rstest",
2785
+ "junit",
2786
+ "testng",
2787
+ "spock",
2788
+ "rspec",
2789
+ "minitest",
2790
+ "phpunit",
2791
+ "pest",
2792
+ "playwright",
2793
+ "cypress",
2794
+ "puppeteer",
2795
+ "selenium"
2796
+ ];
2797
+ var TEST_LEVELS = [
2798
+ { id: "smoke", label: "Smoke", desc: "Quick sanity checks" },
2799
+ { id: "unit", label: "Unit", desc: "Individual functions/components" },
2800
+ { id: "integration", label: "Integration", desc: "Component interactions" },
2801
+ { id: "e2e", label: "E2E", desc: "Full user flows" }
2802
+ ];
2803
+ var PROJECT_TYPES = [
2804
+ { id: "work", label: "Work", icon: "\u{1F4BC}", description: "Professional/enterprise project" },
2805
+ { id: "leisure", label: "Leisure", icon: "\u{1F3AE}", description: "Personal/hobby project" },
2806
+ { id: "opensource", label: "Open Source", icon: "\u{1F30D}", description: "Community-driven project" },
2807
+ { id: "learning", label: "Learning", icon: "\u{1F4DA}", description: "Educational/experimental" }
2808
+ ];
2809
+ function canAccessTier(userTier, requiredTier) {
2810
+ const tierLevels = { free: 0, pro: 1, max: 2, teams: 2 };
2811
+ const requiredLevels = { basic: 0, intermediate: 1, advanced: 2 };
2812
+ return tierLevels[userTier] >= requiredLevels[requiredTier];
2813
+ }
2814
+ function getTierBadge(tier) {
2815
+ switch (tier) {
2816
+ case "intermediate":
2817
+ return { label: "PRO", color: chalk8.cyan };
2818
+ case "advanced":
2819
+ return { label: "MAX", color: chalk8.magenta };
2820
+ default:
2821
+ return null;
2822
+ }
2823
+ }
2824
+ function getAvailableSteps(userTier) {
2825
+ return WIZARD_STEPS.filter((step) => canAccessTier(userTier, step.tier));
2352
2826
  }
2353
2827
  function printBox(lines, color = chalk8.gray) {
2354
2828
  const maxLen = Math.max(...lines.map((l) => l.replace(/\x1b\[[0-9;]*m/g, "").length));
@@ -2362,11 +2836,83 @@ function printBox(lines, color = chalk8.gray) {
2362
2836
  }
2363
2837
  console.log(color(bottom));
2364
2838
  }
2839
+ function showStep(current, step, userTier) {
2840
+ const availableSteps = getAvailableSteps(userTier);
2841
+ const total = availableSteps.length;
2842
+ const progress = "\u25CF".repeat(current) + "\u25CB".repeat(total - current);
2843
+ const badge = getTierBadge(step.tier);
2844
+ console.log();
2845
+ let stepLine = chalk8.cyan(` ${progress} Step ${current}/${total}: ${step.icon} ${step.title}`);
2846
+ if (badge) {
2847
+ stepLine += " " + badge.color(`[${badge.label}]`);
2848
+ }
2849
+ console.log(stepLine);
2850
+ console.log();
2851
+ }
2852
+ function showWizardOverview(userTier) {
2853
+ console.log(chalk8.bold(" \u{1F4CB} Wizard Steps Overview:"));
2854
+ console.log();
2855
+ let stepNum = 1;
2856
+ for (const step of WIZARD_STEPS) {
2857
+ const canAccess = canAccessTier(userTier, step.tier);
2858
+ const badge = getTierBadge(step.tier);
2859
+ if (canAccess) {
2860
+ let line = chalk8.green(` ${stepNum.toString().padStart(2)}. \u2713 ${step.icon} ${step.title}`);
2861
+ if (badge) {
2862
+ line += " " + badge.color(`[${badge.label}]`);
2863
+ }
2864
+ console.log(line);
2865
+ stepNum++;
2866
+ } else {
2867
+ let line = chalk8.gray(` \u2500 \u{1F512} ${step.icon} ${step.title}`);
2868
+ if (badge) {
2869
+ line += " " + badge.color.dim(`[${badge.label}]`);
2870
+ }
2871
+ console.log(line);
2872
+ }
2873
+ }
2874
+ console.log();
2875
+ }
2876
+ var promptConfig = {
2877
+ onCancel: () => {
2878
+ console.log(chalk8.yellow("\n Cancelled. Run 'lynxp wizard' anytime to restart.\n"));
2879
+ process.exit(0);
2880
+ }
2881
+ };
2365
2882
  async function wizardCommand(options) {
2366
2883
  console.log();
2367
2884
  console.log(chalk8.cyan.bold(" \u{1F431} LynxPrompt Wizard"));
2368
2885
  console.log(chalk8.gray(" Generate AI IDE configuration in seconds"));
2369
2886
  console.log();
2887
+ const authenticated = isAuthenticated();
2888
+ const user = getUser();
2889
+ const userPlanRaw = user?.plan?.toLowerCase() || "free";
2890
+ const userTier = ["pro", "max", "teams"].includes(userPlanRaw) ? userPlanRaw : "free";
2891
+ const userPlanDisplay = user?.plan?.toUpperCase() || "FREE";
2892
+ if (!authenticated) {
2893
+ console.log(chalk8.yellow("\u250C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2510"));
2894
+ console.log(chalk8.yellow("\u2502") + chalk8.white(" \u{1F4A1} ") + chalk8.gray("Log in for full wizard features:") + " " + chalk8.yellow("\u2502"));
2895
+ console.log(chalk8.yellow("\u2502") + " " + chalk8.yellow("\u2502"));
2896
+ console.log(chalk8.yellow("\u2502") + chalk8.gray(" \u2022 ") + chalk8.white("Commands & Code Style") + chalk8.cyan(" [PRO]") + " " + chalk8.yellow("\u2502"));
2897
+ console.log(chalk8.yellow("\u2502") + chalk8.gray(" \u2022 ") + chalk8.white("Boundaries, Testing, Static Files") + chalk8.magenta(" [MAX]") + " " + chalk8.yellow("\u2502"));
2898
+ console.log(chalk8.yellow("\u2502") + chalk8.gray(" \u2022 ") + chalk8.white("Push configs to cloud") + chalk8.gray(" (lynxp push)") + " " + chalk8.yellow("\u2502"));
2899
+ console.log(chalk8.yellow("\u2502") + chalk8.gray(" \u2022 ") + chalk8.white("Sync across devices") + chalk8.gray(" (lynxp sync)") + " " + chalk8.yellow("\u2502"));
2900
+ console.log(chalk8.yellow("\u2502") + " " + chalk8.yellow("\u2502"));
2901
+ console.log(chalk8.yellow("\u2502") + chalk8.cyan(" Run: lynxp login") + " " + chalk8.yellow("\u2502"));
2902
+ console.log(chalk8.yellow("\u2514\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2518"));
2903
+ console.log();
2904
+ } else {
2905
+ const planEmoji = userTier === "teams" ? "\u{1F465}" : userTier === "max" ? "\u{1F680}" : userTier === "pro" ? "\u26A1" : "\u{1F193}";
2906
+ console.log(chalk8.green(` \u2713 Logged in as ${chalk8.bold(user?.name || user?.email)} ${planEmoji} ${chalk8.gray(userPlanDisplay)}`));
2907
+ console.log();
2908
+ }
2909
+ showWizardOverview(userTier);
2910
+ const accessibleSteps = getAvailableSteps(userTier);
2911
+ const lockedSteps = WIZARD_STEPS.length - accessibleSteps.length;
2912
+ if (lockedSteps > 0) {
2913
+ console.log(chalk8.gray(` ${lockedSteps} step${lockedSteps > 1 ? "s" : ""} locked. Upgrade at ${chalk8.cyan("https://lynxprompt.com/pricing")}`));
2914
+ console.log();
2915
+ }
2370
2916
  const detected = await detectProject(process.cwd());
2371
2917
  if (detected) {
2372
2918
  const detectedInfo = [
@@ -2398,7 +2944,7 @@ async function wizardCommand(options) {
2398
2944
  commands: detected?.commands || {}
2399
2945
  };
2400
2946
  } else {
2401
- config2 = await runInteractiveWizard(options, detected);
2947
+ config2 = await runInteractiveWizard(options, detected, userTier);
2402
2948
  }
2403
2949
  const spinner = ora7("Generating configuration...").start();
2404
2950
  try {
@@ -2435,14 +2981,21 @@ async function wizardCommand(options) {
2435
2981
  console.log(` ${chalk8.cyan("\u2192")} ${chalk8.bold(filename)}`);
2436
2982
  }
2437
2983
  console.log();
2438
- printBox([
2984
+ const nextStepsLines = [
2439
2985
  chalk8.gray("Your AI assistant will now follow these instructions."),
2440
2986
  "",
2441
2987
  chalk8.gray("Next steps:"),
2442
- chalk8.cyan(" lynxp check ") + chalk8.gray("Validate configuration"),
2443
- chalk8.cyan(" lynxp push ") + chalk8.gray("Sync to cloud"),
2444
- chalk8.cyan(" lynxp status ") + chalk8.gray("View current setup")
2445
- ], chalk8.gray);
2988
+ chalk8.cyan(" lynxp check ") + chalk8.gray("Validate configuration")
2989
+ ];
2990
+ if (authenticated) {
2991
+ nextStepsLines.push(chalk8.cyan(" lynxp push ") + chalk8.gray("Upload to cloud"));
2992
+ nextStepsLines.push(chalk8.cyan(" lynxp link ") + chalk8.gray("Link to a blueprint"));
2993
+ nextStepsLines.push(chalk8.cyan(" lynxp sync ") + chalk8.gray("Sync with linked blueprint"));
2994
+ } else {
2995
+ nextStepsLines.push(chalk8.gray(" lynxp login ") + chalk8.yellow("Log in to push & sync"));
2996
+ }
2997
+ nextStepsLines.push(chalk8.cyan(" lynxp status ") + chalk8.gray("View current setup"));
2998
+ printBox(nextStepsLines, chalk8.gray);
2446
2999
  console.log();
2447
3000
  } catch (error) {
2448
3001
  spinner.fail("Failed to generate files");
@@ -2454,16 +3007,20 @@ async function wizardCommand(options) {
2454
3007
  process.exit(1);
2455
3008
  }
2456
3009
  }
2457
- async function runInteractiveWizard(options, detected) {
3010
+ async function runInteractiveWizard(options, detected, userTier) {
2458
3011
  const answers = {};
2459
- const totalSteps = 5;
2460
- const promptConfig = {
2461
- onCancel: () => {
2462
- console.log(chalk8.yellow("\n Cancelled. Run 'lynxp wizard' anytime to restart.\n"));
2463
- process.exit(0);
3012
+ const availableSteps = getAvailableSteps(userTier);
3013
+ let currentStepNum = 0;
3014
+ const getCurrentStep = (stepId) => {
3015
+ const step = availableSteps.find((s) => s.id === stepId);
3016
+ if (step) {
3017
+ currentStepNum++;
3018
+ return step;
2464
3019
  }
3020
+ return null;
2465
3021
  };
2466
- showStep(1, totalSteps, "Output Format");
3022
+ const formatStep = getCurrentStep("format");
3023
+ showStep(currentStepNum, formatStep, userTier);
2467
3024
  let platforms;
2468
3025
  if (options.format) {
2469
3026
  platforms = options.format.split(",").map((f) => f.trim());
@@ -2482,26 +3039,31 @@ async function runInteractiveWizard(options, detected) {
2482
3039
  hint: chalk8.gray("\u2191\u2193 navigate \u2022 enter select")
2483
3040
  }, promptConfig);
2484
3041
  if (formatResponse.format === "multiple") {
3042
+ console.log();
3043
+ console.log(chalk8.gray(" Select the AI editors you want to generate config for:"));
2485
3044
  console.log();
2486
3045
  const platformResponse = await prompts4({
2487
3046
  type: "multiselect",
2488
3047
  name: "platforms",
2489
- message: chalk8.white("Select AI editors:"),
2490
- choices: PLATFORMS.map((p) => ({
2491
- title: p.title,
2492
- value: p.value
3048
+ message: chalk8.white("Select AI editors (16 supported):"),
3049
+ choices: ALL_PLATFORMS.map((p) => ({
3050
+ title: `${p.icon} ${p.name}`,
3051
+ value: p.id,
3052
+ description: chalk8.gray(p.note)
2493
3053
  })),
2494
3054
  hint: chalk8.gray("space select \u2022 a toggle all \u2022 enter confirm"),
2495
3055
  min: 1,
2496
3056
  instructions: false
2497
3057
  }, promptConfig);
2498
3058
  platforms = platformResponse.platforms || ["agents"];
3059
+ console.log(chalk8.green(` \u2713 Selected ${platforms.length} platform${platforms.length === 1 ? "" : "s"}`));
2499
3060
  } else {
2500
3061
  platforms = [formatResponse.format || "agents"];
2501
3062
  }
2502
3063
  }
2503
3064
  answers.platforms = platforms;
2504
- showStep(2, totalSteps, "Project Info");
3065
+ const projectStep = getCurrentStep("project");
3066
+ showStep(currentStepNum, projectStep, userTier);
2505
3067
  const nameResponse = await prompts4({
2506
3068
  type: "text",
2507
3069
  name: "name",
@@ -2518,18 +3080,30 @@ async function runInteractiveWizard(options, detected) {
2518
3080
  hint: chalk8.gray("optional - helps AI understand context")
2519
3081
  }, promptConfig);
2520
3082
  answers.description = descResponse.description || "";
2521
- showStep(3, totalSteps, "Tech Stack");
2522
- const allStackOptions = [...TECH_STACKS, ...FRAMEWORKS];
3083
+ const typeResponse = await prompts4({
3084
+ type: "select",
3085
+ name: "projectType",
3086
+ message: chalk8.white("Project type:"),
3087
+ choices: PROJECT_TYPES.map((t) => ({
3088
+ title: `${t.icon} ${t.label}`,
3089
+ value: t.id,
3090
+ description: chalk8.gray(t.description)
3091
+ })),
3092
+ initial: 0
3093
+ }, promptConfig);
3094
+ answers.projectType = typeResponse.projectType || "work";
3095
+ const techStep = getCurrentStep("tech");
3096
+ showStep(currentStepNum, techStep, userTier);
3097
+ const allStackOptions = [...LANGUAGES, ...FRAMEWORKS, ...DATABASES];
2523
3098
  const detectedStackSet = new Set(detected?.stack || []);
2524
- const preselected = allStackOptions.map((s, i) => detectedStackSet.has(s.value) ? i : -1).filter((i) => i !== -1);
2525
- if (preselected.length > 0) {
3099
+ if (detectedStackSet.size > 0) {
2526
3100
  console.log(chalk8.gray(` Auto-selected: ${detected?.stack?.join(", ")}`));
2527
3101
  console.log();
2528
3102
  }
2529
3103
  const stackResponse = await prompts4({
2530
3104
  type: "multiselect",
2531
3105
  name: "stack",
2532
- message: chalk8.white("Tech stack:"),
3106
+ message: chalk8.white("Languages, frameworks & databases:"),
2533
3107
  choices: allStackOptions.map((s) => ({
2534
3108
  title: s.title,
2535
3109
  value: s.value,
@@ -2539,52 +3113,370 @@ async function runInteractiveWizard(options, detected) {
2539
3113
  instructions: false
2540
3114
  }, promptConfig);
2541
3115
  answers.stack = stackResponse.stack || [];
2542
- showStep(4, totalSteps, "AI Persona");
3116
+ const repoStep = getCurrentStep("repo");
3117
+ showStep(currentStepNum, repoStep, userTier);
3118
+ const repoHostResponse = await prompts4({
3119
+ type: "select",
3120
+ name: "repoHost",
3121
+ message: chalk8.white("Repository host:"),
3122
+ choices: REPO_HOSTS.map((h) => ({
3123
+ title: `${h.icon} ${h.label}`,
3124
+ value: h.id
3125
+ })),
3126
+ initial: 0
3127
+ }, promptConfig);
3128
+ answers.repoHost = repoHostResponse.repoHost || "github";
3129
+ const visibilityResponse = await prompts4({
3130
+ type: "toggle",
3131
+ name: "isPublic",
3132
+ message: chalk8.white("Public repository?"),
3133
+ initial: false,
3134
+ active: "Yes",
3135
+ inactive: "No"
3136
+ }, promptConfig);
3137
+ answers.isPublic = visibilityResponse.isPublic || false;
3138
+ const licenseResponse = await prompts4({
3139
+ type: "select",
3140
+ name: "license",
3141
+ message: chalk8.white("License:"),
3142
+ choices: LICENSES.map((l) => ({
3143
+ title: l.label,
3144
+ value: l.id
3145
+ })),
3146
+ initial: 0
3147
+ }, promptConfig);
3148
+ answers.license = licenseResponse.license || "mit";
3149
+ const conventionalResponse = await prompts4({
3150
+ type: "toggle",
3151
+ name: "conventionalCommits",
3152
+ message: chalk8.white("Use Conventional Commits?"),
3153
+ initial: true,
3154
+ active: "Yes",
3155
+ inactive: "No"
3156
+ }, promptConfig);
3157
+ answers.conventionalCommits = conventionalResponse.conventionalCommits ?? true;
3158
+ if (canAccessTier(userTier, "intermediate")) {
3159
+ const commandsStep = getCurrentStep("commands");
3160
+ showStep(currentStepNum, commandsStep, userTier);
3161
+ console.log(chalk8.gray(" Select common commands for your project:"));
3162
+ console.log();
3163
+ const buildResponse = await prompts4({
3164
+ type: "multiselect",
3165
+ name: "build",
3166
+ message: chalk8.white("Build commands:"),
3167
+ choices: COMMON_COMMANDS.build.slice(0, 12).map((c) => ({
3168
+ title: chalk8.cyan(c),
3169
+ value: c,
3170
+ selected: detected?.commands?.build === c
3171
+ })),
3172
+ hint: chalk8.gray("space select \u2022 enter confirm"),
3173
+ instructions: false
3174
+ }, promptConfig);
3175
+ const testResponse = await prompts4({
3176
+ type: "multiselect",
3177
+ name: "test",
3178
+ message: chalk8.white("Test commands:"),
3179
+ choices: COMMON_COMMANDS.test.slice(0, 12).map((c) => ({
3180
+ title: chalk8.yellow(c),
3181
+ value: c,
3182
+ selected: detected?.commands?.test === c
3183
+ })),
3184
+ hint: chalk8.gray("space select \u2022 enter confirm"),
3185
+ instructions: false
3186
+ }, promptConfig);
3187
+ const lintResponse = await prompts4({
3188
+ type: "multiselect",
3189
+ name: "lint",
3190
+ message: chalk8.white("Lint/format commands:"),
3191
+ choices: COMMON_COMMANDS.lint.slice(0, 12).map((c) => ({
3192
+ title: chalk8.green(c),
3193
+ value: c,
3194
+ selected: detected?.commands?.lint === c
3195
+ })),
3196
+ hint: chalk8.gray("space select \u2022 enter confirm"),
3197
+ instructions: false
3198
+ }, promptConfig);
3199
+ const devResponse = await prompts4({
3200
+ type: "multiselect",
3201
+ name: "dev",
3202
+ message: chalk8.white("Dev server commands:"),
3203
+ choices: COMMON_COMMANDS.dev.slice(0, 12).map((c) => ({
3204
+ title: chalk8.magenta(c),
3205
+ value: c,
3206
+ selected: detected?.commands?.dev === c
3207
+ })),
3208
+ hint: chalk8.gray("space select \u2022 enter confirm"),
3209
+ instructions: false
3210
+ }, promptConfig);
3211
+ answers.commands = {
3212
+ build: buildResponse.build || [],
3213
+ test: testResponse.test || [],
3214
+ lint: lintResponse.lint || [],
3215
+ dev: devResponse.dev || []
3216
+ };
3217
+ const customCmdResponse = await prompts4({
3218
+ type: "text",
3219
+ name: "custom",
3220
+ message: chalk8.white("Additional custom command (optional):"),
3221
+ hint: chalk8.gray("e.g., npm run migrate, make deploy")
3222
+ }, promptConfig);
3223
+ if (customCmdResponse.custom) {
3224
+ answers.commands.custom = customCmdResponse.custom;
3225
+ }
3226
+ } else {
3227
+ answers.commands = detected?.commands || {};
3228
+ }
3229
+ if (canAccessTier(userTier, "intermediate")) {
3230
+ const styleStep = getCurrentStep("code_style");
3231
+ showStep(currentStepNum, styleStep, userTier);
3232
+ const namingResponse = await prompts4({
3233
+ type: "select",
3234
+ name: "naming",
3235
+ message: chalk8.white("Naming convention:"),
3236
+ choices: NAMING_CONVENTIONS.map((n) => ({
3237
+ title: n.label,
3238
+ value: n.id,
3239
+ description: chalk8.gray(n.desc)
3240
+ })),
3241
+ initial: 0
3242
+ }, promptConfig);
3243
+ answers.namingConvention = namingResponse.naming || "language_default";
3244
+ const errorResponse = await prompts4({
3245
+ type: "select",
3246
+ name: "errorHandling",
3247
+ message: chalk8.white("Error handling pattern:"),
3248
+ choices: ERROR_PATTERNS.map((e) => ({
3249
+ title: e.label,
3250
+ value: e.id
3251
+ })),
3252
+ initial: 0
3253
+ }, promptConfig);
3254
+ answers.errorHandling = errorResponse.errorHandling || "try_catch";
3255
+ const styleNotesResponse = await prompts4({
3256
+ type: "text",
3257
+ name: "styleNotes",
3258
+ message: chalk8.white("Additional style notes (optional):"),
3259
+ hint: chalk8.gray("e.g., prefer named exports, max line length 100")
3260
+ }, promptConfig);
3261
+ answers.styleNotes = styleNotesResponse.styleNotes || "";
3262
+ }
3263
+ const aiStep = getCurrentStep("ai");
3264
+ showStep(currentStepNum, aiStep, userTier);
3265
+ const aiBehaviorResponse = await prompts4({
3266
+ type: "multiselect",
3267
+ name: "aiBehavior",
3268
+ message: chalk8.white("AI behavior rules:"),
3269
+ choices: AI_BEHAVIOR_RULES.map((r) => ({
3270
+ title: r.recommended ? `${r.label} ${chalk8.green("\u2605")}` : r.label,
3271
+ value: r.id,
3272
+ selected: r.recommended
3273
+ })),
3274
+ hint: chalk8.gray("space select \u2022 enter confirm"),
3275
+ instructions: false
3276
+ }, promptConfig);
3277
+ answers.aiBehavior = aiBehaviorResponse.aiBehavior || [];
3278
+ const importantFilesResponse = await prompts4({
3279
+ type: "multiselect",
3280
+ name: "importantFiles",
3281
+ message: chalk8.white("Important files AI should read:"),
3282
+ choices: IMPORTANT_FILES.map((f) => ({
3283
+ title: `${f.icon} ${f.label}`,
3284
+ value: f.id,
3285
+ selected: f.id === "readme" || f.id === "package"
3286
+ })),
3287
+ hint: chalk8.gray("space select \u2022 enter confirm"),
3288
+ instructions: false
3289
+ }, promptConfig);
3290
+ answers.importantFiles = importantFilesResponse.importantFiles || [];
3291
+ const selfImproveResponse = await prompts4({
3292
+ type: "toggle",
3293
+ name: "selfImprove",
3294
+ message: chalk8.white("Enable self-improving blueprint?"),
3295
+ initial: false,
3296
+ active: "Yes",
3297
+ inactive: "No"
3298
+ }, promptConfig);
3299
+ answers.selfImprove = selfImproveResponse.selfImprove || false;
3300
+ if (canAccessTier(userTier, "advanced")) {
3301
+ const boundariesStep = getCurrentStep("boundaries");
3302
+ showStep(currentStepNum, boundariesStep, userTier);
3303
+ const presetResponse = await prompts4({
3304
+ type: "select",
3305
+ name: "boundaryPreset",
3306
+ message: chalk8.white("Boundary preset:"),
3307
+ choices: BOUNDARY_PRESETS.map((b) => ({
3308
+ title: b.title,
3309
+ value: b.value,
3310
+ description: chalk8.gray(b.description)
3311
+ })),
3312
+ initial: 0
3313
+ }, promptConfig);
3314
+ answers.boundaries = presetResponse.boundaryPreset || "standard";
3315
+ const selectedPreset = BOUNDARY_PRESETS.find((b) => b.value === answers.boundaries);
3316
+ if (selectedPreset) {
3317
+ console.log();
3318
+ console.log(chalk8.gray(" Preset details:"));
3319
+ console.log(chalk8.green(` \u2713 Always: ${selectedPreset.always.slice(0, 3).join(", ")}`));
3320
+ console.log(chalk8.yellow(` ? Ask: ${selectedPreset.askFirst.slice(0, 2).join(", ")}`));
3321
+ console.log(chalk8.red(` \u2717 Never: ${selectedPreset.never.slice(0, 2).join(", ")}`));
3322
+ }
3323
+ const customizeResponse = await prompts4({
3324
+ type: "toggle",
3325
+ name: "customize",
3326
+ message: chalk8.white("Customize specific boundaries?"),
3327
+ initial: false,
3328
+ active: "Yes",
3329
+ inactive: "No"
3330
+ }, promptConfig);
3331
+ if (customizeResponse.customize) {
3332
+ console.log();
3333
+ console.log(chalk8.gray(" Select actions AI should NEVER do:"));
3334
+ const neverResponse = await prompts4({
3335
+ type: "multiselect",
3336
+ name: "never",
3337
+ message: chalk8.white("Never allow:"),
3338
+ choices: BOUNDARY_OPTIONS.map((o) => ({
3339
+ title: chalk8.red(o),
3340
+ value: o,
3341
+ selected: selectedPreset?.never.includes(o)
3342
+ })),
3343
+ instructions: false
3344
+ }, promptConfig);
3345
+ answers.boundaryNever = neverResponse.never || [];
3346
+ console.log(chalk8.gray(" Select actions AI should ASK before doing:"));
3347
+ const askResponse = await prompts4({
3348
+ type: "multiselect",
3349
+ name: "ask",
3350
+ message: chalk8.white("Ask first:"),
3351
+ choices: BOUNDARY_OPTIONS.filter((o) => !answers.boundaryNever?.includes(o)).map((o) => ({
3352
+ title: chalk8.yellow(o),
3353
+ value: o,
3354
+ selected: selectedPreset?.askFirst.includes(o)
3355
+ })),
3356
+ instructions: false
3357
+ }, promptConfig);
3358
+ answers.boundaryAsk = askResponse.ask || [];
3359
+ }
3360
+ } else {
3361
+ answers.boundaries = options.boundaries || "standard";
3362
+ }
3363
+ if (canAccessTier(userTier, "advanced")) {
3364
+ const testingStep = getCurrentStep("testing");
3365
+ showStep(currentStepNum, testingStep, userTier);
3366
+ const testLevelsResponse = await prompts4({
3367
+ type: "multiselect",
3368
+ name: "testLevels",
3369
+ message: chalk8.white("Test levels:"),
3370
+ choices: TEST_LEVELS.map((l) => ({
3371
+ title: `${l.label} - ${chalk8.gray(l.desc)}`,
3372
+ value: l.id,
3373
+ selected: l.id === "unit" || l.id === "integration"
3374
+ })),
3375
+ instructions: false
3376
+ }, promptConfig);
3377
+ answers.testLevels = testLevelsResponse.testLevels || [];
3378
+ const detectedFrameworks = answers.stack?.includes("typescript") || answers.stack?.includes("javascript") ? ["jest", "vitest"] : answers.stack?.includes("python") ? ["pytest"] : [];
3379
+ const testFrameworkResponse = await prompts4({
3380
+ type: "multiselect",
3381
+ name: "testFrameworks",
3382
+ message: chalk8.white("Testing frameworks:"),
3383
+ choices: TEST_FRAMEWORKS.slice(0, 16).map((f) => ({
3384
+ title: f,
3385
+ value: f,
3386
+ selected: detectedFrameworks.includes(f)
3387
+ })),
3388
+ hint: chalk8.gray("space select \u2022 enter confirm"),
3389
+ instructions: false
3390
+ }, promptConfig);
3391
+ answers.testFrameworks = testFrameworkResponse.testFrameworks || [];
3392
+ const coverageResponse = await prompts4({
3393
+ type: "number",
3394
+ name: "coverage",
3395
+ message: chalk8.white("Target code coverage (%):"),
3396
+ initial: 80,
3397
+ min: 0,
3398
+ max: 100
3399
+ }, promptConfig);
3400
+ answers.coverageTarget = coverageResponse.coverage ?? 80;
3401
+ const testNotesResponse = await prompts4({
3402
+ type: "text",
3403
+ name: "testNotes",
3404
+ message: chalk8.white("Testing notes (optional):"),
3405
+ hint: chalk8.gray("e.g., run e2e on main only, use msw for mocking")
3406
+ }, promptConfig);
3407
+ answers.testNotes = testNotesResponse.testNotes || "";
3408
+ }
3409
+ if (canAccessTier(userTier, "advanced")) {
3410
+ const staticStep = getCurrentStep("static");
3411
+ showStep(currentStepNum, staticStep, userTier);
3412
+ console.log(chalk8.gray(" Generate additional project files:"));
3413
+ console.log();
3414
+ const staticFilesResponse = await prompts4({
3415
+ type: "multiselect",
3416
+ name: "staticFiles",
3417
+ message: chalk8.white("Include static files:"),
3418
+ choices: [
3419
+ { title: "\u{1F4DD} .editorconfig", value: "editorconfig", description: chalk8.gray("Consistent code formatting") },
3420
+ { title: "\u{1F91D} CONTRIBUTING.md", value: "contributing", description: chalk8.gray("Contributor guidelines") },
3421
+ { title: "\u{1F4DC} CODE_OF_CONDUCT.md", value: "codeOfConduct", description: chalk8.gray("Community standards") },
3422
+ { title: "\u{1F512} SECURITY.md", value: "security", description: chalk8.gray("Vulnerability reporting") },
3423
+ { title: "\u{1F5FA}\uFE0F ROADMAP.md", value: "roadmap", description: chalk8.gray("Project roadmap") },
3424
+ { title: "\u{1F4CB} .gitignore", value: "gitignore", description: chalk8.gray("Git ignore patterns"), selected: true }
3425
+ ],
3426
+ hint: chalk8.gray("space select \u2022 enter confirm"),
3427
+ instructions: false
3428
+ }, promptConfig);
3429
+ answers.staticFiles = staticFilesResponse.staticFiles || [];
3430
+ if (answers.repoHost === "github" && answers.isPublic) {
3431
+ const fundingResponse = await prompts4({
3432
+ type: "toggle",
3433
+ name: "funding",
3434
+ message: chalk8.white("Generate FUNDING.yml for GitHub Sponsors?"),
3435
+ initial: false,
3436
+ active: "Yes",
3437
+ inactive: "No"
3438
+ }, promptConfig);
3439
+ answers.includeFunding = fundingResponse.funding || false;
3440
+ }
3441
+ }
3442
+ const extraStep = getCurrentStep("extra");
3443
+ showStep(currentStepNum, extraStep, userTier);
2543
3444
  const personaResponse = await prompts4({
2544
3445
  type: "select",
2545
3446
  name: "persona",
2546
- message: chalk8.white("What role should the AI take?"),
2547
- choices: PERSONAS.map((p) => ({
2548
- title: p.title,
2549
- value: p.value,
2550
- description: chalk8.gray(p.description)
2551
- })),
2552
- initial: 0,
2553
- hint: chalk8.gray("\u2191\u2193 navigate \u2022 enter select")
3447
+ message: chalk8.white("AI assistant persona:"),
3448
+ choices: [
3449
+ { title: "\u{1F9D1}\u200D\u{1F4BB} Full-Stack Developer", value: "fullstack", description: chalk8.gray("Complete application development") },
3450
+ { title: "\u2699\uFE0F Backend Developer", value: "backend", description: chalk8.gray("APIs, databases, services") },
3451
+ { title: "\u{1F3A8} Frontend Developer", value: "frontend", description: chalk8.gray("UI, components, styling") },
3452
+ { title: "\u{1F680} DevOps Engineer", value: "devops", description: chalk8.gray("Infrastructure, CI/CD") },
3453
+ { title: "\u{1F4CA} Data Engineer", value: "data", description: chalk8.gray("Pipelines, ETL, analytics") },
3454
+ { title: "\u{1F512} Security Engineer", value: "security", description: chalk8.gray("Secure code, auditing") },
3455
+ { title: "\u270F\uFE0F Custom...", value: "custom", description: chalk8.gray("Define your own") }
3456
+ ],
3457
+ initial: 0
2554
3458
  }, promptConfig);
2555
3459
  if (personaResponse.persona === "custom") {
2556
3460
  const customPersona = await prompts4({
2557
3461
  type: "text",
2558
3462
  name: "value",
2559
3463
  message: chalk8.white("Describe the custom persona:"),
2560
- hint: chalk8.gray("e.g., 'ML engineer focused on PyTorch and data pipelines'")
3464
+ hint: chalk8.gray("e.g., 'ML engineer focused on PyTorch'")
2561
3465
  }, promptConfig);
2562
3466
  answers.persona = customPersona.value || "fullstack";
2563
3467
  } else {
2564
3468
  answers.persona = personaResponse.persona || "fullstack";
2565
3469
  }
2566
- showStep(5, totalSteps, "AI Boundaries");
2567
- const boundaryResponse = await prompts4({
2568
- type: "select",
2569
- name: "boundaries",
2570
- message: chalk8.white("How much freedom should the AI have?"),
2571
- choices: BOUNDARY_PRESETS.map((b) => ({
2572
- title: b.title,
2573
- value: b.value,
2574
- description: chalk8.gray(b.description)
2575
- })),
2576
- initial: 0,
2577
- hint: chalk8.gray("\u2191\u2193 navigate \u2022 enter select")
3470
+ const extraNotesResponse = await prompts4({
3471
+ type: "text",
3472
+ name: "extraNotes",
3473
+ message: chalk8.white("Anything else AI should know? (optional):"),
3474
+ hint: chalk8.gray("Special requirements, gotchas, team conventions...")
2578
3475
  }, promptConfig);
2579
- answers.boundaries = boundaryResponse.boundaries || "standard";
2580
- const selectedBoundary = BOUNDARY_PRESETS.find((b) => b.value === answers.boundaries);
2581
- if (selectedBoundary) {
2582
- console.log();
2583
- console.log(chalk8.gray(" Always allowed: ") + chalk8.green(selectedBoundary.always.slice(0, 2).join(", ")));
2584
- console.log(chalk8.gray(" Ask first: ") + chalk8.yellow(selectedBoundary.askFirst.slice(0, 2).join(", ")));
2585
- console.log(chalk8.gray(" Never: ") + chalk8.red(selectedBoundary.never.slice(0, 2).join(", ")));
2586
- }
2587
- answers.commands = detected?.commands || {};
3476
+ answers.extraNotes = extraNotesResponse.extraNotes || "";
3477
+ console.log();
3478
+ console.log(chalk8.green(" \u2705 All steps completed!"));
3479
+ console.log();
2588
3480
  return {
2589
3481
  name: answers.name,
2590
3482
  description: answers.description,
@@ -2592,7 +3484,28 @@ async function runInteractiveWizard(options, detected) {
2592
3484
  platforms: answers.platforms,
2593
3485
  persona: answers.persona,
2594
3486
  boundaries: answers.boundaries,
2595
- commands: answers.commands
3487
+ commands: typeof answers.commands === "object" ? answers.commands : detected?.commands || {},
3488
+ // Extended config for Pro/Max users
3489
+ projectType: answers.projectType,
3490
+ repoHost: answers.repoHost,
3491
+ isPublic: answers.isPublic,
3492
+ license: answers.license,
3493
+ conventionalCommits: answers.conventionalCommits,
3494
+ namingConvention: answers.namingConvention,
3495
+ errorHandling: answers.errorHandling,
3496
+ styleNotes: answers.styleNotes,
3497
+ aiBehavior: answers.aiBehavior,
3498
+ importantFiles: answers.importantFiles,
3499
+ selfImprove: answers.selfImprove,
3500
+ boundaryNever: answers.boundaryNever,
3501
+ boundaryAsk: answers.boundaryAsk,
3502
+ testLevels: answers.testLevels,
3503
+ testFrameworks: answers.testFrameworks,
3504
+ coverageTarget: answers.coverageTarget,
3505
+ testNotes: answers.testNotes,
3506
+ staticFiles: answers.staticFiles,
3507
+ includeFunding: answers.includeFunding,
3508
+ extraNotes: answers.extraNotes
2596
3509
  };
2597
3510
  }
2598
3511