@kontextmind/kxm 0.7.20 → 0.7.22

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.
@@ -14780,7 +14780,7 @@ var require_dist = __commonJS({
14780
14780
 
14781
14781
  // plugins/kxm/src/cli.ts
14782
14782
  import { resolve as resolve30 } from "node:path";
14783
- import { fileURLToPath as fileURLToPath8 } from "node:url";
14783
+ import { fileURLToPath as fileURLToPath4 } from "node:url";
14784
14784
 
14785
14785
  // node_modules/commander/lib/error.js
14786
14786
  var CommanderError = class extends Error {
@@ -18329,6 +18329,25 @@ function planKxmPackageUpdate(source, latest, releaseDir, asset) {
18329
18329
  return steps;
18330
18330
  }
18331
18331
 
18332
+ // plugins/kxm/src/repo-root.ts
18333
+ import { existsSync as existsSync2 } from "node:fs";
18334
+ import { dirname, join as join2 } from "node:path";
18335
+ import { fileURLToPath } from "node:url";
18336
+ var ROOT_MARKERS = ["scripts/kxm-hub.mjs", "scripts/kxm.mjs"];
18337
+ var MAX_WALK_DEPTH = 10;
18338
+ function findKxmRepoRoot(fromUrl = import.meta.url) {
18339
+ let dir = dirname(fileURLToPath(fromUrl));
18340
+ for (let depth = 0; depth < MAX_WALK_DEPTH; depth += 1) {
18341
+ if (ROOT_MARKERS.some((marker) => existsSync2(join2(dir, marker)))) return dir;
18342
+ const parent = dirname(dir);
18343
+ if (parent === dir) break;
18344
+ dir = parent;
18345
+ }
18346
+ throw new Error(
18347
+ `kxm: cannot locate the KXM repo root from ${fileURLToPath(fromUrl)} (walked ${MAX_WALK_DEPTH} levels looking for ${ROOT_MARKERS[0]})`
18348
+ );
18349
+ }
18350
+
18332
18351
  // plugins/kxm/src/client.ts
18333
18352
  import { createHash as createHash3 } from "node:crypto";
18334
18353
 
@@ -19459,7 +19478,7 @@ var HubClient = class {
19459
19478
  while (!this.stopped && this.agent) {
19460
19479
  this.eventsAbort = new AbortController();
19461
19480
  try {
19462
- const response = await fetch(
19481
+ const response = await (this.options.fetchImpl ?? fetch)(
19463
19482
  `${this.options.serverUrl.replace(/\/$/, "")}/v1/events?agentId=${encodeURIComponent(this.agent.id)}`,
19464
19483
  {
19465
19484
  headers: this.headers(),
@@ -19536,7 +19555,7 @@ var HubClient = class {
19536
19555
  const signal = init.signal ? AbortSignal.any([init.signal, timeoutSignal]) : timeoutSignal;
19537
19556
  let response;
19538
19557
  try {
19539
- response = await fetch(`${this.options.serverUrl.replace(/\/$/, "")}${path4}`, {
19558
+ response = await (this.options.fetchImpl ?? fetch)(`${this.options.serverUrl.replace(/\/$/, "")}${path4}`, {
19540
19559
  ...init,
19541
19560
  signal,
19542
19561
  headers: { ...this.headers(includeIdentity), ...init.headers ?? {} }
@@ -19571,14 +19590,82 @@ var HubClient = class {
19571
19590
  }
19572
19591
  };
19573
19592
 
19593
+ // plugins/kxm/src/hub-env.ts
19594
+ import { existsSync as existsSync3, mkdirSync as mkdirSync2, readFileSync as readFileSync2, renameSync, rmSync, writeFileSync as writeFileSync2 } from "node:fs";
19595
+ import { homedir } from "node:os";
19596
+ import { dirname as dirname2, isAbsolute, join as join3, resolve } from "node:path";
19597
+ var HUB_ENV_SCHEMA = "kxm.hub-env.v1";
19598
+ var HubEnvError = class extends Error {
19599
+ constructor(message) {
19600
+ super(message);
19601
+ this.name = "HubEnvError";
19602
+ }
19603
+ };
19604
+ function resolveUserStateRoot(env) {
19605
+ const explicit = env.KXM_STATE_HOME?.trim();
19606
+ if (explicit) {
19607
+ if (!isAbsolute(explicit)) throw new HubEnvError("local_state_root_not_absolute");
19608
+ return resolve(explicit);
19609
+ }
19610
+ if (process.platform === "win32") {
19611
+ const localAppData = env.LOCALAPPDATA?.trim();
19612
+ const base2 = localAppData && isAbsolute(localAppData) ? localAppData : join3(homedir(), "AppData", "Local");
19613
+ return resolve(base2, "KXM");
19614
+ }
19615
+ if (process.platform === "darwin") return resolve(homedir(), "Library", "Application Support", "KXM");
19616
+ const xdgState = env.XDG_STATE_HOME?.trim();
19617
+ const base = xdgState && isAbsolute(xdgState) ? xdgState : join3(homedir(), ".local", "state");
19618
+ return resolve(base, "kxm");
19619
+ }
19620
+ function hubEnvFile(env = process.env) {
19621
+ return join3(resolveUserStateRoot(env), "hub-env.json");
19622
+ }
19623
+ function readHubEnvRecord(env = process.env) {
19624
+ const file = hubEnvFile(env);
19625
+ if (!existsSync3(file)) return void 0;
19626
+ let parsed;
19627
+ try {
19628
+ parsed = JSON.parse(readFileSync2(file, "utf8"));
19629
+ } catch (error) {
19630
+ throw new HubEnvError(`hub env file is malformed at ${file}: ${error instanceof Error ? error.message : String(error)}`);
19631
+ }
19632
+ if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
19633
+ throw new HubEnvError(`hub env file is malformed at ${file}: expected a JSON object`);
19634
+ }
19635
+ const record = parsed;
19636
+ if (record.schema !== HUB_ENV_SCHEMA) {
19637
+ throw new HubEnvError(`hub env file at ${file} has unsupported schema ${String(record.schema)}`);
19638
+ }
19639
+ if (record.authToken !== void 0 && (typeof record.authToken !== "string" || record.authToken.trim().length === 0)) {
19640
+ throw new HubEnvError(`hub env file at ${file} has an invalid authToken`);
19641
+ }
19642
+ if (record.projectTokens !== void 0) {
19643
+ const tokens = record.projectTokens;
19644
+ if (!tokens || typeof tokens !== "object" || Array.isArray(tokens)) {
19645
+ throw new HubEnvError(`hub env file at ${file} has invalid projectTokens`);
19646
+ }
19647
+ for (const [project, token] of Object.entries(tokens)) {
19648
+ if (!project.trim() || typeof token !== "string" || !token.trim()) {
19649
+ throw new HubEnvError(`hub env file at ${file} has an empty project name or token`);
19650
+ }
19651
+ }
19652
+ }
19653
+ return {
19654
+ schema: HUB_ENV_SCHEMA,
19655
+ createdAt: typeof record.createdAt === "string" ? record.createdAt : "",
19656
+ ...record.authToken !== void 0 ? { authToken: record.authToken } : {},
19657
+ ...record.projectTokens !== void 0 ? { projectTokens: record.projectTokens } : {}
19658
+ };
19659
+ }
19660
+
19574
19661
  // plugins/kxm/src/project-name.ts
19575
- import { readFileSync as readFileSync2 } from "node:fs";
19576
- import { basename, join as join2 } from "node:path";
19662
+ import { readFileSync as readFileSync3 } from "node:fs";
19663
+ import { basename, join as join4 } from "node:path";
19577
19664
  function defaultProjectName(cwd, env = process.env) {
19578
19665
  const fromEnv = env.KXM_PROJECT?.trim();
19579
19666
  if (fromEnv) return fromEnv;
19580
19667
  try {
19581
- const pkg = JSON.parse(readFileSync2(join2(cwd, "package.json"), "utf8"));
19668
+ const pkg = JSON.parse(readFileSync3(join4(cwd, "package.json"), "utf8"));
19582
19669
  if (typeof pkg.name === "string" && pkg.name.trim().length > 0) return pkg.name.trim();
19583
19670
  } catch {
19584
19671
  }
@@ -19587,9 +19674,9 @@ function defaultProjectName(cwd, env = process.env) {
19587
19674
 
19588
19675
  // plugins/kxm/src/commands.ts
19589
19676
  import { createHash as createHash4, randomUUID as randomUUID2, timingSafeEqual } from "node:crypto";
19590
- import { chmodSync, existsSync as existsSync2, mkdirSync as mkdirSync2, readFileSync as readFileSync3, unlinkSync, writeFileSync as writeFileSync2 } from "node:fs";
19591
- import { homedir } from "node:os";
19592
- import { dirname, join as join3, resolve } from "node:path";
19677
+ import { chmodSync, existsSync as existsSync4, mkdirSync as mkdirSync3, readFileSync as readFileSync4, unlinkSync, writeFileSync as writeFileSync3 } from "node:fs";
19678
+ import { homedir as homedir2 } from "node:os";
19679
+ import { dirname as dirname3, join as join5, resolve as resolve2 } from "node:path";
19593
19680
  function requiredString(value, name) {
19594
19681
  if (typeof value !== "string" || value.trim() === "") throw new Error(`${name} is required`);
19595
19682
  return value.trim();
@@ -20337,18 +20424,18 @@ function parseSessionToken(token) {
20337
20424
  return void 0;
20338
20425
  }
20339
20426
  function resolveUserConfigDirectory(overrideDir) {
20340
- if (overrideDir) return resolve(overrideDir);
20341
- return resolve(process.env.KXM_USER_CONFIG_DIR?.trim() || join3(homedir(), ".config", "kxm"));
20427
+ if (overrideDir) return resolve2(overrideDir);
20428
+ return resolve2(process.env.KXM_USER_CONFIG_DIR?.trim() || join5(homedir2(), ".config", "kxm"));
20342
20429
  }
20343
20430
  function sessionTokenPath(userConfigDir) {
20344
- return join3(resolveUserConfigDirectory(userConfigDir), "session.token");
20431
+ return join5(resolveUserConfigDirectory(userConfigDir), "session.token");
20345
20432
  }
20346
20433
  function persistSessionTokenToDisk(token, options) {
20347
20434
  const filePath = sessionTokenPath(options?.userConfigDir);
20348
- const dir = dirname(filePath);
20349
- mkdirSync2(dir, { recursive: true, mode: 448 });
20435
+ const dir = dirname3(filePath);
20436
+ mkdirSync3(dir, { recursive: true, mode: 448 });
20350
20437
  const mode = options?.mode ?? 384;
20351
- writeFileSync2(filePath, `${token.trim()}
20438
+ writeFileSync3(filePath, `${token.trim()}
20352
20439
  `, { encoding: "utf8", mode });
20353
20440
  try {
20354
20441
  chmodSync(filePath, mode);
@@ -20358,9 +20445,9 @@ function persistSessionTokenToDisk(token, options) {
20358
20445
  }
20359
20446
  function readSessionTokenFromDisk(options) {
20360
20447
  const filePath = sessionTokenPath(options?.userConfigDir);
20361
- if (!existsSync2(filePath)) return void 0;
20448
+ if (!existsSync4(filePath)) return void 0;
20362
20449
  try {
20363
- const token = readFileSync3(filePath, "utf8").trim();
20450
+ const token = readFileSync4(filePath, "utf8").trim();
20364
20451
  if (!token) return void 0;
20365
20452
  const payload = parseSessionToken(token);
20366
20453
  if (!payload) return void 0;
@@ -20371,7 +20458,7 @@ function readSessionTokenFromDisk(options) {
20371
20458
  }
20372
20459
  function clearSessionTokenFromDisk(options) {
20373
20460
  const filePath = sessionTokenPath(options?.userConfigDir);
20374
- if (!existsSync2(filePath)) return false;
20461
+ if (!existsSync4(filePath)) return false;
20375
20462
  try {
20376
20463
  unlinkSync(filePath);
20377
20464
  return true;
@@ -20470,10 +20557,10 @@ function enforceToolPolicy(commandName, env = process.env, options) {
20470
20557
  return { allowed: true };
20471
20558
  }
20472
20559
  const tokenFile = sessionTokenPath(env.KXM_USER_CONFIG_DIR);
20473
- if (existsSync2(tokenFile)) {
20560
+ if (existsSync4(tokenFile)) {
20474
20561
  let tokenRaw;
20475
20562
  try {
20476
- tokenRaw = readFileSync3(tokenFile, "utf8").trim();
20563
+ tokenRaw = readFileSync4(tokenFile, "utf8").trim();
20477
20564
  } catch {
20478
20565
  return { allowed: false, error: "session_token_invalid", detail: "Session token file on disk could not be read" };
20479
20566
  }
@@ -20497,9 +20584,8 @@ function enforceToolPolicy(commandName, env = process.env, options) {
20497
20584
  var import__ = __toESM(require__(), 1);
20498
20585
  import { spawnSync as spawnSync2 } from "node:child_process";
20499
20586
  import { createHash as createHash6 } from "node:crypto";
20500
- import { existsSync as existsSync4, lstatSync, readFileSync as readFileSync4, readdirSync, realpathSync } from "node:fs";
20501
- import { basename as basename2, dirname as dirname2, extname, isAbsolute, join as join4, relative, resolve as resolve2, sep } from "node:path";
20502
- import { fileURLToPath } from "node:url";
20587
+ import { existsSync as existsSync6, lstatSync, readFileSync as readFileSync5, readdirSync, realpathSync } from "node:fs";
20588
+ import { basename as basename2, dirname as dirname4, extname, isAbsolute as isAbsolute2, join as join6, relative, resolve as resolve3, sep } from "node:path";
20503
20589
 
20504
20590
  // plugins/kxm/src/restricted-yaml.mjs
20505
20591
  var import_yaml = __toESM(require_dist(), 1);
@@ -20827,7 +20913,7 @@ function resolveVnextTemplateBaseline(value) {
20827
20913
 
20828
20914
  // plugins/kxm/src/vnext-harness.ts
20829
20915
  import { spawnSync } from "node:child_process";
20830
- import { existsSync as existsSync3 } from "node:fs";
20916
+ import { existsSync as existsSync5 } from "node:fs";
20831
20917
  import { win32 as win32Path } from "node:path";
20832
20918
 
20833
20919
  // plugins/kxm/src/vnext-oneshot-process.ts
@@ -21376,7 +21462,7 @@ function findWinNpmInnerExe(cliId, options = {}) {
21376
21462
  if ((options.platform ?? process.platform) !== "win32") return void 0;
21377
21463
  const segments = WIN_NPM_INNER_EXE[cliId];
21378
21464
  if (!segments) return void 0;
21379
- const exists = options.existsSync ?? existsSync3;
21465
+ const exists = options.existsSync ?? existsSync5;
21380
21466
  const pathEnv = options.pathEnv ?? process.env.PATH ?? "";
21381
21467
  for (const dir of pathEnv.split(";").filter(Boolean)) {
21382
21468
  if (!exists(win32Path.join(dir, `${cliId}.cmd`))) continue;
@@ -21893,8 +21979,10 @@ var VnextConfigError = class extends Error {
21893
21979
  this.issues = sorted;
21894
21980
  }
21895
21981
  };
21896
- var PACKAGE_ROOT = resolve2(dirname2(fileURLToPath(import.meta.url)), "../../..");
21897
- var DEFAULT_SCHEMA_DIR = join4(PACKAGE_ROOT, "schemas", "vnext");
21982
+ function defaultVnextSchemaDir() {
21983
+ return join6(findKxmRepoRoot(import.meta.url), "schemas", "vnext");
21984
+ }
21985
+ var DEFAULT_SCHEMA_DIR = defaultVnextSchemaDir();
21898
21986
  var RESOURCE_SCHEMA = Object.freeze({
21899
21987
  project: { identity: "kxm.project.v1", file: "project.schema.json" },
21900
21988
  repository: { identity: "kxm.repository.v1", file: "repository.schema.json" },
@@ -21940,7 +22028,7 @@ function parseRestrictedYaml2(input, label = "<yaml>", limits = VNEXT_YAML_LIMIT
21940
22028
  }
21941
22029
  }
21942
22030
  function readJsonObject(file) {
21943
- const parsed = JSON.parse(readFileSync4(file, "utf8"));
22031
+ const parsed = JSON.parse(readFileSync5(file, "utf8"));
21944
22032
  if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) throw new Error(`${file} is not a JSON object`);
21945
22033
  return parsed;
21946
22034
  }
@@ -21957,12 +22045,12 @@ var VnextSchemaRegistry = class {
21957
22045
  permissionDiffValidator;
21958
22046
  runEventValidator;
21959
22047
  constructor(schemasDir = DEFAULT_SCHEMA_DIR) {
21960
- this.schemasDir = resolve2(schemasDir);
22048
+ this.schemasDir = resolve3(schemasDir);
21961
22049
  this.ajv = new import__.Ajv2020({ allErrors: true, strict: true, strictRequired: false });
21962
- const common = readJsonObject(join4(this.schemasDir, "common.schema.json"));
22050
+ const common = readJsonObject(join6(this.schemasDir, "common.schema.json"));
21963
22051
  this.ajv.addSchema(common);
21964
22052
  for (const definition of Object.values(RESOURCE_SCHEMA)) {
21965
- this.ajv.addSchema(readJsonObject(join4(this.schemasDir, definition.file)));
22053
+ this.ajv.addSchema(readJsonObject(join6(this.schemasDir, definition.file)));
21966
22054
  }
21967
22055
  const localBindingsFile = "local-repository-bindings.schema.json";
21968
22056
  const templateProvenanceFile = "template-provenance.schema.json";
@@ -21972,14 +22060,14 @@ var VnextSchemaRegistry = class {
21972
22060
  const migrationReceiptFile = "migration-receipt.schema.json";
21973
22061
  const permissionDiffFile = "permission-diff.schema.json";
21974
22062
  const runEventFile = "run-event.schema.json";
21975
- this.ajv.addSchema(readJsonObject(join4(this.schemasDir, localBindingsFile)));
21976
- this.ajv.addSchema(readJsonObject(join4(this.schemasDir, templateProvenanceFile)));
21977
- this.ajv.addSchema(readJsonObject(join4(this.schemasDir, initOperationFile)));
21978
- this.ajv.addSchema(readJsonObject(join4(this.schemasDir, migrationPlanFile)));
21979
- this.ajv.addSchema(readJsonObject(join4(this.schemasDir, migrationDecisionFile)));
21980
- this.ajv.addSchema(readJsonObject(join4(this.schemasDir, migrationReceiptFile)));
21981
- this.ajv.addSchema(readJsonObject(join4(this.schemasDir, permissionDiffFile)));
21982
- this.ajv.addSchema(readJsonObject(join4(this.schemasDir, runEventFile)));
22063
+ this.ajv.addSchema(readJsonObject(join6(this.schemasDir, localBindingsFile)));
22064
+ this.ajv.addSchema(readJsonObject(join6(this.schemasDir, templateProvenanceFile)));
22065
+ this.ajv.addSchema(readJsonObject(join6(this.schemasDir, initOperationFile)));
22066
+ this.ajv.addSchema(readJsonObject(join6(this.schemasDir, migrationPlanFile)));
22067
+ this.ajv.addSchema(readJsonObject(join6(this.schemasDir, migrationDecisionFile)));
22068
+ this.ajv.addSchema(readJsonObject(join6(this.schemasDir, migrationReceiptFile)));
22069
+ this.ajv.addSchema(readJsonObject(join6(this.schemasDir, permissionDiffFile)));
22070
+ this.ajv.addSchema(readJsonObject(join6(this.schemasDir, runEventFile)));
21983
22071
  for (const [kind, definition] of Object.entries(RESOURCE_SCHEMA)) {
21984
22072
  const validator = this.ajv.getSchema(`https://schemas.kxm.dev/vnext/${definition.file}`);
21985
22073
  if (!validator) throw new Error(`schema did not compile: ${definition.file}`);
@@ -22055,7 +22143,7 @@ function schemaIssue(file, error) {
22055
22143
  return issue2("schema", `schema_${error.keyword}`, file, `${location} ${error.message ?? "is invalid"}${suffix}`);
22056
22144
  }
22057
22145
  function canonicalHostPath(path4) {
22058
- const resolved = resolve2(path4);
22146
+ const resolved = resolve3(path4);
22059
22147
  try {
22060
22148
  return realpathSync.native(resolved);
22061
22149
  } catch {
@@ -22069,20 +22157,20 @@ function sameHostPath(left, right) {
22069
22157
  }
22070
22158
  function containedHostPath(root, candidate) {
22071
22159
  const path4 = relative(root, candidate);
22072
- return path4 === "" || !isAbsolute(path4) && path4 !== ".." && !path4.startsWith(`..${sep}`);
22160
+ return path4 === "" || !isAbsolute2(path4) && path4 !== ".." && !path4.startsWith(`..${sep}`);
22073
22161
  }
22074
22162
  function portableBindingIssue(root, pathHint, repositoryId) {
22075
22163
  let current = root;
22076
22164
  for (const segment of pathHint === "." ? [] : pathHint.split("/")) {
22077
- current = join4(current, segment);
22078
- if (!existsSync4(current)) break;
22165
+ current = join6(current, segment);
22166
+ if (!existsSync6(current)) break;
22079
22167
  const stat = lstatSync(current);
22080
22168
  if (stat.isSymbolicLink()) {
22081
22169
  return issue2("path", "repository_binding_path_link", ".kxm/project.yaml", `portable pathHint for ${repositoryId} traverses a symbolic link or junction`);
22082
22170
  }
22083
22171
  }
22084
- const binding = resolve2(root, ...pathHint.split("/"));
22085
- if (existsSync4(binding)) {
22172
+ const binding = resolve3(root, ...pathHint.split("/"));
22173
+ if (existsSync6(binding)) {
22086
22174
  const realRoot = canonicalHostPath(root);
22087
22175
  const realBinding = canonicalHostPath(binding);
22088
22176
  if (!containedHostPath(realRoot, realBinding)) {
@@ -22119,10 +22207,10 @@ function readResource(registry, root, file, logicalPath, kind, id, containmentRo
22119
22207
  fail2("discovery", "resource_missing", label, "resource does not exist");
22120
22208
  }
22121
22209
  if (stat.isSymbolicLink()) fail2("path", "resource_symlink", label, "configuration resources must not be symbolic links");
22122
- const boundary = resolve2(containmentRoot);
22123
- let parent = dirname2(file);
22210
+ const boundary = resolve3(containmentRoot);
22211
+ let parent = dirname4(file);
22124
22212
  while (parent !== boundary) {
22125
- if (parent === dirname2(parent)) fail2("path", "resource_outside_project", label, "resource escapes the project root");
22213
+ if (parent === dirname4(parent)) fail2("path", "resource_outside_project", label, "resource escapes the project root");
22126
22214
  let parentStat;
22127
22215
  try {
22128
22216
  parentStat = lstatSync(parent);
@@ -22130,33 +22218,33 @@ function readResource(registry, root, file, logicalPath, kind, id, containmentRo
22130
22218
  fail2("discovery", "resource_parent_missing", label, "resource parent does not exist");
22131
22219
  }
22132
22220
  if (parentStat.isSymbolicLink()) fail2("path", "resource_parent_symlink", label, "configuration resource parents must not be symbolic links");
22133
- parent = dirname2(parent);
22221
+ parent = dirname4(parent);
22134
22222
  }
22135
22223
  if (!stat.isFile()) fail2("path", "resource_not_file", label, "configuration resource must be a regular file");
22136
- const value = parseRestrictedYaml2(readFileSync4(file), label);
22224
+ const value = parseRestrictedYaml2(readFileSync5(file), label);
22137
22225
  const issues = registry.validate(kind, value, label);
22138
22226
  if (issues.length > 0) throw new VnextConfigError(issues);
22139
22227
  return { kind, ...id === void 0 ? {} : { id }, file, logicalPath, value };
22140
22228
  }
22141
22229
  function readTemplateProvenance(registry, root) {
22142
- const file = join4(root, ".kxm", "template-provenance.yaml");
22143
- if (!existsSync4(file)) return void 0;
22230
+ const file = join6(root, ".kxm", "template-provenance.yaml");
22231
+ if (!existsSync6(file)) return void 0;
22144
22232
  const label = ".kxm/template-provenance.yaml";
22145
22233
  const stat = lstatSync(file);
22146
22234
  if (stat.isSymbolicLink() || !stat.isFile()) {
22147
22235
  fail2("path", "resource_not_file", label, "template provenance must be a regular file, not a link or directory");
22148
22236
  }
22149
- const configRoot = join4(root, ".kxm");
22150
- let parent = dirname2(file);
22237
+ const configRoot = join6(root, ".kxm");
22238
+ let parent = dirname4(file);
22151
22239
  while (parent !== root) {
22152
22240
  const parentStat = lstatSync(parent);
22153
22241
  if (parentStat.isSymbolicLink() || !parentStat.isDirectory()) {
22154
22242
  fail2("path", "resource_parent_symlink", label, "template provenance parents must be regular directories");
22155
22243
  }
22156
22244
  if (parent === configRoot) break;
22157
- parent = dirname2(parent);
22245
+ parent = dirname4(parent);
22158
22246
  }
22159
- const value = parseRestrictedYaml2(readFileSync4(file), label);
22247
+ const value = parseRestrictedYaml2(readFileSync5(file), label);
22160
22248
  const issues = registry.validateTemplateProvenance(value, label);
22161
22249
  if (issues.length > 0) throw new VnextConfigError(issues);
22162
22250
  if (!resolveVnextTemplateBaseline(value)) {
@@ -22187,7 +22275,7 @@ function readTemplateProvenance(registry, root) {
22187
22275
  }
22188
22276
  function listNamedResources(registry, root, directory, logicalDirectory, kind) {
22189
22277
  const resources = /* @__PURE__ */ new Map();
22190
- if (!existsSync4(directory)) return resources;
22278
+ if (!existsSync6(directory)) return resources;
22191
22279
  const stat = lstatSync(directory);
22192
22280
  if (stat.isSymbolicLink() || !stat.isDirectory()) {
22193
22281
  fail2("path", "resource_directory_invalid", displayPath(root, directory), "resource directory must be a regular directory");
@@ -22196,27 +22284,27 @@ function listNamedResources(registry, root, directory, logicalDirectory, kind) {
22196
22284
  const entries = readdirSync(directory, { withFileTypes: true }).sort((left, right) => compareCodeUnits3(left.name, right.name));
22197
22285
  for (const entry of entries) {
22198
22286
  if (entry.isDirectory()) {
22199
- issues.push(issue2("path", "nested_resource_directory", displayPath(root, join4(directory, entry.name)), "nested resource directories are not allowed"));
22287
+ issues.push(issue2("path", "nested_resource_directory", displayPath(root, join6(directory, entry.name)), "nested resource directories are not allowed"));
22200
22288
  continue;
22201
22289
  }
22202
22290
  if (!entry.name.toLowerCase().endsWith(".yaml") && !entry.name.toLowerCase().endsWith(".yml")) continue;
22203
22291
  if (!entry.isFile() || extname(entry.name) !== ".yaml") {
22204
- issues.push(issue2("path", "resource_filename_invalid", displayPath(root, join4(directory, entry.name)), "resource must be a regular file with the exact .yaml extension"));
22292
+ issues.push(issue2("path", "resource_filename_invalid", displayPath(root, join6(directory, entry.name)), "resource must be a regular file with the exact .yaml extension"));
22205
22293
  continue;
22206
22294
  }
22207
22295
  const id = basename2(entry.name, ".yaml");
22208
22296
  if (kind === "model" && id === "inventory") continue;
22209
22297
  if (!resourceIdentifier(id)) {
22210
- issues.push(issue2("path", "resource_id_invalid", displayPath(root, join4(directory, entry.name)), `filename-derived identity ${id} is invalid or platform-reserved`));
22298
+ issues.push(issue2("path", "resource_id_invalid", displayPath(root, join6(directory, entry.name)), `filename-derived identity ${id} is invalid or platform-reserved`));
22211
22299
  continue;
22212
22300
  }
22213
22301
  const collision = [...resources.keys()].find((candidate) => candidate.toLocaleLowerCase("en-US") === id.toLocaleLowerCase("en-US"));
22214
22302
  if (collision) {
22215
- issues.push(issue2("path", "resource_id_collision", displayPath(root, join4(directory, entry.name)), `${id} case-folds to existing ${collision}`));
22303
+ issues.push(issue2("path", "resource_id_collision", displayPath(root, join6(directory, entry.name)), `${id} case-folds to existing ${collision}`));
22216
22304
  continue;
22217
22305
  }
22218
22306
  try {
22219
- const resource = readResource(registry, root, join4(directory, entry.name), `${logicalDirectory}/${id}.yaml`, kind, id);
22307
+ const resource = readResource(registry, root, join6(directory, entry.name), `${logicalDirectory}/${id}.yaml`, kind, id);
22220
22308
  resources.set(id, resource);
22221
22309
  } catch (error) {
22222
22310
  if (error instanceof VnextConfigError) issues.push(...error.issues);
@@ -22537,8 +22625,8 @@ function validateWorkflow(workflow, agents, models, repositories, gates, issues)
22537
22625
  const writable = Object.values(objectValue(step.repositories) ?? {}).filter((access) => access === "write").length;
22538
22626
  if (maxWriteRepositories > writable) issues.push(issue2("semantic", "write_repository_bound_invalid", file, `${stepId} maxWriteRepositories exceeds writable repository scope`));
22539
22627
  }
22540
- const join48 = objectValue(step.join);
22541
- const minimumPassed = join48 && typeof join48.minimumPassed === "number" ? join48.minimumPassed : void 0;
22628
+ const join50 = objectValue(step.join);
22629
+ const minimumPassed = join50 && typeof join50.minimumPassed === "number" ? join50.minimumPassed : void 0;
22542
22630
  if (minimumPassed !== void 0 && minimumPassed > maximum) issues.push(issue2("semantic", "join_impossible", file, `${stepId} minimumPassed exceeds assignment maximum`));
22543
22631
  const distinctBy = names(assignment?.distinctBy);
22544
22632
  if (distinctBy.length > 0) {
@@ -22752,11 +22840,11 @@ function validateBundle(project, repositories, agents, models, workflows, enviro
22752
22840
  if (!workflows.has(defaultWorkflow)) issues.push(issue2("reference", "default_workflow_unknown", project.logicalPath, `default workflow ${defaultWorkflow} does not exist`));
22753
22841
  for (const workflow of workflows.values()) validateWorkflow(workflow, agents, models, repositoryIds, gates, issues);
22754
22842
  if (projectRoot) {
22755
- const writerRolePath = join4(projectRoot, ".kxm", "roles", "writer.yaml");
22843
+ const writerRolePath = join6(projectRoot, ".kxm", "roles", "writer.yaml");
22756
22844
  const implementerAgent = agents.get("implementer") ?? agents.get("writer");
22757
- if (existsSync4(writerRolePath) && implementerAgent) {
22845
+ if (existsSync6(writerRolePath) && implementerAgent) {
22758
22846
  try {
22759
- const rawRole = parseRestrictedYaml2(readFileSync4(writerRolePath, "utf8"));
22847
+ const rawRole = parseRestrictedYaml2(readFileSync5(writerRolePath, "utf8"));
22760
22848
  const roleObj = objectValue(rawRole);
22761
22849
  const rosterEntries = valuesOf(roleObj ?? {}, "roster").map((candidate) => objectValue(candidate)).filter((entry) => Boolean(entry));
22762
22850
  const enabledRosterModels = rosterEntries.filter((entry) => entry.enabled !== false).map((entry) => stringValue(entry.model)).filter((m2) => Boolean(m2));
@@ -22802,8 +22890,8 @@ function gitEnvironment() {
22802
22890
  return Object.fromEntries(Object.entries(process.env).filter(([name]) => !name.toUpperCase().startsWith("GIT_")));
22803
22891
  }
22804
22892
  function discoverGitRoot(start = process.cwd()) {
22805
- let current = resolve2(start);
22806
- if (existsSync4(current) && !lstatSync(current).isDirectory()) current = dirname2(current);
22893
+ let current = resolve3(start);
22894
+ if (existsSync6(current) && !lstatSync(current).isDirectory()) current = dirname4(current);
22807
22895
  const result = spawnSync2("git", ["-C", current, "rev-parse", "--show-toplevel"], {
22808
22896
  encoding: "utf8",
22809
22897
  env: gitEnvironment(),
@@ -22811,12 +22899,12 @@ function discoverGitRoot(start = process.cwd()) {
22811
22899
  windowsHide: true
22812
22900
  });
22813
22901
  if (result.status !== 0 || result.error || !result.stdout.trim()) return void 0;
22814
- const root = resolve2(result.stdout.trim());
22815
- return existsSync4(root) && lstatSync(root).isDirectory() ? root : void 0;
22902
+ const root = resolve3(result.stdout.trim());
22903
+ return existsSync6(root) && lstatSync(root).isDirectory() ? root : void 0;
22816
22904
  }
22817
22905
  function discoverVnextProjectRoot(start = process.cwd()) {
22818
22906
  const gitRoot = discoverGitRoot(start);
22819
- return gitRoot && existsSync4(join4(gitRoot, ".kxm", "project.yaml")) ? gitRoot : void 0;
22907
+ return gitRoot && existsSync6(join6(gitRoot, ".kxm", "project.yaml")) ? gitRoot : void 0;
22820
22908
  }
22821
22909
  function assertNoRegisteredGates(options) {
22822
22910
  if ("registeredGates" in options) {
@@ -22825,7 +22913,7 @@ function assertNoRegisteredGates(options) {
22825
22913
  }
22826
22914
  function loadVnextProject(projectRoot, options = {}) {
22827
22915
  assertNoRegisteredGates(options);
22828
- const root = resolve2(projectRoot);
22916
+ const root = resolve3(projectRoot);
22829
22917
  let migrationReceipt;
22830
22918
  if (legacyConfigFilesAt(root).length > 0 && options.allowUnreceiptedLegacyConfig !== true) {
22831
22919
  const receiptCheck = readVnextMigrationReceipt(root, options);
@@ -22833,7 +22921,7 @@ function loadVnextProject(projectRoot, options = {}) {
22833
22921
  migrationReceipt = receiptCheck.receipt;
22834
22922
  }
22835
22923
  const registry = new VnextSchemaRegistry(options.schemasDir);
22836
- const project = readResource(registry, root, join4(root, ".kxm", "project.yaml"), ".kxm/project.yaml", "project");
22924
+ const project = readResource(registry, root, join6(root, ".kxm", "project.yaml"), ".kxm/project.yaml", "project");
22837
22925
  const earlyIssues = [];
22838
22926
  validatePortablePaths(project, earlyIssues);
22839
22927
  const templateProvenance = readTemplateProvenance(registry, root);
@@ -22855,16 +22943,16 @@ function loadVnextProject(projectRoot, options = {}) {
22855
22943
  }
22856
22944
  }
22857
22945
  if (earlyIssues.length > 0) throw new VnextConfigError(earlyIssues);
22858
- const agents = listNamedResources(registry, root, join4(root, ".kxm", "agents"), ".kxm/agents", "agent");
22859
- const models = listNamedResources(registry, root, join4(root, ".kxm", "models"), ".kxm/models", "model");
22860
- const workflows = listNamedResources(registry, root, join4(root, ".kxm", "workflows"), ".kxm/workflows", "workflow");
22861
- const gatePath = join4(root, ".kxm", "gates.yaml");
22862
- const gateRegistry = existsSync4(gatePath) ? readResource(registry, root, gatePath, ".kxm/gates.yaml", "gate-registry") : void 0;
22946
+ const agents = listNamedResources(registry, root, join6(root, ".kxm", "agents"), ".kxm/agents", "agent");
22947
+ const models = listNamedResources(registry, root, join6(root, ".kxm", "models"), ".kxm/models", "model");
22948
+ const workflows = listNamedResources(registry, root, join6(root, ".kxm", "workflows"), ".kxm/workflows", "workflow");
22949
+ const gatePath = join6(root, ".kxm", "gates.yaml");
22950
+ const gateRegistry = existsSync6(gatePath) ? readResource(registry, root, gatePath, ".kxm/gates.yaml", "gate-registry") : void 0;
22863
22951
  const environments = [];
22864
22952
  const repositories = /* @__PURE__ */ new Map();
22865
22953
  const loadIssues = [];
22866
- const projectEnvironment = join4(root, ".kxm", "project", "env.yaml");
22867
- if (existsSync4(projectEnvironment)) {
22954
+ const projectEnvironment = join6(root, ".kxm", "project", "env.yaml");
22955
+ if (existsSync6(projectEnvironment)) {
22868
22956
  try {
22869
22957
  environments.push(readResource(registry, root, projectEnvironment, ".kxm/project/env.yaml", "environment"));
22870
22958
  } catch (error) {
@@ -22882,7 +22970,7 @@ function loadVnextProject(projectRoot, options = {}) {
22882
22970
  if (!repositoryId) continue;
22883
22971
  const hasLocalBinding = Object.hasOwn(options.repositoryBindings ?? {}, repositoryId);
22884
22972
  const localBinding = options.repositoryBindings?.[repositoryId];
22885
- if (hasLocalBinding && (!localBinding || !isAbsolute(localBinding))) {
22973
+ if (hasLocalBinding && (!localBinding || !isAbsolute2(localBinding))) {
22886
22974
  loadIssues.push(issue2("path", "repository_binding_not_absolute", ".kxm/project.yaml", `host-local binding for ${repositoryId} must be absolute`));
22887
22975
  continue;
22888
22976
  }
@@ -22901,12 +22989,12 @@ function loadVnextProject(projectRoot, options = {}) {
22901
22989
  continue;
22902
22990
  }
22903
22991
  }
22904
- const binding = hasLocalBinding && localBinding ? resolve2(localBinding) : role === "control" ? root : pathHint && portablePath(pathHint) ? resolve2(root, ...pathHint.split("/")) : void 0;
22992
+ const binding = hasLocalBinding && localBinding ? resolve3(localBinding) : role === "control" ? root : pathHint && portablePath(pathHint) ? resolve3(root, ...pathHint.split("/")) : void 0;
22905
22993
  if (!binding) {
22906
22994
  if (required) loadIssues.push(issue2("discovery", "repository_binding_missing", ".kxm/project.yaml", `required repository ${repositoryId} has no portable pathHint or host-local binding`));
22907
22995
  continue;
22908
22996
  }
22909
- if (!existsSync4(binding)) {
22997
+ if (!existsSync6(binding)) {
22910
22998
  if (required || hasLocalBinding) loadIssues.push(issue2("discovery", "repository_binding_unavailable", ".kxm/project.yaml", `${hasLocalBinding ? "explicit" : "required"} repository binding ${repositoryId} is unavailable`));
22911
22999
  continue;
22912
23000
  }
@@ -22929,9 +23017,9 @@ function loadVnextProject(projectRoot, options = {}) {
22929
23017
  continue;
22930
23018
  }
22931
23019
  seenBindings.set(foldedBinding, repositoryId);
22932
- const repositoryFile = join4(binding, ".kxm", "repo", "repo.yaml");
23020
+ const repositoryFile = join6(binding, ".kxm", "repo", "repo.yaml");
22933
23021
  let definitionValidated = false;
22934
- if (existsSync4(repositoryFile)) {
23022
+ if (existsSync6(repositoryFile)) {
22935
23023
  try {
22936
23024
  const resource = readResource(registry, root, repositoryFile, `.kxm/repositories/${repositoryId}/repo.yaml`, "repository", repositoryId, binding);
22937
23025
  if (resource.value.repositoryId !== repositoryId) {
@@ -22947,8 +23035,8 @@ function loadVnextProject(projectRoot, options = {}) {
22947
23035
  } else if (required || hasLocalBinding) {
22948
23036
  loadIssues.push(issue2("discovery", "repository_definition_missing", `.kxm/repositories/${repositoryId}/repo.yaml`, `${hasLocalBinding ? "explicit" : "required"} repository ${repositoryId} has no repo.yaml`));
22949
23037
  }
22950
- const environmentFile = join4(binding, ".kxm", "repo", "env.yaml");
22951
- if (existsSync4(environmentFile)) {
23038
+ const environmentFile = join6(binding, ".kxm", "repo", "env.yaml");
23039
+ if (existsSync6(environmentFile)) {
22952
23040
  if (!definitionValidated) {
22953
23041
  loadIssues.push(issue2("reference", "repository_environment_without_definition", `.kxm/repositories/${repositoryId}/env.yaml`, `repository ${repositoryId} environment requires a validated matching repo.yaml`));
22954
23042
  } else {
@@ -23016,7 +23104,7 @@ function verifyVnextMigrationReceiptTarget(root, receipt, resources, configRevis
23016
23104
  }
23017
23105
  function relativePortable(root, absolute) {
23018
23106
  const rel = relative(root, absolute);
23019
- if (!rel || isAbsolute(rel) || rel === ".." || rel.startsWith(`..${sep}`)) return void 0;
23107
+ if (!rel || isAbsolute2(rel) || rel === ".." || rel.startsWith(`..${sep}`)) return void 0;
23020
23108
  return rel.split(sep).join("/");
23021
23109
  }
23022
23110
  function legacyInputsAt(root) {
@@ -23026,21 +23114,21 @@ function legacyInputsAt(root) {
23026
23114
  ".kxm/config/workflows",
23027
23115
  ".kxm/state/kxm.db"
23028
23116
  ];
23029
- return candidates.filter((candidate) => existsSync4(join4(root, ...candidate.split("/"))));
23117
+ return candidates.filter((candidate) => existsSync6(join6(root, ...candidate.split("/"))));
23030
23118
  }
23031
23119
  var VNEXT_MIGRATION_RECEIPT_PATH = ".kxm/migration-receipt.yaml";
23032
23120
  var LEGACY_CONFIG_FILES = [".kxm/config/agents.json", ".kxm/config/gates.json"];
23033
23121
  function legacyConfigFilesAt(root) {
23034
23122
  const files = [];
23035
23123
  for (const component of [".kxm", ".kxm/config"]) {
23036
- const absolute = join4(root, ...component.split("/"));
23037
- if (existsSync4(absolute) && lstatSync(absolute).isSymbolicLink()) return [component];
23124
+ const absolute = join6(root, ...component.split("/"));
23125
+ if (existsSync6(absolute) && lstatSync(absolute).isSymbolicLink()) return [component];
23038
23126
  }
23039
23127
  for (const candidate of LEGACY_CONFIG_FILES) {
23040
- if (existsSync4(join4(root, ...candidate.split("/")))) files.push(candidate);
23128
+ if (existsSync6(join6(root, ...candidate.split("/")))) files.push(candidate);
23041
23129
  }
23042
- const workflowsDir = join4(root, ".kxm", "config", "workflows");
23043
- if (existsSync4(workflowsDir)) {
23130
+ const workflowsDir = join6(root, ".kxm", "config", "workflows");
23131
+ if (existsSync6(workflowsDir)) {
23044
23132
  const stat = lstatSync(workflowsDir);
23045
23133
  if (stat.isSymbolicLink()) {
23046
23134
  files.push(".kxm/config/workflows");
@@ -23055,9 +23143,9 @@ function legacyConfigFilesAt(root) {
23055
23143
  return files;
23056
23144
  }
23057
23145
  function hashFileRecord(root, relativePath) {
23058
- const absolute = join4(root, ...relativePath.split("/"));
23059
- if (!existsSync4(absolute)) return void 0;
23060
- const bytes = readFileSync4(absolute);
23146
+ const absolute = join6(root, ...relativePath.split("/"));
23147
+ if (!existsSync6(absolute)) return void 0;
23148
+ const bytes = readFileSync5(absolute);
23061
23149
  return {
23062
23150
  path: relativePath,
23063
23151
  sha256: `sha256:${createHash6("sha256").update(bytes).digest("hex")}`,
@@ -23069,9 +23157,9 @@ function migrationReceiptSelfHash(receipt) {
23069
23157
  return `sha256:${createHash6("sha256").update(vnextCanonicalJson(unsigned), "utf8").digest("hex")}`;
23070
23158
  }
23071
23159
  function readVnextMigrationReceipt(root, options = {}) {
23072
- const receiptPath = join4(root, ...VNEXT_MIGRATION_RECEIPT_PATH.split("/"));
23160
+ const receiptPath = join6(root, ...VNEXT_MIGRATION_RECEIPT_PATH.split("/"));
23073
23161
  const legacyFiles = legacyConfigFilesAt(root);
23074
- if (!existsSync4(receiptPath)) {
23162
+ if (!existsSync6(receiptPath)) {
23075
23163
  return {
23076
23164
  issues: legacyFiles.map((file) => issue2("semantic", "legacy_vnext_conflict", file, "legacy and vNext configuration cannot coexist before an accepted migration receipt"))
23077
23165
  };
@@ -23082,7 +23170,7 @@ function readVnextMigrationReceipt(root, options = {}) {
23082
23170
  }
23083
23171
  let receipt;
23084
23172
  try {
23085
- receipt = parseRestrictedYaml2(readFileSync4(receiptPath), VNEXT_MIGRATION_RECEIPT_PATH);
23173
+ receipt = parseRestrictedYaml2(readFileSync5(receiptPath), VNEXT_MIGRATION_RECEIPT_PATH);
23086
23174
  } catch (error) {
23087
23175
  if (error instanceof VnextConfigError) return { issues: [...error.issues] };
23088
23176
  throw error;
@@ -23115,14 +23203,14 @@ function readVnextMigrationReceipt(root, options = {}) {
23115
23203
  return issues.length > 0 ? { issues } : { receipt, issues: [] };
23116
23204
  }
23117
23205
  function discoverLegacyRoot(start) {
23118
- let initial = resolve2(start);
23119
- if (existsSync4(initial) && !lstatSync(initial).isDirectory()) initial = dirname2(initial);
23206
+ let initial = resolve3(start);
23207
+ if (existsSync6(initial) && !lstatSync(initial).isDirectory()) initial = dirname4(initial);
23120
23208
  const candidate = discoverGitRoot(initial) ?? initial;
23121
23209
  const inputs = legacyInputsAt(candidate);
23122
23210
  return inputs.length > 0 ? { root: candidate, inputs } : void 0;
23123
23211
  }
23124
23212
  function planVnextInitialization(start = process.cwd(), options = {}) {
23125
- const inspectedFrom = resolve2(start);
23213
+ const inspectedFrom = resolve3(start);
23126
23214
  const projectRoot = discoverVnextProjectRoot(inspectedFrom);
23127
23215
  if (projectRoot) {
23128
23216
  try {
@@ -23143,7 +23231,7 @@ function planVnextInitialization(start = process.cwd(), options = {}) {
23143
23231
  }
23144
23232
  const gitRoot = discoverGitRoot(inspectedFrom);
23145
23233
  const candidateRoot = gitRoot ?? inspectedFrom;
23146
- if (existsSync4(join4(candidateRoot, ".kxm"))) {
23234
+ if (existsSync6(join6(candidateRoot, ".kxm"))) {
23147
23235
  return {
23148
23236
  mode: "repair",
23149
23237
  inspectedFrom,
@@ -23159,14 +23247,13 @@ function planVnextInitialization(start = process.cwd(), options = {}) {
23159
23247
  // plugins/kxm/src/vnext-runtime-supervisor.ts
23160
23248
  import { spawn as spawn2 } from "node:child_process";
23161
23249
  import { createHash as createHash11, createHmac, randomBytes as randomBytes2, timingSafeEqual as timingSafeEqual2 } from "node:crypto";
23162
- import { chmodSync as chmodSync4, existsSync as existsSync10, lstatSync as lstatSync6, mkdirSync as mkdirSync7, readFileSync as readFileSync10, renameSync as renameSync2, rmSync as rmSync2, writeFileSync as writeFileSync7 } from "node:fs";
23163
- import { dirname as dirname6, isAbsolute as isAbsolute4, join as join10, resolve as resolve7 } from "node:path";
23164
- import { fileURLToPath as fileURLToPath2 } from "node:url";
23250
+ import { chmodSync as chmodSync4, existsSync as existsSync12, lstatSync as lstatSync6, mkdirSync as mkdirSync8, readFileSync as readFileSync11, renameSync as renameSync3, rmSync as rmSync3, writeFileSync as writeFileSync8 } from "node:fs";
23251
+ import { dirname as dirname8, isAbsolute as isAbsolute5, join as join12 } from "node:path";
23165
23252
 
23166
23253
  // plugins/kxm/src/vnext-runtime-store.ts
23167
23254
  import { createHash as createHash9, randomUUID as randomUUID4 } from "node:crypto";
23168
- import { existsSync as existsSync7, lstatSync as lstatSync4, mkdirSync as mkdirSync5, readFileSync as readFileSync7, realpathSync as realpathSync3, writeFileSync as writeFileSync5 } from "node:fs";
23169
- import { dirname as dirname5, join as join7, resolve as resolve5 } from "node:path";
23255
+ import { existsSync as existsSync9, lstatSync as lstatSync4, mkdirSync as mkdirSync6, readFileSync as readFileSync8, realpathSync as realpathSync3, writeFileSync as writeFileSync6 } from "node:fs";
23256
+ import { dirname as dirname7, join as join9, resolve as resolve6 } from "node:path";
23170
23257
 
23171
23258
  // plugins/kxm/src/vnext-bindings.ts
23172
23259
  import { spawnSync as spawnSync3 } from "node:child_process";
@@ -23174,18 +23261,18 @@ import { createHash as createHash7, randomUUID as randomUUID3 } from "node:crypt
23174
23261
  import {
23175
23262
  chmodSync as chmodSync2,
23176
23263
  closeSync,
23177
- existsSync as existsSync5,
23264
+ existsSync as existsSync7,
23178
23265
  fsyncSync,
23179
23266
  lstatSync as lstatSync2,
23180
- mkdirSync as mkdirSync3,
23267
+ mkdirSync as mkdirSync4,
23181
23268
  openSync,
23182
- readFileSync as readFileSync5,
23269
+ readFileSync as readFileSync6,
23183
23270
  realpathSync as realpathSync2,
23184
- renameSync,
23185
- rmSync,
23186
- writeFileSync as writeFileSync3
23271
+ renameSync as renameSync2,
23272
+ rmSync as rmSync2,
23273
+ writeFileSync as writeFileSync4
23187
23274
  } from "node:fs";
23188
- import { homedir as homedir2 } from "node:os";
23275
+ import { homedir as homedir3 } from "node:os";
23189
23276
 
23190
23277
  // plugins/kxm/src/sqlite.ts
23191
23278
  import { createRequire } from "node:module";
@@ -23227,7 +23314,7 @@ var DatabaseSync = class {
23227
23314
  };
23228
23315
 
23229
23316
  // plugins/kxm/src/vnext-bindings.ts
23230
- import { dirname as dirname3, isAbsolute as isAbsolute2, join as join5, parse, relative as relative2, resolve as resolve3, sep as sep2 } from "node:path";
23317
+ import { dirname as dirname5, isAbsolute as isAbsolute3, join as join7, parse, relative as relative2, resolve as resolve4, sep as sep2 } from "node:path";
23231
23318
  var MAX_BINDING_RECORD_BYTES = 256 * 1024;
23232
23319
  var BINDING_LABEL = "Runtime-local repository bindings";
23233
23320
  var activeLocks = /* @__PURE__ */ new WeakSet();
@@ -23238,7 +23325,7 @@ function bindingError(phase, code, message) {
23238
23325
  throw new VnextConfigError([bindingIssue(phase, code, message)]);
23239
23326
  }
23240
23327
  function canonicalHostPath2(path4) {
23241
- const absolute = resolve3(path4);
23328
+ const absolute = resolve4(path4);
23242
23329
  try {
23243
23330
  return realpathSync2.native(absolute);
23244
23331
  } catch {
@@ -23253,21 +23340,21 @@ function sameHostPath2(left, right, platform = process.platform) {
23253
23340
  function vnextUserStateRoot(options = {}) {
23254
23341
  const env = options.env ?? process.env;
23255
23342
  const platform = options.platform ?? process.platform;
23256
- const home = options.homeDir ?? homedir2();
23343
+ const home = options.homeDir ?? homedir3();
23257
23344
  const explicit = options.stateRoot ?? env.KXM_STATE_HOME?.trim();
23258
23345
  if (explicit) {
23259
- if (!isAbsolute2(explicit)) bindingError("path", "local_state_root_not_absolute", "KXM_STATE_HOME must be an absolute host-local path");
23260
- return resolve3(explicit);
23346
+ if (!isAbsolute3(explicit)) bindingError("path", "local_state_root_not_absolute", "KXM_STATE_HOME must be an absolute host-local path");
23347
+ return resolve4(explicit);
23261
23348
  }
23262
23349
  if (platform === "win32") {
23263
23350
  const localAppData = env.LOCALAPPDATA?.trim();
23264
- const base2 = localAppData && isAbsolute2(localAppData) ? localAppData : join5(home, "AppData", "Local");
23265
- return resolve3(base2, "KXM");
23351
+ const base2 = localAppData && isAbsolute3(localAppData) ? localAppData : join7(home, "AppData", "Local");
23352
+ return resolve4(base2, "KXM");
23266
23353
  }
23267
- if (platform === "darwin") return resolve3(home, "Library", "Application Support", "KXM");
23354
+ if (platform === "darwin") return resolve4(home, "Library", "Application Support", "KXM");
23268
23355
  const xdgState = env.XDG_STATE_HOME?.trim();
23269
- const base = xdgState && isAbsolute2(xdgState) ? xdgState : join5(home, ".local", "state");
23270
- return resolve3(base, "kxm");
23356
+ const base = xdgState && isAbsolute3(xdgState) ? xdgState : join7(home, ".local", "state");
23357
+ return resolve4(base, "kxm");
23271
23358
  }
23272
23359
  function projectBindingKey(projectRoot, platform = process.platform) {
23273
23360
  const canonical2 = canonicalHostPath2(projectRoot);
@@ -23276,10 +23363,10 @@ function projectBindingKey(projectRoot, platform = process.platform) {
23276
23363
  }
23277
23364
  function vnextLocalBindingFile(projectRoot, options = {}) {
23278
23365
  const stateRoot = vnextUserStateRoot(options);
23279
- return join5(stateRoot, "projects", projectBindingKey(projectRoot, options.platform), "repository-bindings.json");
23366
+ return join7(stateRoot, "projects", projectBindingKey(projectRoot, options.platform), "repository-bindings.json");
23280
23367
  }
23281
23368
  function checkedDirectory(path4, description) {
23282
- if (!existsSync5(path4)) return false;
23369
+ if (!existsSync7(path4)) return false;
23283
23370
  const stat = lstatSync2(path4);
23284
23371
  if (stat.isSymbolicLink() || !stat.isDirectory()) {
23285
23372
  bindingError("path", "local_binding_directory_invalid", `${description} must be a regular directory, not a link or file`);
@@ -23287,8 +23374,8 @@ function checkedDirectory(path4, description) {
23287
23374
  return true;
23288
23375
  }
23289
23376
  function existingBindingDirectory(file, stateRoot) {
23290
- const projects = join5(stateRoot, "projects");
23291
- const project = dirname3(file);
23377
+ const projects = join7(stateRoot, "projects");
23378
+ const project = dirname5(file);
23292
23379
  if (!checkedDirectory(stateRoot, "local state root")) return false;
23293
23380
  if (!checkedDirectory(projects, "local projects directory")) return false;
23294
23381
  return checkedDirectory(project, "local project binding directory");
@@ -23311,10 +23398,10 @@ function asRecord2(value, file, projectRoot, schemasDir) {
23311
23398
  };
23312
23399
  }
23313
23400
  function readVnextLocalBindings(projectRoot, options = {}) {
23314
- const root = resolve3(projectRoot);
23401
+ const root = resolve4(projectRoot);
23315
23402
  const stateRoot = vnextUserStateRoot(options);
23316
23403
  const file = vnextLocalBindingFile(root, options);
23317
- if (!existingBindingDirectory(file, stateRoot) || !existsSync5(file)) return void 0;
23404
+ if (!existingBindingDirectory(file, stateRoot) || !existsSync7(file)) return void 0;
23318
23405
  const stat = lstatSync2(file);
23319
23406
  if (stat.isSymbolicLink() || !stat.isFile()) {
23320
23407
  bindingError("path", "local_binding_file_invalid", "binding record must be a regular file, not a link or directory");
@@ -23322,12 +23409,12 @@ function readVnextLocalBindings(projectRoot, options = {}) {
23322
23409
  if (stat.size > MAX_BINDING_RECORD_BYTES) {
23323
23410
  bindingError("parse", "local_binding_file_too_large", `binding record exceeds ${MAX_BINDING_RECORD_BYTES} bytes`);
23324
23411
  }
23325
- const parsed = parseRestrictedYaml2(readFileSync5(file), BINDING_LABEL);
23412
+ const parsed = parseRestrictedYaml2(readFileSync6(file), BINDING_LABEL);
23326
23413
  return asRecord2(parsed, file, root, options.schemasDir);
23327
23414
  }
23328
23415
  function normalizedRecord(projectRoot, projectId, repositories, schemasDir) {
23329
23416
  const normalizedRepositories = Object.fromEntries(Object.entries(repositories).sort(([left], [right]) => left < right ? -1 : left > right ? 1 : 0).map(([repositoryId, path4]) => {
23330
- if (!isAbsolute2(path4)) bindingError("path", "repository_binding_not_absolute", `host-local binding for ${repositoryId} must be absolute`);
23417
+ if (!isAbsolute3(path4)) bindingError("path", "repository_binding_not_absolute", `host-local binding for ${repositoryId} must be absolute`);
23331
23418
  return [repositoryId, canonicalHostPath2(path4)];
23332
23419
  }));
23333
23420
  const value = {
@@ -23362,48 +23449,48 @@ function syncDirectory(path4) {
23362
23449
  }
23363
23450
  }
23364
23451
  function createDirectoryIfMissing(path4) {
23365
- if (existsSync5(path4)) return;
23452
+ if (existsSync7(path4)) return;
23366
23453
  try {
23367
- mkdirSync3(path4, { mode: 448 });
23368
- syncDirectory(dirname3(path4));
23454
+ mkdirSync4(path4, { mode: 448 });
23455
+ syncDirectory(dirname5(path4));
23369
23456
  } catch (error) {
23370
23457
  if (error.code !== "EEXIST") throw error;
23371
23458
  }
23372
23459
  }
23373
23460
  function ensureDurableDirectory(path4, description) {
23374
23461
  const missing = [];
23375
- let current = resolve3(path4);
23376
- while (!existsSync5(current)) {
23462
+ let current = resolve4(path4);
23463
+ while (!existsSync7(current)) {
23377
23464
  missing.push(current);
23378
- const parent = dirname3(current);
23465
+ const parent = dirname5(current);
23379
23466
  if (parent === current) bindingError("path", "local_binding_directory_invalid", `${description} has no existing filesystem ancestor`);
23380
23467
  current = parent;
23381
23468
  }
23382
23469
  checkedDirectory(current, `${description} ancestor`);
23383
23470
  for (const directory of missing.reverse()) {
23384
- mkdirSync3(directory, { mode: 448 });
23471
+ mkdirSync4(directory, { mode: 448 });
23385
23472
  checkedDirectory(directory, description);
23386
- syncDirectory(dirname3(directory));
23473
+ syncDirectory(dirname5(directory));
23387
23474
  }
23388
23475
  }
23389
23476
  function ensureBindingDirectory(file, stateRoot) {
23390
23477
  ensureDurableDirectory(stateRoot, "local state root");
23391
23478
  checkedDirectory(stateRoot, "local state root");
23392
23479
  syncDirectory(stateRoot);
23393
- const projects = join5(stateRoot, "projects");
23480
+ const projects = join7(stateRoot, "projects");
23394
23481
  createDirectoryIfMissing(projects);
23395
23482
  checkedDirectory(projects, "local projects directory");
23396
- const project = dirname3(file);
23483
+ const project = dirname5(file);
23397
23484
  createDirectoryIfMissing(project);
23398
23485
  checkedDirectory(project, "local project binding directory");
23399
23486
  }
23400
23487
  function assertNoLinkedDirectoryComponents(path4, description) {
23401
- const absolute = resolve3(path4);
23488
+ const absolute = resolve4(path4);
23402
23489
  const filesystemRoot = parse(absolute).root;
23403
23490
  let current = filesystemRoot;
23404
23491
  const remainder = relative2(filesystemRoot, absolute);
23405
23492
  for (const segment of remainder.split(sep2).filter(Boolean)) {
23406
- current = join5(current, segment);
23493
+ current = join7(current, segment);
23407
23494
  const stat = lstatSync2(current);
23408
23495
  if (stat.isSymbolicLink() || !stat.isDirectory()) {
23409
23496
  bindingError("path", "project_operation_lock_parent_invalid", `${description} contains a linked or non-directory component`);
@@ -23424,28 +23511,28 @@ function projectOperationLockFile(projectRoot) {
23424
23511
  if (result.status !== 0 || result.error || !result.stdout.trim()) {
23425
23512
  bindingError("discovery", "project_operation_lock_unavailable", "cannot resolve the authoritative Git metadata path for project locking");
23426
23513
  }
23427
- const gitDirectory = resolve3(result.stdout.trim());
23514
+ const gitDirectory = resolve4(result.stdout.trim());
23428
23515
  assertNoLinkedDirectoryComponents(gitDirectory, "authoritative Git metadata path");
23429
23516
  const gitStat = lstatSync2(gitDirectory);
23430
23517
  if (gitStat.isSymbolicLink() || !gitStat.isDirectory()) {
23431
23518
  bindingError("path", "project_operation_lock_parent_invalid", "authoritative Git metadata must resolve to a regular directory");
23432
23519
  }
23433
- const lockDirectory = join5(gitDirectory, "kxm");
23434
- if (existsSync5(lockDirectory)) {
23520
+ const lockDirectory = join7(gitDirectory, "kxm");
23521
+ if (existsSync7(lockDirectory)) {
23435
23522
  const stat = lstatSync2(lockDirectory);
23436
23523
  if (stat.isSymbolicLink() || !stat.isDirectory()) {
23437
23524
  bindingError("path", "project_operation_lock_parent_invalid", "Git-local KXM lock directory must be regular, not a link or file");
23438
23525
  }
23439
23526
  } else {
23440
- mkdirSync3(lockDirectory, { mode: 448 });
23527
+ mkdirSync4(lockDirectory, { mode: 448 });
23441
23528
  syncDirectory(gitDirectory);
23442
23529
  }
23443
- return join5(lockDirectory, "project-operation-lock.sqlite");
23530
+ return join7(lockDirectory, "project-operation-lock.sqlite");
23444
23531
  }
23445
23532
  function withVnextLocalBindingLock(projectRoot, options, callback) {
23446
- const root = resolve3(projectRoot);
23533
+ const root = resolve4(projectRoot);
23447
23534
  const file = projectOperationLockFile(root);
23448
- if (existsSync5(file)) {
23535
+ if (existsSync7(file)) {
23449
23536
  const stat = lstatSync2(file);
23450
23537
  if (stat.isSymbolicLink() || !stat.isFile()) {
23451
23538
  bindingError("path", "local_binding_lock_invalid", "project-operation lock must be a regular file, not a link or directory");
@@ -23478,7 +23565,7 @@ function withVnextLocalBindingLock(projectRoot, options, callback) {
23478
23565
  }
23479
23566
  }
23480
23567
  function planVnextLocalBindings(projectRoot, projectId, repositories, options = {}) {
23481
- const root = resolve3(projectRoot);
23568
+ const root = resolve4(projectRoot);
23482
23569
  const file = vnextLocalBindingFile(root, options);
23483
23570
  const record = normalizedRecord(root, projectId, repositories, options.schemasDir);
23484
23571
  const existing = readVnextLocalBindings(root, options);
@@ -23488,7 +23575,7 @@ function planVnextLocalBindings(projectRoot, projectId, repositories, options =
23488
23575
  return { file, written: !existing || !recordsEqual(existing, record), record };
23489
23576
  }
23490
23577
  function writeVnextLocalBindings(projectRoot, projectId, repositories, options = {}, lock) {
23491
- const root = resolve3(projectRoot);
23578
+ const root = resolve4(projectRoot);
23492
23579
  if (!lock) {
23493
23580
  return withVnextLocalBindingLock(root, options, (acquired) => writeVnextLocalBindings(root, projectId, repositories, options, acquired));
23494
23581
  }
@@ -23499,20 +23586,20 @@ function writeVnextLocalBindings(projectRoot, projectId, repositories, options =
23499
23586
  const { file, record } = planned;
23500
23587
  if (!planned.written) return planned;
23501
23588
  ensureBindingDirectory(file, vnextUserStateRoot(options));
23502
- const temporary = join5(dirname3(file), `.repository-bindings-${process.pid}-${randomUUID3()}.tmp`);
23589
+ const temporary = join7(dirname5(file), `.repository-bindings-${process.pid}-${randomUUID3()}.tmp`);
23503
23590
  let descriptor;
23504
23591
  try {
23505
23592
  descriptor = openSync(temporary, "wx", 384);
23506
- writeFileSync3(descriptor, `${JSON.stringify(record, null, 2)}
23593
+ writeFileSync4(descriptor, `${JSON.stringify(record, null, 2)}
23507
23594
  `, "utf8");
23508
23595
  fsyncSync(descriptor);
23509
23596
  closeSync(descriptor);
23510
23597
  descriptor = void 0;
23511
- renameSync(temporary, file);
23512
- syncDirectory(dirname3(file));
23598
+ renameSync2(temporary, file);
23599
+ syncDirectory(dirname5(file));
23513
23600
  } finally {
23514
23601
  if (descriptor !== void 0) closeSync(descriptor);
23515
- rmSync(temporary, { force: true });
23602
+ rmSync2(temporary, { force: true });
23516
23603
  }
23517
23604
  const verified = readVnextLocalBindings(root, options);
23518
23605
  if (!verified || !recordsEqual(verified, record)) {
@@ -23526,22 +23613,22 @@ import { createHash as createHash8, randomBytes } from "node:crypto";
23526
23613
  import {
23527
23614
  chmodSync as chmodSync3,
23528
23615
  copyFileSync,
23529
- existsSync as existsSync6,
23616
+ existsSync as existsSync8,
23530
23617
  lstatSync as lstatSync3,
23531
- mkdirSync as mkdirSync4,
23618
+ mkdirSync as mkdirSync5,
23532
23619
  readdirSync as readdirSync2,
23533
- readFileSync as readFileSync6,
23620
+ readFileSync as readFileSync7,
23534
23621
  unlinkSync as unlinkSync2,
23535
- writeFileSync as writeFileSync4
23622
+ writeFileSync as writeFileSync5
23536
23623
  } from "node:fs";
23537
- import { basename as basename3, dirname as dirname4, join as join6, resolve as resolve4 } from "node:path";
23624
+ import { basename as basename3, dirname as dirname6, join as join8, resolve as resolve5 } from "node:path";
23538
23625
  function databaseError(code, file, message) {
23539
23626
  const issue3 = { phase: "semantic", code, file, message };
23540
23627
  return new VnextConfigError([issue3]);
23541
23628
  }
23542
23629
  function checkedParent(path4, description) {
23543
- const parent = dirname4(path4);
23544
- if (!existsSync6(parent)) mkdirSync4(parent, { recursive: true, mode: 448 });
23630
+ const parent = dirname6(path4);
23631
+ if (!existsSync8(parent)) mkdirSync5(parent, { recursive: true, mode: 448 });
23545
23632
  const stat = lstatSync3(parent, { throwIfNoEntry: false });
23546
23633
  if (!stat || stat.isSymbolicLink() || !stat.isDirectory()) {
23547
23634
  throw databaseError("runtime_path_invalid", description, `${description} parent must be a regular directory, not a link`);
@@ -23683,18 +23770,18 @@ function checkIntegrity(database) {
23683
23770
  return rows.length === 1 && rows[0]?.integrity_check === "ok";
23684
23771
  }
23685
23772
  function fileSha256(filePath) {
23686
- const bytes = readFileSync6(filePath);
23773
+ const bytes = readFileSync7(filePath);
23687
23774
  return `sha256:${createHash8("sha256").update(bytes).digest("hex")}`;
23688
23775
  }
23689
23776
  function backupDatabaseFile(sourcePath, targetPath, storeId) {
23690
- const resolvedSource = resolve4(sourcePath);
23691
- const resolvedTarget = resolve4(targetPath);
23777
+ const resolvedSource = resolve5(sourcePath);
23778
+ const resolvedTarget = resolve5(targetPath);
23692
23779
  const sourceStat = lstatSync3(resolvedSource, { throwIfNoEntry: false });
23693
23780
  if (!sourceStat || !sourceStat.isFile() || sourceStat.isSymbolicLink()) {
23694
23781
  throw databaseError("runtime_path_invalid", resolvedSource, `source database ${resolvedSource} must be a regular file, not a link or directory`);
23695
23782
  }
23696
23783
  checkedParent(resolvedTarget, "backup target");
23697
- if (existsSync6(resolvedTarget)) {
23784
+ if (existsSync8(resolvedTarget)) {
23698
23785
  unlinkSync2(resolvedTarget);
23699
23786
  }
23700
23787
  const sourceDb = new DatabaseSync(resolvedSource);
@@ -23738,8 +23825,8 @@ function backupDatabaseFile(sourcePath, targetPath, storeId) {
23738
23825
  };
23739
23826
  }
23740
23827
  function restoreDatabaseFile(backupPath, targetPath, storeId, expectedSchemaVersion, maxSupportedVersion) {
23741
- const resolvedBackup = resolve4(backupPath);
23742
- const resolvedTarget = resolve4(targetPath);
23828
+ const resolvedBackup = resolve5(backupPath);
23829
+ const resolvedTarget = resolve5(targetPath);
23743
23830
  const backupStat = lstatSync3(resolvedBackup, { throwIfNoEntry: false });
23744
23831
  if (!backupStat || !backupStat.isFile() || backupStat.isSymbolicLink()) {
23745
23832
  throw databaseError("runtime_path_invalid", resolvedBackup, `backup database ${resolvedBackup} must be a regular file, not a link or directory`);
@@ -23772,7 +23859,7 @@ function restoreDatabaseFile(backupPath, targetPath, storeId, expectedSchemaVers
23772
23859
  }
23773
23860
  checkedParent(resolvedTarget, "restore target");
23774
23861
  for (const file of [resolvedTarget, `${resolvedTarget}-wal`, `${resolvedTarget}-shm`]) {
23775
- if (existsSync6(file)) {
23862
+ if (existsSync8(file)) {
23776
23863
  try {
23777
23864
  unlinkSync2(file);
23778
23865
  } catch {
@@ -23802,29 +23889,29 @@ function restoreDatabaseFile(backupPath, targetPath, storeId, expectedSchemaVers
23802
23889
  };
23803
23890
  }
23804
23891
  function discoverProjectStores(projectRoot, options = {}) {
23805
- const root = resolve4(projectRoot);
23892
+ const root = resolve5(projectRoot);
23806
23893
  const stores = [];
23807
- const hubPath = options.hubDataPath ? resolve4(options.hubDataPath) : join6(root, ".kxm", "state", "kxm.db");
23808
- if (existsSync6(hubPath)) {
23894
+ const hubPath = options.hubDataPath ? resolve5(options.hubDataPath) : join8(root, ".kxm", "state", "kxm.db");
23895
+ if (existsSync8(hubPath)) {
23809
23896
  stores.push({ storeId: "hub-store", sourcePath: hubPath, maxSupportedVersion: 3 });
23810
23897
  }
23811
- const registryPath = join6(root, ".kxm", "runtime", "registry.db");
23812
- if (existsSync6(registryPath)) {
23898
+ const registryPath = join8(root, ".kxm", "runtime", "registry.db");
23899
+ if (existsSync8(registryPath)) {
23813
23900
  stores.push({ storeId: "registry", sourcePath: registryPath, maxSupportedVersion: 1 });
23814
23901
  }
23815
- const bindingsPath = join6(root, ".kxm", "runtime", "bindings.db");
23816
- if (existsSync6(bindingsPath)) {
23902
+ const bindingsPath = join8(root, ".kxm", "runtime", "bindings.db");
23903
+ if (existsSync8(bindingsPath)) {
23817
23904
  stores.push({ storeId: "binding-store", sourcePath: bindingsPath, maxSupportedVersion: 1 });
23818
23905
  }
23819
- const eventsDir = join6(root, ".kxm", "runtime", "events");
23820
- if (existsSync6(eventsDir)) {
23906
+ const eventsDir = join8(root, ".kxm", "runtime", "events");
23907
+ if (existsSync8(eventsDir)) {
23821
23908
  const entries = readdirSync2(eventsDir, { withFileTypes: true });
23822
23909
  for (const entry of entries) {
23823
23910
  if (entry.isFile() && entry.name.endsWith(".db")) {
23824
23911
  const key = entry.name.replace(/\.db$/, "");
23825
23912
  stores.push({
23826
23913
  storeId: `events:${key}`,
23827
- sourcePath: join6(eventsDir, entry.name),
23914
+ sourcePath: join8(eventsDir, entry.name),
23828
23915
  maxSupportedVersion: 3
23829
23916
  });
23830
23917
  }
@@ -23833,7 +23920,7 @@ function discoverProjectStores(projectRoot, options = {}) {
23833
23920
  return stores;
23834
23921
  }
23835
23922
  function createBackup(options = {}) {
23836
- const projectRoot = options.projectRoot ? resolve4(options.projectRoot) : process.cwd();
23923
+ const projectRoot = options.projectRoot ? resolve5(options.projectRoot) : process.cwd();
23837
23924
  const stores = discoverProjectStores(projectRoot, {
23838
23925
  ...options.hubDataPath !== void 0 ? { hubDataPath: options.hubDataPath } : {}
23839
23926
  });
@@ -23843,9 +23930,9 @@ function createBackup(options = {}) {
23843
23930
  const now = /* @__PURE__ */ new Date();
23844
23931
  const timestamp = now.toISOString().replace(/[:.]/g, "-");
23845
23932
  const backupId = `bk_${randomBytes(8).toString("hex")}`;
23846
- const outDir = options.outDir ? resolve4(options.outDir) : join6(projectRoot, ".kxm", "backups", `backup-${timestamp}`);
23847
- if (!existsSync6(outDir)) {
23848
- mkdirSync4(outDir, { recursive: true, mode: 448 });
23933
+ const outDir = options.outDir ? resolve5(options.outDir) : join8(projectRoot, ".kxm", "backups", `backup-${timestamp}`);
23934
+ if (!existsSync8(outDir)) {
23935
+ mkdirSync5(outDir, { recursive: true, mode: 448 });
23849
23936
  }
23850
23937
  const backedUpStores = [];
23851
23938
  const usedFilenames = /* @__PURE__ */ new Set();
@@ -23856,7 +23943,7 @@ function createBackup(options = {}) {
23856
23943
  filename = `${sanitizedId}-${filename}`;
23857
23944
  }
23858
23945
  usedFilenames.add(filename);
23859
- const targetFile2 = join6(outDir, filename);
23946
+ const targetFile2 = join8(outDir, filename);
23860
23947
  const record = backupDatabaseFile(store.sourcePath, targetFile2, store.storeId);
23861
23948
  backedUpStores.push(record);
23862
23949
  }
@@ -23871,24 +23958,24 @@ function createBackup(options = {}) {
23871
23958
  const manifestSha256 = `sha256:${createHash8("sha256").update(manifestJson, "utf8").digest("hex")}`;
23872
23959
  manifest.manifestSha256 = manifestSha256;
23873
23960
  const finalJson = JSON.stringify(manifest, null, 2) + "\n";
23874
- const manifestPath = join6(outDir, "manifest.json");
23875
- writeFileSync4(manifestPath, finalJson, "utf8");
23961
+ const manifestPath = join8(outDir, "manifest.json");
23962
+ writeFileSync5(manifestPath, finalJson, "utf8");
23876
23963
  return { manifest, outDir };
23877
23964
  }
23878
23965
  function restoreBackup(manifestPathOrDir, options = {}) {
23879
- let manifestPath = resolve4(manifestPathOrDir);
23966
+ let manifestPath = resolve5(manifestPathOrDir);
23880
23967
  const stat = lstatSync3(manifestPath, { throwIfNoEntry: false });
23881
23968
  if (!stat) {
23882
23969
  throw databaseError("runtime_path_invalid", manifestPath, `manifest path ${manifestPath} does not exist`);
23883
23970
  }
23884
23971
  if (stat.isDirectory()) {
23885
- manifestPath = join6(manifestPath, "manifest.json");
23972
+ manifestPath = join8(manifestPath, "manifest.json");
23886
23973
  }
23887
- if (!existsSync6(manifestPath)) {
23974
+ if (!existsSync8(manifestPath)) {
23888
23975
  throw databaseError("runtime_path_invalid", manifestPath, `backup manifest ${manifestPath} not found`);
23889
23976
  }
23890
- const manifestDir = dirname4(manifestPath);
23891
- const rawText = readFileSync6(manifestPath, "utf8");
23977
+ const manifestDir = dirname6(manifestPath);
23978
+ const rawText = readFileSync7(manifestPath, "utf8");
23892
23979
  let manifest;
23893
23980
  try {
23894
23981
  manifest = JSON.parse(rawText);
@@ -23900,8 +23987,8 @@ function restoreBackup(manifestPathOrDir, options = {}) {
23900
23987
  }
23901
23988
  const restoredStores = [];
23902
23989
  for (const store of manifest.stores) {
23903
- const backupFilePath = join6(manifestDir, store.backupFile);
23904
- if (!existsSync6(backupFilePath)) {
23990
+ const backupFilePath = join8(manifestDir, store.backupFile);
23991
+ if (!existsSync8(backupFilePath)) {
23905
23992
  throw databaseError("restore_file_missing", backupFilePath, `backup file ${store.backupFile} missing from ${manifestDir}`);
23906
23993
  }
23907
23994
  const actualSha256 = fileSha256(backupFilePath);
@@ -23919,7 +24006,7 @@ function restoreBackup(manifestPathOrDir, options = {}) {
23919
24006
  let targetPath = store.sourcePath;
23920
24007
  if (options.projectRoot && manifest.projectRoot && targetPath.startsWith(manifest.projectRoot)) {
23921
24008
  const rel = targetPath.slice(manifest.projectRoot.length).replace(/^[\\/]+/, "");
23922
- targetPath = join6(resolve4(options.projectRoot), rel);
24009
+ targetPath = join8(resolve5(options.projectRoot), rel);
23923
24010
  }
23924
24011
  const result = restoreDatabaseFile(
23925
24012
  backupFilePath,
@@ -23939,13 +24026,13 @@ function restoreBackup(manifestPathOrDir, options = {}) {
23939
24026
 
23940
24027
  // plugins/kxm/src/vnext-runtime-store.ts
23941
24028
  function vnextRuntimePaths(options = {}) {
23942
- const stateRoot = options.stateRoot ? resolve5(options.stateRoot) : vnextUserStateRoot({ ...options.env ? { env: options.env } : {}, ...options.homeDir ? { homeDir: options.homeDir } : {} });
23943
- const runtimeDir = join7(stateRoot, "runtime");
24029
+ const stateRoot = options.stateRoot ? resolve6(options.stateRoot) : vnextUserStateRoot({ ...options.env ? { env: options.env } : {}, ...options.homeDir ? { homeDir: options.homeDir } : {} });
24030
+ const runtimeDir = join9(stateRoot, "runtime");
23944
24031
  return {
23945
24032
  stateRoot,
23946
24033
  runtimeDir,
23947
- registryDb: join7(runtimeDir, "registry.db"),
23948
- projectsDir: join7(runtimeDir, "projects")
24034
+ registryDb: join9(runtimeDir, "registry.db"),
24035
+ projectsDir: join9(runtimeDir, "projects")
23949
24036
  };
23950
24037
  }
23951
24038
  function runtimeIssue(phase, code, file, message) {
@@ -23957,9 +24044,9 @@ function runtimeError(code, file, message) {
23957
24044
  function projectRuntimeKey(projectRoot) {
23958
24045
  let canonical2;
23959
24046
  try {
23960
- canonical2 = realpathSync3.native(resolve5(projectRoot));
24047
+ canonical2 = realpathSync3.native(resolve6(projectRoot));
23961
24048
  } catch {
23962
- canonical2 = resolve5(projectRoot);
24049
+ canonical2 = resolve6(projectRoot);
23963
24050
  }
23964
24051
  const folded = process.platform === "win32" ? canonical2.toLocaleLowerCase("en-US") : canonical2;
23965
24052
  return createHash9("sha256").update(folded, "utf8").digest("hex").slice(0, 24);
@@ -23993,7 +24080,7 @@ var VnextRuntimeRegistry = class {
23993
24080
  path;
23994
24081
  database;
23995
24082
  constructor(path4) {
23996
- this.path = resolve5(path4);
24083
+ this.path = resolve6(path4);
23997
24084
  this.database = openDatabase(this.path, "runtime registry", {
23998
24085
  schema: REGISTRY_SCHEMA,
23999
24086
  version: VNEXT_REGISTRY_SCHEMA_VERSION,
@@ -24083,7 +24170,7 @@ var VnextRuntimeRegistry = class {
24083
24170
  }
24084
24171
  /** Register or revalidate a project's home binding. Home Runtime is immutable. */
24085
24172
  registerProject(registration) {
24086
- const projectRoot = resolve5(registration.projectRoot);
24173
+ const projectRoot = resolve6(registration.projectRoot);
24087
24174
  const projectKey = projectRuntimeKey(projectRoot);
24088
24175
  this.database.exec("BEGIN IMMEDIATE");
24089
24176
  try {
@@ -24304,7 +24391,7 @@ function compileStep(step, index, stepIndex, requirePlanHash, sink) {
24304
24391
  const maxAttempts = compileCountField(step.maxAttempts, 1, `${id}.maxAttempts`, id, sink);
24305
24392
  const timeoutMs = compileOptionalDuration(step.timeoutMs, `${id}.timeoutMs`, id, sink);
24306
24393
  const assignments = compileAssignments(step, id, agent, sink);
24307
- const join48 = compileJoin(step, id, sink);
24394
+ const join50 = compileJoin(step, id, sink);
24308
24395
  const requiredEvidence = compileEvidence(step, id, sink);
24309
24396
  const transitions = compileTransitions(step, id, index, stepIndex, sink);
24310
24397
  const outcomes = Object.keys(transitions).sort(compareCodeUnits4);
@@ -24332,7 +24419,7 @@ function compileStep(step, index, stepIndex, requirePlanHash, sink) {
24332
24419
  transitions: orderedTransitions,
24333
24420
  requiresPlanHash: requirePlanHash.includes(id),
24334
24421
  assignments,
24335
- join: join48
24422
+ join: join50
24336
24423
  };
24337
24424
  if (kind === "agent" || kind === "moa") {
24338
24425
  if (!agent) return void 0;
@@ -24382,15 +24469,15 @@ function compileAssignments(step, stepId, primaryAgentId, sink) {
24382
24469
  };
24383
24470
  }
24384
24471
  function compileJoin(step, stepId, sink) {
24385
- const join48 = objectValue2(step.join);
24386
- if (!join48) return { strategy: "all" };
24387
- const declared = stringValue2(join48.strategy);
24472
+ const join50 = objectValue2(step.join);
24473
+ if (!join50) return { strategy: "all" };
24474
+ const declared = stringValue2(join50.strategy);
24388
24475
  const strategy = declared && JOIN_STRATEGIES.has(declared) ? declared : "all";
24389
- const minimumPassed = compileOptionalCount(join48.minimumPassed, `${stepId}.join.minimumPassed`, stepId, sink);
24476
+ const minimumPassed = compileOptionalCount(join50.minimumPassed, `${stepId}.join.minimumPassed`, stepId, sink);
24390
24477
  const compiled = {
24391
24478
  strategy,
24392
24479
  ...minimumPassed !== void 0 ? { minimumPassed } : {},
24393
- ...typeof join48.cancelRemaining === "boolean" ? { cancelRemaining: join48.cancelRemaining } : {}
24480
+ ...typeof join50.cancelRemaining === "boolean" ? { cancelRemaining: join50.cancelRemaining } : {}
24394
24481
  };
24395
24482
  return compiled;
24396
24483
  }
@@ -24670,8 +24757,8 @@ var RECORD_LIMIT = 16 * 1024 * 1024;
24670
24757
  // plugins/kxm/src/prices.ts
24671
24758
  var import_yaml3 = __toESM(require_dist(), 1);
24672
24759
  import { createHash as createHash10 } from "node:crypto";
24673
- import { existsSync as existsSync8, readFileSync as readFileSync8, statSync } from "node:fs";
24674
- import { join as join8 } from "node:path";
24760
+ import { existsSync as existsSync10, readFileSync as readFileSync9, statSync } from "node:fs";
24761
+ import { join as join10 } from "node:path";
24675
24762
 
24676
24763
  // plugins/kxm/src/price-calc.ts
24677
24764
  var PRICES_SCHEMA = "kxm.prices.v1";
@@ -24823,11 +24910,11 @@ function parsePriceCatalog(text) {
24823
24910
  return catalog;
24824
24911
  }
24825
24912
  function loadPriceCatalog(rootOrPath) {
24826
- const candidatePath = existsSync8(join8(rootOrPath, ".kxm", "prices.yaml")) ? join8(rootOrPath, ".kxm", "prices.yaml") : existsSync8(join8(rootOrPath, "prices.yaml")) ? join8(rootOrPath, "prices.yaml") : existsSync8(rootOrPath) && statSync(rootOrPath).isFile() ? rootOrPath : void 0;
24827
- if (!candidatePath || !existsSync8(candidatePath)) {
24913
+ const candidatePath = existsSync10(join10(rootOrPath, ".kxm", "prices.yaml")) ? join10(rootOrPath, ".kxm", "prices.yaml") : existsSync10(join10(rootOrPath, "prices.yaml")) ? join10(rootOrPath, "prices.yaml") : existsSync10(rootOrPath) && statSync(rootOrPath).isFile() ? rootOrPath : void 0;
24914
+ if (!candidatePath || !existsSync10(candidatePath)) {
24828
24915
  return void 0;
24829
24916
  }
24830
- const content = readFileSync8(candidatePath, "utf8");
24917
+ const content = readFileSync9(candidatePath, "utf8");
24831
24918
  return parsePriceCatalog(content);
24832
24919
  }
24833
24920
  function loadPriceCatalogForEstimate(options) {
@@ -24848,13 +24935,13 @@ var import_yaml5 = __toESM(require_dist(), 1);
24848
24935
 
24849
24936
  // plugins/kxm/src/producers.ts
24850
24937
  var import_yaml4 = __toESM(require_dist(), 1);
24851
- import { existsSync as existsSync9, readFileSync as readFileSync9, mkdirSync as mkdirSync6, writeFileSync as writeFileSync6, readdirSync as readdirSync3 } from "node:fs";
24852
- import { join as join9 } from "node:path";
24938
+ import { existsSync as existsSync11, readFileSync as readFileSync10, mkdirSync as mkdirSync7, writeFileSync as writeFileSync7, readdirSync as readdirSync3 } from "node:fs";
24939
+ import { join as join11 } from "node:path";
24853
24940
  var empty = () => ({ schema: "kxm.producers.v1", updatedAt: (/* @__PURE__ */ new Date()).toISOString(), promoted: [], demoted: [], enabled: [], disabled: [], roles: {} });
24854
24941
  function loadProducerPolicy(root) {
24855
- const path4 = join9(root, ".kxm", "producers.yaml");
24856
- if (!existsSync9(path4)) return empty();
24857
- const value = (0, import_yaml4.parse)(readFileSync9(path4, "utf8"));
24942
+ const path4 = join11(root, ".kxm", "producers.yaml");
24943
+ if (!existsSync11(path4)) return empty();
24944
+ const value = (0, import_yaml4.parse)(readFileSync10(path4, "utf8"));
24858
24945
  if (value?.schema !== "kxm.producers.v1" || !Array.isArray(value.promoted) || !Array.isArray(value.demoted)) throw new Error("invalid .kxm/producers.yaml");
24859
24946
  return { schema: "kxm.producers.v1", updatedAt: typeof value.updatedAt === "string" ? value.updatedAt : (/* @__PURE__ */ new Date()).toISOString(), promoted: value.promoted.filter((x2) => typeof x2 === "string"), demoted: value.demoted.filter((x2) => typeof x2 === "string"), enabled: Array.isArray(value.enabled) ? value.enabled.filter((x2) => typeof x2 === "string") : [], disabled: Array.isArray(value.disabled) ? value.disabled.filter((x2) => typeof x2 === "string") : [], roles: value.roles && typeof value.roles === "object" ? Object.fromEntries(Object.entries(value.roles).filter(([, v2]) => Array.isArray(v2)).map(([k, v2]) => [k, v2.filter((x2) => typeof x2 === "string")])) : {} };
24860
24947
  }
@@ -24864,8 +24951,8 @@ function updateProducer(root, model, status) {
24864
24951
  policy.demoted = policy.demoted.filter((x2) => x2 !== model);
24865
24952
  policy[status].push(model);
24866
24953
  policy.updatedAt = (/* @__PURE__ */ new Date()).toISOString();
24867
- mkdirSync6(join9(root, ".kxm"), { recursive: true });
24868
- writeFileSync6(join9(root, ".kxm", "producers.yaml"), (0, import_yaml4.stringify)(policy), "utf8");
24954
+ mkdirSync7(join11(root, ".kxm"), { recursive: true });
24955
+ writeFileSync7(join11(root, ".kxm", "producers.yaml"), (0, import_yaml4.stringify)(policy), "utf8");
24869
24956
  return policy;
24870
24957
  }
24871
24958
  function setModelState(root, model, state, role, removeRole2 = false) {
@@ -24875,10 +24962,10 @@ function setModelState(root, model, state, role, removeRole2 = false) {
24875
24962
  policy[state].push(model);
24876
24963
  if (role) {
24877
24964
  if (!/^[a-z][a-z0-9_-]{0,63}$/i.test(role)) throw new Error("invalid role id");
24878
- const rolePath = join9(root, ".kxm", "roles", `${role}.yaml`);
24965
+ const rolePath = join11(root, ".kxm", "roles", `${role}.yaml`);
24879
24966
  let roleFile = {};
24880
- if (existsSync9(rolePath)) {
24881
- const parsed = (0, import_yaml4.parse)(readFileSync9(rolePath, "utf8"));
24967
+ if (existsSync11(rolePath)) {
24968
+ const parsed = (0, import_yaml4.parse)(readFileSync10(rolePath, "utf8"));
24882
24969
  if (parsed && typeof parsed === "object" && !Array.isArray(parsed)) roleFile = parsed;
24883
24970
  }
24884
24971
  const roster = Array.isArray(roleFile.roster) ? roleFile.roster.filter((entry) => Boolean(entry) && typeof entry === "object" && !Array.isArray(entry)) : [];
@@ -24889,42 +24976,42 @@ function setModelState(root, model, state, role, removeRole2 = false) {
24889
24976
  roleFile.schema ??= "kxm.role.v1";
24890
24977
  roleFile.id ??= role;
24891
24978
  roleFile.roster = roster;
24892
- mkdirSync6(join9(root, ".kxm", "roles"), { recursive: true });
24893
- writeFileSync6(rolePath, (0, import_yaml4.stringify)(roleFile), "utf8");
24979
+ mkdirSync7(join11(root, ".kxm", "roles"), { recursive: true });
24980
+ writeFileSync7(rolePath, (0, import_yaml4.stringify)(roleFile), "utf8");
24894
24981
  }
24895
24982
  policy.updatedAt = (/* @__PURE__ */ new Date()).toISOString();
24896
- mkdirSync6(join9(root, ".kxm"), { recursive: true });
24897
- writeFileSync6(join9(root, ".kxm", "producers.yaml"), (0, import_yaml4.stringify)(policy), "utf8");
24983
+ mkdirSync7(join11(root, ".kxm"), { recursive: true });
24984
+ writeFileSync7(join11(root, ".kxm", "producers.yaml"), (0, import_yaml4.stringify)(policy), "utf8");
24898
24985
  return policy;
24899
24986
  }
24900
24987
  function listRoleBindings(root) {
24901
- const dir = join9(root, ".kxm", "roles");
24988
+ const dir = join11(root, ".kxm", "roles");
24902
24989
  const result = {};
24903
- if (!existsSync9(dir)) return result;
24990
+ if (!existsSync11(dir)) return result;
24904
24991
  for (const file of readdirSync3(dir).filter((name) => name.endsWith(".yaml"))) {
24905
24992
  const role = file.slice(0, -5);
24906
- const value = (0, import_yaml4.parse)(readFileSync9(join9(dir, file), "utf8"));
24993
+ const value = (0, import_yaml4.parse)(readFileSync10(join11(dir, file), "utf8"));
24907
24994
  result[role] = (value.roster ?? []).map((entry) => entry.model).filter((model) => typeof model === "string");
24908
24995
  }
24909
24996
  return result;
24910
24997
  }
24911
24998
  function listInventoryModels(root) {
24912
- const path4 = join9(root, ".kxm", "models", "inventory.yaml");
24913
- if (!existsSync9(path4)) return [];
24914
- const value = (0, import_yaml4.parse)(readFileSync9(path4, "utf8"));
24999
+ const path4 = join11(root, ".kxm", "models", "inventory.yaml");
25000
+ if (!existsSync11(path4)) return [];
25001
+ const value = (0, import_yaml4.parse)(readFileSync10(path4, "utf8"));
24915
25002
  return (value.models ?? []).map((m2) => m2.id).filter((id) => typeof id === "string");
24916
25003
  }
24917
25004
 
24918
25005
  // plugins/kxm/src/artifacts-exist.ts
24919
25006
  import { lstatSync as lstatSync5, realpathSync as realpathSync4, statSync as statSync2 } from "node:fs";
24920
- import { isAbsolute as isAbsolute3, relative as relative3, resolve as resolve6 } from "node:path";
25007
+ import { isAbsolute as isAbsolute4, relative as relative3, resolve as resolve7 } from "node:path";
24921
25008
  function staysUnder(root, candidate) {
24922
25009
  const child = relative3(root, candidate);
24923
- return child === "" || !isAbsolute3(child) && child !== ".." && !child.startsWith(`..${process.platform === "win32" ? "\\" : "/"}`);
25010
+ return child === "" || !isAbsolute4(child) && child !== ".." && !child.startsWith(`..${process.platform === "win32" ? "\\" : "/"}`);
24924
25011
  }
24925
25012
  function verifyArtifactExists(rootInput, pathInput) {
24926
- const lexicalRoot = resolve6(rootInput);
24927
- const lexicalPath = resolve6(pathInput);
25013
+ const lexicalRoot = resolve7(rootInput);
25014
+ const lexicalPath = resolve7(pathInput);
24928
25015
  if (!staysUnder(lexicalRoot, lexicalPath)) {
24929
25016
  return { ok: false, error: "artifact_outside_workspace_assets", path: lexicalPath };
24930
25017
  }
@@ -25543,9 +25630,8 @@ function formatRoutingReport(report2, options = {}) {
25543
25630
  }
25544
25631
 
25545
25632
  // plugins/kxm/src/vnext-runtime-supervisor.ts
25546
- var repoRoot = resolve7(fileURLToPath2(new URL("../../../", import.meta.url)));
25547
25633
  function vnextSupervisorTokenFile(paths) {
25548
- return join10(paths.runtimeDir, "supervisor.token");
25634
+ return join12(paths.runtimeDir, "supervisor.token");
25549
25635
  }
25550
25636
  function readVnextSupervisorToken(paths) {
25551
25637
  const file = vnextSupervisorTokenFile(paths);
@@ -25554,7 +25640,7 @@ function readVnextSupervisorToken(paths) {
25554
25640
  if (stat.isSymbolicLink() || !stat.isFile()) {
25555
25641
  throw runtimeError("runtime_path_invalid", file, "supervisor token file must be a regular file, not a link");
25556
25642
  }
25557
- const token = readFileSync10(file, "utf8").trim();
25643
+ const token = readFileSync11(file, "utf8").trim();
25558
25644
  return token.length >= 32 ? token : void 0;
25559
25645
  }
25560
25646
  function processAlive(pid) {
@@ -25568,11 +25654,11 @@ function processAlive(pid) {
25568
25654
  var HEARTBEAT_STALE_MS = 15e3;
25569
25655
  var SUPERVISOR_ERROR_MAX_AGE_MS = 3e4;
25570
25656
  function supervisorErrorFile(paths) {
25571
- return join10(paths.runtimeDir, "supervisor.error");
25657
+ return join12(paths.runtimeDir, "supervisor.error");
25572
25658
  }
25573
25659
  function clearSupervisorError(paths) {
25574
25660
  const file = supervisorErrorFile(paths);
25575
- if (existsSync10(file)) rmSync2(file, { force: true });
25661
+ if (existsSync12(file)) rmSync3(file, { force: true });
25576
25662
  }
25577
25663
  function readRecentSupervisorError(paths) {
25578
25664
  const file = supervisorErrorFile(paths);
@@ -25581,13 +25667,13 @@ function readRecentSupervisorError(paths) {
25581
25667
  const ageMs = Date.now() - stat.mtimeMs;
25582
25668
  if (ageMs > SUPERVISOR_ERROR_MAX_AGE_MS) return void 0;
25583
25669
  try {
25584
- return readFileSync10(file, "utf8").trim();
25670
+ return readFileSync11(file, "utf8").trim();
25585
25671
  } catch {
25586
25672
  return void 0;
25587
25673
  }
25588
25674
  }
25589
25675
  function vnextSupervisorStatus(paths) {
25590
- if (!existsSync10(paths.registryDb)) return { running: false };
25676
+ if (!existsSync12(paths.registryDb)) return { running: false };
25591
25677
  const registry = new VnextRuntimeRegistry(paths.registryDb);
25592
25678
  try {
25593
25679
  const record = registry.supervisor();
@@ -25648,7 +25734,7 @@ async function ensureVnextSupervisor(options = {}) {
25648
25734
  throw runtimeError("runtime_supervisor_unreachable", paths.registryDb, `runtime supervisor pid ${status.pid} is registered as running but cannot be probed`);
25649
25735
  }
25650
25736
  clearSupervisorError(paths);
25651
- const scriptPath = join10(repoRoot, "scripts", "kxm-runtime-supervisor.mjs");
25737
+ const scriptPath = join12(findKxmRepoRoot(import.meta.url), "scripts", "kxm-runtime-supervisor.mjs");
25652
25738
  const spawnImpl = options.spawnImpl ?? ((script, env) => {
25653
25739
  const child = spawn2(process.execPath, [script], {
25654
25740
  detached: true,
@@ -25701,8 +25787,7 @@ async function vnextRuntimeRequest(handle, method, path4, body) {
25701
25787
 
25702
25788
  // plugins/kxm/src/cli/types.ts
25703
25789
  import { spawn as spawn3 } from "node:child_process";
25704
- import { join as join13, resolve as resolve9 } from "node:path";
25705
- import { fileURLToPath as fileURLToPath3 } from "node:url";
25790
+ import { join as join15, resolve as resolve9 } from "node:path";
25706
25791
 
25707
25792
  // plugins/kxm/src/redact.ts
25708
25793
  var SECRET_PATTERNS = [
@@ -25732,8 +25817,8 @@ function redactStringList(values, maxItems = 32) {
25732
25817
  }
25733
25818
 
25734
25819
  // plugins/kxm/src/telemetry.ts
25735
- import { appendFileSync, mkdirSync as mkdirSync8, readFileSync as readFileSync11 } from "node:fs";
25736
- import { dirname as dirname7, join as join11 } from "node:path";
25820
+ import { appendFileSync, mkdirSync as mkdirSync9, readFileSync as readFileSync12 } from "node:fs";
25821
+ import { dirname as dirname9, join as join13 } from "node:path";
25737
25822
  var TELEMETRY_SCHEMA = "kxm.telemetry.v1";
25738
25823
  function inferImprovementTarget(input) {
25739
25824
  const explicit = input.env?.KXM_IMPROVE_TARGET?.trim();
@@ -25743,12 +25828,12 @@ function inferImprovementTarget(input) {
25743
25828
  return project || workflowId ? "project" : "cli";
25744
25829
  }
25745
25830
  function appendTelemetry(path4, event) {
25746
- mkdirSync8(dirname7(path4), { recursive: true });
25831
+ mkdirSync9(dirname9(path4), { recursive: true });
25747
25832
  appendFileSync(path4, `${JSON.stringify(event)}
25748
25833
  `, { encoding: "utf8", mode: 384 });
25749
25834
  }
25750
25835
  function telemetryPath(logsDir) {
25751
- return join11(logsDir, "telemetry.jsonl");
25836
+ return join13(logsDir, "telemetry.jsonl");
25752
25837
  }
25753
25838
  function makeTelemetryEvent(input) {
25754
25839
  return {
@@ -25763,7 +25848,7 @@ function makeTelemetryEvent(input) {
25763
25848
  function readRoutingRecords(path4) {
25764
25849
  const records = [];
25765
25850
  try {
25766
- const raw = readFileSync11(path4, "utf8");
25851
+ const raw = readFileSync12(path4, "utf8");
25767
25852
  for (const line of raw.split(/\r?\n/)) {
25768
25853
  if (!line.trim()) continue;
25769
25854
  try {
@@ -25840,9 +25925,9 @@ function workerResult(worker, payload) {
25840
25925
  }
25841
25926
 
25842
25927
  // plugins/kxm/src/hub-binding.ts
25843
- import { existsSync as existsSync11, mkdirSync as mkdirSync9, readFileSync as readFileSync12, renameSync as renameSync3, rmSync as rmSync3, writeFileSync as writeFileSync8 } from "node:fs";
25844
- import { homedir as homedir3 } from "node:os";
25845
- import { dirname as dirname8, isAbsolute as isAbsolute5, join as join12, resolve as resolve8 } from "node:path";
25928
+ import { existsSync as existsSync13, mkdirSync as mkdirSync10, readFileSync as readFileSync13, renameSync as renameSync4, rmSync as rmSync4, writeFileSync as writeFileSync9 } from "node:fs";
25929
+ import { homedir as homedir4 } from "node:os";
25930
+ import { dirname as dirname10, isAbsolute as isAbsolute6, join as join14, resolve as resolve8 } from "node:path";
25846
25931
  var HUB_BINDING_SCHEMA = "kxm.hub-binding.v1";
25847
25932
  var HUB_HEALTH_PROBE_MS = 300;
25848
25933
  var HubBindingError = class extends Error {
@@ -25851,24 +25936,24 @@ var HubBindingError = class extends Error {
25851
25936
  this.name = "HubBindingError";
25852
25937
  }
25853
25938
  };
25854
- function resolveUserStateRoot(env) {
25939
+ function resolveUserStateRoot2(env) {
25855
25940
  const explicit = env.KXM_STATE_HOME?.trim();
25856
25941
  if (explicit) {
25857
- if (!isAbsolute5(explicit)) throw new HubBindingError("local_state_root_not_absolute");
25942
+ if (!isAbsolute6(explicit)) throw new HubBindingError("local_state_root_not_absolute");
25858
25943
  return resolve8(explicit);
25859
25944
  }
25860
25945
  if (process.platform === "win32") {
25861
25946
  const localAppData = env.LOCALAPPDATA?.trim();
25862
- const base2 = localAppData && isAbsolute5(localAppData) ? localAppData : join12(homedir3(), "AppData", "Local");
25947
+ const base2 = localAppData && isAbsolute6(localAppData) ? localAppData : join14(homedir4(), "AppData", "Local");
25863
25948
  return resolve8(base2, "KXM");
25864
25949
  }
25865
- if (process.platform === "darwin") return resolve8(homedir3(), "Library", "Application Support", "KXM");
25950
+ if (process.platform === "darwin") return resolve8(homedir4(), "Library", "Application Support", "KXM");
25866
25951
  const xdgState = env.XDG_STATE_HOME?.trim();
25867
- const base = xdgState && isAbsolute5(xdgState) ? xdgState : join12(homedir3(), ".local", "state");
25952
+ const base = xdgState && isAbsolute6(xdgState) ? xdgState : join14(homedir4(), ".local", "state");
25868
25953
  return resolve8(base, "kxm");
25869
25954
  }
25870
25955
  function hubBindingFile(env = process.env) {
25871
- return join12(resolveUserStateRoot(env), "hub-binding.json");
25956
+ return join14(resolveUserStateRoot2(env), "hub-binding.json");
25872
25957
  }
25873
25958
  function validateHubUrl(raw) {
25874
25959
  let parsed;
@@ -25893,10 +25978,10 @@ function isAbortError(error) {
25893
25978
  }
25894
25979
  function readHubBinding(env = process.env) {
25895
25980
  const file = hubBindingFile(env);
25896
- if (!existsSync11(file)) return void 0;
25981
+ if (!existsSync13(file)) return void 0;
25897
25982
  let parsed;
25898
25983
  try {
25899
- parsed = JSON.parse(readFileSync12(file, "utf8"));
25984
+ parsed = JSON.parse(readFileSync13(file, "utf8"));
25900
25985
  } catch {
25901
25986
  throw new HubBindingError(`malformed hub binding at ${file}`);
25902
25987
  }
@@ -25918,21 +26003,21 @@ function readHubBinding(env = process.env) {
25918
26003
  }
25919
26004
  function writeHubBinding(record, env = process.env) {
25920
26005
  const file = hubBindingFile(env);
25921
- mkdirSync9(dirname8(file), { recursive: true, mode: 448 });
25922
- const temporary = join12(dirname8(file), `.hub-binding-${process.pid}.tmp`);
26006
+ mkdirSync10(dirname10(file), { recursive: true, mode: 448 });
26007
+ const temporary = join14(dirname10(file), `.hub-binding-${process.pid}.tmp`);
25923
26008
  try {
25924
- writeFileSync8(temporary, `${JSON.stringify(record, null, 2)}
26009
+ writeFileSync9(temporary, `${JSON.stringify(record, null, 2)}
25925
26010
  `, { encoding: "utf8", mode: 384 });
25926
- renameSync3(temporary, file);
26011
+ renameSync4(temporary, file);
25927
26012
  } finally {
25928
- rmSync3(temporary, { force: true });
26013
+ rmSync4(temporary, { force: true });
25929
26014
  }
25930
26015
  return file;
25931
26016
  }
25932
26017
  function removeHubBinding(env = process.env) {
25933
26018
  const file = hubBindingFile(env);
25934
26019
  try {
25935
- rmSync3(file);
26020
+ rmSync4(file);
25936
26021
  return true;
25937
26022
  } catch (error) {
25938
26023
  if (error.code === "ENOENT") return false;
@@ -25964,10 +26049,9 @@ async function probeHubHealth(url, fetchImpl, timeoutMs = HUB_HEALTH_PROBE_MS) {
25964
26049
  }
25965
26050
 
25966
26051
  // plugins/kxm/src/cli/types.ts
25967
- var repoRoot2 = resolve9(fileURLToPath3(new URL("../../../../", import.meta.url)));
25968
26052
  function spawnScript(scriptName, extraEnv = {}) {
25969
26053
  return new Promise((resolveExit) => {
25970
- const child = spawn3(process.execPath, [join13(repoRoot2, "scripts", scriptName)], {
26054
+ const child = spawn3(process.execPath, [join15(findKxmRepoRoot(import.meta.url), "scripts", scriptName)], {
25971
26055
  stdio: "inherit",
25972
26056
  env: { ...process.env, ...extraEnv }
25973
26057
  });
@@ -26057,10 +26141,10 @@ function workspaceDirs(cwd, workspaceFlag, env) {
26057
26141
  return {
26058
26142
  workdir,
26059
26143
  workspace,
26060
- config: derive ? join13(workspace, "config") : resolve9(workdir, env.KXM_CONFIG_DIR?.trim() || join13(workspace, "config")),
26061
- logs: derive ? join13(workspace, "logs") : resolve9(workdir, env.KXM_LOGS_DIR?.trim() || join13(workspace, "logs")),
26062
- assets: derive ? join13(workspace, "assets") : resolve9(workdir, env.KXM_ASSETS_DIR?.trim() || join13(workspace, "assets")),
26063
- state: derive ? join13(workspace, "state") : resolve9(workdir, env.KXM_STATE_DIR?.trim() || join13(workspace, "state"))
26144
+ config: derive ? join15(workspace, "config") : resolve9(workdir, env.KXM_CONFIG_DIR?.trim() || join15(workspace, "config")),
26145
+ logs: derive ? join15(workspace, "logs") : resolve9(workdir, env.KXM_LOGS_DIR?.trim() || join15(workspace, "logs")),
26146
+ assets: derive ? join15(workspace, "assets") : resolve9(workdir, env.KXM_ASSETS_DIR?.trim() || join15(workspace, "assets")),
26147
+ state: derive ? join15(workspace, "state") : resolve9(workdir, env.KXM_STATE_DIR?.trim() || join15(workspace, "state"))
26064
26148
  };
26065
26149
  }
26066
26150
  function maskEnvName(name) {
@@ -26128,20 +26212,20 @@ function workspaceEnv(runtime) {
26128
26212
  // plugins/kxm/src/cli/roles.ts
26129
26213
  var import_yaml8 = __toESM(require_dist(), 1);
26130
26214
  import { randomUUID as randomUUID5 } from "node:crypto";
26131
- import { existsSync as existsSync14, readFileSync as readFileSync15 } from "node:fs";
26132
- import { join as join16, resolve as resolve12 } from "node:path";
26215
+ import { existsSync as existsSync16, readFileSync as readFileSync16 } from "node:fs";
26216
+ import { join as join18, resolve as resolve12 } from "node:path";
26133
26217
  import { createInterface } from "node:readline";
26134
26218
 
26135
26219
  // plugins/kxm/src/role.ts
26136
26220
  var import_yaml7 = __toESM(require_dist(), 1);
26137
- import { existsSync as existsSync13, mkdirSync as mkdirSync11, readdirSync as readdirSync4, readFileSync as readFileSync14, rmSync as rmSync4, writeFileSync as writeFileSync10 } from "node:fs";
26138
- import { join as join15 } from "node:path";
26221
+ import { existsSync as existsSync15, mkdirSync as mkdirSync12, readdirSync as readdirSync4, readFileSync as readFileSync15, rmSync as rmSync5, writeFileSync as writeFileSync11 } from "node:fs";
26222
+ import { join as join17 } from "node:path";
26139
26223
 
26140
26224
  // plugins/kxm/src/config.ts
26141
26225
  var import_yaml6 = __toESM(require_dist(), 1);
26142
- import { existsSync as existsSync12, mkdirSync as mkdirSync10, readFileSync as readFileSync13, writeFileSync as writeFileSync9 } from "node:fs";
26143
- import { homedir as homedir4 } from "node:os";
26144
- import { dirname as dirname9, join as join14, resolve as resolve10 } from "node:path";
26226
+ import { existsSync as existsSync14, mkdirSync as mkdirSync11, readFileSync as readFileSync14, writeFileSync as writeFileSync10 } from "node:fs";
26227
+ import { homedir as homedir5 } from "node:os";
26228
+ import { dirname as dirname11, join as join16, resolve as resolve10 } from "node:path";
26145
26229
  var KXM_CONFIG_SCHEMA = "kxm.config.v1";
26146
26230
  var DEFAULT_KXM_CONFIG = {
26147
26231
  schema: KXM_CONFIG_SCHEMA,
@@ -26195,10 +26279,10 @@ var DEFAULT_KXM_CONFIG = {
26195
26279
  };
26196
26280
  function userConfigDirectory(overrideDir) {
26197
26281
  if (overrideDir) return resolve10(overrideDir);
26198
- return resolve10(process.env.KXM_USER_CONFIG_DIR?.trim() || join14(homedir4(), ".config", "kxm"));
26282
+ return resolve10(process.env.KXM_USER_CONFIG_DIR?.trim() || join16(homedir5(), ".config", "kxm"));
26199
26283
  }
26200
- function repoConfigDirectory(repoRoot6) {
26201
- return resolve10(repoRoot6, ".kxm");
26284
+ function repoConfigDirectory(repoRoot) {
26285
+ return resolve10(repoRoot, ".kxm");
26202
26286
  }
26203
26287
  function deepMerge(target, source) {
26204
26288
  const result = { ...target };
@@ -26216,16 +26300,16 @@ function normalizeHubConfig(raw) {
26216
26300
  const autoStart = raw?.autoStart;
26217
26301
  return { autoStart: autoStart === "off" || autoStart === "background" ? autoStart : DEFAULT_KXM_CONFIG.hub.autoStart };
26218
26302
  }
26219
- function loadKxmConfig(repoRoot6 = process.cwd(), options = {}) {
26303
+ function loadKxmConfig(repoRoot = process.cwd(), options = {}) {
26220
26304
  const userDir = userConfigDirectory(options.userConfigDir);
26221
- const userConfigFile = join14(userDir, "config.yaml");
26222
- const repoDir = repoConfigDirectory(repoRoot6);
26223
- const repoConfigFile = join14(repoDir, "config.yaml");
26305
+ const userConfigFile = join16(userDir, "config.yaml");
26306
+ const repoDir = repoConfigDirectory(repoRoot);
26307
+ const repoConfigFile = join16(repoDir, "config.yaml");
26224
26308
  let userRaw = {};
26225
26309
  let userLoadedPath;
26226
- if (existsSync12(userConfigFile)) {
26310
+ if (existsSync14(userConfigFile)) {
26227
26311
  try {
26228
- const text = readFileSync13(userConfigFile, "utf8");
26312
+ const text = readFileSync14(userConfigFile, "utf8");
26229
26313
  userRaw = (0, import_yaml6.parse)(text) ?? {};
26230
26314
  userLoadedPath = userConfigFile;
26231
26315
  } catch (error) {
@@ -26234,9 +26318,9 @@ function loadKxmConfig(repoRoot6 = process.cwd(), options = {}) {
26234
26318
  }
26235
26319
  let repoRaw = {};
26236
26320
  let repoLoadedPath;
26237
- if (existsSync12(repoConfigFile)) {
26321
+ if (existsSync14(repoConfigFile)) {
26238
26322
  try {
26239
- const text = readFileSync13(repoConfigFile, "utf8");
26323
+ const text = readFileSync14(repoConfigFile, "utf8");
26240
26324
  repoRaw = (0, import_yaml6.parse)(text) ?? {};
26241
26325
  repoLoadedPath = repoConfigFile;
26242
26326
  } catch (error) {
@@ -26271,14 +26355,14 @@ function getKxmConfigValue(config, keyPath) {
26271
26355
  }
26272
26356
  return current;
26273
26357
  }
26274
- function setKxmConfigValue(repoRoot6, keyPath, value, options = {}) {
26358
+ function setKxmConfigValue(repoRoot, keyPath, value, options = {}) {
26275
26359
  const scope = options.scope ?? "project";
26276
- const targetFile2 = scope === "user" ? join14(userConfigDirectory(options.userConfigDir), "config.yaml") : join14(repoConfigDirectory(repoRoot6), "config.yaml");
26277
- mkdirSync10(dirname9(targetFile2), { recursive: true });
26360
+ const targetFile2 = scope === "user" ? join16(userConfigDirectory(options.userConfigDir), "config.yaml") : join16(repoConfigDirectory(repoRoot), "config.yaml");
26361
+ mkdirSync11(dirname11(targetFile2), { recursive: true });
26278
26362
  let existing = {};
26279
- if (existsSync12(targetFile2)) {
26363
+ if (existsSync14(targetFile2)) {
26280
26364
  try {
26281
- existing = (0, import_yaml6.parse)(readFileSync13(targetFile2, "utf8")) ?? {};
26365
+ existing = (0, import_yaml6.parse)(readFileSync14(targetFile2, "utf8")) ?? {};
26282
26366
  } catch {
26283
26367
  existing = {};
26284
26368
  }
@@ -26296,7 +26380,7 @@ function setKxmConfigValue(repoRoot6, keyPath, value, options = {}) {
26296
26380
  cursor2 = cursor2[p];
26297
26381
  }
26298
26382
  cursor2[parts[parts.length - 1]] = value;
26299
- writeFileSync9(targetFile2, (0, import_yaml6.stringify)(existing).trim() + "\n", "utf8");
26383
+ writeFileSync10(targetFile2, (0, import_yaml6.stringify)(existing).trim() + "\n", "utf8");
26300
26384
  }
26301
26385
  function formatKxmConfig(config) {
26302
26386
  const display = {
@@ -26387,23 +26471,23 @@ var DEFAULT_ROLES = {
26387
26471
  ]
26388
26472
  }
26389
26473
  };
26390
- function rolesDirectory(scope, repoRoot6 = process.cwd(), userConfigDir) {
26474
+ function rolesDirectory(scope, repoRoot = process.cwd(), userConfigDir) {
26391
26475
  if (scope === "global") {
26392
- return join15(userConfigDirectory(userConfigDir), "roles");
26476
+ return join17(userConfigDirectory(userConfigDir), "roles");
26393
26477
  }
26394
- return join15(repoConfigDirectory(repoRoot6), "roles");
26478
+ return join17(repoConfigDirectory(repoRoot), "roles");
26395
26479
  }
26396
- function ensureRolesDirectory(scope, repoRoot6 = process.cwd(), userConfigDir) {
26397
- const dir = rolesDirectory(scope, repoRoot6, userConfigDir);
26398
- if (!existsSync13(dir)) {
26399
- mkdirSync11(dir, { recursive: true });
26480
+ function ensureRolesDirectory(scope, repoRoot = process.cwd(), userConfigDir) {
26481
+ const dir = rolesDirectory(scope, repoRoot, userConfigDir);
26482
+ if (!existsSync15(dir)) {
26483
+ mkdirSync12(dir, { recursive: true });
26400
26484
  }
26401
26485
  return dir;
26402
26486
  }
26403
26487
  function parseRoleFile(filePath) {
26404
- if (!existsSync13(filePath)) return void 0;
26488
+ if (!existsSync15(filePath)) return void 0;
26405
26489
  try {
26406
- const raw = readFileSync14(filePath, "utf8");
26490
+ const raw = readFileSync15(filePath, "utf8");
26407
26491
  const parsed = (0, import_yaml7.parse)(raw);
26408
26492
  if (!parsed || typeof parsed !== "object" || parsed.schema !== KXM_ROLE_SCHEMA) {
26409
26493
  return void 0;
@@ -26426,14 +26510,14 @@ function parseRoleFile(filePath) {
26426
26510
  }
26427
26511
  function listRoles(options = {}) {
26428
26512
  const scopeFilter = options.scope ?? "all";
26429
- const repoRoot6 = options.repoRoot ?? process.cwd();
26430
- const globalDir = rolesDirectory("global", repoRoot6, options.userConfigDir);
26431
- const localDir = rolesDirectory("local", repoRoot6, options.userConfigDir);
26513
+ const repoRoot = options.repoRoot ?? process.cwd();
26514
+ const globalDir = rolesDirectory("global", repoRoot, options.userConfigDir);
26515
+ const localDir = rolesDirectory("local", repoRoot, options.userConfigDir);
26432
26516
  const localRoles = /* @__PURE__ */ new Map();
26433
- if (scopeFilter !== "global" && existsSync13(localDir)) {
26517
+ if (scopeFilter !== "global" && existsSync15(localDir)) {
26434
26518
  for (const entry of readdirSync4(localDir)) {
26435
26519
  if (entry.endsWith(".yaml") || entry.endsWith(".yml")) {
26436
- const filePath = join15(localDir, entry);
26520
+ const filePath = join17(localDir, entry);
26437
26521
  const parsed = parseRoleFile(filePath);
26438
26522
  if (parsed) {
26439
26523
  localRoles.set(parsed.id, { role: parsed, filePath });
@@ -26442,10 +26526,10 @@ function listRoles(options = {}) {
26442
26526
  }
26443
26527
  }
26444
26528
  const globalRoles = /* @__PURE__ */ new Map();
26445
- if (scopeFilter !== "local" && existsSync13(globalDir)) {
26529
+ if (scopeFilter !== "local" && existsSync15(globalDir)) {
26446
26530
  for (const entry of readdirSync4(globalDir)) {
26447
26531
  if (entry.endsWith(".yaml") || entry.endsWith(".yml")) {
26448
- const filePath = join15(globalDir, entry);
26532
+ const filePath = join17(globalDir, entry);
26449
26533
  const parsed = parseRoleFile(filePath);
26450
26534
  if (parsed) {
26451
26535
  globalRoles.set(parsed.id, { role: parsed, filePath });
@@ -26490,16 +26574,16 @@ function listRoles(options = {}) {
26490
26574
  }
26491
26575
  function getRole(roleId, options = {}) {
26492
26576
  const scope = options.scope ?? "all";
26493
- const repoRoot6 = options.repoRoot ?? process.cwd();
26577
+ const repoRoot = options.repoRoot ?? process.cwd();
26494
26578
  if (scope !== "global") {
26495
- const localDir = rolesDirectory("local", repoRoot6, options.userConfigDir);
26496
- const localFile = join15(localDir, `${roleId}.yaml`);
26579
+ const localDir = rolesDirectory("local", repoRoot, options.userConfigDir);
26580
+ const localFile = join17(localDir, `${roleId}.yaml`);
26497
26581
  const parsed = parseRoleFile(localFile);
26498
26582
  if (parsed) return { role: parsed, scope: "local", filePath: localFile };
26499
26583
  }
26500
26584
  if (scope !== "local") {
26501
- const globalDir = rolesDirectory("global", repoRoot6, options.userConfigDir);
26502
- const globalFile = join15(globalDir, `${roleId}.yaml`);
26585
+ const globalDir = rolesDirectory("global", repoRoot, options.userConfigDir);
26586
+ const globalFile = join17(globalDir, `${roleId}.yaml`);
26503
26587
  const parsed = parseRoleFile(globalFile);
26504
26588
  if (parsed) return { role: parsed, scope: "global", filePath: globalFile };
26505
26589
  }
@@ -26507,24 +26591,24 @@ function getRole(roleId, options = {}) {
26507
26591
  }
26508
26592
  function addRole(role, options = {}) {
26509
26593
  const scope = options.scope ?? "local";
26510
- const repoRoot6 = options.repoRoot ?? process.cwd();
26511
- const dir = ensureRolesDirectory(scope, repoRoot6, options.userConfigDir);
26512
- const filePath = join15(dir, `${role.id}.yaml`);
26513
- if (existsSync13(filePath) && !options.overwrite) {
26594
+ const repoRoot = options.repoRoot ?? process.cwd();
26595
+ const dir = ensureRolesDirectory(scope, repoRoot, options.userConfigDir);
26596
+ const filePath = join17(dir, `${role.id}.yaml`);
26597
+ if (existsSync15(filePath) && !options.overwrite) {
26514
26598
  throw new Error(`role_already_exists: role '${role.id}' already exists at ${filePath}`);
26515
26599
  }
26516
- writeFileSync10(filePath, (0, import_yaml7.stringify)(role), "utf8");
26600
+ writeFileSync11(filePath, (0, import_yaml7.stringify)(role), "utf8");
26517
26601
  return { id: role.id, filePath, scope };
26518
26602
  }
26519
26603
  function removeRole(roleId, options = {}) {
26520
26604
  const scope = options.scope ?? "local";
26521
- const repoRoot6 = options.repoRoot ?? process.cwd();
26522
- const dir = rolesDirectory(scope, repoRoot6, options.userConfigDir);
26523
- const filePath = join15(dir, `${roleId}.yaml`);
26524
- if (!existsSync13(filePath)) {
26605
+ const repoRoot = options.repoRoot ?? process.cwd();
26606
+ const dir = rolesDirectory(scope, repoRoot, options.userConfigDir);
26607
+ const filePath = join17(dir, `${roleId}.yaml`);
26608
+ if (!existsSync15(filePath)) {
26525
26609
  throw new Error(`role_not_found: role '${roleId}' not found in ${scope} directory (${filePath})`);
26526
26610
  }
26527
- rmSync4(filePath);
26611
+ rmSync5(filePath);
26528
26612
  return { id: roleId, removed: true, filePath, scope };
26529
26613
  }
26530
26614
  function modifyRole(roleId, updates, options = {}) {
@@ -26540,10 +26624,10 @@ function modifyRole(roleId, updates, options = {}) {
26540
26624
  // preserve identity
26541
26625
  };
26542
26626
  const scope = options.scope ?? target.scope;
26543
- const repoRoot6 = options.repoRoot ?? process.cwd();
26544
- const dir = ensureRolesDirectory(scope, repoRoot6, options.userConfigDir);
26545
- const filePath = join15(dir, `${roleId}.yaml`);
26546
- writeFileSync10(filePath, (0, import_yaml7.stringify)(updated), "utf8");
26627
+ const repoRoot = options.repoRoot ?? process.cwd();
26628
+ const dir = ensureRolesDirectory(scope, repoRoot, options.userConfigDir);
26629
+ const filePath = join17(dir, `${roleId}.yaml`);
26630
+ writeFileSync11(filePath, (0, import_yaml7.stringify)(updated), "utf8");
26547
26631
  return { id: roleId, role: updated, filePath, scope };
26548
26632
  }
26549
26633
  var KXM_ROLE_HOSTS_SCHEMA = "kxm.role-hosts.v1";
@@ -26589,20 +26673,20 @@ var DEFAULT_ROLE_SEATS = {
26589
26673
  requiredEvidenceKind: "test_run"
26590
26674
  }
26591
26675
  };
26592
- function findExistingRoleHostsFile(scope, repoRoot6 = process.cwd(), userConfigDir) {
26593
- const dir = scope === "global" ? userConfigDirectory(userConfigDir) : repoConfigDirectory(repoRoot6);
26594
- const yamlPath = join15(dir, "role-hosts.yaml");
26595
- const ymlPath = join15(dir, "role-hosts.yml");
26596
- const jsonPath = join15(dir, "role-hosts.json");
26597
- if (existsSync13(yamlPath)) return { filePath: yamlPath, exists: true, format: "yaml" };
26598
- if (existsSync13(ymlPath)) return { filePath: ymlPath, exists: true, format: "yaml" };
26599
- if (existsSync13(jsonPath)) return { filePath: jsonPath, exists: true, format: "json" };
26676
+ function findExistingRoleHostsFile(scope, repoRoot = process.cwd(), userConfigDir) {
26677
+ const dir = scope === "global" ? userConfigDirectory(userConfigDir) : repoConfigDirectory(repoRoot);
26678
+ const yamlPath = join17(dir, "role-hosts.yaml");
26679
+ const ymlPath = join17(dir, "role-hosts.yml");
26680
+ const jsonPath = join17(dir, "role-hosts.json");
26681
+ if (existsSync15(yamlPath)) return { filePath: yamlPath, exists: true, format: "yaml" };
26682
+ if (existsSync15(ymlPath)) return { filePath: ymlPath, exists: true, format: "yaml" };
26683
+ if (existsSync15(jsonPath)) return { filePath: jsonPath, exists: true, format: "json" };
26600
26684
  return { filePath: yamlPath, exists: false, format: "yaml" };
26601
26685
  }
26602
26686
  function parseRoleHostsFile(filePath) {
26603
- if (!existsSync13(filePath)) return void 0;
26687
+ if (!existsSync15(filePath)) return void 0;
26604
26688
  try {
26605
- const raw = readFileSync14(filePath, "utf8");
26689
+ const raw = readFileSync15(filePath, "utf8");
26606
26690
  const parsed = (0, import_yaml7.parse)(raw);
26607
26691
  if (!parsed || typeof parsed !== "object") return void 0;
26608
26692
  if (parsed.schema && parsed.schema !== KXM_ROLE_HOSTS_SCHEMA) return void 0;
@@ -26617,11 +26701,11 @@ function parseRoleHostsFile(filePath) {
26617
26701
  }
26618
26702
  function loadRoleHostsConfig(options = {}) {
26619
26703
  const scopeFilter = options.scope ?? "all";
26620
- const repoRoot6 = options.repoRoot ?? process.cwd();
26704
+ const repoRoot = options.repoRoot ?? process.cwd();
26621
26705
  let localConfig;
26622
26706
  let localPath;
26623
26707
  if (scopeFilter !== "global") {
26624
- const localFound = findExistingRoleHostsFile("local", repoRoot6, options.userConfigDir);
26708
+ const localFound = findExistingRoleHostsFile("local", repoRoot, options.userConfigDir);
26625
26709
  if (localFound.exists) {
26626
26710
  localConfig = parseRoleHostsFile(localFound.filePath);
26627
26711
  localPath = localFound.filePath;
@@ -26630,7 +26714,7 @@ function loadRoleHostsConfig(options = {}) {
26630
26714
  let globalConfig;
26631
26715
  let globalPath;
26632
26716
  if (scopeFilter !== "local") {
26633
- const globalFound = findExistingRoleHostsFile("global", repoRoot6, options.userConfigDir);
26717
+ const globalFound = findExistingRoleHostsFile("global", repoRoot, options.userConfigDir);
26634
26718
  if (globalFound.exists) {
26635
26719
  globalConfig = parseRoleHostsFile(globalFound.filePath);
26636
26720
  globalPath = globalFound.filePath;
@@ -26672,20 +26756,20 @@ function loadRoleHostsConfig(options = {}) {
26672
26756
  }
26673
26757
  function saveRoleHostsConfig(config, options = {}) {
26674
26758
  const scope = options.scope ?? "local";
26675
- const repoRoot6 = options.repoRoot ?? process.cwd();
26676
- const dir = scope === "global" ? userConfigDirectory(options.userConfigDir) : repoConfigDirectory(repoRoot6);
26677
- if (!existsSync13(dir)) {
26678
- mkdirSync11(dir, { recursive: true });
26759
+ const repoRoot = options.repoRoot ?? process.cwd();
26760
+ const dir = scope === "global" ? userConfigDirectory(options.userConfigDir) : repoConfigDirectory(repoRoot);
26761
+ if (!existsSync15(dir)) {
26762
+ mkdirSync12(dir, { recursive: true });
26679
26763
  }
26680
26764
  const format = options.format ?? "yaml";
26681
- const filePath = join15(dir, format === "json" ? "role-hosts.json" : "role-hosts.yaml");
26765
+ const filePath = join17(dir, format === "json" ? "role-hosts.json" : "role-hosts.yaml");
26682
26766
  const payload = {
26683
26767
  schema: KXM_ROLE_HOSTS_SCHEMA,
26684
26768
  seats: config.seats ?? {},
26685
26769
  ...config.hostProviders && Object.keys(config.hostProviders).length > 0 ? { hostProviders: config.hostProviders } : {}
26686
26770
  };
26687
26771
  const content = format === "json" ? JSON.stringify(payload, null, 2) + "\n" : (0, import_yaml7.stringify)(payload);
26688
- writeFileSync10(filePath, content, "utf8");
26772
+ writeFileSync11(filePath, content, "utf8");
26689
26773
  return { filePath, scope };
26690
26774
  }
26691
26775
  function setRoleSeatHost(seatId, host, options = {}) {
@@ -26920,7 +27004,7 @@ async function cmdRoleAdd(runtime, roleId, options) {
26920
27004
  let roleDef;
26921
27005
  if (options.file) {
26922
27006
  const filePath = resolve12(runtime.cwd, options.file);
26923
- const content = readFileSync15(filePath, "utf8");
27007
+ const content = readFileSync16(filePath, "utf8");
26924
27008
  roleDef = (0, import_yaml8.parse)(content);
26925
27009
  roleDef.id = roleId;
26926
27010
  } else {
@@ -27219,8 +27303,8 @@ async function cmdRoleResume(runtime, runId, ruling) {
27219
27303
  return 1;
27220
27304
  }
27221
27305
  }
27222
- const dbPath = join16(runtime.cwd, ".kxm", "state", "kxm.db");
27223
- if (existsSync14(dbPath)) {
27306
+ const dbPath = join18(runtime.cwd, ".kxm", "state", "kxm.db");
27307
+ if (existsSync16(dbPath)) {
27224
27308
  try {
27225
27309
  const database = new DatabaseSync(dbPath);
27226
27310
  try {
@@ -27282,11 +27366,11 @@ async function cmdRoleResume(runtime, runId, ruling) {
27282
27366
 
27283
27367
  // plugins/kxm/src/cli/workflows.ts
27284
27368
  import { createHmac as createHmac3, randomUUID as randomUUID7 } from "node:crypto";
27285
- import { existsSync as existsSync16, readFileSync as readFileSync17 } from "node:fs";
27286
- import { join as join18, resolve as resolve15 } from "node:path";
27369
+ import { existsSync as existsSync18, readFileSync as readFileSync18 } from "node:fs";
27370
+ import { join as join20, resolve as resolve15 } from "node:path";
27287
27371
 
27288
27372
  // plugins/kxm/src/retrospective.ts
27289
- import { mkdirSync as mkdirSync12, renameSync as renameSync4, writeFileSync as writeFileSync11 } from "node:fs";
27373
+ import { mkdirSync as mkdirSync13, renameSync as renameSync5, writeFileSync as writeFileSync12 } from "node:fs";
27290
27374
  import { resolve as resolve13 } from "node:path";
27291
27375
  var MAX_RETROSPECTIVE_ENTRIES = 500;
27292
27376
  var SAFE_RUN_ID = /^run_[A-Za-z0-9_-]{1,120}$/;
@@ -27499,7 +27583,7 @@ function renderRetrospectiveMarkdown(doc) {
27499
27583
  }
27500
27584
  function writeRetrospective(outDir, doc) {
27501
27585
  if (!SAFE_RUN_ID.test(doc.runId)) throw new Error("invalid retrospective run id");
27502
- mkdirSync12(outDir, { recursive: true });
27586
+ mkdirSync13(outDir, { recursive: true });
27503
27587
  const root = resolve13(outDir);
27504
27588
  const jsonPath = resolve13(root, `${doc.runId}.json`);
27505
27589
  const mdPath = resolve13(root, `${doc.runId}.md`);
@@ -27507,11 +27591,11 @@ function writeRetrospective(outDir, doc) {
27507
27591
  if (!jsonPath.startsWith(prefix) || !mdPath.startsWith(prefix)) throw new Error("retrospective path escaped output directory");
27508
27592
  const jsonTmp = `${jsonPath}.tmp`;
27509
27593
  const mdTmp = `${mdPath}.tmp`;
27510
- writeFileSync11(jsonTmp, `${JSON.stringify(doc, null, 2)}
27594
+ writeFileSync12(jsonTmp, `${JSON.stringify(doc, null, 2)}
27511
27595
  `, { encoding: "utf8", mode: 384 });
27512
- writeFileSync11(mdTmp, renderRetrospectiveMarkdown(doc), { encoding: "utf8", mode: 384 });
27513
- renameSync4(jsonTmp, jsonPath);
27514
- renameSync4(mdTmp, mdPath);
27596
+ writeFileSync12(mdTmp, renderRetrospectiveMarkdown(doc), { encoding: "utf8", mode: 384 });
27597
+ renameSync5(jsonTmp, jsonPath);
27598
+ renameSync5(mdTmp, mdPath);
27515
27599
  return { jsonPath, mdPath };
27516
27600
  }
27517
27601
 
@@ -27701,8 +27785,8 @@ async function watchGithubChecks(input) {
27701
27785
 
27702
27786
  // plugins/kxm/src/workflow-manager.ts
27703
27787
  var import_yaml9 = __toESM(require_dist(), 1);
27704
- import { existsSync as existsSync15, mkdirSync as mkdirSync13, readdirSync as readdirSync5, readFileSync as readFileSync16, rmSync as rmSync5, writeFileSync as writeFileSync12 } from "node:fs";
27705
- import { join as join17 } from "node:path";
27788
+ import { existsSync as existsSync17, mkdirSync as mkdirSync14, readdirSync as readdirSync5, readFileSync as readFileSync17, rmSync as rmSync6, writeFileSync as writeFileSync13 } from "node:fs";
27789
+ import { join as join19 } from "node:path";
27706
27790
  var WORKFLOW_TEMPLATES = {
27707
27791
  "implement-and-verify": {
27708
27792
  schema: "kxm.workflow.v1",
@@ -27851,23 +27935,23 @@ var WORKFLOW_TEMPLATES = {
27851
27935
  }
27852
27936
  };
27853
27937
  var DEFAULT_WORKFLOW_TEMPLATE = WORKFLOW_TEMPLATES["implement-and-verify"];
27854
- function workflowsDirectory(scope, repoRoot6 = process.cwd(), userConfigDir) {
27938
+ function workflowsDirectory(scope, repoRoot = process.cwd(), userConfigDir) {
27855
27939
  if (scope === "global") {
27856
- return join17(userConfigDirectory(userConfigDir), "workflows");
27940
+ return join19(userConfigDirectory(userConfigDir), "workflows");
27857
27941
  }
27858
- return join17(repoConfigDirectory(repoRoot6), "workflows");
27942
+ return join19(repoConfigDirectory(repoRoot), "workflows");
27859
27943
  }
27860
- function ensureWorkflowsDirectory(scope, repoRoot6 = process.cwd(), userConfigDir) {
27861
- const dir = workflowsDirectory(scope, repoRoot6, userConfigDir);
27862
- if (!existsSync15(dir)) {
27863
- mkdirSync13(dir, { recursive: true });
27944
+ function ensureWorkflowsDirectory(scope, repoRoot = process.cwd(), userConfigDir) {
27945
+ const dir = workflowsDirectory(scope, repoRoot, userConfigDir);
27946
+ if (!existsSync17(dir)) {
27947
+ mkdirSync14(dir, { recursive: true });
27864
27948
  }
27865
27949
  return dir;
27866
27950
  }
27867
27951
  function parseWorkflowFile(filePath) {
27868
- if (!existsSync15(filePath)) return void 0;
27952
+ if (!existsSync17(filePath)) return void 0;
27869
27953
  try {
27870
- const raw = readFileSync16(filePath, "utf8");
27954
+ const raw = readFileSync17(filePath, "utf8");
27871
27955
  const parsed = (0, import_yaml9.parse)(raw);
27872
27956
  if (!parsed || typeof parsed !== "object") return void 0;
27873
27957
  return parsed;
@@ -27877,14 +27961,14 @@ function parseWorkflowFile(filePath) {
27877
27961
  }
27878
27962
  function listWorkflowDefinitions(options = {}) {
27879
27963
  const scopeFilter = options.scope ?? "all";
27880
- const repoRoot6 = options.repoRoot ?? process.cwd();
27881
- const globalDir = workflowsDirectory("global", repoRoot6, options.userConfigDir);
27882
- const localDir = workflowsDirectory("local", repoRoot6, options.userConfigDir);
27964
+ const repoRoot = options.repoRoot ?? process.cwd();
27965
+ const globalDir = workflowsDirectory("global", repoRoot, options.userConfigDir);
27966
+ const localDir = workflowsDirectory("local", repoRoot, options.userConfigDir);
27883
27967
  const localDefs = /* @__PURE__ */ new Map();
27884
- if (scopeFilter !== "global" && existsSync15(localDir)) {
27968
+ if (scopeFilter !== "global" && existsSync17(localDir)) {
27885
27969
  for (const entry of readdirSync5(localDir)) {
27886
27970
  if (entry.endsWith(".yaml") || entry.endsWith(".yml")) {
27887
- const filePath = join17(localDir, entry);
27971
+ const filePath = join19(localDir, entry);
27888
27972
  const def = parseWorkflowFile(filePath);
27889
27973
  if (def) {
27890
27974
  const id = def.id || entry.replace(/\.ya?ml$/i, "");
@@ -27894,10 +27978,10 @@ function listWorkflowDefinitions(options = {}) {
27894
27978
  }
27895
27979
  }
27896
27980
  const globalDefs = /* @__PURE__ */ new Map();
27897
- if (scopeFilter !== "local" && existsSync15(globalDir)) {
27981
+ if (scopeFilter !== "local" && existsSync17(globalDir)) {
27898
27982
  for (const entry of readdirSync5(globalDir)) {
27899
27983
  if (entry.endsWith(".yaml") || entry.endsWith(".yml")) {
27900
- const filePath = join17(globalDir, entry);
27984
+ const filePath = join19(globalDir, entry);
27901
27985
  const def = parseWorkflowFile(filePath);
27902
27986
  if (def) {
27903
27987
  const id = def.id || entry.replace(/\.ya?ml$/i, "");
@@ -27950,16 +28034,16 @@ function listWorkflowDefinitions(options = {}) {
27950
28034
  }
27951
28035
  function getWorkflowDefinition(workflowId, options = {}) {
27952
28036
  const scope = options.scope ?? "all";
27953
- const repoRoot6 = options.repoRoot ?? process.cwd();
28037
+ const repoRoot = options.repoRoot ?? process.cwd();
27954
28038
  if (scope !== "global") {
27955
- const localDir = workflowsDirectory("local", repoRoot6, options.userConfigDir);
27956
- const localFile = join17(localDir, `${workflowId}.yaml`);
28039
+ const localDir = workflowsDirectory("local", repoRoot, options.userConfigDir);
28040
+ const localFile = join19(localDir, `${workflowId}.yaml`);
27957
28041
  const parsed = parseWorkflowFile(localFile);
27958
28042
  if (parsed) return { workflow: parsed, scope: "local", filePath: localFile };
27959
28043
  }
27960
28044
  if (scope !== "local") {
27961
- const globalDir = workflowsDirectory("global", repoRoot6, options.userConfigDir);
27962
- const globalFile = join17(globalDir, `${workflowId}.yaml`);
28045
+ const globalDir = workflowsDirectory("global", repoRoot, options.userConfigDir);
28046
+ const globalFile = join19(globalDir, `${workflowId}.yaml`);
27963
28047
  const parsed = parseWorkflowFile(globalFile);
27964
28048
  if (parsed) return { workflow: parsed, scope: "global", filePath: globalFile };
27965
28049
  }
@@ -27967,25 +28051,25 @@ function getWorkflowDefinition(workflowId, options = {}) {
27967
28051
  }
27968
28052
  function addWorkflowDefinition(workflowId, content = DEFAULT_WORKFLOW_TEMPLATE, options = {}) {
27969
28053
  const scope = options.scope ?? "local";
27970
- const repoRoot6 = options.repoRoot ?? process.cwd();
27971
- const dir = ensureWorkflowsDirectory(scope, repoRoot6, options.userConfigDir);
27972
- const filePath = join17(dir, `${workflowId}.yaml`);
27973
- if (existsSync15(filePath) && !options.overwrite) {
28054
+ const repoRoot = options.repoRoot ?? process.cwd();
28055
+ const dir = ensureWorkflowsDirectory(scope, repoRoot, options.userConfigDir);
28056
+ const filePath = join19(dir, `${workflowId}.yaml`);
28057
+ if (existsSync17(filePath) && !options.overwrite) {
27974
28058
  throw new Error(`workflow_already_exists: workflow '${workflowId}' already exists at ${filePath}`);
27975
28059
  }
27976
28060
  const payload = typeof content === "string" ? content : (0, import_yaml9.stringify)(content);
27977
- writeFileSync12(filePath, payload, "utf8");
28061
+ writeFileSync13(filePath, payload, "utf8");
27978
28062
  return { id: workflowId, filePath, scope };
27979
28063
  }
27980
28064
  function removeWorkflowDefinition(workflowId, options = {}) {
27981
28065
  const scope = options.scope ?? "local";
27982
- const repoRoot6 = options.repoRoot ?? process.cwd();
27983
- const dir = workflowsDirectory(scope, repoRoot6, options.userConfigDir);
27984
- const filePath = join17(dir, `${workflowId}.yaml`);
27985
- if (!existsSync15(filePath)) {
28066
+ const repoRoot = options.repoRoot ?? process.cwd();
28067
+ const dir = workflowsDirectory(scope, repoRoot, options.userConfigDir);
28068
+ const filePath = join19(dir, `${workflowId}.yaml`);
28069
+ if (!existsSync17(filePath)) {
27986
28070
  throw new Error(`workflow_not_found: workflow '${workflowId}' not found in ${scope} directory (${filePath})`);
27987
28071
  }
27988
- rmSync5(filePath);
28072
+ rmSync6(filePath);
27989
28073
  return { id: workflowId, removed: true, filePath, scope };
27990
28074
  }
27991
28075
  function modifyWorkflowDefinition(workflowId, updates, options = {}) {
@@ -27998,17 +28082,17 @@ function modifyWorkflowDefinition(workflowId, updates, options = {}) {
27998
28082
  ...updates
27999
28083
  };
28000
28084
  const scope = options.scope ?? target.scope;
28001
- const repoRoot6 = options.repoRoot ?? process.cwd();
28002
- const dir = ensureWorkflowsDirectory(scope, repoRoot6, options.userConfigDir);
28003
- const filePath = join17(dir, `${workflowId}.yaml`);
28004
- writeFileSync12(filePath, (0, import_yaml9.stringify)(updated), "utf8");
28085
+ const repoRoot = options.repoRoot ?? process.cwd();
28086
+ const dir = ensureWorkflowsDirectory(scope, repoRoot, options.userConfigDir);
28087
+ const filePath = join19(dir, `${workflowId}.yaml`);
28088
+ writeFileSync13(filePath, (0, import_yaml9.stringify)(updated), "utf8");
28005
28089
  return { id: workflowId, workflow: updated, filePath, scope };
28006
28090
  }
28007
28091
 
28008
28092
  // plugins/kxm/src/cli/workflows.ts
28009
28093
  var CLI_NAME = "kxm";
28010
28094
  function localWorkflowSnapshot(dataPath, runId) {
28011
- if (!existsSync16(dataPath)) throw new Error("state_database_not_found");
28095
+ if (!existsSync18(dataPath)) throw new Error("state_database_not_found");
28012
28096
  const database = new DatabaseSync(dataPath, { readOnly: true });
28013
28097
  try {
28014
28098
  const rows = runId ? database.prepare("SELECT record FROM workflow_runs WHERE id = ?").all(runId) : database.prepare("SELECT record FROM workflow_runs ORDER BY rowid DESC LIMIT 200").all();
@@ -28085,7 +28169,7 @@ function activeWorkflowDefinition(runtime, definitionId) {
28085
28169
  let raw;
28086
28170
  if (file) {
28087
28171
  try {
28088
- raw = readFileSync17(resolve15(runtime.cwd, file), "utf8");
28172
+ raw = readFileSync18(resolve15(runtime.cwd, file), "utf8");
28089
28173
  } catch {
28090
28174
  throw new Error("workflow definition file is unavailable");
28091
28175
  }
@@ -28167,7 +28251,7 @@ async function cmdWorkflowAdd(runtime, workflowId, options) {
28167
28251
  }
28168
28252
  if (options.file) {
28169
28253
  const filePath = resolve15(runtime.cwd, options.file);
28170
- content = readFileSync17(filePath, "utf8");
28254
+ content = readFileSync18(filePath, "utf8");
28171
28255
  } else if (!content) {
28172
28256
  content = {
28173
28257
  schema: "kxm.workflow.v1",
@@ -28325,7 +28409,7 @@ async function cmdWorkflowStart(runtime, definitionIdArg, options) {
28325
28409
  }
28326
28410
  let payload;
28327
28411
  try {
28328
- const raw = payloadFlag.startsWith("@") ? readFileSync17(resolve15(runtime.cwd, payloadFlag.slice(1)), "utf8") : payloadFlag;
28412
+ const raw = payloadFlag.startsWith("@") ? readFileSync18(resolve15(runtime.cwd, payloadFlag.slice(1)), "utf8") : payloadFlag;
28329
28413
  const value = JSON.parse(raw);
28330
28414
  if (!value || typeof value !== "object" || Array.isArray(value)) throw new Error("object required");
28331
28415
  payload = value;
@@ -28392,7 +28476,7 @@ async function cmdWorkflowDegrade(runtime, runId, stageId, options) {
28392
28476
  }
28393
28477
  }
28394
28478
  async function cmdWorkflowInspect(runtime, action, runId) {
28395
- const dataPath = resolve15(runtime.dirs.workdir, runtime.env.KXM_DATA_PATH?.trim() || join18(runtime.dirs.state, "kxm.db"));
28479
+ const dataPath = resolve15(runtime.dirs.workdir, runtime.env.KXM_DATA_PATH?.trim() || join20(runtime.dirs.state, "kxm.db"));
28396
28480
  if (action === "get" && !runId) {
28397
28481
  runtime.io.stderr(`Usage: ${CLI_NAME} workflow get <runId>
28398
28482
  `);
@@ -28565,10 +28649,10 @@ async function cmdRetrospectiveExport(runtime, runId, options) {
28565
28649
  let snapshot;
28566
28650
  try {
28567
28651
  if (snapshotPath) {
28568
- if (!existsSync16(snapshotPath)) throw new Error("snapshot_missing");
28569
- snapshot = JSON.parse(readFileSync17(snapshotPath, "utf8"));
28652
+ if (!existsSync18(snapshotPath)) throw new Error("snapshot_missing");
28653
+ snapshot = JSON.parse(readFileSync18(snapshotPath, "utf8"));
28570
28654
  } else {
28571
- const dataPath = resolve15(runtime.dirs.workdir, runtime.env.KXM_DATA_PATH?.trim() || join18(runtime.dirs.state, "kxm.db"));
28655
+ const dataPath = resolve15(runtime.dirs.workdir, runtime.env.KXM_DATA_PATH?.trim() || join20(runtime.dirs.state, "kxm.db"));
28572
28656
  const local = localWorkflowSnapshot(dataPath, runId);
28573
28657
  if (!local.runs[0]) throw new Error("workflow_not_found");
28574
28658
  snapshot = { run: local.runs[0], journal: local.journal };
@@ -28580,7 +28664,7 @@ async function cmdRetrospectiveExport(runtime, runId, options) {
28580
28664
  return 1;
28581
28665
  }
28582
28666
  const doc = buildRetrospective(snapshot.run, snapshot.journal);
28583
- const outDir = resolve15(runtime.cwd, String(options.outDir || join18(runtime.dirs.assets, "retrospectives")));
28667
+ const outDir = resolve15(runtime.cwd, String(options.outDir || join20(runtime.dirs.assets, "retrospectives")));
28584
28668
  const assetsRoot = resolve15(runtime.dirs.assets);
28585
28669
  const assetsPrefix = `${assetsRoot}${process.platform === "win32" ? "\\" : "/"}`;
28586
28670
  if (outDir !== assetsRoot && !outDir.startsWith(assetsPrefix)) {
@@ -28598,8 +28682,8 @@ async function cmdRetrospectiveExport(runtime, runId, options) {
28598
28682
 
28599
28683
  // plugins/kxm/src/cli/tasks.ts
28600
28684
  var import_yaml13 = __toESM(require_dist(), 1);
28601
- import { existsSync as existsSync22, readFileSync as readFileSync22, readdirSync as readdirSync8 } from "node:fs";
28602
- import { basename as basename6, join as join26, resolve as resolve21 } from "node:path";
28685
+ import { existsSync as existsSync24, readFileSync as readFileSync23, readdirSync as readdirSync8 } from "node:fs";
28686
+ import { basename as basename6, join as join28, resolve as resolve21 } from "node:path";
28603
28687
 
28604
28688
  // plugins/kxm/src/suggest.ts
28605
28689
  var WORKFLOW_PATTERNS = [
@@ -28710,19 +28794,19 @@ function suggestWorkflowAndRoles(prompt, options = {}) {
28710
28794
  // plugins/kxm/src/task-manager.ts
28711
28795
  var import_yaml10 = __toESM(require_dist(), 1);
28712
28796
  import { randomUUID as randomUUID8 } from "node:crypto";
28713
- import { existsSync as existsSync17, mkdirSync as mkdirSync14, readFileSync as readFileSync18, readdirSync as readdirSync6, writeFileSync as writeFileSync13 } from "node:fs";
28714
- import { join as join19, resolve as resolve16 } from "node:path";
28797
+ import { existsSync as existsSync19, mkdirSync as mkdirSync15, readFileSync as readFileSync19, readdirSync as readdirSync6, writeFileSync as writeFileSync14 } from "node:fs";
28798
+ import { join as join21, resolve as resolve16 } from "node:path";
28715
28799
  var GOAL_SCHEMA = "kxm.goal.v1";
28716
28800
  var TASK_SCHEMA = "kxm.task.v1";
28717
- function goalsDirectory(repoRoot6) {
28718
- return resolve16(repoRoot6, ".kxm", "goals");
28801
+ function goalsDirectory(repoRoot) {
28802
+ return resolve16(repoRoot, ".kxm", "goals");
28719
28803
  }
28720
- function tasksDirectory(repoRoot6) {
28721
- return resolve16(repoRoot6, ".kxm", "tasks");
28804
+ function tasksDirectory(repoRoot) {
28805
+ return resolve16(repoRoot, ".kxm", "tasks");
28722
28806
  }
28723
- function createGoal(repoRoot6, input) {
28724
- const dir = goalsDirectory(repoRoot6);
28725
- mkdirSync14(dir, { recursive: true });
28807
+ function createGoal(repoRoot, input) {
28808
+ const dir = goalsDirectory(repoRoot);
28809
+ mkdirSync15(dir, { recursive: true });
28726
28810
  const id = `goal_${randomUUID8().replaceAll("-", "").slice(0, 12)}`;
28727
28811
  const now = (/* @__PURE__ */ new Date()).toISOString();
28728
28812
  const record = {
@@ -28736,19 +28820,19 @@ function createGoal(repoRoot6, input) {
28736
28820
  createdAt: now,
28737
28821
  updatedAt: now
28738
28822
  };
28739
- const filePath = join19(dir, `${id}.yaml`);
28740
- writeFileSync13(filePath, (0, import_yaml10.stringify)(record).trim() + "\n", "utf8");
28823
+ const filePath = join21(dir, `${id}.yaml`);
28824
+ writeFileSync14(filePath, (0, import_yaml10.stringify)(record).trim() + "\n", "utf8");
28741
28825
  return record;
28742
28826
  }
28743
- function listGoals(repoRoot6) {
28744
- const dir = goalsDirectory(repoRoot6);
28745
- if (!existsSync17(dir)) return [];
28827
+ function listGoals(repoRoot) {
28828
+ const dir = goalsDirectory(repoRoot);
28829
+ if (!existsSync19(dir)) return [];
28746
28830
  const goals = [];
28747
28831
  const entries = readdirSync6(dir, { withFileTypes: true });
28748
28832
  for (const entry of entries) {
28749
28833
  if (entry.isFile() && (entry.name.endsWith(".yaml") || entry.name.endsWith(".yml"))) {
28750
28834
  try {
28751
- const text = readFileSync18(join19(dir, entry.name), "utf8");
28835
+ const text = readFileSync19(join21(dir, entry.name), "utf8");
28752
28836
  const doc = (0, import_yaml10.parse)(text);
28753
28837
  if (doc && doc.schema === GOAL_SCHEMA) goals.push(doc);
28754
28838
  } catch {
@@ -28757,9 +28841,9 @@ function listGoals(repoRoot6) {
28757
28841
  }
28758
28842
  return goals.sort((a, b2) => a.createdAt.localeCompare(b2.createdAt));
28759
28843
  }
28760
- function createTask(repoRoot6, input) {
28761
- const dir = tasksDirectory(repoRoot6);
28762
- mkdirSync14(dir, { recursive: true });
28844
+ function createTask(repoRoot, input) {
28845
+ const dir = tasksDirectory(repoRoot);
28846
+ mkdirSync15(dir, { recursive: true });
28763
28847
  const id = `task_${randomUUID8().replaceAll("-", "").slice(0, 12)}`;
28764
28848
  const now = (/* @__PURE__ */ new Date()).toISOString();
28765
28849
  const record = {
@@ -28781,19 +28865,19 @@ function createTask(repoRoot6, input) {
28781
28865
  createdAt: now,
28782
28866
  updatedAt: now
28783
28867
  };
28784
- const filePath = join19(dir, `${id}.yaml`);
28785
- writeFileSync13(filePath, (0, import_yaml10.stringify)(record).trim() + "\n", "utf8");
28868
+ const filePath = join21(dir, `${id}.yaml`);
28869
+ writeFileSync14(filePath, (0, import_yaml10.stringify)(record).trim() + "\n", "utf8");
28786
28870
  return record;
28787
28871
  }
28788
- function listTasks(repoRoot6, options = {}) {
28789
- const dir = tasksDirectory(repoRoot6);
28790
- if (!existsSync17(dir)) return [];
28872
+ function listTasks(repoRoot, options = {}) {
28873
+ const dir = tasksDirectory(repoRoot);
28874
+ if (!existsSync19(dir)) return [];
28791
28875
  const tasks = [];
28792
28876
  const entries = readdirSync6(dir, { withFileTypes: true });
28793
28877
  for (const entry of entries) {
28794
28878
  if (entry.isFile() && (entry.name.endsWith(".yaml") || entry.name.endsWith(".yml"))) {
28795
28879
  try {
28796
- const text = readFileSync18(join19(dir, entry.name), "utf8");
28880
+ const text = readFileSync19(join21(dir, entry.name), "utf8");
28797
28881
  const doc = (0, import_yaml10.parse)(text);
28798
28882
  if (doc && doc.schema === TASK_SCHEMA) {
28799
28883
  if (options.goalId && doc.goalId !== options.goalId) continue;
@@ -28806,32 +28890,32 @@ function listTasks(repoRoot6, options = {}) {
28806
28890
  }
28807
28891
  return tasks.sort((a, b2) => a.createdAt.localeCompare(b2.createdAt));
28808
28892
  }
28809
- function getTask(repoRoot6, taskId) {
28810
- const dir = tasksDirectory(repoRoot6);
28811
- const filePath = join19(dir, `${taskId}.yaml`);
28812
- if (!existsSync17(filePath)) return void 0;
28893
+ function getTask(repoRoot, taskId) {
28894
+ const dir = tasksDirectory(repoRoot);
28895
+ const filePath = join21(dir, `${taskId}.yaml`);
28896
+ if (!existsSync19(filePath)) return void 0;
28813
28897
  try {
28814
- const text = readFileSync18(filePath, "utf8");
28898
+ const text = readFileSync19(filePath, "utf8");
28815
28899
  const doc = (0, import_yaml10.parse)(text);
28816
28900
  return doc && doc.schema === TASK_SCHEMA ? doc : void 0;
28817
28901
  } catch {
28818
28902
  return void 0;
28819
28903
  }
28820
28904
  }
28821
- function updateTaskStatus(repoRoot6, taskId, status, options = {}) {
28822
- const task = getTask(repoRoot6, taskId);
28905
+ function updateTaskStatus(repoRoot, taskId, status, options = {}) {
28906
+ const task = getTask(repoRoot, taskId);
28823
28907
  if (!task) {
28824
28908
  throw new Error(`Task ${taskId} not found`);
28825
28909
  }
28826
28910
  task.status = status;
28827
28911
  if (options.workflowRunId) task.workflowRunId = options.workflowRunId;
28828
28912
  task.updatedAt = (/* @__PURE__ */ new Date()).toISOString();
28829
- const filePath = join19(tasksDirectory(repoRoot6), `${taskId}.yaml`);
28830
- writeFileSync13(filePath, (0, import_yaml10.stringify)(task).trim() + "\n", "utf8");
28913
+ const filePath = join21(tasksDirectory(repoRoot), `${taskId}.yaml`);
28914
+ writeFileSync14(filePath, (0, import_yaml10.stringify)(task).trim() + "\n", "utf8");
28831
28915
  return task;
28832
28916
  }
28833
- function syncTaskWithTracker(repoRoot6, taskId, options = {}) {
28834
- const task = getTask(repoRoot6, taskId);
28917
+ function syncTaskWithTracker(repoRoot, taskId, options = {}) {
28918
+ const task = getTask(repoRoot, taskId);
28835
28919
  if (!task) {
28836
28920
  throw new Error(`Task ${taskId} not found`);
28837
28921
  }
@@ -28842,8 +28926,8 @@ function syncTaskWithTracker(repoRoot6, taskId, options = {}) {
28842
28926
  task.trackerSync.syncStatus = "synced";
28843
28927
  task.trackerSync.lastSyncedAt = now;
28844
28928
  task.updatedAt = now;
28845
- const filePath = join19(tasksDirectory(repoRoot6), `${taskId}.yaml`);
28846
- writeFileSync13(filePath, (0, import_yaml10.stringify)(task).trim() + "\n", "utf8");
28929
+ const filePath = join21(tasksDirectory(repoRoot), `${taskId}.yaml`);
28930
+ writeFileSync14(filePath, (0, import_yaml10.stringify)(task).trim() + "\n", "utf8");
28847
28931
  return task;
28848
28932
  }
28849
28933
 
@@ -29609,14 +29693,13 @@ function createStudioServer(options = {}) {
29609
29693
  }
29610
29694
 
29611
29695
  // plugins/kxm/src/cli/vnext.ts
29612
- import { join as join25, resolve as resolve20 } from "node:path";
29696
+ import { join as join27, resolve as resolve20 } from "node:path";
29613
29697
  import { createInterface as createInterface2 } from "node:readline";
29614
- import { fileURLToPath as fileURLToPath4 } from "node:url";
29615
29698
 
29616
29699
  // plugins/kxm/src/model-inventory.ts
29617
29700
  var import_yaml11 = __toESM(require_dist(), 1);
29618
- import { mkdirSync as mkdirSync15, writeFileSync as writeFileSync14 } from "node:fs";
29619
- import { join as join20 } from "node:path";
29701
+ import { mkdirSync as mkdirSync16, writeFileSync as writeFileSync15 } from "node:fs";
29702
+ import { join as join22 } from "node:path";
29620
29703
  var OR_URL = "https://openrouter.ai/api/v1/models";
29621
29704
  var NOUS_URL = "https://inference-api.nousresearch.com/v1/models";
29622
29705
  function price(value) {
@@ -29702,41 +29785,41 @@ async function refreshModelInventory(options) {
29702
29785
  sources.nous = { url: nousUrl, ok: !nous.error, ...nous.error ? { error: nous.error } : {} };
29703
29786
  for (const item of nous.data) add(item, "nous", "discount");
29704
29787
  const inventory = { schema: "kxm.model-inventory.v1", fetchedAt, currency: "USD", sources, models: [...byId.values()].sort((a, b2) => a.id.localeCompare(b2.id)) };
29705
- mkdirSync15(join20(options.outputRoot, ".kxm", "models"), { recursive: true });
29706
- writeFileSync14(join20(options.outputRoot, ".kxm", "models", "inventory.yaml"), (0, import_yaml11.stringify)(inventory), "utf8");
29788
+ mkdirSync16(join22(options.outputRoot, ".kxm", "models"), { recursive: true });
29789
+ writeFileSync15(join22(options.outputRoot, ".kxm", "models", "inventory.yaml"), (0, import_yaml11.stringify)(inventory), "utf8");
29707
29790
  return inventory;
29708
29791
  }
29709
29792
 
29710
29793
  // plugins/kxm/src/vnext-init.ts
29711
29794
  import { randomUUID as randomUUID11 } from "node:crypto";
29712
- import { existsSync as existsSync20 } from "node:fs";
29713
- import { basename as basename5, join as join23 } from "node:path";
29795
+ import { existsSync as existsSync22 } from "node:fs";
29796
+ import { basename as basename5, join as join25 } from "node:path";
29714
29797
 
29715
29798
  // plugins/kxm/src/vnext-repair.ts
29716
29799
  import { randomUUID as randomUUID10 } from "node:crypto";
29717
29800
  import {
29718
29801
  chmodSync as chmodSync5,
29719
29802
  closeSync as closeSync2,
29720
- existsSync as existsSync19,
29803
+ existsSync as existsSync21,
29721
29804
  fsyncSync as fsyncSync2,
29722
29805
  linkSync,
29723
29806
  lstatSync as lstatSync7,
29724
- mkdirSync as mkdirSync17,
29807
+ mkdirSync as mkdirSync18,
29725
29808
  openSync as openSync2,
29726
- readFileSync as readFileSync20,
29809
+ readFileSync as readFileSync21,
29727
29810
  readdirSync as readdirSync7,
29728
- renameSync as renameSync5,
29729
- rmSync as rmSync7,
29730
- writeFileSync as writeFileSync16
29811
+ renameSync as renameSync6,
29812
+ rmSync as rmSync8,
29813
+ writeFileSync as writeFileSync17
29731
29814
  } from "node:fs";
29732
- import { dirname as dirname13, isAbsolute as isAbsolute6, join as join22, relative as relative4, resolve as resolve18 } from "node:path";
29815
+ import { dirname as dirname15, isAbsolute as isAbsolute7, join as join24, relative as relative4, resolve as resolve18 } from "node:path";
29733
29816
 
29734
29817
  // plugins/kxm/src/vnext-permission.ts
29735
29818
  import { spawnSync as spawnSync4 } from "node:child_process";
29736
29819
  import { createHash as createHash12 } from "node:crypto";
29737
- import { existsSync as existsSync18, mkdtempSync, mkdirSync as mkdirSync16, readFileSync as readFileSync19, rmSync as rmSync6, writeFileSync as writeFileSync15 } from "node:fs";
29820
+ import { existsSync as existsSync20, mkdtempSync, mkdirSync as mkdirSync17, readFileSync as readFileSync20, rmSync as rmSync7, writeFileSync as writeFileSync16 } from "node:fs";
29738
29821
  import { tmpdir } from "node:os";
29739
- import { dirname as dirname12, join as join21, resolve as resolve17, sep as sep3 } from "node:path";
29822
+ import { dirname as dirname14, join as join23, resolve as resolve17, sep as sep3 } from "node:path";
29740
29823
  var PROSE_FIELDS = {
29741
29824
  project: /* @__PURE__ */ new Set(["name", "description"]),
29742
29825
  repository: /* @__PURE__ */ new Set(["description"]),
@@ -30257,7 +30340,7 @@ function loadVnextProjectAtRevision(root, revision, options = {}) {
30257
30340
  const tree = resolveTreeRevision(root, revision);
30258
30341
  const listing = gitBuffer(root, ["ls-tree", "-r", "-z", "--name-only", tree]).toString("utf8");
30259
30342
  const paths = listing.split("\0").filter((line) => line.length > 0 && (line.startsWith(".kxm/") || line.includes("/.kxm/")));
30260
- const shadow = mkdtempSync(join21(tmpdir(), "kxm-permission-base-"));
30343
+ const shadow = mkdtempSync(join23(tmpdir(), "kxm-permission-base-"));
30261
30344
  const shadowResolved = resolve17(shadow);
30262
30345
  const shadowMembersDir = `.kxm-shadow-members-${createHash12("sha256").update(shadowResolved, "utf8").digest("hex").slice(0, 8)}`;
30263
30346
  try {
@@ -30271,7 +30354,7 @@ function loadVnextProjectAtRevision(root, revision, options = {}) {
30271
30354
  message: "Git tree entry contains a traversal or non-portable segment"
30272
30355
  }]);
30273
30356
  }
30274
- const absolute = join21(shadowResolved, ...segments);
30357
+ const absolute = join23(shadowResolved, ...segments);
30275
30358
  const resolved = resolve17(absolute);
30276
30359
  if (!resolved.startsWith(`${shadowResolved}${sep3}`)) {
30277
30360
  throw new VnextConfigError([{
@@ -30282,11 +30365,11 @@ function loadVnextProjectAtRevision(root, revision, options = {}) {
30282
30365
  }]);
30283
30366
  }
30284
30367
  const content = gitBuffer(root, ["cat-file", "blob", `${tree}:${path4}`]);
30285
- mkdirSync16(dirname12(absolute), { recursive: true });
30286
- writeFileSync15(absolute, content);
30368
+ mkdirSync17(dirname14(absolute), { recursive: true });
30369
+ writeFileSync16(absolute, content);
30287
30370
  }
30288
30371
  initShadowGitRoot(shadowResolved);
30289
- const baseProjectFile = join21(shadowResolved, ".kxm", "project.yaml");
30372
+ const baseProjectFile = join23(shadowResolved, ".kxm", "project.yaml");
30290
30373
  let baseProject;
30291
30374
  try {
30292
30375
  baseProject = loadBaseProjectDeclarations(baseProjectFile);
@@ -30317,7 +30400,7 @@ function loadVnextProjectAtRevision(root, revision, options = {}) {
30317
30400
  }
30318
30401
  const boundPath = options.repositoryBindings?.[member.repositoryId];
30319
30402
  const memberWorktree = boundPath ? resolve17(boundPath) : member.pathHint ? resolve17(root, ...member.pathHint.split("/")) : void 0;
30320
- if (!memberWorktree || !existsSync18(memberWorktree)) {
30403
+ if (!memberWorktree || !existsSync20(memberWorktree)) {
30321
30404
  if (member.required === false) continue;
30322
30405
  throw new VnextConfigError([{
30323
30406
  phase: "discovery",
@@ -30364,7 +30447,7 @@ function loadVnextProjectAtRevision(root, revision, options = {}) {
30364
30447
  const memberTree = git(memberWorktree, ["rev-parse", "--verify", "--quiet", `${pinnedCommit}^{tree}`]).trim();
30365
30448
  const memberListing = gitBuffer(memberWorktree, ["ls-tree", "-r", "-z", "--name-only", memberTree]).toString("utf8");
30366
30449
  const memberPaths = memberListing.split("\0").filter((line) => line.length > 0 && (line.startsWith(".kxm/") || line.includes("/.kxm/")));
30367
- const memberShadowRoot = join21(shadowResolved, shadowMembersDir, member.repositoryId);
30450
+ const memberShadowRoot = join23(shadowResolved, shadowMembersDir, member.repositoryId);
30368
30451
  if (!resolve17(memberShadowRoot).startsWith(`${resolve17(shadowResolved, shadowMembersDir)}${sep3}`)) {
30369
30452
  throw new VnextConfigError([{
30370
30453
  phase: "path",
@@ -30378,14 +30461,14 @@ function loadVnextProjectAtRevision(root, revision, options = {}) {
30378
30461
  if (segments.some((segment) => segment === "" || segment === "." || segment === ".." || /[\\:]/.test(segment))) {
30379
30462
  throw new VnextConfigError([{ phase: "path", code: "git_tree_path_invalid", file: path4, message: "member Git tree entry contains a traversal or non-portable segment" }]);
30380
30463
  }
30381
- const absolute = join21(memberShadowRoot, ...segments);
30464
+ const absolute = join23(memberShadowRoot, ...segments);
30382
30465
  const resolved = resolve17(absolute);
30383
30466
  if (!resolved.startsWith(`${resolve17(memberShadowRoot)}${sep3}`)) {
30384
30467
  throw new VnextConfigError([{ phase: "path", code: "git_tree_path_invalid", file: path4, message: "member Git tree entry escapes the shadow root" }]);
30385
30468
  }
30386
30469
  const content = gitBuffer(memberWorktree, ["cat-file", "blob", `${memberTree}:${path4}`]);
30387
- mkdirSync16(dirname12(absolute), { recursive: true });
30388
- writeFileSync15(absolute, content);
30470
+ mkdirSync17(dirname14(absolute), { recursive: true });
30471
+ writeFileSync16(absolute, content);
30389
30472
  }
30390
30473
  initShadowGitRoot(memberShadowRoot);
30391
30474
  shadowBindings[member.repositoryId] = memberShadowRoot;
@@ -30399,15 +30482,15 @@ function loadVnextProjectAtRevision(root, revision, options = {}) {
30399
30482
  throw error;
30400
30483
  }
30401
30484
  } finally {
30402
- rmSync6(shadow, { recursive: true, force: true });
30485
+ rmSync7(shadow, { recursive: true, force: true });
30403
30486
  }
30404
30487
  }
30405
30488
  function portableMemberPathHint(pathHint) {
30406
30489
  return pathHint !== "." && vnextPortablePath(pathHint);
30407
30490
  }
30408
30491
  function loadBaseProjectDeclarations(projectFile) {
30409
- if (!existsSync18(projectFile)) return [];
30410
- const value = parseRestrictedYaml2(readFileSync19(projectFile, "utf8"), ".kxm/project.yaml");
30492
+ if (!existsSync20(projectFile)) return [];
30493
+ const value = parseRestrictedYaml2(readFileSync20(projectFile, "utf8"), ".kxm/project.yaml");
30411
30494
  const repositories = Array.isArray(value?.repositories) ? value.repositories : [];
30412
30495
  const members = [];
30413
30496
  for (const entry of repositories) {
@@ -30499,7 +30582,7 @@ function writeDurableNew(file, bytes, mode) {
30499
30582
  let descriptor;
30500
30583
  try {
30501
30584
  descriptor = openSync2(file, "wx", mode);
30502
- writeFileSync16(descriptor, bytes);
30585
+ writeFileSync17(descriptor, bytes);
30503
30586
  fsyncSync2(descriptor);
30504
30587
  closeSync2(descriptor);
30505
30588
  descriptor = void 0;
@@ -30510,13 +30593,13 @@ function writeDurableNew(file, bytes, mode) {
30510
30593
  } finally {
30511
30594
  if (descriptor !== void 0) closeSync2(descriptor);
30512
30595
  }
30513
- syncDirectory2(dirname13(file));
30596
+ syncDirectory2(dirname15(file));
30514
30597
  }
30515
30598
  function writeDurable(file, bytes, mode) {
30516
30599
  let descriptor;
30517
30600
  try {
30518
30601
  descriptor = openSync2(file, "w", mode);
30519
- writeFileSync16(descriptor, bytes);
30602
+ writeFileSync17(descriptor, bytes);
30520
30603
  fsyncSync2(descriptor);
30521
30604
  closeSync2(descriptor);
30522
30605
  descriptor = void 0;
@@ -30527,7 +30610,7 @@ function writeDurable(file, bytes, mode) {
30527
30610
  } finally {
30528
30611
  if (descriptor !== void 0) closeSync2(descriptor);
30529
30612
  }
30530
- syncDirectory2(dirname13(file));
30613
+ syncDirectory2(dirname15(file));
30531
30614
  }
30532
30615
  function sameHostPath3(left, right) {
30533
30616
  const first = resolve18(left);
@@ -30535,45 +30618,45 @@ function sameHostPath3(left, right) {
30535
30618
  return process.platform === "win32" ? first.toLocaleLowerCase("en-US") === second.toLocaleLowerCase("en-US") : first === second;
30536
30619
  }
30537
30620
  function transactionRoot(projectRoot) {
30538
- return join22(resolve18(projectRoot), TRANSACTION_NAME);
30621
+ return join24(resolve18(projectRoot), TRANSACTION_NAME);
30539
30622
  }
30540
30623
  function operationFile(projectRoot) {
30541
- return join22(transactionRoot(projectRoot), OPERATION_FILE);
30624
+ return join24(transactionRoot(projectRoot), OPERATION_FILE);
30542
30625
  }
30543
30626
  function targetFile(projectRoot, portablePath2) {
30544
- return join22(transactionRoot(projectRoot), "targets", ...portablePath2.split("/"));
30627
+ return join24(transactionRoot(projectRoot), "targets", ...portablePath2.split("/"));
30545
30628
  }
30546
30629
  function shadowRoot(projectRoot) {
30547
- return join22(transactionRoot(projectRoot), "shadow");
30630
+ return join24(transactionRoot(projectRoot), "shadow");
30548
30631
  }
30549
30632
  function backupFile(projectRoot, portablePath2) {
30550
- return join22(transactionRoot(projectRoot), "backups", ...portablePath2.split("/"));
30633
+ return join24(transactionRoot(projectRoot), "backups", ...portablePath2.split("/"));
30551
30634
  }
30552
30635
  function portableManagedPath(path4) {
30553
- return path4.startsWith(".kxm/") && path4 !== VNEXT_TEMPLATE_PROVENANCE_PATH && path4.length <= 1024 && !path4.includes("\\") && !isAbsolute6(path4) && PORTABLE_PATH.test(path4) && !/[<>:"|?*]/.test(path4);
30636
+ return path4.startsWith(".kxm/") && path4 !== VNEXT_TEMPLATE_PROVENANCE_PATH && path4.length <= 1024 && !path4.includes("\\") && !isAbsolute7(path4) && PORTABLE_PATH.test(path4) && !/[<>:"|?*]/.test(path4);
30554
30637
  }
30555
30638
  function readRegularBounded(file, label) {
30556
30639
  const stat = lstatSync7(file);
30557
30640
  if (stat.isSymbolicLink() || !stat.isFile()) fail3("repair_file_invalid", label, "managed file must be a regular file, not a link or directory", "path");
30558
30641
  if (stat.size > MAX_MANAGED_FILE_BYTES) fail3("repair_file_too_large", label, `managed file exceeds ${MAX_MANAGED_FILE_BYTES} bytes`, "parse");
30559
- return readFileSync20(file);
30642
+ return readFileSync21(file);
30560
30643
  }
30561
30644
  function readOptionalManaged(projectRoot, path4) {
30562
- const file = join22(projectRoot, ...path4.split("/"));
30563
- if (!existsSync19(file)) return void 0;
30564
- let parent = dirname13(file);
30645
+ const file = join24(projectRoot, ...path4.split("/"));
30646
+ if (!existsSync21(file)) return void 0;
30647
+ let parent = dirname15(file);
30565
30648
  const boundary = resolve18(projectRoot);
30566
30649
  while (parent !== boundary) {
30567
30650
  const stat = lstatSync7(parent);
30568
30651
  if (stat.isSymbolicLink() || !stat.isDirectory()) fail3("repair_parent_invalid", path4, "managed file parents must be regular directories", "path");
30569
- parent = dirname13(parent);
30652
+ parent = dirname15(parent);
30570
30653
  }
30571
30654
  return readRegularBounded(file, path4);
30572
30655
  }
30573
30656
  function readProjectAndProvenance(projectRoot, schemasDir) {
30574
- const projectFile = join22(projectRoot, ".kxm", "project.yaml");
30575
- const provenanceFile = join22(projectRoot, ...VNEXT_TEMPLATE_PROVENANCE_PATH.split("/"));
30576
- if (!existsSync19(projectFile) || !existsSync19(provenanceFile)) return void 0;
30657
+ const projectFile = join24(projectRoot, ".kxm", "project.yaml");
30658
+ const provenanceFile = join24(projectRoot, ...VNEXT_TEMPLATE_PROVENANCE_PATH.split("/"));
30659
+ if (!existsSync21(projectFile) || !existsSync21(provenanceFile)) return void 0;
30577
30660
  const projectBytes = readOptionalManaged(projectRoot, ".kxm/project.yaml");
30578
30661
  const provenanceBytes = readOptionalManaged(projectRoot, VNEXT_TEMPLATE_PROVENANCE_PATH);
30579
30662
  if (!projectBytes || !provenanceBytes) return void 0;
@@ -30737,14 +30820,14 @@ function operationPlanSha(operation) {
30737
30820
  function writeOperation(projectRoot, operation) {
30738
30821
  const root = transactionRoot(projectRoot);
30739
30822
  const file = operationFile(projectRoot);
30740
- const temporary = join22(root, `.operation-${operation.operationId}-${randomUUID10()}.tmp`);
30823
+ const temporary = join24(root, `.operation-${operation.operationId}-${randomUUID10()}.tmp`);
30741
30824
  try {
30742
30825
  writeDurableNew(temporary, Buffer.from(`${JSON.stringify(operation, null, 2)}
30743
30826
  `, "utf8"), 384);
30744
- renameSync5(temporary, file);
30827
+ renameSync6(temporary, file);
30745
30828
  syncDirectory2(root);
30746
30829
  } finally {
30747
- rmSync7(temporary, { force: true });
30830
+ rmSync8(temporary, { force: true });
30748
30831
  }
30749
30832
  }
30750
30833
  function updatePhase(projectRoot, operation, phase) {
@@ -30754,11 +30837,11 @@ function updatePhase(projectRoot, operation, phase) {
30754
30837
  }
30755
30838
  function readOperation(projectRoot, schemasDir) {
30756
30839
  const root = transactionRoot(projectRoot);
30757
- if (!existsSync19(root)) return void 0;
30840
+ if (!existsSync21(root)) return void 0;
30758
30841
  const stat = lstatSync7(root);
30759
30842
  if (stat.isSymbolicLink() || !stat.isDirectory()) fail3("init_transaction_invalid", TRANSACTION_NAME, "initialization transaction must be a regular directory", "path");
30760
30843
  const file = operationFile(projectRoot);
30761
- if (!existsSync19(file)) {
30844
+ if (!existsSync21(file)) {
30762
30845
  const entries = readdirSync7(root, { withFileTypes: true });
30763
30846
  const recoverable = entries.every((entry) => entry.isFile() && /^\.operation-op_[a-f0-9]{32}-[a-f0-9-]{36}\.tmp$/.test(entry.name));
30764
30847
  if (recoverable) return void 0;
@@ -30781,20 +30864,20 @@ function readOperation(projectRoot, schemasDir) {
30781
30864
  seen.add(folded);
30782
30865
  prior = entry.path;
30783
30866
  }
30784
- if (!isAbsolute6(operation.projectRoot)) fail3("init_transaction_project_root_invalid", TRANSACTION_NAME, "operation project root must be absolute", "path");
30867
+ if (!isAbsolute7(operation.projectRoot)) fail3("init_transaction_project_root_invalid", TRANSACTION_NAME, "operation project root must be absolute", "path");
30785
30868
  validateOperationIntent(projectRoot, operation);
30786
30869
  return operation;
30787
30870
  }
30788
30871
  function hasVnextInitTransaction(projectRoot) {
30789
- return existsSync19(transactionRoot(projectRoot));
30872
+ return existsSync21(transactionRoot(projectRoot));
30790
30873
  }
30791
30874
  function readTarget(projectRoot, path4) {
30792
- return readOptionalManaged(join22(transactionRoot(projectRoot), "targets"), path4);
30875
+ return readOptionalManaged(join24(transactionRoot(projectRoot), "targets"), path4);
30793
30876
  }
30794
30877
  function writeTarget(projectRoot, path4, bytes) {
30795
30878
  if (bytes.byteLength > MAX_MANAGED_FILE_BYTES) fail3("template_target_too_large", path4, `target exceeds ${MAX_MANAGED_FILE_BYTES} bytes`);
30796
30879
  const file = targetFile(projectRoot, path4);
30797
- mkdirSync17(dirname13(file), { recursive: true, mode: 448 });
30880
+ mkdirSync18(dirname15(file), { recursive: true, mode: 448 });
30798
30881
  writeDurableNew(file, bytes, 384);
30799
30882
  }
30800
30883
  function writeAndVerifyBackups(projectRoot, operation) {
@@ -30806,7 +30889,7 @@ function writeAndVerifyBackups(projectRoot, operation) {
30806
30889
  fail3("repair_preimage_changed", entry.path, "destination changed before transaction preparation; local bytes were preserved");
30807
30890
  }
30808
30891
  const file = backupFile(projectRoot, entry.path);
30809
- mkdirSync17(dirname13(file), { recursive: true, mode: 448 });
30892
+ mkdirSync18(dirname15(file), { recursive: true, mode: 448 });
30810
30893
  writeDurableNew(file, current, 384);
30811
30894
  }
30812
30895
  }
@@ -30821,7 +30904,7 @@ function writeKnownBackups(projectRoot, operation) {
30821
30904
  fail3("init_transaction_backup_source_invalid", entry.path, "supported source template cannot reproduce the pinned preimage");
30822
30905
  }
30823
30906
  const file = backupFile(projectRoot, entry.path);
30824
- mkdirSync17(dirname13(file), { recursive: true, mode: 448 });
30907
+ mkdirSync18(dirname15(file), { recursive: true, mode: 448 });
30825
30908
  writeDurableNew(file, bytes, 384);
30826
30909
  }
30827
30910
  }
@@ -30829,7 +30912,7 @@ function verifyBackups(projectRoot, operation) {
30829
30912
  if (operation.kind !== "repair") return;
30830
30913
  for (const entry of operation.files) {
30831
30914
  if (entry.observedSha256 === null) continue;
30832
- const bytes = readOptionalManaged(join22(transactionRoot(projectRoot), "backups"), entry.path);
30915
+ const bytes = readOptionalManaged(join24(transactionRoot(projectRoot), "backups"), entry.path);
30833
30916
  if (!bytes || vnextContentSha256(bytes) !== entry.observedSha256) {
30834
30917
  fail3("init_transaction_backup_invalid", entry.path, "pinned preimage backup is missing or corrupt");
30835
30918
  }
@@ -30863,10 +30946,10 @@ function sourceConfigFiles(projectRoot) {
30863
30946
  ".kxm/repo/repo.yaml",
30864
30947
  ".kxm/repo/env.yaml"
30865
30948
  ];
30866
- const files = fixed.filter((path4) => existsSync19(join22(projectRoot, ...path4.split("/"))));
30949
+ const files = fixed.filter((path4) => existsSync21(join24(projectRoot, ...path4.split("/"))));
30867
30950
  for (const directory of ["agents", "models", "workflows"]) {
30868
- const absolute = join22(projectRoot, ".kxm", directory);
30869
- if (!existsSync19(absolute)) continue;
30951
+ const absolute = join24(projectRoot, ".kxm", directory);
30952
+ if (!existsSync21(absolute)) continue;
30870
30953
  const stat = lstatSync7(absolute);
30871
30954
  if (stat.isSymbolicLink() || !stat.isDirectory()) fail3("repair_directory_invalid", `.kxm/${directory}`, "configuration directory must be regular", "path");
30872
30955
  for (const entry of readdirSync7(absolute, { withFileTypes: true })) {
@@ -30888,23 +30971,23 @@ function absoluteMemberBindings(projectRoot, project, explicit = {}) {
30888
30971
  if (repository.role !== "member" || typeof repository.id !== "string" || Object.hasOwn(bindings, repository.id)) continue;
30889
30972
  if (typeof repository.pathHint === "string") {
30890
30973
  const candidate2 = resolve18(projectRoot, ...repository.pathHint.split("/"));
30891
- if (existsSync19(candidate2)) bindings[repository.id] = candidate2;
30974
+ if (existsSync21(candidate2)) bindings[repository.id] = candidate2;
30892
30975
  }
30893
30976
  }
30894
30977
  return bindings;
30895
30978
  }
30896
30979
  function prepareShadow(projectRoot, operation, options) {
30897
30980
  const shadow = shadowRoot(projectRoot);
30898
- mkdirSync17(shadow, { recursive: true, mode: 448 });
30981
+ mkdirSync18(shadow, { recursive: true, mode: 448 });
30899
30982
  let total = 0;
30900
30983
  if (operation.kind === "repair") {
30901
30984
  for (const path4 of sourceConfigFiles(projectRoot)) {
30902
30985
  const bytes = readOptionalManaged(projectRoot, path4);
30903
30986
  if (!bytes) fail3("repair_snapshot_file_missing", path4, "configuration changed during shadow preparation");
30904
30987
  total += bytes.byteLength;
30905
- const source = join22(projectRoot, ...path4.split("/"));
30906
- const destination = join22(shadow, ...path4.split("/"));
30907
- mkdirSync17(dirname13(destination), { recursive: true, mode: 448 });
30988
+ const source = join24(projectRoot, ...path4.split("/"));
30989
+ const destination = join24(shadow, ...path4.split("/"));
30990
+ mkdirSync18(dirname15(destination), { recursive: true, mode: 448 });
30908
30991
  writeDurableNew(destination, bytes, lstatSync7(source).mode & 511);
30909
30992
  if (total > MAX_MANAGED_TOTAL_BYTES) fail3("repair_snapshot_too_large", ".kxm", `configuration snapshot exceeds ${MAX_MANAGED_TOTAL_BYTES} bytes`, "parse");
30910
30993
  }
@@ -30912,12 +30995,12 @@ function prepareShadow(projectRoot, operation, options) {
30912
30995
  for (const entry of operation.files) {
30913
30996
  const bytes = readTarget(projectRoot, entry.path);
30914
30997
  if (!bytes) fail3("init_transaction_target_missing", entry.path, "pinned target artifact is missing");
30915
- const destination = join22(shadow, ...entry.path.split("/"));
30916
- mkdirSync17(dirname13(destination), { recursive: true, mode: 448 });
30917
- const mode = existsSync19(destination) ? lstatSync7(destination).mode & 511 : 420;
30998
+ const destination = join24(shadow, ...entry.path.split("/"));
30999
+ mkdirSync18(dirname15(destination), { recursive: true, mode: 448 });
31000
+ const mode = existsSync21(destination) ? lstatSync7(destination).mode & 511 : 420;
30918
31001
  writeDurable(destination, bytes, mode);
30919
31002
  }
30920
- const project = parseRestrictedYaml2(readFileSync20(join22(shadow, ".kxm", "project.yaml")), ".kxm/project.yaml");
31003
+ const project = parseRestrictedYaml2(readFileSync21(join24(shadow, ".kxm", "project.yaml")), ".kxm/project.yaml");
30921
31004
  const bound = absoluteMemberBindings(projectRoot, project, options.repositoryBindings);
30922
31005
  loadVnextProject(shadow, { ...loaderOptions(options), repositoryBindings: bound });
30923
31006
  const provenance = readProjectAndProvenance(shadow, options.schemasDir)?.provenance;
@@ -30955,8 +31038,8 @@ function prepareOperation(projectRoot, operation, rendered, options) {
30955
31038
  const transaction = transactionRoot(projectRoot);
30956
31039
  validateOperationRecord(operation, options.schemasDir);
30957
31040
  validateOperationIntent(projectRoot, operation);
30958
- if (existsSync19(transaction)) fail3("init_transaction_exists", TRANSACTION_NAME, "an initialization transaction already exists and must be resumed");
30959
- mkdirSync17(transaction, { mode: 448 });
31041
+ if (existsSync21(transaction)) fail3("init_transaction_exists", TRANSACTION_NAME, "an initialization transaction already exists and must be resumed");
31042
+ mkdirSync18(transaction, { mode: 448 });
30960
31043
  syncDirectory2(projectRoot);
30961
31044
  writeOperation(projectRoot, operation);
30962
31045
  try {
@@ -30972,7 +31055,7 @@ function prepareOperation(projectRoot, operation, rendered, options) {
30972
31055
  syncTreeDirectories(transaction);
30973
31056
  return updatePhase(projectRoot, operation, "prepared");
30974
31057
  } catch (error) {
30975
- rmSync7(transaction, { recursive: true, force: true });
31058
+ rmSync8(transaction, { recursive: true, force: true });
30976
31059
  throw error;
30977
31060
  }
30978
31061
  }
@@ -30981,21 +31064,21 @@ function ensureDestinationParents(projectRoot, path4) {
30981
31064
  const segments = path4.split("/").slice(0, -1);
30982
31065
  let current = boundary;
30983
31066
  for (const segment of segments) {
30984
- current = join22(current, segment);
30985
- if (!existsSync19(current)) mkdirSync17(current, { mode: 448 });
31067
+ current = join24(current, segment);
31068
+ if (!existsSync21(current)) mkdirSync18(current, { mode: 448 });
30986
31069
  const stat = lstatSync7(current);
30987
31070
  if (stat.isSymbolicLink() || !stat.isDirectory()) fail3("repair_destination_parent_invalid", path4, "destination parent must be a regular directory", "path");
30988
31071
  }
30989
31072
  }
30990
31073
  function destinationSha(projectRoot, path4) {
30991
- const file = join22(projectRoot, ...path4.split("/"));
30992
- if (!existsSync19(file)) return void 0;
31074
+ const file = join24(projectRoot, ...path4.split("/"));
31075
+ if (!existsSync21(file)) return void 0;
30993
31076
  return vnextContentSha256(readRegularBounded(file, path4));
30994
31077
  }
30995
31078
  function requireConditionalLinkSupport(directory, operationId, path4) {
30996
31079
  const nonce = randomUUID10();
30997
- const source = join22(directory, `.kxm-repair-${operationId}-${nonce}.link-source`);
30998
- const target = join22(directory, `.kxm-repair-${operationId}-${nonce}.link-target`);
31080
+ const source = join24(directory, `.kxm-repair-${operationId}-${nonce}.link-source`);
31081
+ const target = join24(directory, `.kxm-repair-${operationId}-${nonce}.link-target`);
30999
31082
  try {
31000
31083
  writeDurableNew(source, Buffer.from("kxm-link-probe\n", "utf8"), 384);
31001
31084
  try {
@@ -31004,25 +31087,25 @@ function requireConditionalLinkSupport(directory, operationId, path4) {
31004
31087
  fail3("repair_hard_link_unsupported", path4, "filesystem does not support the conditional hard-link install required for safe repair");
31005
31088
  }
31006
31089
  } finally {
31007
- rmSync7(target, { force: true });
31008
- rmSync7(source, { force: true });
31090
+ rmSync8(target, { force: true });
31091
+ rmSync8(source, { force: true });
31009
31092
  syncDirectory2(directory);
31010
31093
  }
31011
31094
  }
31012
31095
  function atomicInstallTarget(projectRoot, operation, entry) {
31013
- const destination = join22(projectRoot, ...entry.path.split("/"));
31096
+ const destination = join24(projectRoot, ...entry.path.split("/"));
31014
31097
  ensureDestinationParents(projectRoot, entry.path);
31015
- const directory = dirname13(destination);
31098
+ const directory = dirname15(destination);
31016
31099
  const temporaryPrefix = `.kxm-repair-${operation.operationId}-`;
31017
31100
  const pathKey = vnextContentSha256(entry.path).slice("sha256:".length, "sha256:".length + 16);
31018
- const displaced = join22(directory, `${temporaryPrefix}${pathKey}.preimage`);
31019
- if (existsSync19(displaced)) {
31101
+ const displaced = join24(directory, `${temporaryPrefix}${pathKey}.preimage`);
31102
+ if (existsSync21(displaced)) {
31020
31103
  const stat = lstatSync7(displaced);
31021
31104
  if (stat.isSymbolicLink() || !stat.isFile()) fail3("repair_preimage_temporary_invalid", entry.path, "stale displaced preimage is not a regular file", "path");
31022
- if (entry.observedSha256 === null || vnextContentSha256(readFileSync20(displaced)) !== entry.observedSha256) {
31105
+ if (entry.observedSha256 === null || vnextContentSha256(readFileSync21(displaced)) !== entry.observedSha256) {
31023
31106
  fail3("repair_preimage_temporary_mismatch", entry.path, "stale displaced preimage does not match the pinned operation");
31024
31107
  }
31025
- if (!existsSync19(destination)) {
31108
+ if (!existsSync21(destination)) {
31026
31109
  try {
31027
31110
  linkSync(displaced, destination);
31028
31111
  } catch {
@@ -31030,14 +31113,14 @@ function atomicInstallTarget(projectRoot, operation, entry) {
31030
31113
  }
31031
31114
  syncDirectory2(directory);
31032
31115
  }
31033
- rmSync7(displaced, { force: true });
31116
+ rmSync8(displaced, { force: true });
31034
31117
  syncDirectory2(directory);
31035
31118
  }
31036
31119
  for (const candidate of readdirSync7(directory, { withFileTypes: true })) {
31037
31120
  const owned = candidate.name.startsWith(temporaryPrefix) && (candidate.name.endsWith(".tmp") || candidate.name.endsWith(".link-source") || candidate.name.endsWith(".link-target"));
31038
31121
  if (!owned) continue;
31039
31122
  if (!candidate.isFile()) fail3("repair_temporary_invalid", entry.path, "stale operation temporary is not a regular file", "path");
31040
- rmSync7(join22(directory, candidate.name), { force: true });
31123
+ rmSync8(join24(directory, candidate.name), { force: true });
31041
31124
  }
31042
31125
  const current = destinationSha(projectRoot, entry.path);
31043
31126
  if (current === entry.targetSha256) return;
@@ -31047,22 +31130,22 @@ function atomicInstallTarget(projectRoot, operation, entry) {
31047
31130
  requireConditionalLinkSupport(directory, operation.operationId, entry.path);
31048
31131
  const bytes = readTarget(projectRoot, entry.path);
31049
31132
  if (!bytes) fail3("init_transaction_target_missing", entry.path, "pinned target artifact is missing");
31050
- const temporary = join22(directory, `${temporaryPrefix}${randomUUID10()}.tmp`);
31051
- const mode = existsSync19(destination) ? lstatSync7(destination).mode & 511 : 420;
31133
+ const temporary = join24(directory, `${temporaryPrefix}${randomUUID10()}.tmp`);
31134
+ const mode = existsSync21(destination) ? lstatSync7(destination).mode & 511 : 420;
31052
31135
  try {
31053
31136
  writeDurableNew(temporary, bytes, mode);
31054
31137
  if (entry.observedSha256 !== null) {
31055
- renameSync5(destination, displaced);
31138
+ renameSync6(destination, displaced);
31056
31139
  syncDirectory2(directory);
31057
- if (vnextContentSha256(readFileSync20(displaced)) !== entry.observedSha256) {
31058
- if (!existsSync19(destination)) {
31140
+ if (vnextContentSha256(readFileSync21(displaced)) !== entry.observedSha256) {
31141
+ if (!existsSync21(destination)) {
31059
31142
  try {
31060
31143
  linkSync(displaced, destination);
31061
31144
  } catch {
31062
31145
  fail3("repair_preimage_restore_blocked", entry.path, "changed destination was displaced but could not be conditionally restored; its bytes remain in the operation preimage file");
31063
31146
  }
31064
31147
  syncDirectory2(directory);
31065
- rmSync7(displaced, { force: true });
31148
+ rmSync8(displaced, { force: true });
31066
31149
  syncDirectory2(directory);
31067
31150
  }
31068
31151
  fail3("repair_preimage_changed", entry.path, "destination changed at replacement time; concurrent bytes were preserved at the destination or in the operation preimage file");
@@ -31071,7 +31154,7 @@ function atomicInstallTarget(projectRoot, operation, entry) {
31071
31154
  try {
31072
31155
  linkSync(temporary, destination);
31073
31156
  } catch {
31074
- if (!existsSync19(destination) && existsSync19(displaced)) {
31157
+ if (!existsSync21(destination) && existsSync21(displaced)) {
31075
31158
  try {
31076
31159
  linkSync(displaced, destination);
31077
31160
  } catch {
@@ -31079,26 +31162,26 @@ function atomicInstallTarget(projectRoot, operation, entry) {
31079
31162
  }
31080
31163
  syncDirectory2(directory);
31081
31164
  }
31082
- rmSync7(displaced, { force: true });
31165
+ rmSync8(displaced, { force: true });
31083
31166
  syncDirectory2(directory);
31084
31167
  fail3("repair_destination_recreated", entry.path, "destination was recreated concurrently or conditional install is unsupported; pinned target was not installed");
31085
31168
  }
31086
31169
  syncDirectory2(directory);
31087
- rmSync7(temporary, { force: true });
31088
- rmSync7(displaced, { force: true });
31170
+ rmSync8(temporary, { force: true });
31171
+ rmSync8(displaced, { force: true });
31089
31172
  syncDirectory2(directory);
31090
31173
  } finally {
31091
- rmSync7(temporary, { force: true });
31174
+ rmSync8(temporary, { force: true });
31092
31175
  }
31093
31176
  if (destinationSha(projectRoot, entry.path) !== entry.targetSha256) fail3("repair_install_verification_failed", entry.path, "installed target hash does not match the pinned operation");
31094
31177
  }
31095
31178
  function installedCreateMatches(projectRoot, operation) {
31096
- const configRoot = join22(projectRoot, ".kxm");
31097
- if (!existsSync19(configRoot)) return false;
31179
+ const configRoot = join24(projectRoot, ".kxm");
31180
+ if (!existsSync21(configRoot)) return false;
31098
31181
  const actual = [];
31099
31182
  const visit2 = (directory) => {
31100
31183
  for (const entry of readdirSync7(directory, { withFileTypes: true })) {
31101
- const absolute = join22(directory, entry.name);
31184
+ const absolute = join24(directory, entry.name);
31102
31185
  if (entry.isSymbolicLink()) fail3("create_resume_link", relativeConfigPath(projectRoot, absolute), "created configuration must not contain links", "path");
31103
31186
  if (entry.isDirectory()) visit2(absolute);
31104
31187
  else if (entry.isFile()) actual.push(relativeConfigPath(projectRoot, absolute));
@@ -31114,12 +31197,12 @@ function relativeConfigPath(projectRoot, file) {
31114
31197
  return relative4(resolve18(projectRoot), file).replaceAll("\\", "/");
31115
31198
  }
31116
31199
  function syncTreeDirectories(root) {
31117
- if (!existsSync19(root)) return;
31200
+ if (!existsSync21(root)) return;
31118
31201
  const directories = [];
31119
31202
  const visit2 = (directory) => {
31120
31203
  directories.push(directory);
31121
31204
  for (const entry of readdirSync7(directory, { withFileTypes: true })) {
31122
- if (entry.isDirectory()) visit2(join22(directory, entry.name));
31205
+ if (entry.isDirectory()) visit2(join24(directory, entry.name));
31123
31206
  }
31124
31207
  };
31125
31208
  visit2(root);
@@ -31127,13 +31210,13 @@ function syncTreeDirectories(root) {
31127
31210
  }
31128
31211
  function rebuildCreateShadow(projectRoot, operation, options) {
31129
31212
  const shadow = shadowRoot(projectRoot);
31130
- rmSync7(shadow, { recursive: true, force: true });
31213
+ rmSync8(shadow, { recursive: true, force: true });
31131
31214
  prepareShadow(projectRoot, operation, options);
31132
31215
  const stat = lstatSync7(shadow);
31133
31216
  if (stat.isSymbolicLink() || !stat.isDirectory() || !installedCreateMatches(shadow, operation)) {
31134
31217
  fail3("create_shadow_invalid", TRANSACTION_NAME, "reconstructed create shadow does not exactly match pinned target files", "path");
31135
31218
  }
31136
- syncTreeDirectories(join22(shadow, ".kxm"));
31219
+ syncTreeDirectories(join24(shadow, ".kxm"));
31137
31220
  }
31138
31221
  function applyOperation(projectRoot, original, options, resumed) {
31139
31222
  assertNoRegisteredGates(options);
@@ -31143,10 +31226,10 @@ function applyOperation(projectRoot, original, options, resumed) {
31143
31226
  verifyBackups(projectRoot, operation);
31144
31227
  operation = updatePhase(projectRoot, operation, "applying");
31145
31228
  if (operation.kind === "create") {
31146
- const destination = join22(projectRoot, ".kxm");
31147
- if (!existsSync19(destination)) {
31229
+ const destination = join24(projectRoot, ".kxm");
31230
+ if (!existsSync21(destination)) {
31148
31231
  rebuildCreateShadow(projectRoot, operation, effectiveOptions);
31149
- renameSync5(join22(shadowRoot(projectRoot), ".kxm"), destination);
31232
+ renameSync6(join24(shadowRoot(projectRoot), ".kxm"), destination);
31150
31233
  syncDirectory2(projectRoot);
31151
31234
  } else if (!installedCreateMatches(projectRoot, operation)) {
31152
31235
  fail3("create_resume_conflict", ".kxm", "existing project configuration does not match the pinned create operation");
@@ -31173,7 +31256,7 @@ function applyOperation(projectRoot, original, options, resumed) {
31173
31256
  operation = updatePhase(projectRoot, operation, "verified");
31174
31257
  if (options.testFaultAt === "verified") throw new Error("injected init fault after verification");
31175
31258
  const files = operation.files.map((entry) => entry.path);
31176
- syncTreeDirectories(join22(projectRoot, ".kxm"));
31259
+ syncTreeDirectories(join24(projectRoot, ".kxm"));
31177
31260
  return { kind: operation.kind, resumed, bundle, files };
31178
31261
  }
31179
31262
  function prepareAndApplyVnextCreate(projectRoot, rendered, options = {}) {
@@ -31288,7 +31371,7 @@ function finishPreparingOperation(projectRoot, operation, options) {
31288
31371
  const rendered = rendererForOperation(operation);
31289
31372
  if (!rendered) fail3("init_transaction_renderer_unavailable", TRANSACTION_NAME, "this binary cannot reproduce the pinned pre-application target");
31290
31373
  for (const directory of ["targets", "backups", "shadow"]) {
31291
- rmSync7(join22(transactionRoot(projectRoot), directory), { recursive: true, force: true });
31374
+ rmSync8(join24(transactionRoot(projectRoot), directory), { recursive: true, force: true });
31292
31375
  }
31293
31376
  for (const entry of operation.files) {
31294
31377
  const bytes = rendered.files.get(entry.path);
@@ -31307,8 +31390,8 @@ function resumeVnextInitTransaction(projectRoot, options = {}) {
31307
31390
  let operation = readOperation(projectRoot, options.schemasDir);
31308
31391
  if (!operation) {
31309
31392
  const root = transactionRoot(projectRoot);
31310
- if (existsSync19(root)) {
31311
- rmSync7(root, { recursive: true, force: true });
31393
+ if (existsSync21(root)) {
31394
+ rmSync8(root, { recursive: true, force: true });
31312
31395
  syncDirectory2(projectRoot);
31313
31396
  }
31314
31397
  return void 0;
@@ -31323,10 +31406,10 @@ function commitVnextInitTransaction(projectRoot, schemasDir) {
31323
31406
  fail3("init_transaction_not_verified", TRANSACTION_NAME, "initialization transaction cannot commit before installed state is verified");
31324
31407
  }
31325
31408
  const transaction = transactionRoot(projectRoot);
31326
- const retired = join22(projectRoot, `${TRANSACTION_NAME}-cleanup-${operation.operationId}-${randomUUID10()}`);
31327
- renameSync5(transaction, retired);
31409
+ const retired = join24(projectRoot, `${TRANSACTION_NAME}-cleanup-${operation.operationId}-${randomUUID10()}`);
31410
+ renameSync6(transaction, retired);
31328
31411
  syncDirectory2(projectRoot);
31329
- rmSync7(retired, { recursive: true, force: true });
31412
+ rmSync8(retired, { recursive: true, force: true });
31330
31413
  syncDirectory2(projectRoot);
31331
31414
  }
31332
31415
  function inspectVnextInitTransaction(projectRoot, schemasDir) {
@@ -31432,7 +31515,7 @@ function validateBindingIdentities(bundle, persisted, explicit) {
31432
31515
  }
31433
31516
  function initializeVnextProjectAtGitRoot(start, gitRoot, options, mutationLock) {
31434
31517
  const storeOptions = bindingStoreOptions(options);
31435
- const persisted = existsSync20(join23(gitRoot, ".kxm", "project.yaml")) ? readVnextLocalBindings(gitRoot, storeOptions) : void 0;
31518
+ const persisted = existsSync22(join25(gitRoot, ".kxm", "project.yaml")) ? readVnextLocalBindings(gitRoot, storeOptions) : void 0;
31436
31519
  const repositoryBindings = Object.fromEntries([
31437
31520
  ...Object.entries(persisted?.repositories ?? {}),
31438
31521
  ...Object.entries(options.repositoryBindings ?? {})
@@ -31621,7 +31704,7 @@ function initializeVnextProjectAtGitRoot(start, gitRoot, options, mutationLock)
31621
31704
  const files = [...rendered.files.keys()];
31622
31705
  if (options.dryRun) return { action: "planned", plan, projectRoot: gitRoot, files };
31623
31706
  if (!mutationLock) throw new Error("project mutation lock is required to create configuration");
31624
- if (existsSync20(join23(gitRoot, ".kxm"))) {
31707
+ if (existsSync22(join25(gitRoot, ".kxm"))) {
31625
31708
  throw new VnextConfigError([initIssue("workspace_changed", ".kxm", "workspace changed after planning; existing .kxm state was not overwritten")]);
31626
31709
  }
31627
31710
  const created = prepareAndApplyVnextCreate(gitRoot, rendered, transactionOptions);
@@ -31653,8 +31736,8 @@ function initializeVnextProject(start = process.cwd(), options = {}) {
31653
31736
  // plugins/kxm/src/vnext-migrate.ts
31654
31737
  var import_yaml12 = __toESM(require_dist(), 1);
31655
31738
  import { createHash as createHash13 } from "node:crypto";
31656
- import { chmodSync as chmodSync6, closeSync as closeSync3, existsSync as existsSync21, fsyncSync as fsyncSync3, lstatSync as lstatSync8, mkdirSync as mkdirSync18, openSync as openSync3, readFileSync as readFileSync21, renameSync as renameSync6, rmSync as rmSync8, writeFileSync as writeFileSync17 } from "node:fs";
31657
- import { join as join24 } from "node:path";
31739
+ import { chmodSync as chmodSync6, closeSync as closeSync3, existsSync as existsSync23, fsyncSync as fsyncSync3, lstatSync as lstatSync8, mkdirSync as mkdirSync19, openSync as openSync3, readFileSync as readFileSync22, renameSync as renameSync7, rmSync as rmSync9, writeFileSync as writeFileSync18 } from "node:fs";
31740
+ import { join as join26 } from "node:path";
31658
31741
  var MAX_LEGACY_JSON_BYTES = 1024 * 1024;
31659
31742
  var MAX_LEGACY_JSON_DEPTH = 32;
31660
31743
  var MAX_LEGACY_JSON_NODES = 32768;
@@ -31823,12 +31906,12 @@ function readVnextLegacySources(root) {
31823
31906
  throw new VnextConfigError([migrateIssue("discovery", "legacy_source_limit", ".kxm/config", `legacy configuration exceeds ${MAX_LEGACY_SOURCES} files`)]);
31824
31907
  }
31825
31908
  return files.map((path4) => {
31826
- const absolute = join24(root, ...path4.split("/"));
31909
+ const absolute = join26(root, ...path4.split("/"));
31827
31910
  const stat = lstatSync8(absolute);
31828
31911
  if (stat.isSymbolicLink() || !stat.isFile()) {
31829
31912
  throw new VnextConfigError([migrateIssue("path", "legacy_source_invalid", path4, "legacy configuration must be a regular file, not a link")]);
31830
31913
  }
31831
- const buffer = readFileSync21(absolute);
31914
+ const buffer = readFileSync22(absolute);
31832
31915
  let text;
31833
31916
  try {
31834
31917
  text = new TextDecoder("utf-8", { fatal: true }).decode(buffer);
@@ -32901,11 +32984,11 @@ function planVnextMigration(projectRoot, options = {}) {
32901
32984
  };
32902
32985
  }
32903
32986
  function readVnextMigrationDecisions(path4, schemasDir) {
32904
- if (!existsSync21(path4)) {
32987
+ if (!existsSync23(path4)) {
32905
32988
  throw new VnextConfigError([migrateIssue("discovery", "decisions_missing", path4, "migration decisions file does not exist")]);
32906
32989
  }
32907
32990
  const registry = new VnextSchemaRegistry(schemasDir);
32908
- const value = parseRestrictedYaml2(readFileSync21(path4), path4);
32991
+ const value = parseRestrictedYaml2(readFileSync22(path4), path4);
32909
32992
  const issues = registry.validateMigrationDecision(value, path4);
32910
32993
  if (issues.length > 0) throw new VnextConfigError(issues);
32911
32994
  return value;
@@ -32934,19 +33017,19 @@ function writeDurable2(path4, content) {
32934
33017
  const descriptor = openSync3(temp, "wx", 384);
32935
33018
  created = true;
32936
33019
  try {
32937
- writeFileSync17(descriptor, content);
33020
+ writeFileSync18(descriptor, content);
32938
33021
  fsyncSync3(descriptor);
32939
33022
  } finally {
32940
33023
  closeSync3(descriptor);
32941
33024
  }
32942
- renameSync6(temp, path4);
33025
+ renameSync7(temp, path4);
32943
33026
  try {
32944
33027
  chmodSync6(path4, 384);
32945
33028
  } catch {
32946
33029
  }
32947
- syncDirectory3(join24(path4, ".."));
33030
+ syncDirectory3(join26(path4, ".."));
32948
33031
  } finally {
32949
- if (created && existsSync21(temp)) rmSync8(temp, { force: true });
33032
+ if (created && existsSync23(temp)) rmSync9(temp, { force: true });
32950
33033
  }
32951
33034
  }
32952
33035
  function applyVnextMigration(projectRoot, options = {}) {
@@ -32956,8 +33039,8 @@ function applyVnextMigration(projectRoot, options = {}) {
32956
33039
  ...options.schemasDir === void 0 ? {} : { schemasDir: options.schemasDir }
32957
33040
  };
32958
33041
  const execute = (lock) => {
32959
- const receiptAbsolute = join24(root, ...VNEXT_MIGRATION_RECEIPT_PATH.split("/"));
32960
- if (existsSync21(receiptAbsolute)) {
33042
+ const receiptAbsolute = join26(root, ...VNEXT_MIGRATION_RECEIPT_PATH.split("/"));
33043
+ if (existsSync23(receiptAbsolute)) {
32961
33044
  const stat = lstatSync8(receiptAbsolute);
32962
33045
  if (stat.isSymbolicLink() || !stat.isFile()) {
32963
33046
  throw new VnextConfigError([migrateIssue("path", "migration_receipt_invalid", VNEXT_MIGRATION_RECEIPT_PATH, "migration receipt must be a regular file, not a link")]);
@@ -33010,7 +33093,7 @@ function applyVnextMigration(projectRoot, options = {}) {
33010
33093
  return { action: "planned", projectRoot: root, files: [], plan: first.plan };
33011
33094
  }
33012
33095
  const files = [...first.resources.entries()].sort(([left], [right]) => compareCodeUnits6(left, right)).map(([path4, value]) => ({ path: path4, bytes: Buffer.from((0, import_yaml12.stringify)(value, { lineWidth: 0 }), "utf8") }));
33013
- const collisions = files.filter((file) => existsSync21(join24(root, ...file.path.split("/"))));
33096
+ const collisions = files.filter((file) => existsSync23(join26(root, ...file.path.split("/"))));
33014
33097
  if (collisions.length > 0) {
33015
33098
  throw new VnextConfigError(collisions.map((file) => migrateIssue("semantic", "migration_target_exists", file.path, "target resource already exists; refusing to overwrite")));
33016
33099
  }
@@ -33019,8 +33102,8 @@ function applyVnextMigration(projectRoot, options = {}) {
33019
33102
  const segments = file.path.split("/");
33020
33103
  let current = root;
33021
33104
  for (const segment of segments.slice(0, -1)) {
33022
- current = join24(current, segment);
33023
- if (!existsSync21(current)) continue;
33105
+ current = join26(current, segment);
33106
+ if (!existsSync23(current)) continue;
33024
33107
  const stat = lstatSync8(current);
33025
33108
  if (stat.isSymbolicLink() || !stat.isDirectory()) {
33026
33109
  parentIssues.push(migrateIssue("path", "migration_target_parent_invalid", file.path, `migration target parent ${segment} must be a regular directory, not a link`));
@@ -33036,8 +33119,8 @@ function applyVnextMigration(projectRoot, options = {}) {
33036
33119
  const written = [];
33037
33120
  try {
33038
33121
  for (const file of files) {
33039
- const absolute = join24(root, ...file.path.split("/"));
33040
- mkdirSync18(join24(absolute, ".."), { recursive: true });
33122
+ const absolute = join26(root, ...file.path.split("/"));
33123
+ mkdirSync19(join26(absolute, ".."), { recursive: true });
33041
33124
  written.push(absolute);
33042
33125
  writeDurable2(absolute, file.bytes);
33043
33126
  }
@@ -33071,7 +33154,7 @@ ${bundle.configRevision}`).slice(7, 39)}`,
33071
33154
  } catch (error) {
33072
33155
  for (const absolute of written.reverse()) {
33073
33156
  try {
33074
- rmSync8(absolute, { force: true });
33157
+ rmSync9(absolute, { force: true });
33075
33158
  } catch {
33076
33159
  }
33077
33160
  }
@@ -33083,8 +33166,8 @@ ${bundle.configRevision}`).slice(7, 39)}`,
33083
33166
  }
33084
33167
  function verifyVnextMigration(projectRoot, options = {}) {
33085
33168
  const root = migrationGitRoot(projectRoot);
33086
- const receiptAbsolute = join24(root, ...VNEXT_MIGRATION_RECEIPT_PATH.split("/"));
33087
- if (!existsSync21(receiptAbsolute)) {
33169
+ const receiptAbsolute = join26(root, ...VNEXT_MIGRATION_RECEIPT_PATH.split("/"));
33170
+ if (!existsSync23(receiptAbsolute)) {
33088
33171
  return {
33089
33172
  ok: false,
33090
33173
  projectRoot: root,
@@ -33132,7 +33215,6 @@ function verifyVnextMigration(projectRoot, options = {}) {
33132
33215
 
33133
33216
  // plugins/kxm/src/cli/vnext.ts
33134
33217
  var vnextDriveCliSeams = {};
33135
- var repoRoot3 = resolve20(fileURLToPath4(new URL("../../../../", import.meta.url)));
33136
33218
  function initPlanPayload(plan) {
33137
33219
  return {
33138
33220
  mode: plan.mode,
@@ -33394,7 +33476,7 @@ async function cmdBackup(runtime, options) {
33394
33476
  const summary = [
33395
33477
  `Created SQLite backup with ${manifest.stores.length} store(s):`,
33396
33478
  ...manifest.stores.map((s) => ` - ${s.storeId}: ${s.sourcePath} -> ${s.backupFile} (schema v${s.schemaVersion}, ${s.bytes} bytes, sha256 ${s.sha256.slice(0, 12)}...)`),
33397
- `Manifest: ${join25(outDir, "manifest.json")}`
33479
+ `Manifest: ${join27(outDir, "manifest.json")}`
33398
33480
  ].join("\n");
33399
33481
  print(runtime.io, runtime.json, payload, summary);
33400
33482
  return 0;
@@ -33963,8 +34045,8 @@ async function cmdStudioLayout(runtime, workflowPath) {
33963
34045
  }
33964
34046
  let yamlContent;
33965
34047
  let workflowId = "default";
33966
- if (existsSync22(filePath)) {
33967
- yamlContent = readFileSync22(filePath, "utf8");
34048
+ if (existsSync24(filePath)) {
34049
+ yamlContent = readFileSync23(filePath, "utf8");
33968
34050
  } else {
33969
34051
  yamlContent = `schema: kxm.workflow.v1
33970
34052
  description: Feature implementation workflow
@@ -34037,15 +34119,15 @@ async function cmdStudioServe(runtime, options) {
34037
34119
  sessionToken,
34038
34120
  planProvider: () => {
34039
34121
  try {
34040
- const wfDir = join26(runtime.cwd, ".kxm", "workflows");
34041
- const defaultPath = join26(wfDir, "default.yaml");
34042
- let targetPath = existsSync22(defaultPath) ? defaultPath : void 0;
34043
- if (!targetPath && existsSync22(wfDir)) {
34122
+ const wfDir = join28(runtime.cwd, ".kxm", "workflows");
34123
+ const defaultPath = join28(wfDir, "default.yaml");
34124
+ let targetPath = existsSync24(defaultPath) ? defaultPath : void 0;
34125
+ if (!targetPath && existsSync24(wfDir)) {
34044
34126
  const yml = readdirSync8(wfDir).find((f) => f.endsWith(".yaml") || f.endsWith(".yml"));
34045
- if (yml) targetPath = join26(wfDir, yml);
34127
+ if (yml) targetPath = join28(wfDir, yml);
34046
34128
  }
34047
- if (targetPath && existsSync22(targetPath)) {
34048
- const raw = readFileSync22(targetPath, "utf8");
34129
+ if (targetPath && existsSync24(targetPath)) {
34130
+ const raw = readFileSync23(targetPath, "utf8");
34049
34131
  const parsed = (0, import_yaml13.parse)(raw);
34050
34132
  const wfId = basename6(targetPath).replace(/\.(yaml|yml)$/, "");
34051
34133
  return compileVnextWorkflow({ id: wfId, value: parsed });
@@ -34095,14 +34177,14 @@ Press Ctrl+C to stop.
34095
34177
  }
34096
34178
 
34097
34179
  // plugins/kxm/src/cli/context-skills.ts
34098
- import { readFileSync as readFileSync25 } from "node:fs";
34099
- import { join as join30, relative as relative5 } from "node:path";
34180
+ import { readFileSync as readFileSync26 } from "node:fs";
34181
+ import { join as join32, relative as relative5 } from "node:path";
34100
34182
 
34101
34183
  // plugins/kxm/src/memory.ts
34102
34184
  var import_yaml14 = __toESM(require_dist(), 1);
34103
34185
  import { randomUUID as randomUUID12 } from "node:crypto";
34104
- import { existsSync as existsSync23, mkdirSync as mkdirSync19, readdirSync as readdirSync9, readFileSync as readFileSync23, writeFileSync as writeFileSync18 } from "node:fs";
34105
- import { extname as extname2, join as join27, resolve as resolve22 } from "node:path";
34186
+ import { existsSync as existsSync25, mkdirSync as mkdirSync20, readdirSync as readdirSync9, readFileSync as readFileSync24, writeFileSync as writeFileSync19 } from "node:fs";
34187
+ import { extname as extname2, join as join29, resolve as resolve22 } from "node:path";
34106
34188
  var MEMORY_SCHEMA = "kxm.memory.v1";
34107
34189
  var MEMORY_BRIEF_SCHEMA = "kxm.memory-brief.v1";
34108
34190
  var MEMORY_MARKER_START = "<!-- kxm:memory:start -->";
@@ -34227,22 +34309,22 @@ ${yamlText}
34227
34309
  ---
34228
34310
  `;
34229
34311
  }
34230
- function memoryDirectories(repoRoot6) {
34231
- const root = resolve22(repoRoot6);
34232
- const memoryDir = join27(root, ".kxm", "memory");
34233
- const candidatesDir = join27(memoryDir, "candidates");
34312
+ function memoryDirectories(repoRoot) {
34313
+ const root = resolve22(repoRoot);
34314
+ const memoryDir = join29(root, ".kxm", "memory");
34315
+ const candidatesDir = join29(memoryDir, "candidates");
34234
34316
  return { memoryDir, candidatesDir };
34235
34317
  }
34236
- function loadAuthoredMemory(repoRoot6) {
34237
- const { memoryDir } = memoryDirectories(repoRoot6);
34238
- if (!existsSync23(memoryDir)) return [];
34318
+ function loadAuthoredMemory(repoRoot) {
34319
+ const { memoryDir } = memoryDirectories(repoRoot);
34320
+ if (!existsSync25(memoryDir)) return [];
34239
34321
  const records = [];
34240
34322
  const entries = readdirSync9(memoryDir, { withFileTypes: true });
34241
34323
  for (const entry of entries) {
34242
34324
  if (entry.isFile() && extname2(entry.name) === ".md") {
34243
- const fullPath = join27(memoryDir, entry.name);
34325
+ const fullPath = join29(memoryDir, entry.name);
34244
34326
  try {
34245
- const text = readFileSync23(fullPath, "utf8");
34327
+ const text = readFileSync24(fullPath, "utf8");
34246
34328
  const record = parseMemoryRecord(text, entry.name);
34247
34329
  if (record.lifecycle === "active") {
34248
34330
  records.push(record);
@@ -34254,9 +34336,9 @@ function loadAuthoredMemory(repoRoot6) {
34254
34336
  }
34255
34337
  return records.sort((left, right) => left.id.localeCompare(right.id));
34256
34338
  }
34257
- function createMemoryNote(repoRoot6, summary, options = {}) {
34258
- const { candidatesDir } = memoryDirectories(repoRoot6);
34259
- mkdirSync19(candidatesDir, { recursive: true });
34339
+ function createMemoryNote(repoRoot, summary, options = {}) {
34340
+ const { candidatesDir } = memoryDirectories(repoRoot);
34341
+ mkdirSync20(candidatesDir, { recursive: true });
34260
34342
  const scope = options.scope ?? "project";
34261
34343
  if (!VALID_SCOPES.has(scope)) {
34262
34344
  throw new Error(`invalid memory note scope: ${scope}; must be one of agent, project, run, operator`);
@@ -34281,12 +34363,12 @@ function createMemoryNote(repoRoot6, summary, options = {}) {
34281
34363
  evidenceRefs: [],
34282
34364
  ...options.body ? { body: options.body.trim() } : {}
34283
34365
  };
34284
- const targetPath = join27(candidatesDir, `${id}.md`);
34285
- writeFileSync18(targetPath, formatMemoryRecord(record), "utf8");
34366
+ const targetPath = join29(candidatesDir, `${id}.md`);
34367
+ writeFileSync19(targetPath, formatMemoryRecord(record), "utf8");
34286
34368
  return { record, path: targetPath };
34287
34369
  }
34288
- function generateMemoryBrief(repoRoot6) {
34289
- const facts = loadAuthoredMemory(repoRoot6);
34370
+ function generateMemoryBrief(repoRoot) {
34371
+ const facts = loadAuthoredMemory(repoRoot);
34290
34372
  return {
34291
34373
  schema: MEMORY_BRIEF_SCHEMA,
34292
34374
  generatedAt: (/* @__PURE__ */ new Date()).toISOString(),
@@ -34318,8 +34400,8 @@ function formatHarnessMemoryBlock(records) {
34318
34400
  }
34319
34401
  function updateHarnessDocument(filePath, block, defaultHeader) {
34320
34402
  let original = "";
34321
- if (existsSync23(filePath)) {
34322
- original = readFileSync23(filePath, "utf8");
34403
+ if (existsSync25(filePath)) {
34404
+ original = readFileSync24(filePath, "utf8");
34323
34405
  }
34324
34406
  let updated = "";
34325
34407
  if (original.includes(MEMORY_MARKER_START) && original.includes(MEMORY_MARKER_END)) {
@@ -34347,25 +34429,25 @@ ${block}
34347
34429
  `;
34348
34430
  }
34349
34431
  if (updated !== original) {
34350
- writeFileSync18(filePath, updated, "utf8");
34432
+ writeFileSync19(filePath, updated, "utf8");
34351
34433
  return true;
34352
34434
  }
34353
34435
  return false;
34354
34436
  }
34355
- function syncHarnessMemory(repoRoot6) {
34356
- const root = resolve22(repoRoot6);
34437
+ function syncHarnessMemory(repoRoot) {
34438
+ const root = resolve22(repoRoot);
34357
34439
  const records = loadAuthoredMemory(root);
34358
34440
  const block = formatHarnessMemoryBlock(records);
34359
34441
  const updated = [];
34360
34442
  const created = [];
34361
- const agentsPath = join27(root, "AGENTS.md");
34443
+ const agentsPath = join29(root, "AGENTS.md");
34362
34444
  const agentsHeader = "# AGENTS\n\nFollow project instructions.\n";
34363
- const agentsExisted = existsSync23(agentsPath);
34445
+ const agentsExisted = existsSync25(agentsPath);
34364
34446
  if (updateHarnessDocument(agentsPath, block, agentsHeader)) {
34365
34447
  if (agentsExisted) updated.push("AGENTS.md");
34366
34448
  else created.push("AGENTS.md");
34367
34449
  }
34368
- const claudePath = join27(root, "CLAUDE.md");
34450
+ const claudePath = join29(root, "CLAUDE.md");
34369
34451
  const claudeHeader = `# KXM (Claude)
34370
34452
 
34371
34453
  Follow [\`AGENTS.md\`](AGENTS.md). Official phase tracking:
@@ -34376,12 +34458,12 @@ you to implement. Default writer is native Grok CLI (\`grok --model grok-4.6\`).
34376
34458
  If \`grok\` is logged out, fail closed; do not fall back to Pi. Your reviews are
34377
34459
  artifacts, not hub \`peer-reply\` evidence.
34378
34460
  `;
34379
- const claudeExisted = existsSync23(claudePath);
34461
+ const claudeExisted = existsSync25(claudePath);
34380
34462
  if (updateHarnessDocument(claudePath, block, claudeHeader)) {
34381
34463
  if (claudeExisted) updated.push("CLAUDE.md");
34382
34464
  else created.push("CLAUDE.md");
34383
34465
  }
34384
- const geminiPath = join27(root, "GEMINI.md");
34466
+ const geminiPath = join29(root, "GEMINI.md");
34385
34467
  const geminiHeader = `# KXM (Gemini / Antigravity)
34386
34468
 
34387
34469
  Follow [\`AGENTS.md\`](AGENTS.md). Official phase tracking:
@@ -34390,7 +34472,7 @@ Follow [\`AGENTS.md\`](AGENTS.md). Official phase tracking:
34390
34472
  Google / Antigravity CLI (\`agy\`) is an admitted native writer and experiment edit route
34391
34473
  for Gemini models. Starting rotation remains Grok.
34392
34474
  `;
34393
- const geminiExisted = existsSync23(geminiPath);
34475
+ const geminiExisted = existsSync25(geminiPath);
34394
34476
  if (updateHarnessDocument(geminiPath, block, geminiHeader)) {
34395
34477
  if (geminiExisted) updated.push("GEMINI.md");
34396
34478
  else created.push("GEMINI.md");
@@ -34401,8 +34483,8 @@ for Gemini models. Starting rotation remains Grok.
34401
34483
  // plugins/kxm/src/skills.ts
34402
34484
  var import_yaml15 = __toESM(require_dist(), 1);
34403
34485
  import { createHash as createHash14 } from "node:crypto";
34404
- import { existsSync as existsSync24, mkdirSync as mkdirSync20, readdirSync as readdirSync10, readFileSync as readFileSync24, renameSync as renameSync7, rmSync as rmSync9, statSync as statSync3, writeFileSync as writeFileSync19 } from "node:fs";
34405
- import { join as join28 } from "node:path";
34486
+ import { existsSync as existsSync26, mkdirSync as mkdirSync21, readdirSync as readdirSync10, readFileSync as readFileSync25, renameSync as renameSync8, rmSync as rmSync10, statSync as statSync3, writeFileSync as writeFileSync20 } from "node:fs";
34487
+ import { join as join30 } from "node:path";
34406
34488
  var SKILL_CANDIDATE_SCHEMA = "kxm.skill-candidate.v1";
34407
34489
  var SKILL_EVALUATION_SCHEMA = "kxm.skill-evaluation.v1";
34408
34490
  var SKILL_DECISION_SCHEMA = "kxm.skill-decision.v1";
@@ -34496,48 +34578,48 @@ var SkillLifecycle = class {
34496
34578
  this.allowOptimizationEvals = options.allowOptimizationEvals === true;
34497
34579
  }
34498
34580
  dir(state) {
34499
- return join28(this.root, state === "candidate" ? "candidates" : `${state}s`.replace("rejecteds", "rejected").replace("promoteds", "promoted"));
34581
+ return join30(this.root, state === "candidate" ? "candidates" : `${state}s`.replace("rejecteds", "rejected").replace("promoteds", "promoted"));
34500
34582
  }
34501
34583
  historyFile(id) {
34502
- return join28(this.root, "history", `${id}.jsonl`);
34584
+ return join30(this.root, "history", `${id}.jsonl`);
34503
34585
  }
34504
34586
  paths(state, id) {
34505
- const dir = join28(this.dir(state), id);
34506
- return { dir, metadata: join28(dir, "metadata.json"), skill: join28(dir, "SKILL.md") };
34587
+ const dir = join30(this.dir(state), id);
34588
+ return { dir, metadata: join30(dir, "metadata.json"), skill: join30(dir, "SKILL.md") };
34507
34589
  }
34508
34590
  appendHistory(id, record) {
34509
- mkdirSync20(join28(this.root, "history"), { recursive: true });
34591
+ mkdirSync21(join30(this.root, "history"), { recursive: true });
34510
34592
  const line = `${JSON.stringify(record)}
34511
34593
  `;
34512
- if (existsSync24(this.historyFile(id))) {
34513
- const existing = readFileSync24(this.historyFile(id), "utf8");
34594
+ if (existsSync26(this.historyFile(id))) {
34595
+ const existing = readFileSync25(this.historyFile(id), "utf8");
34514
34596
  const lines = existing.split("\n").filter((entry) => entry.trim());
34515
- writeFileSync19(this.historyFile(id), [...lines.slice(-499), line.trim()].join("\n") + "\n");
34597
+ writeFileSync20(this.historyFile(id), [...lines.slice(-499), line.trim()].join("\n") + "\n");
34516
34598
  } else {
34517
- writeFileSync19(this.historyFile(id), line);
34599
+ writeFileSync20(this.historyFile(id), line);
34518
34600
  }
34519
34601
  }
34520
34602
  history(id) {
34521
34603
  const file = this.historyFile(id);
34522
- if (!existsSync24(file)) return [];
34523
- return readFileSync24(file, "utf8").split("\n").filter((line) => line.trim()).map((line) => JSON.parse(line));
34604
+ if (!existsSync26(file)) return [];
34605
+ return readFileSync25(file, "utf8").split("\n").filter((line) => line.trim()).map((line) => JSON.parse(line));
34524
34606
  }
34525
34607
  readMetadata(state, id) {
34526
34608
  const { metadata } = this.paths(state, id);
34527
- if (!existsSync24(metadata)) {
34609
+ if (!existsSync26(metadata)) {
34528
34610
  throw new SkillLifecycleError("skill_not_found", `skill ${id} not found in ${state}`);
34529
34611
  }
34530
- return JSON.parse(readFileSync24(metadata, "utf8"));
34612
+ return JSON.parse(readFileSync25(metadata, "utf8"));
34531
34613
  }
34532
34614
  move(from, to, id) {
34533
- const fromDir = join28(this.dir(from), id);
34534
- const toDir = join28(this.dir(to), id);
34535
- if (!existsSync24(fromDir)) {
34615
+ const fromDir = join30(this.dir(from), id);
34616
+ const toDir = join30(this.dir(to), id);
34617
+ if (!existsSync26(fromDir)) {
34536
34618
  throw new SkillLifecycleError("skill_not_found", `skill ${id} not found in ${from}`);
34537
34619
  }
34538
- mkdirSync20(this.dir(to), { recursive: true });
34539
- if (existsSync24(toDir)) rmSync9(toDir, { recursive: true, force: true });
34540
- renameSync7(fromDir, toDir);
34620
+ mkdirSync21(this.dir(to), { recursive: true });
34621
+ if (existsSync26(toDir)) rmSync10(toDir, { recursive: true, force: true });
34622
+ renameSync8(fromDir, toDir);
34541
34623
  }
34542
34624
  /** Submit a new skill candidate. Content is redacted of secret material at
34543
34625
  * creation; the ID is derived from name + content hash. */
@@ -34579,7 +34661,7 @@ var SkillLifecycle = class {
34579
34661
  const contentSha256 = skillContentSha256(content);
34580
34662
  const id = skillIdFor(name, contentSha256);
34581
34663
  const { dir, metadata, skill } = this.paths("candidate", id);
34582
- if (existsSync24(metadata)) {
34664
+ if (existsSync26(metadata)) {
34583
34665
  throw new SkillLifecycleError(
34584
34666
  "skill_candidate_exists",
34585
34667
  `identical candidate ${id} already exists; changed behavior requires changed content`
@@ -34598,9 +34680,9 @@ var SkillLifecycle = class {
34598
34680
  createdAt: this.now(),
34599
34681
  ...input.supersedes ? { supersedes: input.supersedes } : {}
34600
34682
  };
34601
- mkdirSync20(dir, { recursive: true });
34602
- writeFileSync19(skill, content);
34603
- writeFileSync19(metadata, `${JSON.stringify(record, null, 2)}
34683
+ mkdirSync21(dir, { recursive: true });
34684
+ writeFileSync20(skill, content);
34685
+ writeFileSync20(metadata, `${JSON.stringify(record, null, 2)}
34604
34686
  `);
34605
34687
  this.appendHistory(id, { schema: "kxm.skill-history-event.v1", event: "candidate_created", by: createdBy, supersedes: input.supersedes, at: record.createdAt });
34606
34688
  return record;
@@ -34689,18 +34771,18 @@ var SkillLifecycle = class {
34689
34771
  };
34690
34772
  const candidatePaths = this.paths("candidate", candidateId);
34691
34773
  const promotedPaths = this.paths("promoted", candidateId);
34692
- mkdirSync20(promotedPaths.dir, { recursive: true });
34693
- const skillContent = readFileSync24(candidatePaths.skill, "utf8");
34694
- const metadataContent = readFileSync24(candidatePaths.metadata, "utf8");
34695
- writeFileSync19(promotedPaths.skill, skillContent);
34696
- writeFileSync19(promotedPaths.metadata, metadataContent);
34697
- const patchesDir = join28(this.root, "patches");
34698
- mkdirSync20(patchesDir, { recursive: true });
34699
- const patchPath = join28(patchesDir, `${candidateId}.patch`);
34774
+ mkdirSync21(promotedPaths.dir, { recursive: true });
34775
+ const skillContent = readFileSync25(candidatePaths.skill, "utf8");
34776
+ const metadataContent = readFileSync25(candidatePaths.metadata, "utf8");
34777
+ writeFileSync20(promotedPaths.skill, skillContent);
34778
+ writeFileSync20(promotedPaths.metadata, metadataContent);
34779
+ const patchesDir = join30(this.root, "patches");
34780
+ mkdirSync21(patchesDir, { recursive: true });
34781
+ const patchPath = join30(patchesDir, `${candidateId}.patch`);
34700
34782
  const relSkillPath = `.kxm/skills/promoted/${candidateId}/SKILL.md`;
34701
34783
  const relMetaPath = `.kxm/skills/promoted/${candidateId}/metadata.json`;
34702
34784
  const patch = `${createUnifiedPatch(relSkillPath, skillContent)}${createUnifiedPatch(relMetaPath, metadataContent)}`;
34703
- writeFileSync19(patchPath, patch, "utf8");
34785
+ writeFileSync20(patchPath, patch, "utf8");
34704
34786
  this.appendHistory(candidateId, record);
34705
34787
  return { ...metadata, patch, patchPath };
34706
34788
  }
@@ -34724,7 +34806,7 @@ var SkillLifecycle = class {
34724
34806
  verify(state, id) {
34725
34807
  const metadata = this.readMetadata(state, id);
34726
34808
  const { skill } = this.paths(state, id);
34727
- const content = readFileSync24(skill, "utf8");
34809
+ const content = readFileSync25(skill, "utf8");
34728
34810
  if (skillContentSha256(content) !== metadata.contentSha256) {
34729
34811
  throw new SkillLifecycleError(
34730
34812
  "skill_integrity_violation",
@@ -34742,7 +34824,7 @@ var SkillLifecycle = class {
34742
34824
  }
34743
34825
  list(state) {
34744
34826
  const dir = this.dir(state);
34745
- if (!existsSync24(dir)) return [];
34827
+ if (!existsSync26(dir)) return [];
34746
34828
  const ids = readdirSorted(dir);
34747
34829
  return ids.map((id) => {
34748
34830
  try {
@@ -34755,7 +34837,7 @@ var SkillLifecycle = class {
34755
34837
  read(state, id) {
34756
34838
  const metadata = this.readMetadata(state, id);
34757
34839
  const { skill } = this.paths(state, id);
34758
- return { metadata, content: readFileSync24(skill, "utf8") };
34840
+ return { metadata, content: readFileSync25(skill, "utf8") };
34759
34841
  }
34760
34842
  };
34761
34843
  function boundedList(value, field) {
@@ -34770,18 +34852,18 @@ function boundedList(value, field) {
34770
34852
  return [...new Set(refs)];
34771
34853
  }
34772
34854
  function readdirSorted(dir) {
34773
- return readdirSync10(dir).filter((entry) => statSync3(join28(dir, entry)).isDirectory()).sort();
34855
+ return readdirSync10(dir).filter((entry) => statSync3(join30(dir, entry)).isDirectory()).sort();
34774
34856
  }
34775
34857
 
34776
34858
  // plugins/kxm/src/wiki.ts
34777
- import { mkdirSync as mkdirSync21, writeFileSync as writeFileSync20 } from "node:fs";
34778
- import { join as join29 } from "node:path";
34859
+ import { mkdirSync as mkdirSync22, writeFileSync as writeFileSync21 } from "node:fs";
34860
+ import { join as join31 } from "node:path";
34779
34861
  function writeCompiledWiki(root, wiki) {
34780
34862
  const written = [];
34781
34863
  for (const [relativePath, content] of [...wiki.pages].sort(([left], [right]) => left.localeCompare(right))) {
34782
- const absolute = join29(root, relativePath);
34783
- mkdirSync21(absolute.slice(0, absolute.lastIndexOf("/")), { recursive: true });
34784
- writeFileSync20(absolute, content);
34864
+ const absolute = join31(root, relativePath);
34865
+ mkdirSync22(absolute.slice(0, absolute.lastIndexOf("/")), { recursive: true });
34866
+ writeFileSync21(absolute, content);
34785
34867
  written.push(relativePath);
34786
34868
  }
34787
34869
  return written;
@@ -34947,7 +35029,7 @@ function skillStateFromFlag(value) {
34947
35029
  throw new Error(`invalid skill state ${value}`);
34948
35030
  }
34949
35031
  function skillsRoot(runtime) {
34950
- return join30(runtime.dirs.workdir, ".kxm", "skills");
35032
+ return join32(runtime.dirs.workdir, ".kxm", "skills");
34951
35033
  }
34952
35034
  function csv(value) {
34953
35035
  if (!value) return void 0;
@@ -34964,7 +35046,7 @@ async function cmdSkillsCreate(runtime, options) {
34964
35046
  const metadata = lifecycle.create({
34965
35047
  name: options.name,
34966
35048
  description: options.description ?? "",
34967
- content: readFileSync25(options.file, "utf8"),
35049
+ content: readFileSync26(options.file, "utf8"),
34968
35050
  createdBy: options.createdBy,
34969
35051
  sources: {
34970
35052
  runIds: csv(options.run) ?? [],
@@ -35122,8 +35204,8 @@ async function cmdMemorySync(runtime) {
35122
35204
 
35123
35205
  // plugins/kxm/src/cli/hub.ts
35124
35206
  import { randomUUID as randomUUID14 } from "node:crypto";
35125
- import { existsSync as existsSync30, mkdirSync as mkdirSync25, readFileSync as readFileSync31, readdirSync as readdirSync12, rmSync as rmSync10, writeFileSync as writeFileSync23 } from "node:fs";
35126
- import { join as join40, resolve as resolve25 } from "node:path";
35207
+ import { existsSync as existsSync32, mkdirSync as mkdirSync26, readFileSync as readFileSync32, readdirSync as readdirSync12, rmSync as rmSync11, writeFileSync as writeFileSync24 } from "node:fs";
35208
+ import { join as join42, resolve as resolve25 } from "node:path";
35127
35209
 
35128
35210
  // node_modules/marked/lib/marked.esm.js
35129
35211
  function M() {
@@ -41056,19 +41138,19 @@ import * as path2 from "node:path";
41056
41138
 
41057
41139
  // node_modules/@earendil-works/pi-tui/dist/native-module-path.js
41058
41140
  import { createRequire as createRequire2 } from "node:module";
41059
- import { dirname as dirname16, join as join31 } from "node:path";
41060
- import { fileURLToPath as fileURLToPath5 } from "node:url";
41141
+ import { dirname as dirname17, join as join33 } from "node:path";
41142
+ import { fileURLToPath as fileURLToPath2 } from "node:url";
41061
41143
  var moduleRequire = createRequire2(import.meta.url);
41062
41144
  var TUI_PACKAGE_NAME = "@earendil-works/pi-tui";
41063
41145
  function getNativeModuleCandidates(nativePath, options = {}) {
41064
- const moduleDir = dirname16(fileURLToPath5(options.moduleUrl ?? import.meta.url));
41146
+ const moduleDir = dirname17(fileURLToPath2(options.moduleUrl ?? import.meta.url));
41065
41147
  const candidates = [];
41066
41148
  try {
41067
41149
  const packageEntry = (options.resolvePackage ?? moduleRequire.resolve)(TUI_PACKAGE_NAME);
41068
- candidates.push(join31(dirname16(packageEntry), "..", nativePath));
41150
+ candidates.push(join33(dirname17(packageEntry), "..", nativePath));
41069
41151
  } catch {
41070
41152
  }
41071
- candidates.push(join31(moduleDir, "..", nativePath), join31(moduleDir, nativePath), join31(dirname16(options.execPath ?? process.execPath), nativePath));
41153
+ candidates.push(join33(moduleDir, "..", nativePath), join33(moduleDir, nativePath), join33(dirname17(options.execPath ?? process.execPath), nativePath));
41072
41154
  return Array.from(new Set(candidates));
41073
41155
  }
41074
41156
 
@@ -43524,8 +43606,8 @@ var TuiAltScreen = class extends TuiBase {
43524
43606
  var MAX_RENDER_WRITE_CHARS = 1024 * 1024;
43525
43607
 
43526
43608
  // plugins/kxm/src/tui.ts
43527
- import { mkdirSync as mkdirSync22 } from "node:fs";
43528
- import { join as join35, resolve as resolve24, dirname as dirname17 } from "node:path";
43609
+ import { mkdirSync as mkdirSync23 } from "node:fs";
43610
+ import { join as join37, resolve as resolve24, dirname as dirname18 } from "node:path";
43529
43611
  import { spawnSync as spawnSync5 } from "node:child_process";
43530
43612
 
43531
43613
  // plugins/kxm/src/external-effects.ts
@@ -43536,9 +43618,9 @@ function slugifyBranchPart(text, maxLength = 40) {
43536
43618
  }
43537
43619
 
43538
43620
  // plugins/kxm/src/local-snapshot.ts
43539
- import { existsSync as existsSync25, readdirSync as readdirSync11, readFileSync as readFileSync26 } from "node:fs";
43540
- import { homedir as homedir5 } from "node:os";
43541
- import { isAbsolute as isAbsolute7, join as join34, resolve as resolve23 } from "node:path";
43621
+ import { existsSync as existsSync27, readdirSync as readdirSync11, readFileSync as readFileSync27 } from "node:fs";
43622
+ import { homedir as homedir6 } from "node:os";
43623
+ import { isAbsolute as isAbsolute8, join as join36, resolve as resolve23 } from "node:path";
43542
43624
  function processExists2(pid) {
43543
43625
  try {
43544
43626
  process.kill(pid, 0);
@@ -43658,36 +43740,36 @@ function readOpenMessageMetadata(database) {
43658
43740
  return messages;
43659
43741
  }
43660
43742
  function resolveKxmSnapshotPaths(cwd, env = process.env) {
43661
- const stateDir = env.KXM_STATE_DIR?.trim() || join34(cwd, ".kxm", "state");
43743
+ const stateDir = env.KXM_STATE_DIR?.trim() || join36(cwd, ".kxm", "state");
43662
43744
  const configured = env.KXM_DATA_PATH?.trim();
43663
- const dataPath = configured ? resolve23(cwd, configured) : join34(stateDir, "kxm.db");
43745
+ const dataPath = configured ? resolve23(cwd, configured) : join36(stateDir, "kxm.db");
43664
43746
  return { dataPath, stateDir };
43665
43747
  }
43666
43748
  function resolveVnextStateRoot(stateDir, options) {
43667
- if (options?.vnextStateRoot && existsSync25(options.vnextStateRoot)) {
43749
+ if (options?.vnextStateRoot && existsSync27(options.vnextStateRoot)) {
43668
43750
  return resolve23(options.vnextStateRoot);
43669
43751
  }
43670
- if (existsSync25(join34(stateDir, "runtime", "registry.db")) || existsSync25(join34(stateDir, "runtime", "projects"))) {
43752
+ if (existsSync27(join36(stateDir, "runtime", "registry.db")) || existsSync27(join36(stateDir, "runtime", "projects"))) {
43671
43753
  return stateDir;
43672
43754
  }
43673
43755
  const env = options?.env ?? process.env;
43674
43756
  const explicit = env.KXM_STATE_HOME?.trim() || env.KXM_USER_STATE_DIR?.trim() || env.KXM_STATE_ROOT?.trim();
43675
- if (explicit && isAbsolute7(explicit) && existsSync25(resolve23(explicit))) {
43757
+ if (explicit && isAbsolute8(explicit) && existsSync27(resolve23(explicit))) {
43676
43758
  return resolve23(explicit);
43677
43759
  }
43678
43760
  let base;
43679
43761
  if (process.platform === "win32") {
43680
43762
  const localAppData = env.LOCALAPPDATA?.trim();
43681
- base = localAppData && isAbsolute7(localAppData) ? localAppData : join34(homedir5(), "AppData", "Local");
43763
+ base = localAppData && isAbsolute8(localAppData) ? localAppData : join36(homedir6(), "AppData", "Local");
43682
43764
  base = resolve23(base, "KXM");
43683
43765
  } else if (process.platform === "darwin") {
43684
- base = resolve23(homedir5(), "Library", "Application Support", "KXM");
43766
+ base = resolve23(homedir6(), "Library", "Application Support", "KXM");
43685
43767
  } else {
43686
43768
  const xdgState = env.XDG_STATE_HOME?.trim();
43687
- base = xdgState && isAbsolute7(xdgState) ? xdgState : join34(homedir5(), ".local", "state");
43769
+ base = xdgState && isAbsolute8(xdgState) ? xdgState : join36(homedir6(), ".local", "state");
43688
43770
  base = resolve23(base, "kxm");
43689
43771
  }
43690
- if (existsSync25(base)) return base;
43772
+ if (existsSync27(base)) return base;
43691
43773
  return void 0;
43692
43774
  }
43693
43775
  function loadLocalMeshSnapshot(dataPath, stateDir, options) {
@@ -43698,7 +43780,7 @@ function loadLocalMeshSnapshot(dataPath, stateDir, options) {
43698
43780
  let legacyRuns = [];
43699
43781
  let legacyRunTotal = 0;
43700
43782
  let plans = [];
43701
- if (existsSync25(dataPath)) {
43783
+ if (existsSync27(dataPath)) {
43702
43784
  hasLegacy = true;
43703
43785
  const database = new DatabaseSync(dataPath, { readOnly: true });
43704
43786
  try {
@@ -43718,11 +43800,11 @@ function loadLocalMeshSnapshot(dataPath, stateDir, options) {
43718
43800
  let vnextRunTotal = 0;
43719
43801
  const vnextStateRoot = resolveVnextStateRoot(stateDir, options);
43720
43802
  if (vnextStateRoot) {
43721
- const runtimeDir = join34(vnextStateRoot, "runtime");
43722
- const registryDbPath = join34(runtimeDir, "registry.db");
43723
- const projectsDir = join34(runtimeDir, "projects");
43803
+ const runtimeDir = join36(vnextStateRoot, "runtime");
43804
+ const registryDbPath = join36(runtimeDir, "registry.db");
43805
+ const projectsDir = join36(runtimeDir, "projects");
43724
43806
  const projectKeys = /* @__PURE__ */ new Set();
43725
- if (existsSync25(registryDbPath)) {
43807
+ if (existsSync27(registryDbPath)) {
43726
43808
  hasVnext = true;
43727
43809
  try {
43728
43810
  const regDb = new DatabaseSync(registryDbPath, { readOnly: true });
@@ -43738,7 +43820,7 @@ function loadLocalMeshSnapshot(dataPath, stateDir, options) {
43738
43820
  } catch {
43739
43821
  }
43740
43822
  }
43741
- if (existsSync25(projectsDir)) {
43823
+ if (existsSync27(projectsDir)) {
43742
43824
  try {
43743
43825
  for (const entry of readdirSync11(projectsDir, { withFileTypes: true })) {
43744
43826
  if (entry.isDirectory()) {
@@ -43749,8 +43831,8 @@ function loadLocalMeshSnapshot(dataPath, stateDir, options) {
43749
43831
  }
43750
43832
  }
43751
43833
  for (const key of projectKeys) {
43752
- const eventDbPath = join34(projectsDir, key, "run-events.db");
43753
- if (existsSync25(eventDbPath)) {
43834
+ const eventDbPath = join36(projectsDir, key, "run-events.db");
43835
+ if (existsSync27(eventDbPath)) {
43754
43836
  hasVnext = true;
43755
43837
  try {
43756
43838
  const eventDb = new DatabaseSync(eventDbPath, { readOnly: true });
@@ -43780,10 +43862,10 @@ function loadLocalMeshSnapshot(dataPath, stateDir, options) {
43780
43862
  }
43781
43863
  }
43782
43864
  const pids = [];
43783
- if (existsSync25(stateDir)) {
43865
+ if (existsSync27(stateDir)) {
43784
43866
  for (const file of readdirSync11(stateDir).filter((name) => name.endsWith(".pid"))) {
43785
43867
  try {
43786
- const record = JSON.parse(readFileSync26(join34(stateDir, file), "utf8"));
43868
+ const record = JSON.parse(readFileSync27(join36(stateDir, file), "utf8"));
43787
43869
  pids.push({
43788
43870
  file,
43789
43871
  ...record.role ? { role: record.role } : {},
@@ -43822,8 +43904,8 @@ function loadLocalMeshSnapshot(dataPath, stateDir, options) {
43822
43904
  } else {
43823
43905
  source = "legacy";
43824
43906
  }
43825
- const telemetryFile = join34(stateDir, "telemetry.jsonl");
43826
- const spend = existsSync25(telemetryFile) ? readRoutingRecords(telemetryFile) : [];
43907
+ const telemetryFile = join36(stateDir, "telemetry.jsonl");
43908
+ const spend = existsSync27(telemetryFile) ? readRoutingRecords(telemetryFile) : [];
43827
43909
  return {
43828
43910
  source,
43829
43911
  agents: agents.sort((a, b2) => Number(b2.online) - Number(a.online) || a.name.localeCompare(b2.name)),
@@ -43938,10 +44020,10 @@ function copyToClipboard(text) {
43938
44020
  return false;
43939
44021
  }
43940
44022
  }
43941
- function spawnDegradeWorktree(repoRoot6, runId, options) {
44023
+ function spawnDegradeWorktree(repoRoot, runId, options) {
43942
44024
  const runner = options?.execFn ?? ((cmd, args) => {
43943
44025
  const res = spawnSync5(cmd, args, {
43944
- cwd: repoRoot6,
44026
+ cwd: repoRoot,
43945
44027
  encoding: "utf8",
43946
44028
  windowsHide: true,
43947
44029
  env: Object.fromEntries(
@@ -43957,11 +44039,11 @@ function spawnDegradeWorktree(repoRoot6, runId, options) {
43957
44039
  const cleanRunId = runId.replace(/^run_/, "");
43958
44040
  const desc = options?.description ? slugifyBranchPart(options.description, 30) : "degrade";
43959
44041
  const branchName = `kxm/run-${cleanRunId}-${desc}`;
43960
- const relativeWtPath = join35(".kxm", "worktrees", `run-${cleanRunId}-${desc}`);
43961
- const absoluteWtPath = resolve24(repoRoot6, relativeWtPath);
44042
+ const relativeWtPath = join37(".kxm", "worktrees", `run-${cleanRunId}-${desc}`);
44043
+ const absoluteWtPath = resolve24(repoRoot, relativeWtPath);
43962
44044
  const jumpCommand = `cd "${absoluteWtPath}"`;
43963
44045
  try {
43964
- mkdirSync22(dirname17(absoluteWtPath), { recursive: true });
44046
+ mkdirSync23(dirname18(absoluteWtPath), { recursive: true });
43965
44047
  const branchCheck = runner("git", ["rev-parse", "--verify", `refs/heads/${branchName}`]);
43966
44048
  let wtRes;
43967
44049
  if (branchCheck.status === 0) {
@@ -44556,8 +44638,8 @@ async function runMeshTui(input) {
44556
44638
  body: JSON.stringify({ signalKey: "operator-degrade", status: "degraded", summary: "Degraded to operator worktree from kxm dash" }),
44557
44639
  signal: abort.signal
44558
44640
  });
44559
- const repoRoot6 = process.cwd();
44560
- const degradeRes = spawnDegradeWorktree(repoRoot6, targetId, {
44641
+ const repoRoot = process.cwd();
44642
+ const degradeRes = spawnDegradeWorktree(repoRoot, targetId, {
44561
44643
  description: "operator-degrade"
44562
44644
  });
44563
44645
  if (dashboard) {
@@ -44727,8 +44809,8 @@ async function runMeshTui(input) {
44727
44809
  // plugins/kxm/src/session-work.ts
44728
44810
  import { spawnSync as spawnSync6 } from "node:child_process";
44729
44811
  import { randomUUID as randomUUID13 } from "node:crypto";
44730
- import { existsSync as existsSync26, mkdirSync as mkdirSync23, readFileSync as readFileSync27, renameSync as renameSync8, writeFileSync as writeFileSync21 } from "node:fs";
44731
- import { join as join36 } from "node:path";
44812
+ import { existsSync as existsSync28, mkdirSync as mkdirSync24, readFileSync as readFileSync28, renameSync as renameSync9, writeFileSync as writeFileSync22 } from "node:fs";
44813
+ import { join as join38 } from "node:path";
44732
44814
  var MAX_SESSION_BRIEF_TASKS = 5;
44733
44815
  var MAX_SESSION_BRIEF_PLANS = 5;
44734
44816
  var SESSION_BRIEF_SCHEMA = "kxm.session-brief.v1";
@@ -44884,10 +44966,10 @@ function buildSessionBrief(snapshot, current, hub, ship, updateLatest, cost, ses
44884
44966
  };
44885
44967
  }
44886
44968
  function readCachedSessionBrief(stateDir) {
44887
- const file = join36(stateDir, "session-brief.json");
44969
+ const file = join38(stateDir, "session-brief.json");
44888
44970
  try {
44889
- if (!existsSync26(file)) return void 0;
44890
- const raw = readFileSync27(file, "utf8");
44971
+ if (!existsSync28(file)) return void 0;
44972
+ const raw = readFileSync28(file, "utf8");
44891
44973
  const parsed = JSON.parse(raw);
44892
44974
  if (parsed && parsed.schema === "kxm.session-brief.v1" && typeof parsed.generatedAt === "string") {
44893
44975
  const ageMs = Date.now() - Date.parse(parsed.generatedAt);
@@ -44902,18 +44984,18 @@ function readCachedSessionBrief(stateDir) {
44902
44984
  }
44903
44985
  function writeCachedSessionBrief(stateDir, brief) {
44904
44986
  try {
44905
- mkdirSync23(stateDir, { recursive: true, mode: 448 });
44906
- const file = join36(stateDir, "session-brief.json");
44987
+ mkdirSync24(stateDir, { recursive: true, mode: 448 });
44988
+ const file = join38(stateDir, "session-brief.json");
44907
44989
  const tmp = `${file}.tmp.${randomUUID13().slice(0, 8)}`;
44908
- writeFileSync21(tmp, JSON.stringify(brief, null, 2), { encoding: "utf8", mode: 384 });
44909
- renameSync8(tmp, file);
44990
+ writeFileSync22(tmp, JSON.stringify(brief, null, 2), { encoding: "utf8", mode: 384 });
44991
+ renameSync9(tmp, file);
44910
44992
  } catch {
44911
44993
  }
44912
44994
  }
44913
44995
  function estimateSessionCost(stateDir) {
44914
44996
  try {
44915
- const telemetryFile = join36(stateDir, "telemetry.jsonl");
44916
- if (!existsSync26(telemetryFile)) return void 0;
44997
+ const telemetryFile = join38(stateDir, "telemetry.jsonl");
44998
+ if (!existsSync28(telemetryFile)) return void 0;
44917
44999
  const records = readRoutingRecords(telemetryFile);
44918
45000
  if (records.length === 0) return void 0;
44919
45001
  let totalCost = 0;
@@ -45081,11 +45163,11 @@ function formatSessionBriefText(brief) {
45081
45163
  }
45082
45164
 
45083
45165
  // plugins/kxm/src/kxm-install-kind.ts
45084
- import { existsSync as existsSync27, readFileSync as readFileSync28 } from "node:fs";
45085
- import { dirname as dirname18, join as join37 } from "node:path";
45166
+ import { existsSync as existsSync29, readFileSync as readFileSync29 } from "node:fs";
45167
+ import { dirname as dirname19, join as join39 } from "node:path";
45086
45168
  function packageIsKxm(root) {
45087
45169
  try {
45088
- const pkg = JSON.parse(readFileSync28(join37(root, "package.json"), "utf8"));
45170
+ const pkg = JSON.parse(readFileSync29(join39(root, "package.json"), "utf8"));
45089
45171
  return pkg.name === "@kontextmind/kxm";
45090
45172
  } catch {
45091
45173
  return false;
@@ -45107,8 +45189,8 @@ function lastSegments(path4) {
45107
45189
  function segmentEq(left, right, platform) {
45108
45190
  return platform === "win32" ? left.toLocaleLowerCase("en-US") === right.toLocaleLowerCase("en-US") : left === right;
45109
45191
  }
45110
- function isNpmPackageLayout(repoRoot6, platform) {
45111
- const last = lastSegments(repoRoot6);
45192
+ function isNpmPackageLayout(repoRoot, platform) {
45193
+ const last = lastSegments(repoRoot);
45112
45194
  const expected = ["node_modules", "@kontextmind", "kxm"];
45113
45195
  return last.length === 3 && last.every((part, i) => segmentEq(part, expected[i], platform));
45114
45196
  }
@@ -45134,12 +45216,12 @@ function report(kind, root) {
45134
45216
  return { kind, root, instruction: installKindInstruction(kind, root) };
45135
45217
  }
45136
45218
  function classifyInstallRoot(probe) {
45137
- const piGitRoot = join37(probe.homeDir, ".pi", "agent", "git");
45219
+ const piGitRoot = join39(probe.homeDir, ".pi", "agent", "git");
45138
45220
  if (isUnder(probe.repoRoot, piGitRoot, probe.platform)) return report("pi-git", probe.repoRoot);
45139
- const claudeHome = probe.env.CLAUDE_CONFIG_DIR?.trim() || join37(probe.homeDir, ".claude");
45140
- const pluginsRoot = join37(claudeHome, "plugins");
45221
+ const claudeHome = probe.env.CLAUDE_CONFIG_DIR?.trim() || join39(probe.homeDir, ".claude");
45222
+ const pluginsRoot = join39(claudeHome, "plugins");
45141
45223
  if (isUnder(probe.moduleDir, pluginsRoot, probe.platform)) return report("claude-marketplace", probe.moduleDir);
45142
- const hasGit = existsSync27(join37(probe.repoRoot, ".git"));
45224
+ const hasGit = existsSync29(join39(probe.repoRoot, ".git"));
45143
45225
  if (hasGit && packageIsKxm(probe.repoRoot)) return report("source", probe.repoRoot);
45144
45226
  if (isNpmPackageLayout(probe.repoRoot, probe.platform) && packageIsKxm(probe.repoRoot) && !hasGit) {
45145
45227
  return report("npm-package", probe.repoRoot);
@@ -45153,21 +45235,21 @@ function resolveInstallKind(probe, npmGlobalRoot) {
45153
45235
  if (typeof globalRoot !== "string" || globalRoot.trim() === "") {
45154
45236
  return report("unknown", classified.root);
45155
45237
  }
45156
- const expected = dirname18(dirname18(classified.root));
45238
+ const expected = dirname19(dirname19(classified.root));
45157
45239
  if (sameHostPath2(globalRoot.trim(), expected, probe.platform)) return report("npm-global", classified.root);
45158
45240
  return report("npm-local", classified.root);
45159
45241
  }
45160
45242
 
45161
45243
  // plugins/kxm/src/kxm-update-config.ts
45162
45244
  var import_yaml16 = __toESM(require_dist(), 1);
45163
- import { existsSync as existsSync28, readFileSync as readFileSync29 } from "node:fs";
45164
- import { join as join38 } from "node:path";
45245
+ import { existsSync as existsSync30, readFileSync as readFileSync30 } from "node:fs";
45246
+ import { join as join40 } from "node:path";
45165
45247
  function loadKxmUpdateConfig(env = process.env) {
45166
- const path4 = join38(vnextUserStateRoot({ env }), "update.yaml");
45167
- if (!existsSync28(path4)) return { schema: KXM_UPDATE_SCHEMA, auto: false, source: "github" };
45248
+ const path4 = join40(vnextUserStateRoot({ env }), "update.yaml");
45249
+ if (!existsSync30(path4)) return { schema: KXM_UPDATE_SCHEMA, auto: false, source: "github" };
45168
45250
  let parsed;
45169
45251
  try {
45170
- parsed = (0, import_yaml16.parse)(readFileSync29(path4, "utf8"));
45252
+ parsed = (0, import_yaml16.parse)(readFileSync30(path4, "utf8"));
45171
45253
  } catch {
45172
45254
  throw new KxmUpdateConfigError("update.yaml is not valid YAML");
45173
45255
  }
@@ -45193,8 +45275,8 @@ function loadKxmUpdateConfig(env = process.env) {
45193
45275
  }
45194
45276
 
45195
45277
  // plugins/kxm/src/session.ts
45196
- import { existsSync as existsSync29, mkdirSync as mkdirSync24, readFileSync as readFileSync30, writeFileSync as writeFileSync22 } from "node:fs";
45197
- import { join as join39 } from "node:path";
45278
+ import { existsSync as existsSync31, mkdirSync as mkdirSync25, readFileSync as readFileSync31, writeFileSync as writeFileSync23 } from "node:fs";
45279
+ import { join as join41 } from "node:path";
45198
45280
  var SESSION_SCHEMA = "kxm.session.v1";
45199
45281
  var SessionConfigError = class extends Error {
45200
45282
  code = "session_config_invalid";
@@ -45204,12 +45286,12 @@ var SessionConfigError = class extends Error {
45204
45286
  }
45205
45287
  };
45206
45288
  function workflowAssetDirs(assetsDir, workflowId) {
45207
- const root = join39(assetsDir, "workflows", workflowId);
45208
- return [root, join39(root, "inputs"), join39(root, "outputs"), join39(root, "generated")];
45289
+ const root = join41(assetsDir, "workflows", workflowId);
45290
+ return [root, join41(root, "inputs"), join41(root, "outputs"), join41(root, "generated")];
45209
45291
  }
45210
45292
  function sessionAssetDirs(assetsDir, sessionId) {
45211
- const root = join39(assetsDir, "sessions", sessionId);
45212
- return [root, join39(root, "inputs"), join39(root, "outputs")];
45293
+ const root = join41(assetsDir, "sessions", sessionId);
45294
+ return [root, join41(root, "inputs"), join41(root, "outputs")];
45213
45295
  }
45214
45296
  function rosterNames(configDir) {
45215
45297
  return [...loadRosterMap(configDir).values()].map((row) => String(row.name));
@@ -45259,7 +45341,7 @@ function workerFromRosterRow(name, row, project) {
45259
45341
  function loadRosterMap(configDir) {
45260
45342
  const byName = /* @__PURE__ */ new Map();
45261
45343
  for (const [file, key] of [["agents.json", "agents"], ["gates.json", "gates"]]) {
45262
- const path4 = join39(configDir, file);
45344
+ const path4 = join41(configDir, file);
45263
45345
  for (const row of loadRoster(path4, key)) {
45264
45346
  const name = String(row.name).trim();
45265
45347
  const lowered = name.toLowerCase();
@@ -45273,10 +45355,10 @@ function loadRosterMap(configDir) {
45273
45355
  return byName;
45274
45356
  }
45275
45357
  function loadRoster(path4, key) {
45276
- if (!existsSync29(path4)) return [];
45358
+ if (!existsSync31(path4)) return [];
45277
45359
  let parsed;
45278
45360
  try {
45279
- parsed = JSON.parse(readFileSync30(path4, "utf8"));
45361
+ parsed = JSON.parse(readFileSync31(path4, "utf8"));
45280
45362
  } catch (error) {
45281
45363
  throw new SessionConfigError(
45282
45364
  `${key} roster at ${path4} is not valid JSON: ${error instanceof Error ? error.message : String(error)}`
@@ -45301,7 +45383,7 @@ function loadRoster(path4, key) {
45301
45383
  });
45302
45384
  }
45303
45385
  function createSession(input) {
45304
- const assetDir = input.mode === "workflow" && input.workflowId ? join39("assets", "workflows", input.workflowId) : join39("assets", "sessions", input.id);
45386
+ const assetDir = input.mode === "workflow" && input.workflowId ? join41("assets", "workflows", input.workflowId) : join41("assets", "sessions", input.id);
45305
45387
  return {
45306
45388
  schema: SESSION_SCHEMA,
45307
45389
  id: input.id,
@@ -45314,20 +45396,20 @@ function createSession(input) {
45314
45396
  };
45315
45397
  }
45316
45398
  function writeSession(assetsDir, session, dryRun = false) {
45317
- const dir = join39(assetsDir, "sessions", session.id);
45318
- const path4 = join39(dir, "session.json");
45399
+ const dir = join41(assetsDir, "sessions", session.id);
45400
+ const path4 = join41(dir, "session.json");
45319
45401
  if (!dryRun) {
45320
- mkdirSync24(dir, { recursive: true });
45321
- writeFileSync22(path4, `${JSON.stringify(session, null, 2)}
45402
+ mkdirSync25(dir, { recursive: true });
45403
+ writeFileSync23(path4, `${JSON.stringify(session, null, 2)}
45322
45404
  `, { encoding: "utf8" });
45323
45405
  }
45324
45406
  return path4;
45325
45407
  }
45326
45408
 
45327
45409
  // plugins/kxm/src/cli/hub.ts
45328
- import { fileURLToPath as fileURLToPath6 } from "node:url";
45329
- import { dirname as dirname19 } from "node:path";
45330
- import { homedir as homedir6 } from "node:os";
45410
+ import { fileURLToPath as fileURLToPath3 } from "node:url";
45411
+ import { dirname as dirname20 } from "node:path";
45412
+ import { homedir as homedir7 } from "node:os";
45331
45413
  async function hubGet(url, fetchImpl) {
45332
45414
  try {
45333
45415
  const response = await fetchImpl(url);
@@ -45345,17 +45427,17 @@ async function hubGet(url, fetchImpl) {
45345
45427
  function installProbeFrom(runtime) {
45346
45428
  const partial = runtime.io.installProbe ?? {};
45347
45429
  return {
45348
- moduleDir: partial.moduleDir ?? dirname19(fileURLToPath6(import.meta.url)),
45430
+ moduleDir: partial.moduleDir ?? dirname20(fileURLToPath3(import.meta.url)),
45349
45431
  repoRoot: partial.repoRoot ?? resolve25("."),
45350
- homeDir: partial.homeDir ?? homedir6(),
45432
+ homeDir: partial.homeDir ?? homedir7(),
45351
45433
  platform: partial.platform ?? process.platform,
45352
45434
  env: partial.env ?? runtime.env
45353
45435
  };
45354
45436
  }
45355
45437
  function warnIgnoredProjectUpdateYaml(runtime) {
45356
- const projectFile = join40(runtime.dirs.workspace, "update.yaml");
45357
- if (!existsSync30(projectFile)) return;
45358
- const userFile = join40(vnextUserStateRoot({ env: runtime.env }), "update.yaml");
45438
+ const projectFile = join42(runtime.dirs.workspace, "update.yaml");
45439
+ if (!existsSync32(projectFile)) return;
45440
+ const userFile = join42(vnextUserStateRoot({ env: runtime.env }), "update.yaml");
45359
45441
  runtime.io.stderr(`kxm: ignoring .kxm/update.yaml in ${runtime.dirs.workdir}; update settings are read only from ${userFile}
45360
45442
  `);
45361
45443
  }
@@ -45381,7 +45463,7 @@ async function cmdDash(runtime, options = {}) {
45381
45463
  return 2;
45382
45464
  }
45383
45465
  const screen = requested;
45384
- const dataPath = resolve25(runtime.dirs.workdir, runtime.env.KXM_DATA_PATH?.trim() || join40(runtime.dirs.state, "kxm.db"));
45466
+ const dataPath = resolve25(runtime.dirs.workdir, runtime.env.KXM_DATA_PATH?.trim() || join42(runtime.dirs.state, "kxm.db"));
45385
45467
  if (runtime.dryRun) {
45386
45468
  print(runtime.io, runtime.json, {
45387
45469
  ok: true,
@@ -45427,7 +45509,7 @@ async function cmdHub(runtime) {
45427
45509
  config = loadKxmUpdateConfig(runtime.env);
45428
45510
  } catch (error) {
45429
45511
  if (error instanceof KxmUpdateConfigError) {
45430
- const yamlPath = join40(vnextUserStateRoot({ env: runtime.env }), "update.yaml");
45512
+ const yamlPath = join42(vnextUserStateRoot({ env: runtime.env }), "update.yaml");
45431
45513
  runtime.io.stderr(`kxm: ${error.message}; update check skipped; fix or remove ${yamlPath}
45432
45514
  `);
45433
45515
  } else {
@@ -45563,7 +45645,7 @@ async function cmdWorker(runtime, options) {
45563
45645
  return await (runtime.io.spawnWorker ?? ((launchEnv) => spawnScript("kxm-worker.mjs", launchEnv)))(extraEnv);
45564
45646
  }
45565
45647
  async function cmdStop(runtime, waitMsFlag) {
45566
- const pids = existsSync30(runtime.dirs.state) ? readdirSync12(runtime.dirs.state).filter((name) => name.endsWith(".pid")) : [];
45648
+ const pids = existsSync32(runtime.dirs.state) ? readdirSync12(runtime.dirs.state).filter((name) => name.endsWith(".pid")) : [];
45567
45649
  if (runtime.dryRun) {
45568
45650
  print(runtime.io, runtime.json, { ok: true, command: "stop", dryRun: true, pidFiles: pids }, "would signal pid files");
45569
45651
  return 0;
@@ -45578,7 +45660,7 @@ async function cmdStop(runtime, waitMsFlag) {
45578
45660
  const orphans = [];
45579
45661
  for (const file of pids) {
45580
45662
  try {
45581
- const record = JSON.parse(readFileSync31(join40(runtime.dirs.state, file), "utf8"));
45663
+ const record = JSON.parse(readFileSync32(join42(runtime.dirs.state, file), "utf8"));
45582
45664
  const expectedControl = file === "hub.pid" ? "hub.stop" : file.startsWith("worker-") ? `${file.slice(0, -4)}.stop` : void 0;
45583
45665
  const expectedRole = file === "hub.pid" ? "hub" : file.startsWith("worker-") ? "worker" : void 0;
45584
45666
  if (record.version !== 1 || !Number.isInteger(record.pid) || record.pid <= 0 || !record.startedAt || !expectedControl || record.controlFile !== expectedControl || record.role !== expectedRole) {
@@ -45598,7 +45680,7 @@ async function cmdStop(runtime, waitMsFlag) {
45598
45680
  ignored.push(file);
45599
45681
  continue;
45600
45682
  }
45601
- writeFileSync23(join40(runtime.dirs.state, record.controlFile), `${JSON.stringify({ startedAt: record.startedAt, ...record.generation ? { generation: record.generation } : {}, requestedAt: (/* @__PURE__ */ new Date()).toISOString() })}
45683
+ writeFileSync24(join42(runtime.dirs.state, record.controlFile), `${JSON.stringify({ startedAt: record.startedAt, ...record.generation ? { generation: record.generation } : {}, requestedAt: (/* @__PURE__ */ new Date()).toISOString() })}
45602
45684
  `, { encoding: "utf8", mode: 384 });
45603
45685
  requested.push(file);
45604
45686
  records.set(file, { pid: record.pid, startedAt: record.startedAt, ...record.generation ? { generation: record.generation } : {} });
@@ -45616,7 +45698,7 @@ async function cmdStop(runtime, waitMsFlag) {
45616
45698
  while (Date.now() <= deadline && stopped.size < requested.length) {
45617
45699
  for (const [file, record] of records) {
45618
45700
  try {
45619
- const current = JSON.parse(readFileSync31(join40(runtime.dirs.state, file), "utf8"));
45701
+ const current = JSON.parse(readFileSync32(join42(runtime.dirs.state, file), "utf8"));
45620
45702
  if (current.pid !== record.pid || current.startedAt !== record.startedAt || current.generation !== record.generation || !processExists(record.pid)) stopped.add(file);
45621
45703
  } catch {
45622
45704
  stopped.add(file);
@@ -45629,7 +45711,7 @@ async function cmdStop(runtime, waitMsFlag) {
45629
45711
  for (const file of orphans) {
45630
45712
  while (Date.now() <= deadlineOrphans) {
45631
45713
  try {
45632
- const current = JSON.parse(readFileSync31(join40(runtime.dirs.state, file), "utf8"));
45714
+ const current = JSON.parse(readFileSync32(join42(runtime.dirs.state, file), "utf8"));
45633
45715
  if (!Number.isInteger(current.serverPid) || !processExists(current.serverPid)) break;
45634
45716
  } catch {
45635
45717
  break;
@@ -45637,14 +45719,14 @@ async function cmdStop(runtime, waitMsFlag) {
45637
45719
  await (runtime.io.sleep ?? ((ms) => new Promise((resolveSleep) => setTimeout(resolveSleep, ms))))(100);
45638
45720
  }
45639
45721
  try {
45640
- const current = JSON.parse(readFileSync31(join40(runtime.dirs.state, file), "utf8"));
45722
+ const current = JSON.parse(readFileSync32(join42(runtime.dirs.state, file), "utf8"));
45641
45723
  if (Number.isInteger(current.serverPid) && processExists(current.serverPid)) {
45642
45724
  try {
45643
45725
  process.kill(current.serverPid, "SIGKILL");
45644
45726
  } catch {
45645
45727
  }
45646
45728
  }
45647
- rmSync10(join40(runtime.dirs.state, file), { force: true });
45729
+ rmSync11(join42(runtime.dirs.state, file), { force: true });
45648
45730
  } catch {
45649
45731
  }
45650
45732
  stopped.add(file);
@@ -45655,11 +45737,11 @@ async function cmdStop(runtime, waitMsFlag) {
45655
45737
  }
45656
45738
  async function cmdSessionStatus(runtime) {
45657
45739
  const stateDir = runtime.dirs.state;
45658
- const names3 = existsSync30(stateDir) ? readdirSync12(stateDir) : [];
45740
+ const names3 = existsSync32(stateDir) ? readdirSync12(stateDir) : [];
45659
45741
  const claims = [];
45660
45742
  for (const file of names3.filter((name) => name.endsWith(".pid"))) {
45661
45743
  try {
45662
- const record = JSON.parse(readFileSync31(join40(stateDir, file), "utf8"));
45744
+ const record = JSON.parse(readFileSync32(join42(stateDir, file), "utf8"));
45663
45745
  claims.push({
45664
45746
  file,
45665
45747
  role: record.role,
@@ -45674,7 +45756,7 @@ async function cmdSessionStatus(runtime) {
45674
45756
  const recoveries = [];
45675
45757
  for (const file of names3.filter((name) => name.startsWith("worker-recovery-") && name.endsWith(".json"))) {
45676
45758
  try {
45677
- const envelope = JSON.parse(readFileSync31(join40(stateDir, file), "utf8"));
45759
+ const envelope = JSON.parse(readFileSync32(join42(stateDir, file), "utf8"));
45678
45760
  recoveries.push({
45679
45761
  file,
45680
45762
  reason: envelope.reason,
@@ -45779,7 +45861,7 @@ async function cmdSessionBrief(runtime, options = {}) {
45779
45861
  print(runtime.io, runtime.json, { ok: true, command: "session brief", sessionToken }, sessionToken);
45780
45862
  return 0;
45781
45863
  }
45782
- const dataPath = resolve25(runtime.dirs.workdir, runtime.env.KXM_DATA_PATH?.trim() || join40(runtime.dirs.state, "kxm.db"));
45864
+ const dataPath = resolve25(runtime.dirs.workdir, runtime.env.KXM_DATA_PATH?.trim() || join42(runtime.dirs.state, "kxm.db"));
45783
45865
  const env = {
45784
45866
  ...runtime.env,
45785
45867
  KXM_STATE_DIR: runtime.dirs.state,
@@ -45855,7 +45937,7 @@ async function cmdSessionStart(runtime, options) {
45855
45937
  ...workflowId ? workflowAssetDirs(runtime.dirs.assets, workflowId) : []
45856
45938
  ];
45857
45939
  if (!runtime.dryRun) {
45858
- for (const directory of created) mkdirSync25(directory, { recursive: true });
45940
+ for (const directory of created) mkdirSync26(directory, { recursive: true });
45859
45941
  writeSession(runtime.dirs.assets, session);
45860
45942
  }
45861
45943
  print(runtime.io, runtime.json, {
@@ -45871,16 +45953,15 @@ async function cmdSessionStart(runtime, options) {
45871
45953
  // plugins/kxm/src/cli/system.ts
45872
45954
  import { spawnSync as spawnSync8 } from "node:child_process";
45873
45955
  import { createHash as createHash16 } from "node:crypto";
45874
- import { existsSync as existsSync36, mkdtempSync as mkdtempSync2, readFileSync as readFileSync36, rmSync as rmSync12 } from "node:fs";
45956
+ import { existsSync as existsSync38, mkdtempSync as mkdtempSync2, readFileSync as readFileSync37, rmSync as rmSync13 } from "node:fs";
45875
45957
  import { tmpdir as tmpdir2 } from "node:os";
45876
- import { join as join46, resolve as resolve29 } from "node:path";
45958
+ import { join as join48, resolve as resolve29 } from "node:path";
45877
45959
  import { createInterface as createInterface3 } from "node:readline";
45878
- import { fileURLToPath as fileURLToPath7 } from "node:url";
45879
45960
 
45880
45961
  // plugins/kxm/src/improve.ts
45881
45962
  import { createHash as createHash15 } from "node:crypto";
45882
- import { existsSync as existsSync31, mkdirSync as mkdirSync26, writeFileSync as writeFileSync24 } from "node:fs";
45883
- import { join as join41, relative as relative6, resolve as resolve26 } from "node:path";
45963
+ import { existsSync as existsSync33, mkdirSync as mkdirSync27, writeFileSync as writeFileSync25 } from "node:fs";
45964
+ import { join as join43, relative as relative6, resolve as resolve26 } from "node:path";
45884
45965
  var CANDIDATE_SCHEMA = "kxm.candidate.v1";
45885
45966
  var IMPROVEMENT_REPORT_SCHEMA = "kxm.improvement-report.v2";
45886
45967
  function classifyCandidateKind(stepId, agentRole) {
@@ -46052,7 +46133,7 @@ function groupRoutingRecords(records, options = {}) {
46052
46133
  }
46053
46134
  function buildImprovementReport(records, options = {}) {
46054
46135
  const projectRoot = options.projectRoot ? resolve26(options.projectRoot) : process.cwd();
46055
- const candidatesDir = options.candidatesDir ? resolve26(options.candidatesDir) : join41(projectRoot, ".kxm", "candidates");
46136
+ const candidatesDir = options.candidatesDir ? resolve26(options.candidatesDir) : join43(projectRoot, ".kxm", "candidates");
46056
46137
  const groups = groupRoutingRecords(records, options);
46057
46138
  const candidates = [];
46058
46139
  for (const group of groups) {
@@ -46064,7 +46145,7 @@ function buildImprovementReport(records, options = {}) {
46064
46145
  group.workflowHash
46065
46146
  );
46066
46147
  const diffFileName = `${group.candidateId}.diff`;
46067
- const diffFilePath = join41(candidatesDir, diffFileName);
46148
+ const diffFilePath = join43(candidatesDir, diffFileName);
46068
46149
  const relDiffPath = relative6(projectRoot, diffFilePath).replace(/\\/g, "/");
46069
46150
  const candidate = {
46070
46151
  schema: CANDIDATE_SCHEMA,
@@ -46086,12 +46167,12 @@ function buildImprovementReport(records, options = {}) {
46086
46167
  createdAt: nowIso()
46087
46168
  };
46088
46169
  if (!options.dryRun) {
46089
- if (!existsSync31(candidatesDir)) {
46090
- mkdirSync26(candidatesDir, { recursive: true });
46170
+ if (!existsSync33(candidatesDir)) {
46171
+ mkdirSync27(candidatesDir, { recursive: true });
46091
46172
  }
46092
- writeFileSync24(diffFilePath, diff, "utf8");
46093
- const jsonFilePath = join41(candidatesDir, `${group.candidateId}.json`);
46094
- writeFileSync24(jsonFilePath, JSON.stringify(candidate, null, 2) + "\n", "utf8");
46173
+ writeFileSync25(diffFilePath, diff, "utf8");
46174
+ const jsonFilePath = join43(candidatesDir, `${group.candidateId}.json`);
46175
+ writeFileSync25(jsonFilePath, JSON.stringify(candidate, null, 2) + "\n", "utf8");
46095
46176
  }
46096
46177
  candidates.push(candidate);
46097
46178
  }
@@ -46106,10 +46187,10 @@ function buildImprovementReport(records, options = {}) {
46106
46187
  }
46107
46188
  function writeImprovementReport(improvementsDir, report2, dryRun = false) {
46108
46189
  const stamp = report2.createdAt.replace(/[:.]/g, "-");
46109
- const path4 = join41(improvementsDir, `${stamp}.json`);
46190
+ const path4 = join43(improvementsDir, `${stamp}.json`);
46110
46191
  if (!dryRun) {
46111
- mkdirSync26(improvementsDir, { recursive: true });
46112
- writeFileSync24(path4, `${JSON.stringify(report2, null, 2)}
46192
+ mkdirSync27(improvementsDir, { recursive: true });
46193
+ writeFileSync25(path4, `${JSON.stringify(report2, null, 2)}
46113
46194
  `, { encoding: "utf8" });
46114
46195
  }
46115
46196
  return path4;
@@ -46149,8 +46230,8 @@ function formatImprovementReport(report2) {
46149
46230
 
46150
46231
  // plugins/kxm/src/modes.ts
46151
46232
  var import_yaml17 = __toESM(require_dist(), 1);
46152
- import { existsSync as existsSync32, readFileSync as readFileSync33 } from "node:fs";
46153
- import { join as join42 } from "node:path";
46233
+ import { existsSync as existsSync34, readFileSync as readFileSync34 } from "node:fs";
46234
+ import { join as join44 } from "node:path";
46154
46235
  var DEFAULT_MODES_CONFIG = Object.freeze({
46155
46236
  schema: "kxm.modes.v1",
46156
46237
  majorModes: {
@@ -46213,12 +46294,12 @@ function loadModesConfig(projectRoot) {
46213
46294
  if (!projectRoot) {
46214
46295
  return DEFAULT_MODES_CONFIG;
46215
46296
  }
46216
- const modesPath = join42(projectRoot, ".kxm", "modes.yaml");
46217
- if (!existsSync32(modesPath)) {
46297
+ const modesPath = join44(projectRoot, ".kxm", "modes.yaml");
46298
+ if (!existsSync34(modesPath)) {
46218
46299
  return DEFAULT_MODES_CONFIG;
46219
46300
  }
46220
46301
  try {
46221
- const raw = readFileSync33(modesPath, "utf8");
46302
+ const raw = readFileSync34(modesPath, "utf8");
46222
46303
  const parsed = (0, import_yaml17.parse)(raw);
46223
46304
  if (parsed && parsed.schema === "kxm.modes.v1" && parsed.majorModes) {
46224
46305
  return {
@@ -46304,11 +46385,11 @@ function calculatePromptFootprint(resolved, projectRoot = process.cwd(), catalog
46304
46385
  estimatedTokens: estimateTokens(baseSystemPromptChars)
46305
46386
  });
46306
46387
  for (const relPath of resolved.contextFiles) {
46307
- const fullPath = join42(projectRoot, relPath);
46388
+ const fullPath = join44(projectRoot, relPath);
46308
46389
  let chars = 0;
46309
- if (existsSync32(fullPath)) {
46390
+ if (existsSync34(fullPath)) {
46310
46391
  try {
46311
- chars = readFileSync33(fullPath, "utf8").length;
46392
+ chars = readFileSync34(fullPath, "utf8").length;
46312
46393
  } catch {
46313
46394
  chars = 0;
46314
46395
  }
@@ -46440,9 +46521,9 @@ ${divider}
46440
46521
 
46441
46522
  // plugins/kxm/src/ssh-remote.ts
46442
46523
  import { spawnSync as spawnSync7 } from "node:child_process";
46443
- import { existsSync as existsSync33, mkdirSync as mkdirSync27, readFileSync as readFileSync34, readdirSync as readdirSync13, rmSync as rmSync11, statSync as statSync5 } from "node:fs";
46444
- import { homedir as homedir7 } from "node:os";
46445
- import { join as join43, resolve as resolve27 } from "node:path";
46524
+ import { existsSync as existsSync35, mkdirSync as mkdirSync28, readFileSync as readFileSync35, readdirSync as readdirSync13, rmSync as rmSync12, statSync as statSync5 } from "node:fs";
46525
+ import { homedir as homedir8 } from "node:os";
46526
+ import { join as join45, resolve as resolve27 } from "node:path";
46446
46527
  var MAX_SSH_OUTPUT_BYTES = 50 * 1024;
46447
46528
  var MAX_SSH_OUTPUT_LINES = 2e3;
46448
46529
  var DEFAULT_SOCKET_DIR = ".kxm/run/ssh-sockets";
@@ -46468,12 +46549,12 @@ function truncateSshOutput(raw) {
46468
46549
  return { text, truncated };
46469
46550
  }
46470
46551
  function parseSshConfig(configPath) {
46471
- const targetPath = configPath ?? join43(homedir7(), ".ssh", "config");
46472
- if (!existsSync33(targetPath)) {
46552
+ const targetPath = configPath ?? join45(homedir8(), ".ssh", "config");
46553
+ if (!existsSync35(targetPath)) {
46473
46554
  return [];
46474
46555
  }
46475
46556
  try {
46476
- const content = readFileSync34(targetPath, "utf-8");
46557
+ const content = readFileSync35(targetPath, "utf-8");
46477
46558
  const lines = content.split("\n");
46478
46559
  const hosts = [];
46479
46560
  let currentHosts = [];
@@ -46551,14 +46632,14 @@ function resolveSshHostG(host, execFn = spawnSync7) {
46551
46632
  }
46552
46633
  function ensureSocketDir(socketDir = DEFAULT_SOCKET_DIR) {
46553
46634
  const resolved = resolve27(socketDir);
46554
- if (!existsSync33(resolved)) {
46555
- mkdirSync27(resolved, { recursive: true, mode: 448 });
46635
+ if (!existsSync35(resolved)) {
46636
+ mkdirSync28(resolved, { recursive: true, mode: 448 });
46556
46637
  }
46557
46638
  return resolved;
46558
46639
  }
46559
46640
  function buildSshArgs(options) {
46560
46641
  const socketDir = ensureSocketDir(options.socketDir ?? DEFAULT_SOCKET_DIR);
46561
- const controlPath = join43(socketDir, "%C");
46642
+ const controlPath = join45(socketDir, "%C");
46562
46643
  const persist = options.controlPersist ?? DEFAULT_CONTROL_PERSIST;
46563
46644
  const args = [
46564
46645
  "-o",
@@ -46583,7 +46664,7 @@ function buildSshArgs(options) {
46583
46664
  }
46584
46665
  function checkControlSocket(host, socketDir = DEFAULT_SOCKET_DIR, execFn = spawnSync7) {
46585
46666
  const resolvedDir = ensureSocketDir(socketDir);
46586
- const controlPath = join43(resolvedDir, "%C");
46667
+ const controlPath = join45(resolvedDir, "%C");
46587
46668
  try {
46588
46669
  const result = execFn("ssh", ["-O", "check", "-o", `ControlPath=${controlPath}`, host], {
46589
46670
  encoding: "utf-8"
@@ -46595,7 +46676,7 @@ function checkControlSocket(host, socketDir = DEFAULT_SOCKET_DIR, execFn = spawn
46595
46676
  }
46596
46677
  function closeControlSocket(host, socketDir = DEFAULT_SOCKET_DIR, execFn = spawnSync7) {
46597
46678
  const resolvedDir = ensureSocketDir(socketDir);
46598
- const controlPath = join43(resolvedDir, "%C");
46679
+ const controlPath = join45(resolvedDir, "%C");
46599
46680
  try {
46600
46681
  const result = execFn("ssh", ["-O", "stop", "-o", `ControlPath=${controlPath}`, host], {
46601
46682
  encoding: "utf-8"
@@ -47041,9 +47122,9 @@ complete -c kxm -n "__fish_seen_subcommand_from goal" -a "create list get"
47041
47122
  }
47042
47123
 
47043
47124
  // plugins/kxm/src/completion-install.ts
47044
- import { existsSync as existsSync34, mkdirSync as mkdirSync28, readFileSync as readFileSync35, writeFileSync as writeFileSync25 } from "node:fs";
47045
- import { homedir as homedir8 } from "node:os";
47046
- import { basename as basename9, delimiter, dirname as dirname21, isAbsolute as isAbsolute8, join as join44, resolve as resolve28 } from "node:path";
47125
+ import { existsSync as existsSync36, mkdirSync as mkdirSync29, readFileSync as readFileSync36, writeFileSync as writeFileSync26 } from "node:fs";
47126
+ import { homedir as homedir9 } from "node:os";
47127
+ import { basename as basename9, delimiter, dirname as dirname22, isAbsolute as isAbsolute9, join as join46, resolve as resolve28 } from "node:path";
47047
47128
  var COMPLETION_MARKER = "# kxm completion";
47048
47129
  var PATH_MARKER = "# kxm path";
47049
47130
  function detectShell(env = process.env, platform = process.platform) {
@@ -47059,31 +47140,31 @@ function effectiveHome(options) {
47059
47140
  const env = options.env ?? process.env;
47060
47141
  if (options.homeDir) return options.homeDir;
47061
47142
  const envHome = env.HOME?.trim() ?? env.USERPROFILE?.trim();
47062
- return envHome && envHome.length > 0 ? resolve28(envHome) : homedir8();
47143
+ return envHome && envHome.length > 0 ? resolve28(envHome) : homedir9();
47063
47144
  }
47064
47145
  function completionScriptPath(shell, options = {}) {
47065
47146
  const env = options.env ?? process.env;
47066
47147
  const explicit = options.configDir ?? env.KXM_USER_CONFIG_DIR?.trim();
47067
47148
  const base = explicit && explicit.length > 0 ? resolve28(explicit) : resolve28(effectiveHome(options), ".config", "kxm");
47068
- return join44(base, "completions", `kxm.${shell}`);
47149
+ return join46(base, "completions", `kxm.${shell}`);
47069
47150
  }
47070
47151
  function bashRcCandidate(options) {
47071
47152
  const home = effectiveHome(options);
47072
- const candidates = [join44(home, ".bashrc"), join44(home, ".bash_profile")];
47073
- const existing = candidates.find((candidate) => existsSync34(candidate));
47153
+ const candidates = [join46(home, ".bashrc"), join46(home, ".bash_profile")];
47154
+ const existing = candidates.find((candidate) => existsSync36(candidate));
47074
47155
  return existing ?? candidates[0];
47075
47156
  }
47076
47157
  function zshRcCandidate(options) {
47077
47158
  const env = options.env ?? process.env;
47078
47159
  const home = effectiveHome(options);
47079
- if (env.ZDOTDIR?.trim()) return join44(resolve28(env.ZDOTDIR.trim()), ".zshrc");
47080
- return join44(home, ".zshrc");
47160
+ if (env.ZDOTDIR?.trim()) return join46(resolve28(env.ZDOTDIR.trim()), ".zshrc");
47161
+ return join46(home, ".zshrc");
47081
47162
  }
47082
47163
  function fishCompletionTarget(shell, options) {
47083
47164
  const env = options.env ?? process.env;
47084
47165
  const home = effectiveHome(options);
47085
- if (env.XDG_CONFIG_HOME?.trim()) return join44(resolve28(env.XDG_CONFIG_HOME.trim()), "fish", "completions", "kxm.fish");
47086
- return join44(home, ".config", "fish", "completions", "kxm.fish");
47166
+ if (env.XDG_CONFIG_HOME?.trim()) return join46(resolve28(env.XDG_CONFIG_HOME.trim()), "fish", "completions", "kxm.fish");
47167
+ return join46(home, ".config", "fish", "completions", "kxm.fish");
47087
47168
  }
47088
47169
  function completionRcTarget(shell, options = {}) {
47089
47170
  if (shell === "fish") {
@@ -47115,17 +47196,17 @@ function installShellCompletion(shellInput, options = {}) {
47115
47196
  const scriptPath = completionScriptPath(shell, options);
47116
47197
  const { rcFile } = completionRcTarget(shell, options);
47117
47198
  const script = generateShellCompletion(shell);
47118
- const existingScript = existsSync34(scriptPath);
47119
- const existingScriptMatches = existingScript && readFileSync35(scriptPath, "utf8") === script;
47199
+ const existingScript = existsSync36(scriptPath);
47200
+ const existingScriptMatches = existingScript && readFileSync36(scriptPath, "utf8") === script;
47120
47201
  let rcModified = false;
47121
47202
  let alreadyInstalled = false;
47122
47203
  if (shell === "fish") {
47123
47204
  const fishTarget = fishCompletionTarget(shell, options);
47124
- const fishInstalled = existsSync34(fishTarget) && readFileSync35(fishTarget, "utf8") === script;
47205
+ const fishInstalled = existsSync36(fishTarget) && readFileSync36(fishTarget, "utf8") === script;
47125
47206
  alreadyInstalled = fishInstalled;
47126
47207
  if (!options.dryRun && (!fishInstalled || options.overwrite)) {
47127
- mkdirSync28(resolve28(fishTarget, ".."), { recursive: true });
47128
- writeFileSync25(fishTarget, script, { encoding: "utf8" });
47208
+ mkdirSync29(resolve28(fishTarget, ".."), { recursive: true });
47209
+ writeFileSync26(fishTarget, script, { encoding: "utf8" });
47129
47210
  }
47130
47211
  return {
47131
47212
  ok: true,
@@ -47138,13 +47219,13 @@ function installShellCompletion(shellInput, options = {}) {
47138
47219
  }
47139
47220
  if (rcFile) {
47140
47221
  const line = sourceLine(shell, scriptPath);
47141
- const rcContent = existsSync34(rcFile) ? readFileSync35(rcFile, "utf8") : "";
47222
+ const rcContent = existsSync36(rcFile) ? readFileSync36(rcFile, "utf8") : "";
47142
47223
  alreadyInstalled = rcContent.includes(line) || rcContent.includes(`${COMPLETION_MARKER}`);
47143
47224
  }
47144
47225
  if (!options.dryRun) {
47145
47226
  if (!existingScriptMatches || options.overwrite) {
47146
- mkdirSync28(resolve28(scriptPath, ".."), { recursive: true });
47147
- writeFileSync25(scriptPath, script, { encoding: "utf8" });
47227
+ mkdirSync29(resolve28(scriptPath, ".."), { recursive: true });
47228
+ writeFileSync26(scriptPath, script, { encoding: "utf8" });
47148
47229
  }
47149
47230
  if (rcFile && !alreadyInstalled) {
47150
47231
  const line = sourceLine(shell, scriptPath);
@@ -47153,8 +47234,8 @@ function installShellCompletion(shellInput, options = {}) {
47153
47234
  ${marker}
47154
47235
  ${line}
47155
47236
  `;
47156
- mkdirSync28(resolve28(rcFile, ".."), { recursive: true });
47157
- writeFileSync25(rcFile, (existsSync34(rcFile) ? readFileSync35(rcFile, "utf8") : "") + stanza, { encoding: "utf8" });
47237
+ mkdirSync29(resolve28(rcFile, ".."), { recursive: true });
47238
+ writeFileSync26(rcFile, (existsSync36(rcFile) ? readFileSync36(rcFile, "utf8") : "") + stanza, { encoding: "utf8" });
47158
47239
  rcModified = true;
47159
47240
  }
47160
47241
  }
@@ -47169,15 +47250,15 @@ ${line}
47169
47250
  }
47170
47251
  function kxmBinDir(env = process.env) {
47171
47252
  const argv1 = env.KXM_ENTRY ?? process.argv[1];
47172
- if (argv1 && isAbsolute8(argv1)) {
47173
- const dir = dirname21(argv1);
47174
- if (existsSync34(join44(dir, process.platform === "win32" ? "kxm.cmd" : "kxm"))) return dir;
47253
+ if (argv1 && isAbsolute9(argv1)) {
47254
+ const dir = dirname22(argv1);
47255
+ if (existsSync36(join46(dir, process.platform === "win32" ? "kxm.cmd" : "kxm"))) return dir;
47175
47256
  }
47176
47257
  const pathEnv = env.PATH ?? "";
47177
47258
  for (const part of pathEnv.split(delimiter)) {
47178
47259
  if (!part) continue;
47179
47260
  const candidate = resolve28(part, process.platform === "win32" ? "kxm.cmd" : "kxm");
47180
- if (existsSync34(candidate)) return resolve28(part);
47261
+ if (existsSync36(candidate)) return resolve28(part);
47181
47262
  }
47182
47263
  return void 0;
47183
47264
  }
@@ -47195,11 +47276,11 @@ function installPathEntry(shellInput, options = {}) {
47195
47276
  }
47196
47277
  const { rcFile } = completionRcTarget(shell, options);
47197
47278
  const line = pathLine(binDir);
47198
- const rcContent = existsSync34(rcFile ?? "") ? readFileSync35(rcFile, "utf8") : "";
47279
+ const rcContent = existsSync36(rcFile ?? "") ? readFileSync36(rcFile, "utf8") : "";
47199
47280
  const alreadyInstalled = rcContent.includes(binDir) || (options.env?.PATH ?? process.env.PATH ?? "").split(delimiter).includes(binDir);
47200
47281
  if (!options.dryRun && rcFile && !alreadyInstalled) {
47201
- mkdirSync28(dirname21(rcFile), { recursive: true });
47202
- writeFileSync25(rcFile, rcContent + `
47282
+ mkdirSync29(dirname22(rcFile), { recursive: true });
47283
+ writeFileSync26(rcFile, rcContent + `
47203
47284
  ${PATH_MARKER}
47204
47285
  ${line}
47205
47286
  `, { encoding: "utf8" });
@@ -47209,8 +47290,8 @@ ${line}
47209
47290
 
47210
47291
  // plugins/kxm/src/init-guide-setup.ts
47211
47292
  var import_yaml18 = __toESM(require_dist(), 1);
47212
- import { existsSync as existsSync35, mkdirSync as mkdirSync29, writeFileSync as writeFileSync26 } from "node:fs";
47213
- import { dirname as dirname22, join as join45 } from "node:path";
47293
+ import { existsSync as existsSync37, mkdirSync as mkdirSync30, writeFileSync as writeFileSync27 } from "node:fs";
47294
+ import { dirname as dirname23, join as join47 } from "node:path";
47214
47295
  var NATIVE_VENDOR_HARNESS = Object.freeze({
47215
47296
  anthropic: "claude",
47216
47297
  openai: "codex",
@@ -47609,13 +47690,13 @@ function renderGuideSetupFiles(projectRoot, plan) {
47609
47690
  const stage = roleStages.get(role);
47610
47691
  if (!stage) continue;
47611
47692
  files.push({
47612
- path: join45(projectRoot, ".kxm", "agents", `${role}.yaml`),
47693
+ path: join47(projectRoot, ".kxm", "agents", `${role}.yaml`),
47613
47694
  content: (0, import_yaml18.stringify)(agentDocument(role, stage, binding))
47614
47695
  });
47615
47696
  }
47616
47697
  for (const workflow of plan.workflows) {
47617
47698
  files.push({
47618
- path: join45(projectRoot, ".kxm", "workflows", `${workflow.slug}.yaml`),
47699
+ path: join47(projectRoot, ".kxm", "workflows", `${workflow.slug}.yaml`),
47619
47700
  content: (0, import_yaml18.stringify)(workflowDocument(workflow))
47620
47701
  });
47621
47702
  }
@@ -47625,12 +47706,12 @@ function writeGuideSetupFiles(files) {
47625
47706
  const written = [];
47626
47707
  const existed = [];
47627
47708
  for (const file of files) {
47628
- if (existsSync35(file.path)) {
47709
+ if (existsSync37(file.path)) {
47629
47710
  existed.push(file.path);
47630
47711
  continue;
47631
47712
  }
47632
- mkdirSync29(dirname22(file.path), { recursive: true });
47633
- writeFileSync26(file.path, file.content, "utf8");
47713
+ mkdirSync30(dirname23(file.path), { recursive: true });
47714
+ writeFileSync27(file.path, file.content, "utf8");
47634
47715
  written.push(file.path);
47635
47716
  }
47636
47717
  return { written, existed };
@@ -47653,7 +47734,6 @@ function parseGuideSelection(input, catalog = GUIDE_WORKFLOWS) {
47653
47734
  }
47654
47735
 
47655
47736
  // plugins/kxm/src/cli/system.ts
47656
- var repoRoot4 = resolve29(fileURLToPath7(new URL("../../../../", import.meta.url)));
47657
47737
  function cliSpawn(runtime, command, args, extra) {
47658
47738
  if (runtime.io.spawnSync) return runtime.io.spawnSync(command, args);
47659
47739
  const result = spawnSync8(command, [...args], {
@@ -47694,7 +47774,7 @@ function applyKxmPackageUpdate(runtime, notice) {
47694
47774
  detail: `release v${notice.latest} has no sha256 digest for ${name}; refusing to install`
47695
47775
  };
47696
47776
  }
47697
- const releaseDir = mkdtempSync2(join46(tmpdir2(), "kxm-pkg-update-"));
47777
+ const releaseDir = mkdtempSync2(join48(tmpdir2(), "kxm-pkg-update-"));
47698
47778
  try {
47699
47779
  const planned = planKxmPackageUpdate(notice.source, notice.latest, releaseDir, notice.asset);
47700
47780
  if (runtime.dryRun) {
@@ -47703,7 +47783,7 @@ function applyKxmPackageUpdate(runtime, notice) {
47703
47783
  for (const step of planned) {
47704
47784
  if (step.kind === "verify") {
47705
47785
  if (!verifyReleaseAssetDigest(step.path, step.sha256)) {
47706
- const actual = existsSync36(step.path) ? createHash16("sha256").update(readFileSync36(step.path)).digest("hex") : "missing";
47786
+ const actual = existsSync38(step.path) ? createHash16("sha256").update(readFileSync37(step.path)).digest("hex") : "missing";
47707
47787
  return {
47708
47788
  ok: false,
47709
47789
  error: "release_digest_mismatch",
@@ -47720,7 +47800,7 @@ function applyKxmPackageUpdate(runtime, notice) {
47720
47800
  }
47721
47801
  return { ok: true, detail: `installed ${notice.latest} from ${notice.source}` };
47722
47802
  } finally {
47723
- rmSync12(releaseDir, { recursive: true, force: true });
47803
+ rmSync13(releaseDir, { recursive: true, force: true });
47724
47804
  }
47725
47805
  }
47726
47806
  async function cmdExplain(runtime, options) {
@@ -47822,7 +47902,7 @@ async function cmdUpdate(runtime, harness, options) {
47822
47902
  warnIgnoredProjectUpdateYaml(runtime);
47823
47903
  const probe = installProbeFrom(runtime);
47824
47904
  const classified = classifyInstallRoot(probe);
47825
- const current = readInstalledKxmVersion(repoRoot4);
47905
+ const current = readInstalledKxmVersion(findKxmRepoRoot(import.meta.url));
47826
47906
  let notice;
47827
47907
  let kindReport = classified;
47828
47908
  if (classified.kind === "source") {
@@ -47969,12 +48049,12 @@ async function cmdValidate(runtime, fileFlag) {
47969
48049
  }
47970
48050
  const selectedFile = explicitFile || configuredFile;
47971
48051
  const file = selectedFile ? resolve29(runtime.cwd, selectedFile) : void 0;
47972
- if (file && !existsSync36(file)) {
48052
+ if (file && !existsSync38(file)) {
47973
48053
  printWorker(runtime, worker, { ok: false, command: "validate", error: "file_not_found", file }, `workflow file not found: ${file}`);
47974
48054
  return 1;
47975
48055
  }
47976
48056
  try {
47977
- const raw = file ? readFileSync36(file, "utf8") : inline;
48057
+ const raw = file ? readFileSync37(file, "utf8") : inline;
47978
48058
  const warnings = [];
47979
48059
  const definitions = parseWorkflowDefinitions(raw, runtime.env, (message) => warnings.push(message));
47980
48060
  const secretEnvs = definitions.map((definition) => ({
@@ -48019,14 +48099,14 @@ async function cmdArtifactsExist(runtime, pathFlag) {
48019
48099
  }
48020
48100
  async function cmdImprove(runtime, options = {}) {
48021
48101
  const file = options.file ? resolve29(runtime.cwd, options.file) : telemetryPath(runtime.dirs.logs);
48022
- const routingRecords = existsSync36(file) ? readRoutingRecords(file).map((entry) => entry.routing) : [];
48023
- const candidatesDir = options.outDir ? resolve29(runtime.cwd, options.outDir) : join46(runtime.cwd, ".kxm", "candidates");
48102
+ const routingRecords = existsSync38(file) ? readRoutingRecords(file).map((entry) => entry.routing) : [];
48103
+ const candidatesDir = options.outDir ? resolve29(runtime.cwd, options.outDir) : join48(runtime.cwd, ".kxm", "candidates");
48024
48104
  const report2 = buildImprovementReport(routingRecords, {
48025
48105
  candidatesDir,
48026
48106
  projectRoot: runtime.cwd,
48027
48107
  dryRun: runtime.dryRun
48028
48108
  });
48029
- const reportDir = join46(runtime.dirs.assets, "improvements");
48109
+ const reportDir = join48(runtime.dirs.assets, "improvements");
48030
48110
  const reportPath = writeImprovementReport(reportDir, report2, runtime.dryRun);
48031
48111
  const text = formatImprovementReport(report2);
48032
48112
  print(runtime.io, runtime.json, {
@@ -48158,9 +48238,9 @@ async function maybeOfferCompletionInstall(runtime) {
48158
48238
  if (!pathNeeded) {
48159
48239
  const scriptPath = completionScriptPath(shell, { env: runtime.env, configDir: runtime.env.KXM_USER_CONFIG_DIR });
48160
48240
  const { rcFile } = completionRcTarget(shell, { env: runtime.env });
48161
- if (rcFile && existsSync36(rcFile)) {
48241
+ if (rcFile && existsSync38(rcFile)) {
48162
48242
  try {
48163
- if (readFileSync36(rcFile, "utf8").includes(scriptPath)) return;
48243
+ if (readFileSync37(rcFile, "utf8").includes(scriptPath)) return;
48164
48244
  } catch {
48165
48245
  }
48166
48246
  }
@@ -48292,7 +48372,7 @@ async function cmdRoutingReport(runtime, options) {
48292
48372
  let catalog;
48293
48373
  if (includeEquivalentListCost) {
48294
48374
  try {
48295
- const pricesPath = options.prices ? resolve29(runtime.cwd, options.prices) : join46(runtime.dirs.workspace, "prices.yaml");
48375
+ const pricesPath = options.prices ? resolve29(runtime.cwd, options.prices) : join48(runtime.dirs.workspace, "prices.yaml");
48296
48376
  catalog = loadPriceCatalog(pricesPath);
48297
48377
  } catch {
48298
48378
  }
@@ -48376,7 +48456,12 @@ async function cmdRoutingBenchmark(runtime, options) {
48376
48456
 
48377
48457
  // plugins/kxm/src/cli.ts
48378
48458
  var CLI_NAME2 = "kxm";
48379
- var repoRoot5 = resolve30(fileURLToPath8(new URL("../../../", import.meta.url)));
48459
+ function resolveCliAuthToken(runtime, project) {
48460
+ const envToken = runtime.env.KXM_AUTH_TOKEN?.trim();
48461
+ if (envToken) return envToken;
48462
+ const record = readHubEnvRecord(runtime.env);
48463
+ return record?.projectTokens?.[project]?.trim() || record?.authToken?.trim() || void 0;
48464
+ }
48380
48465
  var USAGE_ERROR_CODES = /* @__PURE__ */ new Set([
48381
48466
  "commander.help",
48382
48467
  "commander.helpDisplayed",
@@ -48398,12 +48483,13 @@ async function ensureCliClient(runtime) {
48398
48483
  const project = defaultProjectName(runtime.cwd, runtime.env);
48399
48484
  const name = runtime.env.KXM_AGENT_NAME?.trim() || `cli-${process.pid}`;
48400
48485
  const purpose = runtime.env.KXM_AGENT_PURPOSE?.trim() || "CLI agent client";
48401
- const authToken = runtime.env.KXM_AUTH_TOKEN?.trim();
48486
+ const authToken = resolveCliAuthToken(runtime, project);
48402
48487
  const client = new HubClient({
48403
48488
  serverUrl,
48404
48489
  name,
48405
48490
  project,
48406
48491
  purpose,
48492
+ fetchImpl: runtime.fetchImpl,
48407
48493
  ...authToken ? { authToken } : {}
48408
48494
  });
48409
48495
  await client.start(() => {
@@ -48519,7 +48605,7 @@ function createProgram(ctx, result) {
48519
48605
  };
48520
48606
  };
48521
48607
  const program2 = new Command(CLI_NAME2);
48522
- program2.description("KontextMind local-first orchestration CLI").version(readInstalledKxmVersion(repoRoot5), "-V, --version", "Print the installed kxm version").exitOverride().configureOutput({
48608
+ program2.description("KontextMind local-first orchestration CLI").version(readInstalledKxmVersion(findKxmRepoRoot(import.meta.url)), "-V, --version", "Print the installed kxm version").exitOverride().configureOutput({
48523
48609
  writeOut: (text) => ctx.io.stdout(text),
48524
48610
  writeErr: (text) => ctx.io.stderr(text)
48525
48611
  }).helpCommand("help", "Show help");
@@ -48986,7 +49072,7 @@ async function runCli(argv, env = process.env, io = { stdout: (text) => process.
48986
49072
  throw error;
48987
49073
  }
48988
49074
  }
48989
- if (process.argv[1] && resolve30(process.argv[1]) === fileURLToPath8(import.meta.url)) {
49075
+ if (process.argv[1] && resolve30(process.argv[1]) === fileURLToPath4(import.meta.url)) {
48990
49076
  const code = await runCli(process.argv.slice(2));
48991
49077
  process.exitCode = code;
48992
49078
  }