archondev 2.5.0 → 2.6.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.
Files changed (2) hide show
  1. package/dist/index.js +118 -97
  2. package/package.json +1 -1
package/dist/index.js CHANGED
@@ -311,7 +311,7 @@ function formatDateTime(date) {
311
311
  // src/cli/start.ts
312
312
  import chalk5 from "chalk";
313
313
  import readline from "readline";
314
- import { existsSync as existsSync4, readFileSync as readFileSync2, readdirSync as readdirSync2, appendFileSync } from "fs";
314
+ import { existsSync as existsSync5, readFileSync as readFileSync2, readdirSync as readdirSync2, appendFileSync } from "fs";
315
315
  import { join as join5 } from "path";
316
316
 
317
317
  // src/core/context/manager.ts
@@ -880,21 +880,37 @@ async function runAutoCleanupCheck(cwd) {
880
880
 
881
881
  // src/cli/update-check.ts
882
882
  import chalk4 from "chalk";
883
- import { readFileSync } from "fs";
883
+ import { readFileSync, existsSync as existsSync4 } from "fs";
884
884
  import { join as join4, dirname as dirname3 } from "path";
885
885
  import { fileURLToPath } from "url";
886
+ import { execSync as execSync2 } from "child_process";
886
887
  var __dirname = dirname3(fileURLToPath(import.meta.url));
887
888
  var UPDATE_CHECK_INTERVAL_MS = 24 * 60 * 60 * 1e3;
888
889
  function getCurrentVersion() {
890
+ try {
891
+ const result = execSync2("npm list -g archondev --depth=0 --json 2>/dev/null", {
892
+ encoding: "utf-8",
893
+ timeout: 3e3,
894
+ stdio: ["pipe", "pipe", "pipe"]
895
+ });
896
+ const data = JSON.parse(result);
897
+ if (data.dependencies?.archondev?.version) {
898
+ return data.dependencies.archondev.version;
899
+ }
900
+ } catch {
901
+ }
889
902
  try {
890
903
  const paths = [
904
+ // From dist/ (when bundled - tsup puts files in dist/)
905
+ join4(__dirname, "package.json"),
906
+ join4(__dirname, "..", "package.json"),
907
+ // From dist/cli/ or src/cli/
891
908
  join4(__dirname, "..", "..", "package.json"),
892
- // from dist/
893
909
  join4(__dirname, "..", "..", "..", "package.json")
894
- // from src/cli/
895
910
  ];
896
911
  for (const pkgPath of paths) {
897
912
  try {
913
+ if (!existsSync4(pkgPath)) continue;
898
914
  const pkg = JSON.parse(readFileSync(pkgPath, "utf-8"));
899
915
  if (pkg.name === "archondev" && pkg.version) {
900
916
  return pkg.version;
@@ -903,10 +919,9 @@ function getCurrentVersion() {
903
919
  continue;
904
920
  }
905
921
  }
906
- return "0.0.0";
907
922
  } catch {
908
- return "0.0.0";
909
923
  }
924
+ return "0.0.0";
910
925
  }
911
926
  async function fetchLatestVersion() {
912
927
  try {
@@ -2581,7 +2596,7 @@ async function start(options = {}) {
2581
2596
  }
2582
2597
  }
2583
2598
  if (!config.tier || config.tier === "FREE") {
2584
- const isFirstRun = !existsSync4(join5(cwd, ".archon")) && !existsSync4(join5(cwd, "ARCHITECTURE.md"));
2599
+ const isFirstRun = !existsSync5(join5(cwd, ".archon")) && !existsSync5(join5(cwd, "ARCHITECTURE.md"));
2585
2600
  if (isFirstRun && !config.tierConfirmed) {
2586
2601
  console.log(chalk5.bold("How would you like to use ArchonDev?\n"));
2587
2602
  const selection = await promptTierSelection();
@@ -2603,7 +2618,13 @@ async function start(options = {}) {
2603
2618
  }
2604
2619
  }
2605
2620
  }
2606
- console.log(chalk5.dim(`Tier: ${formatTierName(config.tier || "FREE")}`));
2621
+ if (config.email) {
2622
+ console.log(chalk5.dim(`Logged in as: ${config.email}`));
2623
+ }
2624
+ const currentTier = config.tier || "FREE";
2625
+ const tierDisplay = formatTierName(currentTier);
2626
+ const upgradeHint = currentTier === "FREE" ? chalk5.dim(" \u2014 Run `archon pricing` to upgrade") : "";
2627
+ console.log(chalk5.dim(`Tier: `) + tierDisplay + upgradeHint);
2607
2628
  console.log();
2608
2629
  const updateResult = await updateCheckPromise;
2609
2630
  if (updateResult?.hasUpdate) {
@@ -2689,7 +2710,7 @@ function detectProjectState(cwd) {
2689
2710
  const sourceExtensions = [".ts", ".tsx", ".js", ".jsx", ".py", ".go", ".rs", ".java", ".rb", ".php"];
2690
2711
  let hasSourceFiles = false;
2691
2712
  for (const dir of sourceDirs) {
2692
- if (existsSync4(join5(cwd, dir))) {
2713
+ if (existsSync5(join5(cwd, dir))) {
2693
2714
  hasSourceFiles = true;
2694
2715
  break;
2695
2716
  }
@@ -2705,11 +2726,11 @@ function detectProjectState(cwd) {
2705
2726
  }
2706
2727
  const projectMarkers = ["package.json", "Cargo.toml", "pyproject.toml", "go.mod", "pom.xml", "build.gradle"];
2707
2728
  if (!hasSourceFiles) {
2708
- hasSourceFiles = projectMarkers.some((marker) => existsSync4(join5(cwd, marker)));
2729
+ hasSourceFiles = projectMarkers.some((marker) => existsSync5(join5(cwd, marker)));
2709
2730
  }
2710
- const hasArchitecture = existsSync4(join5(cwd, "ARCHITECTURE.md"));
2711
- const hasProgress = existsSync4(join5(cwd, "progress.txt"));
2712
- const hasReviewDb = existsSync4(join5(cwd, "docs", "code-review", "review-tasks.db"));
2731
+ const hasArchitecture = existsSync5(join5(cwd, "ARCHITECTURE.md"));
2732
+ const hasProgress = existsSync5(join5(cwd, "progress.txt"));
2733
+ const hasReviewDb = existsSync5(join5(cwd, "docs", "code-review", "review-tasks.db"));
2713
2734
  let hasProgressEntries = false;
2714
2735
  let lastProgressEntry;
2715
2736
  if (hasProgress) {
@@ -2754,7 +2775,7 @@ async function gatherGovernanceStatus(cwd) {
2754
2775
  pendingAtomsCount: 0
2755
2776
  };
2756
2777
  const archPath = join5(cwd, "ARCHITECTURE.md");
2757
- if (existsSync4(archPath)) {
2778
+ if (existsSync5(archPath)) {
2758
2779
  const parser = new ArchitectureParser(archPath);
2759
2780
  const result = await parser.parse();
2760
2781
  if (result.success && result.schema) {
@@ -2772,7 +2793,7 @@ async function gatherGovernanceStatus(cwd) {
2772
2793
  }
2773
2794
  }
2774
2795
  const progressPath = join5(cwd, "progress.txt");
2775
- if (existsSync4(progressPath)) {
2796
+ if (existsSync5(progressPath)) {
2776
2797
  try {
2777
2798
  const content = readFileSync2(progressPath, "utf-8");
2778
2799
  const dateMatches = content.match(/^## (\d{4}-\d{2}-\d{2})/gm);
@@ -2787,7 +2808,7 @@ async function gatherGovernanceStatus(cwd) {
2787
2808
  }
2788
2809
  }
2789
2810
  const atomsDir = join5(cwd, ".archon", "atoms");
2790
- if (existsSync4(atomsDir)) {
2811
+ if (existsSync5(atomsDir)) {
2791
2812
  try {
2792
2813
  const files = readdirSync2(atomsDir);
2793
2814
  status2.pendingAtomsCount = files.filter((f) => f.endsWith(".yaml") || f.endsWith(".yml")).length;
@@ -3009,7 +3030,7 @@ ${state.forbiddenPatterns?.length ? `- **Forbidden patterns:** ${state.forbidden
3009
3030
  - Ready for first atom
3010
3031
  `;
3011
3032
  const progressPath = join5(cwd, "progress.txt");
3012
- if (!existsSync4(progressPath)) {
3033
+ if (!existsSync5(progressPath)) {
3013
3034
  const { writeFileSync: writeFileSync2 } = await import("fs");
3014
3035
  writeFileSync2(progressPath, "# ArchonDev Progress Log\n\nThis file tracks learnings and decisions across sessions.\n");
3015
3036
  }
@@ -3039,7 +3060,7 @@ ${state.forbiddenPatterns?.length ? `- **Forbidden patterns:** ${state.forbidden
3039
3060
  async function quickStart(cwd) {
3040
3061
  const today = (/* @__PURE__ */ new Date()).toISOString().split("T")[0];
3041
3062
  const progressPath = join5(cwd, "progress.txt");
3042
- if (!existsSync4(progressPath)) {
3063
+ if (!existsSync5(progressPath)) {
3043
3064
  const { writeFileSync: writeFileSync2 } = await import("fs");
3044
3065
  writeFileSync2(progressPath, `# ArchonDev Progress Log
3045
3066
 
@@ -3098,7 +3119,7 @@ async function analyzeAndAdapt(cwd) {
3098
3119
  await init2({ analyze: true, git: true });
3099
3120
  const today = (/* @__PURE__ */ new Date()).toISOString().split("T")[0];
3100
3121
  const progressPath = join5(cwd, "progress.txt");
3101
- if (!existsSync4(progressPath)) {
3122
+ if (!existsSync5(progressPath)) {
3102
3123
  const { writeFileSync: writeFileSync2 } = await import("fs");
3103
3124
  writeFileSync2(progressPath, "# ArchonDev Progress Log\n\nThis file tracks learnings and decisions across sessions.\n");
3104
3125
  }
@@ -3123,7 +3144,7 @@ async function codeReviewFirst(cwd) {
3123
3144
  console.log(chalk5.dim("I'll analyze your code for issues without making any changes.\n"));
3124
3145
  const { reviewInit: reviewInit2, reviewAnalyze: reviewAnalyze2, reviewRun: reviewRun2 } = await import("./review-XDUNVTOK.js");
3125
3146
  const reviewDbPath = join5(cwd, "docs", "code-review", "review-tasks.db");
3126
- if (!existsSync4(reviewDbPath)) {
3147
+ if (!existsSync5(reviewDbPath)) {
3127
3148
  await reviewInit2();
3128
3149
  }
3129
3150
  await reviewAnalyze2();
@@ -3151,7 +3172,7 @@ async function quickAdapt(cwd) {
3151
3172
  await init2({ analyze: true, git: true });
3152
3173
  const today = (/* @__PURE__ */ new Date()).toISOString().split("T")[0];
3153
3174
  const progressPath = join5(cwd, "progress.txt");
3154
- if (!existsSync4(progressPath)) {
3175
+ if (!existsSync5(progressPath)) {
3155
3176
  const { writeFileSync: writeFileSync2 } = await import("fs");
3156
3177
  writeFileSync2(progressPath, "# ArchonDev Progress Log\n\nThis file tracks learnings and decisions across sessions.\n");
3157
3178
  }
@@ -3189,7 +3210,7 @@ async function handleContinueSession(cwd, state) {
3189
3210
  function checkForHandoff(cwd) {
3190
3211
  try {
3191
3212
  const progressPath = join5(cwd, "progress.txt");
3192
- if (!existsSync4(progressPath)) return null;
3213
+ if (!existsSync5(progressPath)) return null;
3193
3214
  const content = readFileSync2(progressPath, "utf-8");
3194
3215
  const handoffMatch = content.match(/## Context Handoff[^\n]*\n([\s\S]*?)(?=\n## |\n*$)/);
3195
3216
  if (handoffMatch && handoffMatch[1]) {
@@ -3320,7 +3341,7 @@ async function settingsMenu() {
3320
3341
  async function reviewCode() {
3321
3342
  const cwd = process.cwd();
3322
3343
  const reviewDbPath = join5(cwd, "docs", "code-review", "review-tasks.db");
3323
- if (!existsSync4(reviewDbPath)) {
3344
+ if (!existsSync5(reviewDbPath)) {
3324
3345
  console.log(chalk5.dim("Code review not initialized. Starting setup...\n"));
3325
3346
  const { reviewInit: reviewInit2 } = await import("./review-XDUNVTOK.js");
3326
3347
  await reviewInit2();
@@ -3996,7 +4017,7 @@ async function watch() {
3996
4017
  import { Command } from "commander";
3997
4018
  import chalk7 from "chalk";
3998
4019
  import { readFile as readFile4, writeFile as writeFile4 } from "fs/promises";
3999
- import { existsSync as existsSync6 } from "fs";
4020
+ import { existsSync as existsSync7 } from "fs";
4000
4021
  var DEPENDENCIES_FILENAME = "DEPENDENCIES.md";
4001
4022
  function createDepsCommand() {
4002
4023
  const deps = new Command("deps").description("Manage file-level dependencies (DEPENDENCIES.md)").addHelpText(
@@ -4146,7 +4167,7 @@ ${yaml3}---${markdownBody}`, "utf-8");
4146
4167
  }
4147
4168
  });
4148
4169
  deps.command("init").description("Create a starter DEPENDENCIES.md file").action(async () => {
4149
- if (existsSync6(DEPENDENCIES_FILENAME)) {
4170
+ if (existsSync7(DEPENDENCIES_FILENAME)) {
4150
4171
  console.log(chalk7.yellow("DEPENDENCIES.md already exists."));
4151
4172
  return;
4152
4173
  }
@@ -4233,7 +4254,7 @@ function generateYamlFrontmatter(rules) {
4233
4254
 
4234
4255
  // src/cli/a11y.ts
4235
4256
  import chalk8 from "chalk";
4236
- import { existsSync as existsSync7 } from "fs";
4257
+ import { existsSync as existsSync8 } from "fs";
4237
4258
  import { readFile as readFile5, writeFile as writeFile5, mkdir as mkdir3 } from "fs/promises";
4238
4259
  import { join as join7 } from "path";
4239
4260
  import { createInterface } from "readline";
@@ -4367,7 +4388,7 @@ async function a11yCheck(options) {
4367
4388
  passed: issues.length === 0
4368
4389
  };
4369
4390
  const archonDir = join7(process.cwd(), ".archon");
4370
- if (!existsSync7(archonDir)) {
4391
+ if (!existsSync8(archonDir)) {
4371
4392
  await mkdir3(archonDir, { recursive: true });
4372
4393
  }
4373
4394
  await writeFile5(join7(archonDir, "a11y-report.json"), JSON.stringify(report, null, 2));
@@ -4421,7 +4442,7 @@ async function a11yFix(options) {
4421
4442
  try {
4422
4443
  console.log(chalk8.blue("\n\u267F Accessibility Auto-Fix\n"));
4423
4444
  const reportPath = join7(process.cwd(), ".archon/a11y-report.json");
4424
- if (!existsSync7(reportPath)) {
4445
+ if (!existsSync8(reportPath)) {
4425
4446
  console.log(chalk8.yellow("No accessibility report found. Running check first...\n"));
4426
4447
  await a11yCheck({});
4427
4448
  }
@@ -4538,7 +4559,7 @@ async function a11yPreDeploy() {
4538
4559
  console.log(chalk8.dim("Before deploying a live website, accessibility compliance is required.\n"));
4539
4560
  await a11yCheck({});
4540
4561
  const reportPath = join7(process.cwd(), ".archon/a11y-report.json");
4541
- if (!existsSync7(reportPath)) {
4562
+ if (!existsSync8(reportPath)) {
4542
4563
  return false;
4543
4564
  }
4544
4565
  const reportContent = await readFile5(reportPath, "utf-8");
@@ -4576,7 +4597,7 @@ async function a11yPreDeploy() {
4576
4597
  import { Command as Command2 } from "commander";
4577
4598
  import chalk9 from "chalk";
4578
4599
  import { readFile as readFile6, writeFile as writeFile6, mkdir as mkdir4 } from "fs/promises";
4579
- import { existsSync as existsSync8 } from "fs";
4600
+ import { existsSync as existsSync9 } from "fs";
4580
4601
  import { join as join8 } from "path";
4581
4602
  import { createInterface as createInterface2 } from "readline";
4582
4603
  import { glob as glob2 } from "glob";
@@ -4596,7 +4617,7 @@ function createPrompt2() {
4596
4617
  }
4597
4618
  async function loadGeoConfig(cwd) {
4598
4619
  const configPath = join8(cwd, CONFIG_PATH2);
4599
- if (!existsSync8(configPath)) {
4620
+ if (!existsSync9(configPath)) {
4600
4621
  return {};
4601
4622
  }
4602
4623
  try {
@@ -4609,11 +4630,11 @@ async function loadGeoConfig(cwd) {
4609
4630
  async function saveGeoConfig(cwd, config) {
4610
4631
  const configPath = join8(cwd, CONFIG_PATH2);
4611
4632
  const archonDir = join8(cwd, ".archon");
4612
- if (!existsSync8(archonDir)) {
4633
+ if (!existsSync9(archonDir)) {
4613
4634
  await mkdir4(archonDir, { recursive: true });
4614
4635
  }
4615
4636
  let existing = {};
4616
- if (existsSync8(configPath)) {
4637
+ if (existsSync9(configPath)) {
4617
4638
  try {
4618
4639
  const content = await readFile6(configPath, "utf-8");
4619
4640
  existing = yaml2.parse(content);
@@ -4786,7 +4807,7 @@ async function geoSchema(options) {
4786
4807
  let orgName = identityPhrase.split(" ").slice(0, 2).join(" ");
4787
4808
  try {
4788
4809
  const pkgPath = join8(cwd, "package.json");
4789
- if (existsSync8(pkgPath)) {
4810
+ if (existsSync9(pkgPath)) {
4790
4811
  const pkg = JSON.parse(await readFile6(pkgPath, "utf-8"));
4791
4812
  if (pkg.name) {
4792
4813
  orgName = pkg.name.replace(/-/g, " ").replace(/^\w/, (c) => c.toUpperCase());
@@ -5052,7 +5073,7 @@ Examples:
5052
5073
  import { Command as Command3 } from "commander";
5053
5074
  import chalk10 from "chalk";
5054
5075
  import { readFile as readFile7, writeFile as writeFile7, mkdir as mkdir5 } from "fs/promises";
5055
- import { existsSync as existsSync9 } from "fs";
5076
+ import { existsSync as existsSync10 } from "fs";
5056
5077
  import { join as join9 } from "path";
5057
5078
  import { createInterface as createInterface3 } from "readline";
5058
5079
  import { glob as glob3 } from "glob";
@@ -5211,7 +5232,7 @@ async function seoCheck(options) {
5211
5232
  `));
5212
5233
  const issues = await scanForSeoIssues(files);
5213
5234
  const archonDir = join9(process.cwd(), ".archon");
5214
- if (!existsSync9(archonDir)) {
5235
+ if (!existsSync10(archonDir)) {
5215
5236
  await mkdir5(archonDir, { recursive: true });
5216
5237
  }
5217
5238
  const report = {
@@ -5265,7 +5286,7 @@ async function seoFix(options) {
5265
5286
  try {
5266
5287
  console.log(chalk10.blue("\n\u{1F527} SEO Auto-Fix\n"));
5267
5288
  const reportPath = join9(process.cwd(), ".archon/seo-report.json");
5268
- if (!existsSync9(reportPath)) {
5289
+ if (!existsSync10(reportPath)) {
5269
5290
  console.log(chalk10.yellow("No SEO report found. Running check first...\n"));
5270
5291
  await seoCheck({});
5271
5292
  }
@@ -5371,7 +5392,7 @@ async function seoOpenGraph(options) {
5371
5392
  targetFile = fileChoice.startsWith("/") ? fileChoice : join9(process.cwd(), fileChoice);
5372
5393
  }
5373
5394
  }
5374
- if (!existsSync9(targetFile)) {
5395
+ if (!existsSync10(targetFile)) {
5375
5396
  console.log(chalk10.red(`File not found: ${targetFile}`));
5376
5397
  return;
5377
5398
  }
@@ -5435,7 +5456,7 @@ async function seoTwitter(options) {
5435
5456
  targetFile = fileChoice.startsWith("/") ? fileChoice : join9(process.cwd(), fileChoice);
5436
5457
  }
5437
5458
  }
5438
- if (!existsSync9(targetFile)) {
5459
+ if (!existsSync10(targetFile)) {
5439
5460
  console.log(chalk10.red(`File not found: ${targetFile}`));
5440
5461
  return;
5441
5462
  }
@@ -5528,7 +5549,7 @@ import chalk11 from "chalk";
5528
5549
  import ora2 from "ora";
5529
5550
  import os from "os";
5530
5551
  import { readFile as readFile8, writeFile as writeFile8 } from "fs/promises";
5531
- import { existsSync as existsSync10 } from "fs";
5552
+ import { existsSync as existsSync11 } from "fs";
5532
5553
  import { join as join10 } from "path";
5533
5554
  import { createClient as createClient2 } from "@supabase/supabase-js";
5534
5555
  function getSupabaseClient2(accessToken) {
@@ -5543,21 +5564,21 @@ async function getProjectInfo(cwd) {
5543
5564
  const archonConfigPath = join10(cwd, ".archon", "config.yaml");
5544
5565
  const packageJsonPath = join10(cwd, "package.json");
5545
5566
  let projectName = "Unknown Project";
5546
- if (existsSync10(packageJsonPath)) {
5567
+ if (existsSync11(packageJsonPath)) {
5547
5568
  try {
5548
5569
  const pkg = JSON.parse(await readFile8(packageJsonPath, "utf-8"));
5549
5570
  projectName = pkg.name || projectName;
5550
5571
  } catch {
5551
5572
  }
5552
5573
  }
5553
- if (!existsSync10(archonConfigPath)) {
5574
+ if (!existsSync11(archonConfigPath)) {
5554
5575
  return null;
5555
5576
  }
5556
5577
  return { name: projectName, path: cwd };
5557
5578
  }
5558
5579
  async function getCurrentAtomId(cwd) {
5559
5580
  const stateFile = join10(cwd, ".archon", "state.json");
5560
- if (!existsSync10(stateFile)) return null;
5581
+ if (!existsSync11(stateFile)) return null;
5561
5582
  try {
5562
5583
  const state = JSON.parse(await readFile8(stateFile, "utf-8"));
5563
5584
  return state.currentAtomId || null;
@@ -5567,7 +5588,7 @@ async function getCurrentAtomId(cwd) {
5567
5588
  }
5568
5589
  async function getPendingAtoms(cwd) {
5569
5590
  const stateFile = join10(cwd, ".archon", "state.json");
5570
- if (!existsSync10(stateFile)) return [];
5591
+ if (!existsSync11(stateFile)) return [];
5571
5592
  try {
5572
5593
  const state = JSON.parse(await readFile8(stateFile, "utf-8"));
5573
5594
  return state.pendingAtoms || [];
@@ -5576,7 +5597,7 @@ async function getPendingAtoms(cwd) {
5576
5597
  }
5577
5598
  }
5578
5599
  async function getFileContent(path2) {
5579
- if (!existsSync10(path2)) return null;
5600
+ if (!existsSync11(path2)) return null;
5580
5601
  try {
5581
5602
  return await readFile8(path2, "utf-8");
5582
5603
  } catch {
@@ -5740,7 +5761,7 @@ async function syncSession() {
5740
5761
  return;
5741
5762
  }
5742
5763
  const stateFile = join10(cwd, ".archon", "state.json");
5743
- if (!existsSync10(stateFile)) {
5764
+ if (!existsSync11(stateFile)) {
5744
5765
  spinner.info("No active session to sync");
5745
5766
  return;
5746
5767
  }
@@ -5775,16 +5796,16 @@ async function syncSession() {
5775
5796
 
5776
5797
  // src/cli/deploy.ts
5777
5798
  import chalk12 from "chalk";
5778
- import { existsSync as existsSync11 } from "fs";
5799
+ import { existsSync as existsSync12 } from "fs";
5779
5800
  import { join as join11 } from "path";
5780
- import { execSync as execSync2 } from "child_process";
5801
+ import { execSync as execSync3 } from "child_process";
5781
5802
  function detectPlatform(cwd) {
5782
- if (existsSync11(join11(cwd, "fly.toml"))) return "fly";
5783
- if (existsSync11(join11(cwd, "vercel.json"))) return "vercel";
5784
- if (existsSync11(join11(cwd, "netlify.toml"))) return "netlify";
5785
- if (existsSync11(join11(cwd, "railway.json"))) return "railway";
5786
- if (existsSync11(join11(cwd, "render.yaml"))) return "render";
5787
- if (existsSync11(join11(cwd, "Dockerfile"))) return "fly";
5803
+ if (existsSync12(join11(cwd, "fly.toml"))) return "fly";
5804
+ if (existsSync12(join11(cwd, "vercel.json"))) return "vercel";
5805
+ if (existsSync12(join11(cwd, "netlify.toml"))) return "netlify";
5806
+ if (existsSync12(join11(cwd, "railway.json"))) return "railway";
5807
+ if (existsSync12(join11(cwd, "render.yaml"))) return "render";
5808
+ if (existsSync12(join11(cwd, "Dockerfile"))) return "fly";
5788
5809
  return "unknown";
5789
5810
  }
5790
5811
  async function deploy(options) {
@@ -5799,23 +5820,23 @@ async function deploy(options) {
5799
5820
  switch (platform) {
5800
5821
  case "fly":
5801
5822
  console.log(chalk12.blue("Deploying to Fly.io..."));
5802
- execSync2("fly deploy", { cwd, stdio: "inherit" });
5823
+ execSync3("fly deploy", { cwd, stdio: "inherit" });
5803
5824
  break;
5804
5825
  case "vercel": {
5805
5826
  console.log(chalk12.blue("Deploying to Vercel..."));
5806
5827
  const cmd = options.preview ? "vercel" : "vercel --prod";
5807
- execSync2(cmd, { cwd, stdio: "inherit" });
5828
+ execSync3(cmd, { cwd, stdio: "inherit" });
5808
5829
  break;
5809
5830
  }
5810
5831
  case "netlify": {
5811
5832
  console.log(chalk12.blue("Deploying to Netlify..."));
5812
5833
  const netlifyCmd = options.preview ? "netlify deploy" : "netlify deploy --prod";
5813
- execSync2(netlifyCmd, { cwd, stdio: "inherit" });
5834
+ execSync3(netlifyCmd, { cwd, stdio: "inherit" });
5814
5835
  break;
5815
5836
  }
5816
5837
  case "railway":
5817
5838
  console.log(chalk12.blue("Deploying to Railway..."));
5818
- execSync2("railway up", { cwd, stdio: "inherit" });
5839
+ execSync3("railway up", { cwd, stdio: "inherit" });
5819
5840
  break;
5820
5841
  case "render":
5821
5842
  console.log(chalk12.blue("Deploying to Render..."));
@@ -5831,7 +5852,7 @@ async function deploy(options) {
5831
5852
  import chalk13 from "chalk";
5832
5853
 
5833
5854
  // src/core/indexing/local.ts
5834
- import { existsSync as existsSync12, mkdirSync } from "fs";
5855
+ import { existsSync as existsSync13, mkdirSync } from "fs";
5835
5856
  import { readFile as readFile9 } from "fs/promises";
5836
5857
  import { join as join12, extname } from "path";
5837
5858
  import Database from "better-sqlite3";
@@ -5881,7 +5902,7 @@ var LocalIndexer = class {
5881
5902
  }
5882
5903
  async init(cwd) {
5883
5904
  const archonDir = join12(cwd, ".archon");
5884
- if (!existsSync12(archonDir)) {
5905
+ if (!existsSync13(archonDir)) {
5885
5906
  mkdirSync(archonDir, { recursive: true });
5886
5907
  }
5887
5908
  this.db = new Database(join12(cwd, this.config.dbPath));
@@ -5935,7 +5956,7 @@ var LocalIndexer = class {
5935
5956
  return 0;
5936
5957
  }
5937
5958
  const fullPath = join12(cwd, filePath);
5938
- if (!existsSync12(fullPath)) {
5959
+ if (!existsSync13(fullPath)) {
5939
5960
  return 0;
5940
5961
  }
5941
5962
  const content = await readFile9(fullPath, "utf-8");
@@ -6017,7 +6038,7 @@ var LocalIndexer = class {
6017
6038
  // src/core/indexing/cloud.ts
6018
6039
  import { createClient as createClient3 } from "@supabase/supabase-js";
6019
6040
  import { readFile as readFile10 } from "fs/promises";
6020
- import { existsSync as existsSync13 } from "fs";
6041
+ import { existsSync as existsSync14 } from "fs";
6021
6042
  import { join as join13, extname as extname2 } from "path";
6022
6043
  import { createHash as createHash2 } from "crypto";
6023
6044
  var CHUNK_SIZE2 = 1e3;
@@ -6146,7 +6167,7 @@ var CloudIndexer = class {
6146
6167
  return 0;
6147
6168
  }
6148
6169
  const fullPath = join13(cwd, filePath);
6149
- if (!existsSync13(fullPath)) {
6170
+ if (!existsSync14(fullPath)) {
6150
6171
  return 0;
6151
6172
  }
6152
6173
  const content = await readFile10(fullPath, "utf-8");
@@ -6596,7 +6617,7 @@ async function githubDisconnect() {
6596
6617
  import chalk15 from "chalk";
6597
6618
  import readline2 from "readline";
6598
6619
  import ora3 from "ora";
6599
- import { existsSync as existsSync14, readFileSync as readFileSync4, writeFileSync, mkdirSync as mkdirSync2 } from "fs";
6620
+ import { existsSync as existsSync15, readFileSync as readFileSync4, writeFileSync, mkdirSync as mkdirSync2 } from "fs";
6600
6621
  import { join as join15 } from "path";
6601
6622
  import { randomUUID } from "crypto";
6602
6623
  function getConstitutionPath(cwd) {
@@ -6608,14 +6629,14 @@ function getDraftPath(cwd) {
6608
6629
  async function interview(options = {}) {
6609
6630
  const cwd = process.cwd();
6610
6631
  const archonDir = join15(cwd, ".archon");
6611
- if (!existsSync14(archonDir)) {
6632
+ if (!existsSync15(archonDir)) {
6612
6633
  mkdirSync2(archonDir, { recursive: true });
6613
6634
  }
6614
6635
  console.log(chalk15.bold("\n\u{1F3AF} ArchonDev Project Interview"));
6615
6636
  console.log(chalk15.dim("Let's define what you're building.\n"));
6616
6637
  const constitutionPath = getConstitutionPath(cwd);
6617
6638
  const draftPath = getDraftPath(cwd);
6618
- if (existsSync14(constitutionPath)) {
6639
+ if (existsSync15(constitutionPath)) {
6619
6640
  const existing = deserializeConstitution(readFileSync4(constitutionPath, "utf-8"));
6620
6641
  if (existing.state === "FROZEN") {
6621
6642
  console.log(chalk15.yellow("[!] A frozen Constitution already exists."));
@@ -6634,7 +6655,7 @@ async function interview(options = {}) {
6634
6655
  }
6635
6656
  let constitution;
6636
6657
  let startPhase = 1;
6637
- if (existsSync14(draftPath) && options.resume !== false) {
6658
+ if (existsSync15(draftPath) && options.resume !== false) {
6638
6659
  const draft = deserializeConstitution(readFileSync4(draftPath, "utf-8"));
6639
6660
  console.log(chalk15.blue("[i] Found draft from previous session."));
6640
6661
  console.log(chalk15.dim(` Project: ${draft.branding.projectName || "(unnamed)"}`));
@@ -6789,7 +6810,7 @@ async function interview(options = {}) {
6789
6810
  try {
6790
6811
  const frozen = freezeConstitution(constitution);
6791
6812
  writeFileSync(constitutionPath, serializeConstitution(frozen));
6792
- if (existsSync14(draftPath)) {
6813
+ if (existsSync15(draftPath)) {
6793
6814
  const { unlinkSync } = await import("fs");
6794
6815
  unlinkSync(draftPath);
6795
6816
  }
@@ -6892,10 +6913,10 @@ async function showConstitution() {
6892
6913
  const cwd = process.cwd();
6893
6914
  const constitutionPath = getConstitutionPath(cwd);
6894
6915
  const draftPath = getDraftPath(cwd);
6895
- if (existsSync14(constitutionPath)) {
6916
+ if (existsSync15(constitutionPath)) {
6896
6917
  const constitution = deserializeConstitution(readFileSync4(constitutionPath, "utf-8"));
6897
6918
  console.log(summarizeConstitution(constitution));
6898
- } else if (existsSync14(draftPath)) {
6919
+ } else if (existsSync15(draftPath)) {
6899
6920
  const draft = deserializeConstitution(readFileSync4(draftPath, "utf-8"));
6900
6921
  console.log(chalk15.yellow("[DRAFT]"));
6901
6922
  console.log(summarizeConstitution(draft));
@@ -6907,8 +6928,8 @@ async function validateConstitutionCommand() {
6907
6928
  const cwd = process.cwd();
6908
6929
  const constitutionPath = getConstitutionPath(cwd);
6909
6930
  const draftPath = getDraftPath(cwd);
6910
- const path2 = existsSync14(constitutionPath) ? constitutionPath : draftPath;
6911
- if (!existsSync14(path2)) {
6931
+ const path2 = existsSync15(constitutionPath) ? constitutionPath : draftPath;
6932
+ if (!existsSync15(path2)) {
6912
6933
  console.log(chalk15.dim("No Constitution found. Run `archon interview` to create one."));
6913
6934
  return;
6914
6935
  }
@@ -6932,7 +6953,7 @@ async function validateConstitutionCommand() {
6932
6953
  async function exportConstitution(format) {
6933
6954
  const cwd = process.cwd();
6934
6955
  const constitutionPath = getConstitutionPath(cwd);
6935
- if (!existsSync14(constitutionPath)) {
6956
+ if (!existsSync15(constitutionPath)) {
6936
6957
  console.log(chalk15.dim("No frozen Constitution found."));
6937
6958
  return;
6938
6959
  }
@@ -6952,7 +6973,7 @@ async function exportConstitution(format) {
6952
6973
  async function generateAtoms(options = {}) {
6953
6974
  const cwd = process.cwd();
6954
6975
  const constitutionPath = getConstitutionPath(cwd);
6955
- if (!existsSync14(constitutionPath)) {
6976
+ if (!existsSync15(constitutionPath)) {
6956
6977
  console.log(chalk15.red("No frozen Constitution found."));
6957
6978
  console.log(chalk15.dim("Run `archon interview` to create one first."));
6958
6979
  return;
@@ -6983,7 +7004,7 @@ async function generateAtoms(options = {}) {
6983
7004
  }
6984
7005
  const prdPath = options.output ?? join15(cwd, "prd.json");
6985
7006
  const prdContent = formatAsPrdJson(result, constitution);
6986
- if (existsSync14(prdPath)) {
7007
+ if (existsSync15(prdPath)) {
6987
7008
  const overwrite = await promptYesNo2("prd.json already exists. Overwrite?", false);
6988
7009
  if (!overwrite) {
6989
7010
  console.log(chalk15.dim("Cancelled. Existing prd.json preserved."));
@@ -7003,7 +7024,7 @@ async function generateAtoms(options = {}) {
7003
7024
 
7004
7025
  // src/cli/eject.ts
7005
7026
  import chalk16 from "chalk";
7006
- import { existsSync as existsSync15, rmSync } from "fs";
7027
+ import { existsSync as existsSync16, rmSync } from "fs";
7007
7028
  import { readFile as readFile11, writeFile as writeFile9 } from "fs/promises";
7008
7029
  import { join as join16 } from "path";
7009
7030
  import readline3 from "readline";
@@ -7021,7 +7042,7 @@ async function eject(options = {}) {
7021
7042
  const cwd = process.cwd();
7022
7043
  console.log(chalk16.blue("\n\u{1F680} ArchonDev Eject\n"));
7023
7044
  const archonDir = join16(cwd, ".archon");
7024
- if (!existsSync15(archonDir)) {
7045
+ if (!existsSync16(archonDir)) {
7025
7046
  console.log(chalk16.yellow("This does not appear to be an ArchonDev project (.archon/ not found)."));
7026
7047
  return;
7027
7048
  }
@@ -7029,20 +7050,20 @@ async function eject(options = {}) {
7029
7050
  const filesToRemove = [];
7030
7051
  for (const file of ARCHON_FILES) {
7031
7052
  const filePath = join16(cwd, file);
7032
- if (existsSync15(filePath)) {
7053
+ if (existsSync16(filePath)) {
7033
7054
  filesToRemove.push(file);
7034
7055
  console.log(chalk16.red(` \u2717 ${file}`));
7035
7056
  }
7036
7057
  }
7037
7058
  const archMd = join16(cwd, "ARCHITECTURE.md");
7038
- if (existsSync15(archMd) && !options.keepArchitecture) {
7059
+ if (existsSync16(archMd) && !options.keepArchitecture) {
7039
7060
  console.log(chalk16.yellow(` ? ARCHITECTURE.md (will be kept by default)`));
7040
7061
  }
7041
7062
  console.log();
7042
7063
  console.log(chalk16.dim("Files to be modified:"));
7043
7064
  for (const file of METADATA_FILES) {
7044
7065
  const filePath = join16(cwd, file);
7045
- if (existsSync15(filePath)) {
7066
+ if (existsSync16(filePath)) {
7046
7067
  console.log(chalk16.yellow(` \u25CF ${file}`));
7047
7068
  }
7048
7069
  }
@@ -7094,7 +7115,7 @@ async function performEject(cwd, options) {
7094
7115
  warnings: []
7095
7116
  };
7096
7117
  const archonDir = join16(cwd, ".archon");
7097
- if (existsSync15(archonDir)) {
7118
+ if (existsSync16(archonDir)) {
7098
7119
  try {
7099
7120
  rmSync(archonDir, { recursive: true, force: true });
7100
7121
  result.filesRemoved.push(".archon/");
@@ -7103,7 +7124,7 @@ async function performEject(cwd, options) {
7103
7124
  }
7104
7125
  }
7105
7126
  const prdPath = join16(cwd, "prd.json");
7106
- if (existsSync15(prdPath)) {
7127
+ if (existsSync16(prdPath)) {
7107
7128
  try {
7108
7129
  rmSync(prdPath);
7109
7130
  result.filesRemoved.push("prd.json");
@@ -7112,7 +7133,7 @@ async function performEject(cwd, options) {
7112
7133
  }
7113
7134
  }
7114
7135
  const progressPath = join16(cwd, "progress.txt");
7115
- if (existsSync15(progressPath)) {
7136
+ if (existsSync16(progressPath)) {
7116
7137
  try {
7117
7138
  rmSync(progressPath);
7118
7139
  result.filesRemoved.push("progress.txt");
@@ -7121,7 +7142,7 @@ async function performEject(cwd, options) {
7121
7142
  }
7122
7143
  }
7123
7144
  const promptPath = join16(cwd, "prompt.md");
7124
- if (existsSync15(promptPath)) {
7145
+ if (existsSync16(promptPath)) {
7125
7146
  try {
7126
7147
  rmSync(promptPath);
7127
7148
  result.filesRemoved.push("prompt.md");
@@ -7130,7 +7151,7 @@ async function performEject(cwd, options) {
7130
7151
  }
7131
7152
  }
7132
7153
  const pkgPath = join16(cwd, "package.json");
7133
- if (existsSync15(pkgPath)) {
7154
+ if (existsSync16(pkgPath)) {
7134
7155
  try {
7135
7156
  const pkgContent = await readFile11(pkgPath, "utf-8");
7136
7157
  const pkg = JSON.parse(pkgContent);
@@ -7158,7 +7179,7 @@ async function performEject(cwd, options) {
7158
7179
  }
7159
7180
  if (!options.keepReadme) {
7160
7181
  const readmePath = join16(cwd, "README.md");
7161
- if (existsSync15(readmePath)) {
7182
+ if (existsSync16(readmePath)) {
7162
7183
  try {
7163
7184
  const content = await readFile11(readmePath, "utf-8");
7164
7185
  const archonPatterns = [
@@ -7191,14 +7212,14 @@ async function ejectDryRun() {
7191
7212
  const cwd = process.cwd();
7192
7213
  console.log(chalk16.blue("\n\u{1F50D} Eject Dry Run\n"));
7193
7214
  const archonDir = join16(cwd, ".archon");
7194
- if (!existsSync15(archonDir)) {
7215
+ if (!existsSync16(archonDir)) {
7195
7216
  console.log(chalk16.yellow("This does not appear to be an ArchonDev project."));
7196
7217
  return;
7197
7218
  }
7198
7219
  console.log("The following would be removed:\n");
7199
7220
  for (const file of ARCHON_FILES) {
7200
7221
  const filePath = join16(cwd, file);
7201
- if (existsSync15(filePath)) {
7222
+ if (existsSync16(filePath)) {
7202
7223
  console.log(chalk16.red(` \u2717 ${file}`));
7203
7224
  }
7204
7225
  }
@@ -7206,7 +7227,7 @@ async function ejectDryRun() {
7206
7227
  console.log("The following would be modified:\n");
7207
7228
  for (const file of METADATA_FILES) {
7208
7229
  const filePath = join16(cwd, file);
7209
- if (existsSync15(filePath)) {
7230
+ if (existsSync16(filePath)) {
7210
7231
  console.log(chalk16.yellow(` \u25CF ${file}`));
7211
7232
  }
7212
7233
  }
@@ -7233,15 +7254,15 @@ function promptYesNo3(question, defaultValue) {
7233
7254
 
7234
7255
  // src/cli/revert.ts
7235
7256
  import chalk17 from "chalk";
7236
- import { execSync as execSync3 } from "child_process";
7237
- import { existsSync as existsSync16 } from "fs";
7257
+ import { execSync as execSync4 } from "child_process";
7258
+ import { existsSync as existsSync17 } from "fs";
7238
7259
  import { readFile as readFile12, writeFile as writeFile10 } from "fs/promises";
7239
7260
  import { join as join17 } from "path";
7240
7261
  import readline4 from "readline";
7241
7262
  async function findAtomCommits(limit = 50) {
7242
7263
  const cwd = process.cwd();
7243
7264
  try {
7244
- const logOutput = execSync3(
7265
+ const logOutput = execSync4(
7245
7266
  `git log --oneline --no-merges -n ${limit} --format="%H|%s|%ai|%an"`,
7246
7267
  { cwd, encoding: "utf-8" }
7247
7268
  );
@@ -7257,7 +7278,7 @@ async function findAtomCommits(limit = 50) {
7257
7278
  const atomId = atomMatch[1] ?? atomMatch[2] ?? "unknown";
7258
7279
  let filesChanged = 0;
7259
7280
  try {
7260
- const statOutput = execSync3(
7281
+ const statOutput = execSync4(
7261
7282
  `git diff --shortstat ${hash}^..${hash}`,
7262
7283
  { cwd, encoding: "utf-8" }
7263
7284
  );
@@ -7327,7 +7348,7 @@ async function revertCommand(atomIdOrHash, options = {}) {
7327
7348
  console.log();
7328
7349
  try {
7329
7350
  console.log(chalk17.dim("Changes to be reverted:"));
7330
- const diffStat = execSync3(
7351
+ const diffStat = execSync4(
7331
7352
  `git diff --stat ${commit.commitHash}^..${commit.commitHash}`,
7332
7353
  { cwd, encoding: "utf-8" }
7333
7354
  );
@@ -7343,7 +7364,7 @@ async function revertCommand(atomIdOrHash, options = {}) {
7343
7364
  }
7344
7365
  try {
7345
7366
  const revertArgs = options.noCommit ? "--no-commit" : "";
7346
- execSync3(`git revert ${revertArgs} ${commit.commitHash}`, { cwd, stdio: "pipe" });
7367
+ execSync4(`git revert ${revertArgs} ${commit.commitHash}`, { cwd, stdio: "pipe" });
7347
7368
  console.log(chalk17.green(`
7348
7369
  \u2705 Successfully reverted ${commit.atomId}`));
7349
7370
  if (options.noCommit) {
@@ -7368,7 +7389,7 @@ async function revertCommand(atomIdOrHash, options = {}) {
7368
7389
  }
7369
7390
  async function updateAtomStatus(atomId, status2) {
7370
7391
  const atomPath = join17(process.cwd(), ".archon", "atoms", `${atomId}.json`);
7371
- if (!existsSync16(atomPath)) {
7392
+ if (!existsSync17(atomPath)) {
7372
7393
  return;
7373
7394
  }
7374
7395
  try {
@@ -7422,7 +7443,7 @@ function promptYesNo4(question, defaultValue) {
7422
7443
 
7423
7444
  // src/cli/index.ts
7424
7445
  var program = new Command4();
7425
- program.name("archon").description("Local-first AI-powered development governance").version("1.1.0").action(async () => {
7446
+ program.name("archon").description("Local-first AI-powered development governance").version(getCurrentVersion()).action(async () => {
7426
7447
  const cwd = process.cwd();
7427
7448
  const wasInitialized = isInitialized(cwd);
7428
7449
  if (!wasInitialized) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "archondev",
3
- "version": "2.5.0",
3
+ "version": "2.6.0",
4
4
  "description": "Local-first AI-powered development governance system",
5
5
  "main": "dist/index.js",
6
6
  "bin": {