@hasna/skills 0.10.75 → 0.10.77

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/bin/index.js CHANGED
@@ -36888,7 +36888,7 @@ var package_default;
36888
36888
  var init_package = __esm(() => {
36889
36889
  package_default = {
36890
36890
  name: "@hasna/skills",
36891
- version: "0.10.75",
36891
+ version: "0.10.77",
36892
36892
  description: "Skills library for AI coding agents",
36893
36893
  type: "module",
36894
36894
  bin: {
@@ -50455,6 +50455,40 @@ var init_codex_settings_witness_v1 = __esm(() => {
50455
50455
  VERBOSITY = new Set(["low", "medium", "high"]);
50456
50456
  });
50457
50457
 
50458
+ // src/lib/codex-plugin-capability-paths.ts
50459
+ function foldCodexPluginEntryName(name) {
50460
+ return name.toUpperCase().toLowerCase();
50461
+ }
50462
+ function codexPluginRootCapabilityEntry(name) {
50463
+ const folded = foldCodexPluginEntryName(name);
50464
+ return CODEX_PLUGIN_ROOT_CAPABILITY_ENTRIES.includes(folded) ? folded : null;
50465
+ }
50466
+ function isCodexSkillDocumentName(name) {
50467
+ return foldCodexPluginEntryName(name) === "skill.md";
50468
+ }
50469
+ var CODEX_PLUGIN_MANIFEST_LOCATIONS, CODEX_PLUGIN_MANIFEST_DIRECTORIES, CODEX_PLUGIN_ROOT_CAPABILITY_ENTRIES;
50470
+ var init_codex_plugin_capability_paths = __esm(() => {
50471
+ CODEX_PLUGIN_MANIFEST_LOCATIONS = Object.freeze([
50472
+ "plugin.json",
50473
+ ".codex-plugin/plugin.json",
50474
+ ".claude-plugin/plugin.json",
50475
+ ".cursor-plugin/plugin.json"
50476
+ ]);
50477
+ CODEX_PLUGIN_MANIFEST_DIRECTORIES = Object.freeze([".codex-plugin", ".claude-plugin", ".cursor-plugin"]);
50478
+ CODEX_PLUGIN_ROOT_CAPABILITY_ENTRIES = Object.freeze([
50479
+ "plugin.json",
50480
+ ".codex-plugin",
50481
+ ".claude-plugin",
50482
+ ".cursor-plugin",
50483
+ "hooks",
50484
+ "hooks.json",
50485
+ ".mcp.json",
50486
+ ".app.json",
50487
+ "commands",
50488
+ "agents"
50489
+ ]);
50490
+ });
50491
+
50458
50492
  // src/lib/codex-hook-mcp-dependencies.ts
50459
50493
  import { createHash as createHash13 } from "crypto";
50460
50494
  import { basename as basename6, dirname as dirname11, isAbsolute as isAbsolute11, join as join17, resolve as resolve12, sep as sep4 } from "path";
@@ -50599,15 +50633,13 @@ function captureCodexHookMcpDependencies(configPath, reviewed, configText, chang
50599
50633
  }
50600
50634
  };
50601
50635
  const root = join17(cacheRoot, identity3, selectCodexPluginVersion(versions, selectionBudget));
50602
- const agent = read2(join17(root, "plugin.json"));
50636
+ const [agentPluginManifest, ...legacyManifests] = CODEX_PLUGIN_MANIFEST_LOCATIONS;
50637
+ const agent = read2(join17(root, agentPluginManifest));
50603
50638
  if (agent !== null) {
50604
50639
  const schema = JSON.parse(agent).$schema;
50605
50640
  need5(typeof schema !== "string" || !schema.startsWith("https://agent-plugins.org/schemas/"));
50606
50641
  }
50607
- const codex = read2(join17(root, ".codex-plugin/plugin.json"));
50608
- const claude = read2(join17(root, ".claude-plugin/plugin.json"));
50609
- const cursor = read2(join17(root, ".cursor-plugin/plugin.json"));
50610
- const text2 = codex ?? claude ?? cursor;
50642
+ const text2 = legacyManifests.map((location) => read2(join17(root, location))).find((value) => value !== null) ?? null;
50611
50643
  if (text2 === null)
50612
50644
  continue;
50613
50645
  const manifest = JSON.parse(text2);
@@ -50629,6 +50661,7 @@ var init_codex_hook_mcp_dependencies = __esm(() => {
50629
50661
  init_claude_settings_witness();
50630
50662
  init_agent_discovery_directories();
50631
50663
  init_agent_discovery_bytes();
50664
+ init_codex_plugin_capability_paths();
50632
50665
  events = new Set(["PreToolUse", "PermissionRequest", "PostToolUse", "PreCompact", "PostCompact", "SessionStart", "SessionEnd", "UserPromptSubmit", "SubagentStart", "SubagentStop", "Stop", "Interrupt"]);
50633
50666
  });
50634
50667
 
@@ -51502,10 +51535,31 @@ var init_agent_discovery_path_bytes = __esm(() => {
51502
51535
 
51503
51536
  // src/lib/codex-corpus-write.ts
51504
51537
  import { KernelLock } from "@hasna/contracts/kernel-lock";
51505
- import { execFileSync } from "child_process";
51538
+ import { AsyncLocalStorage } from "async_hooks";
51539
+ import { execFileSync, spawnSync as spawnSync2 } from "child_process";
51506
51540
  import { createHash as createHash16 } from "crypto";
51507
- import { accessSync, constants as constants8, lstatSync as lstatSync12, readFileSync as readFileSync10, realpathSync as realpathSync2, statSync as statSync7 } from "fs";
51541
+ import { accessSync, constants as constants8, lstatSync as lstatSync12, mkdirSync as mkdirSync5, mkdtempSync, readdirSync as readdirSync5, readFileSync as readFileSync10, realpathSync as realpathSync2, rmSync as rmSync2, statSync as statSync7 } from "fs";
51508
51542
  import { basename as basename7, delimiter, dirname as dirname13, isAbsolute as isAbsolute13, join as join19, relative as relative3, resolve as resolve14, sep as sep6 } from "path";
51543
+ function codexAdmissionRecord(options) {
51544
+ const record4 = options.onCodexAdmission;
51545
+ const invalid = () => {
51546
+ throw new Error("CODEX_CORPUS_ADMISSION_RECORD_INVALID: onCodexAdmission must be a synchronous function");
51547
+ };
51548
+ if (record4 !== undefined && typeof record4 !== "function")
51549
+ invalid();
51550
+ return { policy: { fallback: typeof record4 === "function" }, deliver(admission) {
51551
+ if (!admission || typeof record4 !== "function")
51552
+ return;
51553
+ const result2 = record4(admission);
51554
+ if (result2 !== null && (typeof result2 === "object" || typeof result2 === "function") && typeof result2.then === "function") {
51555
+ Promise.resolve(result2).catch(() => {});
51556
+ invalid();
51557
+ }
51558
+ } };
51559
+ }
51560
+ function codexAdmissionReceipt(admission) {
51561
+ return admission?.nativeAdmission === "unavailable" && admission.probe ? { nativeAdmission: "unavailable", nativeAdmissionProbe: { ...admission.probe } } : {};
51562
+ }
51509
51563
  function physicalTarget(path) {
51510
51564
  const suffix = [];
51511
51565
  for (let cursor = path;; cursor = dirname13(cursor)) {
@@ -51587,13 +51641,224 @@ function executable(options) {
51587
51641
  const digest = hash2();
51588
51642
  if (options.codexSha256 && digest !== options.codexSha256)
51589
51643
  return fail2();
51590
- return { path, assertCurrent() {
51644
+ return { path, sha256: digest, size: Number(initial2.size), assertCurrent() {
51591
51645
  const current = statSync7(path, { bigint: true });
51592
51646
  if (realpathSync2(found) !== path || ["dev", "ino", "size", "mtimeNs", "ctimeNs", "mode"].some((key2) => initial2[key2] !== current[key2]) || hash2() !== digest)
51593
51647
  fail2();
51594
51648
  } };
51595
51649
  }
51596
- function acquireCodexCorpusWrite(roots, options) {
51650
+ function nativeLockAbsent(root) {
51651
+ for (const name of [`${KEY}.flock-v1`, `${KEY}.lock`]) {
51652
+ try {
51653
+ lstatSync12(join19(root, name));
51654
+ return false;
51655
+ } catch (error) {
51656
+ if (error.code !== "ENOENT")
51657
+ throw error;
51658
+ }
51659
+ }
51660
+ return true;
51661
+ }
51662
+ function skillsState(root, leaf, roots) {
51663
+ const chain = [realpathSync2(dirname13(root))];
51664
+ for (const part of [".hasna", "skills", leaf])
51665
+ chain.push(join19(chain.at(-1), part));
51666
+ const path = chain.at(-1);
51667
+ const uid2 = process.getuid();
51668
+ const verify = () => {
51669
+ if (roots.some((item) => contains(item, path)) || codexCorpusRootForPath(path) !== undefined)
51670
+ fail2();
51671
+ for (let ancestor = dirname13(chain[0]);; ancestor = dirname13(ancestor)) {
51672
+ const stat2 = lstatSync12(ancestor), sticky = stat2.uid === 0 && (stat2.mode & 512) !== 0;
51673
+ if (!stat2.isDirectory() || stat2.uid !== uid2 && stat2.uid !== 0 || (stat2.mode & 18) !== 0 && !sticky)
51674
+ fail2();
51675
+ if (dirname13(ancestor) === ancestor)
51676
+ break;
51677
+ }
51678
+ for (const component of chain) {
51679
+ const stat2 = lstatSync12(component, { throwIfNoEntry: false });
51680
+ if (!stat2)
51681
+ return;
51682
+ if (!stat2.isDirectory() || stat2.uid !== uid2 && stat2.uid !== 0 || (stat2.mode & 18) !== 0 || component === path && stat2.uid !== uid2)
51683
+ fail2();
51684
+ }
51685
+ };
51686
+ verify();
51687
+ return { path, ensure() {
51688
+ verify();
51689
+ for (const component of chain.slice(1)) {
51690
+ try {
51691
+ mkdirSync5(component, { mode: 448 });
51692
+ } catch (error) {
51693
+ if (error.code !== "EEXIST")
51694
+ throw error;
51695
+ }
51696
+ }
51697
+ verify();
51698
+ if (realpathSync2(path) !== path)
51699
+ fail2();
51700
+ return path;
51701
+ } };
51702
+ }
51703
+ function probeParent(roots) {
51704
+ const dataRoot = resolve14(getDataDirReadOnly()), path = join19(dataRoot, PROBE_PARENT), uid2 = process.getuid();
51705
+ const chain = [];
51706
+ for (let component = path;; component = dirname13(component)) {
51707
+ chain.unshift(component);
51708
+ if (dirname13(component) === component)
51709
+ break;
51710
+ }
51711
+ const verify = () => {
51712
+ if (roots.some((item) => contains(item, path)) || codexCorpusRootForPath(path) !== undefined)
51713
+ fail2();
51714
+ for (const component of chain) {
51715
+ const stat2 = lstatSync12(component, { throwIfNoEntry: false });
51716
+ if (!stat2)
51717
+ return;
51718
+ const skills = contains(dataRoot, component), sticky = !skills && stat2.uid === 0 && (stat2.mode & 512) !== 0;
51719
+ if (!stat2.isDirectory() || stat2.uid !== uid2 && (skills || stat2.uid !== 0) || (stat2.mode & 18) !== 0 && !sticky)
51720
+ fail2();
51721
+ }
51722
+ };
51723
+ verify();
51724
+ for (const component of chain) {
51725
+ if (lstatSync12(component, { throwIfNoEntry: false }))
51726
+ continue;
51727
+ try {
51728
+ mkdirSync5(component, { mode: 448 });
51729
+ } catch (error) {
51730
+ if (error.code !== "EEXIST")
51731
+ throw error;
51732
+ }
51733
+ }
51734
+ verify();
51735
+ if (realpathSync2(path) !== path)
51736
+ fail2();
51737
+ return path;
51738
+ }
51739
+ function probeHomeIntact(home, empty) {
51740
+ const stat2 = lstatSync12(home.path, { bigint: true, throwIfNoEntry: false });
51741
+ return !!stat2 && stat2.isDirectory() && stat2.dev === home.dev && stat2.ino === home.ino && stat2.uid === BigInt(process.getuid()) && (stat2.mode & 0o777n) === 0o700n && realpathSync2(home.path) === home.path && (!empty || readdirSync5(home.path).length === 0);
51742
+ }
51743
+ function removeProbeHome(home) {
51744
+ try {
51745
+ const stat2 = lstatSync12(home.path, { bigint: true });
51746
+ if (stat2.isDirectory() && stat2.dev === home.dev && stat2.ino === home.ino)
51747
+ rmSync2(home.path, { recursive: true, force: true });
51748
+ } catch {}
51749
+ }
51750
+ function probe(path, args, parent, stdio) {
51751
+ const created = mkdtempSync(join19(parent, "probe-")), stat2 = lstatSync12(created, { bigint: true });
51752
+ const home = { path: created, dev: stat2.dev, ino: stat2.ino };
51753
+ try {
51754
+ if (!probeHomeIntact(home, true))
51755
+ return;
51756
+ const env3 = { CODEX_HOME: home.path };
51757
+ for (const key2 of ["PATH", "HOME"])
51758
+ if (process.env[key2] !== undefined)
51759
+ env3[key2] = process.env[key2];
51760
+ const result2 = spawnSync2(path, args, { ...PROBE, cwd: home.path, env: env3, stdio: ["ignore", stdio, stdio] });
51761
+ return probeHomeIntact(home, false) ? result2 : undefined;
51762
+ } finally {
51763
+ removeProbeHome(home);
51764
+ }
51765
+ }
51766
+ function probeAdmissionCommand(path, parent) {
51767
+ const help = probe(path, ["help", "corpus-admission-inspect"], parent, "pipe");
51768
+ if (!help || help.error || help.signal !== null)
51769
+ return "inconclusive";
51770
+ if (help.status === 0)
51771
+ return "present";
51772
+ if (help.status !== 2 || help.stdout !== "" || typeof help.stderr !== "string" || !UNRECOGNIZED.test(help.stderr))
51773
+ return "inconclusive";
51774
+ const control = probe(path, ["help", "exec"], parent, "ignore");
51775
+ return control && !control.error && control.signal === null && control.status === 0 ? "absent" : "inconclusive";
51776
+ }
51777
+ function strictVersion(path, parent) {
51778
+ const result2 = probe(path, ["--version"], parent, "pipe");
51779
+ if (!result2 || result2.error || result2.signal !== null || result2.status !== 0 || typeof result2.stdout !== "string")
51780
+ return;
51781
+ const line = result2.stdout.replace(/\r?\n$/, "");
51782
+ return VERSION.test(line) ? line : undefined;
51783
+ }
51784
+ function rootLockKey(root, id) {
51785
+ return `codex-corpus-${createHash16("sha256").update(`${root}\x00${id.device}\x00${id.inode}`).digest("hex")}`;
51786
+ }
51787
+ function acquireFallback(inputs, options) {
51788
+ let reason2 = "executable-unverified";
51789
+ const refs = new Map, held = [];
51790
+ const close = () => {
51791
+ for (const ref of [...refs.values()].reverse())
51792
+ release(ref);
51793
+ };
51794
+ try {
51795
+ const native = executable(options);
51796
+ reason2 = "skills-lock-unavailable";
51797
+ const roots = inputs.map((item) => item.root);
51798
+ const locks = new Map(roots.map((root) => [root, skillsState(root, LOCK_DIRECTORY, roots)]));
51799
+ const parent = probeParent(roots);
51800
+ reason2 = "probe-inconclusive";
51801
+ const state = probeAdmissionCommand(native.path, parent);
51802
+ if (state === "present")
51803
+ reason2 = "command-present";
51804
+ if (state !== "absent")
51805
+ fail2();
51806
+ const version = strictVersion(native.path, parent);
51807
+ if (version === undefined)
51808
+ fail2();
51809
+ reason2 = "executable-unverified";
51810
+ native.assertCurrent();
51811
+ reason2 = "skills-lock-unavailable";
51812
+ for (const { input, root } of inputs) {
51813
+ const id = identity4(root), key2 = rootLockKey(root, id);
51814
+ if (!refs.has(key2)) {
51815
+ const owner2 = enclosing.getStore()?.get(key2);
51816
+ if (owner2 && !owner2.released)
51817
+ refs.set(key2, retain(owner2.hold));
51818
+ else {
51819
+ const lock = new KernelLock(locks.get(root).ensure(), key2, { mode: "exclusive" });
51820
+ refs.set(key2, retain({ lock, refs: 0 }));
51821
+ if (!lock.trySync(1000)) {
51822
+ reason2 = "writer-busy";
51823
+ fail2();
51824
+ }
51825
+ }
51826
+ }
51827
+ held.push({ input, root, id, ref: refs.get(key2) });
51828
+ }
51829
+ const assertCurrent = () => {
51830
+ try {
51831
+ for (const item of held) {
51832
+ if (item.ref.released)
51833
+ fail2();
51834
+ item.ref.hold.lock.assertUnchanged();
51835
+ if (realpathSync2(item.input) !== item.root || !sameIdentity(identity4(item.root), item.id) || !nativeLockAbsent(item.root))
51836
+ fail2();
51837
+ }
51838
+ native.assertCurrent();
51839
+ } catch {
51840
+ fail2("lease-changed");
51841
+ }
51842
+ };
51843
+ reason2 = "lease-changed";
51844
+ assertCurrent();
51845
+ const lease = { assertCurrent, close, admission: { nativeAdmission: "unavailable", probe: {
51846
+ kind: "help-unrecognized-subcommand",
51847
+ executable: native.path,
51848
+ sha256: native.sha256,
51849
+ size: native.size,
51850
+ version,
51851
+ probeExitCode: 2,
51852
+ controlExitCode: 0
51853
+ } } };
51854
+ leaseHolds.set(lease, refs);
51855
+ return lease;
51856
+ } catch {
51857
+ close();
51858
+ return fail2(reason2);
51859
+ }
51860
+ }
51861
+ function acquireCodexCorpusWrite(roots, options, policy = {}) {
51597
51862
  const held = [];
51598
51863
  const close = () => {
51599
51864
  for (const item of held.reverse())
@@ -51606,10 +51871,20 @@ function acquireCodexCorpusWrite(roots, options) {
51606
51871
  fail2();
51607
51872
  }
51608
51873
  };
51874
+ let fallback = false, refusal;
51609
51875
  try {
51610
51876
  if (roots.some((root) => typeof root !== "string" || !isAbsolute13(root) || root.includes("\x00")))
51611
51877
  fail2();
51612
51878
  const inputs = [...new Set(roots)].map((input) => ({ input, root: realpathSync2(input) })).sort((a, b) => a.root.localeCompare(b.root));
51879
+ const absent = inputs.filter(({ root }) => nativeLockAbsent(root));
51880
+ if (absent.length && absent.length !== inputs.length) {
51881
+ refusal = "native-lock-present";
51882
+ fail2();
51883
+ }
51884
+ if (absent.length && policy.fallback !== false) {
51885
+ fallback = true;
51886
+ return acquireFallback(inputs, options);
51887
+ }
51613
51888
  for (const { input, root } of inputs) {
51614
51889
  const lock = new KernelLock(root, KEY, { mode: "shared", existingOnly: true });
51615
51890
  held.push({ input, root, lock });
@@ -51637,42 +51912,67 @@ function acquireCodexCorpusWrite(roots, options) {
51637
51912
  if (Object.keys(row).sort().join(",") !== "lock,root,schema,state" || row.schema !== "codex-corpus-admission-status/v1" || row.state !== "committed-v1" && row.state !== "committed-v2" || !sameIdentity(row.root, rootIdentity) || !sameIdentity(row.lock, lockIdentity))
51638
51913
  fail2();
51639
51914
  }
51640
- return { assertCurrent, close };
51641
- } catch {
51915
+ return { assertCurrent, close, admission: { nativeAdmission: "verified" } };
51916
+ } catch (error) {
51917
+ if (fallback)
51918
+ throw error;
51642
51919
  close();
51643
- return fail2();
51920
+ return fail2(refusal);
51644
51921
  }
51645
51922
  }
51646
- function withCodexCorpusWrite(roots, run, options = {}) {
51923
+ function scoped(lease, run) {
51924
+ const holds = leaseHolds.get(lease);
51925
+ return holds?.size ? enclosing.run(new Map([...enclosing.getStore() ?? [], ...holds]), run) : run();
51926
+ }
51927
+ function withCodexCorpusWrite(roots, run, options = {}, policy = {}) {
51647
51928
  if (!roots.length)
51648
51929
  return run(() => {});
51649
- const lease = acquireCodexCorpusWrite(roots, options);
51930
+ const lease = acquireCodexCorpusWrite(roots, options, policy);
51650
51931
  try {
51651
51932
  lease.assertCurrent();
51652
- const result2 = run(lease.assertCurrent);
51933
+ const result2 = scoped(lease, () => run(lease.assertCurrent, lease.admission));
51653
51934
  lease.assertCurrent();
51654
51935
  return result2;
51655
51936
  } finally {
51656
51937
  lease.close();
51657
51938
  }
51658
51939
  }
51659
- async function withCodexCorpusWriteAsync(roots, run, options = {}) {
51940
+ async function withCodexCorpusWriteAsync(roots, run, options = {}, policy = {}) {
51660
51941
  if (!roots.length)
51661
51942
  return run(() => {});
51662
- const lease = acquireCodexCorpusWrite(roots, options);
51943
+ const lease = acquireCodexCorpusWrite(roots, options, policy);
51663
51944
  try {
51664
51945
  lease.assertCurrent();
51665
- const result2 = await run(lease.assertCurrent);
51946
+ const result2 = await scoped(lease, () => run(lease.assertCurrent, lease.admission));
51666
51947
  lease.assertCurrent();
51667
51948
  return result2;
51668
51949
  } finally {
51669
51950
  lease.close();
51670
51951
  }
51671
51952
  }
51672
- var KEY = ".native-corpus-admission", fail2 = () => {
51673
- throw new Error("CODEX_CORPUS_ADMISSION_REQUIRED: verified native admission and its existing shared lock are required");
51953
+ var KEY = ".native-corpus-admission", fail2 = (reason2) => {
51954
+ throw new Error(`CODEX_CORPUS_ADMISSION_REQUIRED: verified native admission and its existing shared lock are required${reason2 ? ` (${reason2})` : ""}`);
51955
+ }, PROBE, UNRECOGNIZED, VERSION, LOCK_DIRECTORY = "codex-corpus-locks", PROBE_PARENT = "codex-probe-homes", retain = (hold) => {
51956
+ hold.refs++;
51957
+ return { hold, released: false };
51958
+ }, release = (ref) => {
51959
+ if (ref.released)
51960
+ return;
51961
+ ref.released = true;
51962
+ if (--ref.hold.refs === 0)
51963
+ ref.hold.lock.close();
51964
+ }, enclosing, leaseHolds, contains = (base2, path) => {
51965
+ const distance = relative3(base2, path);
51966
+ return distance === "" || !distance.startsWith(`..${sep6}`) && distance !== ".." && !isAbsolute13(distance);
51674
51967
  };
51675
- var init_codex_corpus_write = () => {};
51968
+ var init_codex_corpus_write = __esm(() => {
51969
+ init_config();
51970
+ PROBE = { timeout: 5000, maxBuffer: 4096, killSignal: "SIGKILL", encoding: "utf8" };
51971
+ UNRECOGNIZED = /^error: unrecognized subcommand 'corpus-admission-inspect'(?:\r?\n|$)/;
51972
+ VERSION = /^codex-cli (?:0|[1-9][0-9]{0,5})\.(?:0|[1-9][0-9]{0,5})\.(?:0|[1-9][0-9]{0,5})(?:-[0-9A-Za-z-]{1,32}(?:\.[0-9A-Za-z-]{1,32}){0,7})?$/;
51973
+ enclosing = new AsyncLocalStorage;
51974
+ leaseHolds = new WeakMap;
51975
+ });
51676
51976
 
51677
51977
  // src/lib/codex-hook-rpc.ts
51678
51978
  import { join as join20 } from "path";
@@ -51785,6 +52085,7 @@ async function connectCodexHookRpc(options) {
51785
52085
  const rpc = {
51786
52086
  version,
51787
52087
  processId: child2.pid,
52088
+ admission: corpusLease.admission,
51788
52089
  request(method2, params) {
51789
52090
  if (stopped)
51790
52091
  return Promise.reject(new Error(configInvalid ? CODEX_CONFIG_INVALID : "CODEX_HOOK_TRUST_NATIVE_RPC_CLOSED"));
@@ -51992,7 +52293,7 @@ var init_codex_native_skill_catalog = __esm(() => {
51992
52293
  // src/lib/codex-plugin-skill-controls.ts
51993
52294
  import { createHash as createHash17 } from "crypto";
51994
52295
  import { basename as basename8, dirname as dirname14, join as join21, relative as relative4, resolve as resolve15, sep as sep7 } from "path";
51995
- import { lstatSync as lstatSync13, readdirSync as readdirSync5, readFileSync as readFileSync11, readlinkSync as readlinkSync3, realpathSync as realpathSync5 } from "fs";
52296
+ import { lstatSync as lstatSync13, readdirSync as readdirSync6, readFileSync as readFileSync11, readlinkSync as readlinkSync3, realpathSync as realpathSync5 } from "fs";
51996
52297
  function refuse2() {
51997
52298
  throw new Error("CODEX_NATIVE_SKILL_IDENTITY_UNSUPPORTED: review native plugin names and hook controls");
51998
52299
  }
@@ -52245,7 +52546,7 @@ function reviewedRetiredCodexRoot(cache3, root, controls, rules, read2, allowAbs
52245
52546
  if (!enrolled.some((control) => control.namespace === parsed.namespace && control.manifestSha256 === parsed.manifestSha256 && !parsed.appSha256 && !parsed.mcpSha256))
52246
52547
  return false;
52247
52548
  let entries = 0;
52248
- const emptySkills = (directory, depth) => depth <= 64 && readdirSync5(directory).every((name) => {
52549
+ const emptySkills = (directory, depth) => depth <= 64 && readdirSync6(directory).every((name) => {
52249
52550
  if (++entries > 4096 || name === "SKILL.md")
52250
52551
  return false;
52251
52552
  const path = join21(directory, name), stat2 = lstatSync13(path);
@@ -52270,7 +52571,7 @@ function reviewedCodexPluginCapabilitiesUnchanged(cache3, controls, read2, rules
52270
52571
  if (control.remotePluginId !== undefined && !remoteInstallationMatches(parent, control.remotePluginId, read2))
52271
52572
  return false;
52272
52573
  }
52273
- const names = readdirSync5(parent);
52574
+ const names = readdirSync6(parent);
52274
52575
  entries += names.length;
52275
52576
  if (entries > 4096)
52276
52577
  return false;
@@ -52465,7 +52766,7 @@ var init_codex_plugin_skill_controls = __esm(() => {
52465
52766
  });
52466
52767
 
52467
52768
  // src/lib/codex-vendor-refresh.ts
52468
- import { lstatSync as lstatSync14, readdirSync as readdirSync6, readFileSync as readFileSync12 } from "fs";
52769
+ import { lstatSync as lstatSync14, readdirSync as readdirSync7, readFileSync as readFileSync12 } from "fs";
52469
52770
  import { isAbsolute as isAbsolute16, join as join22, relative as relative5, resolve as resolve16, sep as sep8 } from "path";
52470
52771
  import { isDeepStrictEqual as isDeepStrictEqual6 } from "util";
52471
52772
  function codexVendorMarketplace(cache3, path) {
@@ -52482,7 +52783,7 @@ function codexVendorMarketplace(cache3, path) {
52482
52783
  function pluginTreeVisible(path, hidden, insideSkill, depth, budget2) {
52483
52784
  if (depth > MAX_SUBTREE_DEPTH)
52484
52785
  return false;
52485
- const names = readdirSync6(path);
52786
+ const names = readdirSync7(path);
52486
52787
  const skill = names.some(isSkillDocument);
52487
52788
  if (skill && (hidden || insideSkill))
52488
52789
  return false;
@@ -52506,7 +52807,7 @@ function codexVendorPluginRootRefreshSafe(root, budget2 = { remaining: MAX_SUBTR
52506
52807
  return false;
52507
52808
  if (!directory(join22(root, ".codex-plugin")))
52508
52809
  return false;
52509
- const controls = readdirSync6(join22(root, ".codex-plugin"));
52810
+ const controls = readdirSync7(join22(root, ".codex-plugin"));
52510
52811
  if (controls.length !== 1 || controls[0] !== "plugin.json")
52511
52812
  return false;
52512
52813
  const manifest = join22(root, ".codex-plugin", "plugin.json"), stat2 = lstatSync14(manifest, { throwIfNoEntry: false });
@@ -52529,7 +52830,7 @@ function codexVendorPluginRootRefreshSafe(root, budget2 = { remaining: MAX_SUBTR
52529
52830
  }
52530
52831
  function vendorMembers(path, budget2) {
52531
52832
  const directories = [];
52532
- for (const name of readdirSync6(path)) {
52833
+ for (const name of readdirSync7(path)) {
52533
52834
  if (--budget2.remaining < 0)
52534
52835
  return null;
52535
52836
  const stat2 = lstatSync14(join22(path, name));
@@ -52674,15 +52975,17 @@ function codexVendorConfigCandidates(text2, cache3, options = {}) {
52674
52975
  var CODEX_VENDOR_MARKETPLACES, CODEX_REMOTE_VENDOR_MARKETPLACES, identifier3 = (value) => typeof value === "string" && /^[A-Za-z0-9_-]{1,64}$/.test(value), record4 = (value) => Boolean(value && typeof value === "object" && !Array.isArray(value)), directory = (path) => {
52675
52976
  const stat2 = lstatSync14(path, { throwIfNoEntry: false });
52676
52977
  return Boolean(stat2?.isDirectory() && !stat2.isSymbolicLink());
52677
- }, OTHER_PLUGIN_CONTROLS, VENDOR_MANIFEST_KEYS, DEFAULT_SKILLS_PATHS, VENDOR_APP_DECLARATION = "./.app.json", MAX_SUBTREE_ENTRIES = 20000, MAX_SUBTREE_DEPTH = 32, hiddenName = (name) => name.startsWith(".") || name === "node_modules", isSkillDocument = (name) => name.toLowerCase() === "skill.md", present = (path) => lstatSync14(path, { throwIfNoEntry: false }) !== undefined, holdsOtherControl = (path) => readdirSync6(path).some((name) => OTHER_PLUGIN_CONTROLS.includes(name.toLowerCase())), MAX_TRAILING_VENDOR_ROWS = 16, MAX_VENDOR_TABLES = 8, MAX_CONFIG_CANDIDATES = 128, HEADER;
52978
+ }, OTHER_PLUGIN_CONTROLS, VENDOR_MANIFEST_KEYS, DEFAULT_SKILLS_PATHS, VENDOR_APP_DECLARATION = "./.app.json", MAX_SUBTREE_ENTRIES = 20000, MAX_SUBTREE_DEPTH = 32, hiddenName = (name) => name.startsWith(".") || name === "node_modules", isSkillDocument, present = (path) => lstatSync14(path, { throwIfNoEntry: false }) !== undefined, holdsOtherControl = (path) => readdirSync7(path).some((name) => OTHER_PLUGIN_CONTROLS.includes(codexPluginRootCapabilityEntry(name) ?? "")), MAX_TRAILING_VENDOR_ROWS = 16, MAX_VENDOR_TABLES = 8, MAX_CONFIG_CANDIDATES = 128, HEADER;
52678
52979
  var init_codex_vendor_refresh = __esm(() => {
52679
52980
  init_claude_settings_witness();
52680
52981
  init_codex_plugin_skill_controls();
52982
+ init_codex_plugin_capability_paths();
52681
52983
  CODEX_VENDOR_MARKETPLACES = Object.freeze(["openai-bundled", "openai-curated", "openai-curated-remote"]);
52682
52984
  CODEX_REMOTE_VENDOR_MARKETPLACES = Object.freeze(["openai-curated-remote"]);
52683
- OTHER_PLUGIN_CONTROLS = Object.freeze(["plugin.json", ".claude-plugin", ".cursor-plugin", "hooks", "hooks.json", ".mcp.json", "commands", "agents"]);
52985
+ OTHER_PLUGIN_CONTROLS = Object.freeze(CODEX_PLUGIN_ROOT_CAPABILITY_ENTRIES.filter((entry) => entry !== ".codex-plugin" && entry !== ".app.json"));
52684
52986
  VENDOR_MANIFEST_KEYS = Object.freeze(["name", "version", "description", "author", "homepage", "repository", "license", "keywords", "interface", "skills", "apps"]);
52685
52987
  DEFAULT_SKILLS_PATHS = Object.freeze(["./skills", "./skills/"]);
52988
+ isSkillDocument = isCodexSkillDocumentName;
52686
52989
  HEADER = /^[ \t]*(\[\[|\[)[ \t]*([^[\]\r\n]+?)[ \t]*(\]\]|\])[ \t]*(?:#[^\r\n]*)?\r?\n?$/;
52687
52990
  });
52688
52991
 
@@ -52862,7 +53165,7 @@ var init_claude_plugin_manifest_witness = __esm(() => {
52862
53165
 
52863
53166
  // node_modules/@hasna/contracts/dist/client/transport.js
52864
53167
  import { isIP as isIP2 } from "net";
52865
- import { spawnSync as spawnSync2 } from "child_process";
53168
+ import { spawnSync as spawnSync3 } from "child_process";
52866
53169
  import { closeSync as closeSync22, fstatSync as fstatSync22, openSync as openSync22, readFileSync as readFileSync22 } from "fs";
52867
53170
  import { O_NOFOLLOW as O_NOFOLLOW2, O_NONBLOCK as O_NONBLOCK2, O_RDONLY as O_RDONLY2 } from "constants";
52868
53171
  import { hostname as osHostname } from "os";
@@ -53220,7 +53523,7 @@ function isAmbientEnvironment(env3) {
53220
53523
  return env3 === process.env || env3[AMBIENT_ENVIRONMENT] === true;
53221
53524
  }
53222
53525
  function defaultKeychainRunner(argv) {
53223
- const result2 = spawnSync2(KEYCHAIN_SECURITY_BIN, [...argv], {
53526
+ const result2 = spawnSync3(KEYCHAIN_SECURITY_BIN, [...argv], {
53224
53527
  encoding: "utf8",
53225
53528
  stdio: ["ignore", "pipe", "pipe"],
53226
53529
  timeout: KEYCHAIN_SPAWN_TIMEOUT_MS
@@ -53788,6 +54091,10 @@ function skillsFileHasCredential(file) {
53788
54091
  return false;
53789
54092
  return /^\s*(?:export\s+)?(?:HASNA_SKILLS_API_KEY|SKILLS_API_KEY|HASNA_SKILLS_API_KEY_REF)\s*=\s*\S/m.test(text2);
53790
54093
  }
54094
+ function skillsFileHasVaultReference(file) {
54095
+ const text2 = readMetadataText(file);
54096
+ return text2 !== null && /^\s*(?:export\s+)?HASNA_SKILLS_API_KEY_REF\s*=\s*\S/m.test(text2);
54097
+ }
53791
54098
  var SKILLS_BOUND_API_URL = "HASNA_SKILLS_BOUND_API_URL";
53792
54099
  var init_instance_credentials = __esm(() => {
53793
54100
  init_transport();
@@ -53822,6 +54129,25 @@ var init_local_opt_in = __esm(() => {
53822
54129
  // src/lib/product-default.ts
53823
54130
  var SKILLS_PRODUCT_DEFAULT_ORIGIN = "https://skills.md";
53824
54131
 
54132
+ // src/lib/credential-profile-command.ts
54133
+ function skillsShellArgument(value) {
54134
+ return /^[A-Za-z0-9._:/-]+$/.test(value) ? value : `'${value.replace(/'/g, "'\\''")}'`;
54135
+ }
54136
+ function skillsApiUrlEnvironment(origin) {
54137
+ return urlKeys.map((name) => `${name}=${skillsShellArgument(origin)}`).join(" ");
54138
+ }
54139
+ function skillsProfileCommand(command, env3 = process.env, origin) {
54140
+ const profile = selectedSkillsProfile(env3);
54141
+ const prefix = origin && urlKeys.some((name) => env3[name]?.trim()) ? `${skillsApiUrlEnvironment(origin)} ` : "";
54142
+ return `${prefix}skills${profile ? ` --profile ${profile}` : ""} ${command}`;
54143
+ }
54144
+ var urlKeys;
54145
+ var init_credential_profile_command = __esm(() => {
54146
+ init_instance_credentials();
54147
+ init_transport();
54148
+ urlKeys = clientTransportEnvKeys("skills").apiUrlKeys;
54149
+ });
54150
+
53825
54151
  // src/lib/fleet-credentials.ts
53826
54152
  var exports_fleet_credentials = {};
53827
54153
  __export(exports_fleet_credentials, {
@@ -53846,6 +54172,8 @@ __export(exports_fleet_credentials, {
53846
54172
  gatewaySignInRefusal: () => gatewaySignInRefusal,
53847
54173
  credentialPairing: () => credentialPairing,
53848
54174
  configuredSkillsApiUrl: () => configuredSkillsApiUrl,
54175
+ captureSkillsSignInTarget: () => captureSkillsSignInTarget,
54176
+ assertSkillsSignInCredentialReplaceable: () => assertSkillsSignInCredentialReplaceable,
53849
54177
  SkillsFleetCredentialError: () => SkillsFleetCredentialError,
53850
54178
  SKILLS_LOCAL_OPT_IN_ENV_KEYS: () => SKILLS_LOCAL_OPT_IN_ENV_KEYS,
53851
54179
  SKILLS_CREDENTIAL_TIERS: () => SKILLS_CREDENTIAL_TIERS,
@@ -54151,8 +54479,24 @@ function gatewaySignInRefusal(target) {
54151
54479
  if (normalizeSkillsApiOrigin(target.origin) !== normalizeSkillsApiOrigin(defaultFleetGatewayBaseUrl(SKILLS_APP)))
54152
54480
  return null;
54153
54481
  const cause = target.credentialSource ? `${target.credentialSource} holds a Skills credential for the internal gateway` : target.source === "--url" ? "--url names the internal gateway" : `${target.source} selects the internal gateway`;
54154
- const unset2 = target.credentialSource ?? (target.source === "--url" ? null : target.source);
54155
- return new SkillsFleetCredentialError(`${cause}, which has no sign-in service. Nothing was sent.` + (unset2 ? ` To sign in to the default server instead, first unset ${unset2} (or remove it from where it is stored), then run: skills login.` : ""), "GATEWAY_AUTH_UNAVAILABLE", unset2 ? [`unset ${unset2}`, "skills login"] : undefined);
54482
+ const command = (SKILLS_API_URL_ENV_KEYS.includes(target.source) ? `${skillsApiUrlEnvironment(SKILLS_PRODUCT_DEFAULT_ORIGIN)} ` : "") + "skills --profile <new-profile> login";
54483
+ return new SkillsFleetCredentialError(`${cause}, which has no sign-in service. Nothing was sent. ` + `Keep the fleet configuration and use a separate profile for product sign-in: ${command}.`, "GATEWAY_AUTH_UNAVAILABLE", [command]);
54484
+ }
54485
+ function assertSkillsSignInCredentialReplaceable(env3 = process.env, profile) {
54486
+ const files = skillsProfileCredentialFiles(env3, profile);
54487
+ const verifyUnchanged = captureSkillsCredentialFiles(files);
54488
+ const gateway = normalizeSkillsApiOrigin(defaultFleetGatewayBaseUrl(SKILLS_APP));
54489
+ const command = (SKILLS_API_URL_ENV_KEYS.some((name) => env3[name]?.trim()) ? `${skillsApiUrlEnvironment(SKILLS_PRODUCT_DEFAULT_ORIGIN)} ` : "") + "skills --profile <new-profile> login";
54490
+ for (const file of files) {
54491
+ if (!skillsFileHasCredential(file))
54492
+ continue;
54493
+ const metadata = readSkillsInstanceMetadata(file);
54494
+ const instance = metadata.binding ?? metadata.apiUrl;
54495
+ if (skillsFileHasVaultReference(file) || !instance || normalizeSkillsApiOrigin(instance) === gateway) {
54496
+ throw new SkillsFleetCredentialError("The selected profile contains a protected fleet credential or vault reference. Nothing was sent or changed. " + `Use a separate profile for product sign-in: ${command}.`, "STORED_CREDENTIAL_PROTECTED", [command]);
54497
+ }
54498
+ }
54499
+ verifyUnchanged();
54156
54500
  }
54157
54501
  function explicitSignInOrigin(url) {
54158
54502
  if (!url.trim() || /[\x00-\x1f\x7f]/.test(url)) {
@@ -54180,13 +54524,15 @@ function resolveSkillsSignInOrigin(env3 = process.env, options = {}, explicitUrl
54180
54524
  const snapshot = snapshotSkillsEnvironment(env3);
54181
54525
  const resolvedOptions = snapshotSkillsOptions(env3, options);
54182
54526
  const profile = resolvedOptions.credentials?.profile;
54527
+ assertSkillsSignInCredentialReplaceable(snapshot, profile);
54183
54528
  const configured = configuredSkillsApiUrl(snapshot, resolvedOptions.credentials?.keychain, profile);
54184
54529
  const declared = configured && configured.source !== "default" ? configured : null;
54185
54530
  if (explicitUrl !== undefined) {
54186
54531
  const origin = explicitSignInOrigin(explicitUrl);
54187
54532
  const storedHere = declared ? skillsProfileCredentialFiles(snapshot, profile).includes(declared.source) : false;
54188
54533
  if (declared && !storedHere && normalizeSkillsApiOrigin(declared.value) !== origin) {
54189
- throw new SkillsFleetCredentialError(`--url ${origin} conflicts with ${declared.source}, which outranks the saved configuration and would ` + `shadow the key this sign-in stores. Unset ${declared.source} or pass the same URL.`, "INVALID_API_URL");
54534
+ const command = `${skillsApiUrlEnvironment(origin)} skills --profile <new-profile> login`;
54535
+ throw new SkillsFleetCredentialError(`--url ${origin} conflicts with ${declared.source}, which outranks the saved configuration and would ` + `shadow the key this sign-in stores. Keep the existing configuration and use a separate process and profile: ${command}.`, "INVALID_API_URL", [command]);
54190
54536
  }
54191
54537
  return { origin, source: "--url" };
54192
54538
  }
@@ -54218,6 +54564,14 @@ function resolveSkillsSignInOrigin(env3 = process.env, options = {}, explicitUrl
54218
54564
  throw error;
54219
54565
  }
54220
54566
  }
54567
+ function captureSkillsSignInTarget(env3 = process.env, options = {}, explicitUrl) {
54568
+ const snapshot = snapshotSkillsEnvironment(env3);
54569
+ const profile = options.credentials?.profile ?? selectedCliSkillsCredentialProfile();
54570
+ const unchanged2 = captureSkillsCredentialFiles(skillsProfileCredentialFiles(snapshot, profile));
54571
+ const target = resolveSkillsSignInOrigin(env3, options, explicitUrl);
54572
+ unchanged2();
54573
+ return { ...target, unchanged: unchanged2 };
54574
+ }
54221
54575
  function requireSkillsFleet(action = "This command", env3 = process.env, options = {}) {
54222
54576
  const fleet = resolveSkillsFleet(env3, options);
54223
54577
  if (fleet.mode === "hosted")
@@ -54229,6 +54583,7 @@ var init_fleet_credentials = __esm(() => {
54229
54583
  init_transport();
54230
54584
  init_instance_credentials();
54231
54585
  init_local_opt_in();
54586
+ init_credential_profile_command();
54232
54587
  init_local_opt_in();
54233
54588
  ENV_KEYS = clientTransportEnvKeys(SKILLS_APP);
54234
54589
  SKILLS_API_URL_ENV_KEYS = ENV_KEYS.apiUrlKeys;
@@ -54559,7 +54914,7 @@ function capturePreparationProcess(child2, platform2 = process.platform, signalG
54559
54914
  }
54560
54915
 
54561
54916
  // src/lib/dependency-preparation.ts
54562
- import { constants as constants11, closeSync as closeSync10, fstatSync as fstatSync10, lstatSync as lstatSync18, mkdirSync as mkdirSync5, openSync as openSync10, readFileSync as readFileSync14, readdirSync as readdirSync7, rmdirSync as rmdirSync2, unlinkSync as unlinkSync3, ftruncateSync, writeSync as writeSync2 } from "fs";
54917
+ import { constants as constants11, closeSync as closeSync10, fstatSync as fstatSync10, lstatSync as lstatSync18, mkdirSync as mkdirSync6, openSync as openSync10, readFileSync as readFileSync14, readdirSync as readdirSync8, rmdirSync as rmdirSync2, unlinkSync as unlinkSync3, ftruncateSync, writeSync as writeSync2 } from "fs";
54563
54918
  import { join as join26 } from "path";
54564
54919
  function hasDependencyPreparationMarker(skillPath) {
54565
54920
  try {
@@ -54574,7 +54929,7 @@ function claimPreparation(skillPath) {
54574
54929
  const state = join26(marker, "state.json"), active = join26(marker, "active");
54575
54930
  let created = false;
54576
54931
  try {
54577
- mkdirSync5(marker, { mode: 448 });
54932
+ mkdirSync6(marker, { mode: 448 });
54578
54933
  created = true;
54579
54934
  } catch (error) {
54580
54935
  if (error.code !== "EEXIST")
@@ -54585,7 +54940,7 @@ function claimPreparation(skillPath) {
54585
54940
  if (!lstatSync18(marker).isDirectory() || lstatSync18(marker).isSymbolicLink())
54586
54941
  return;
54587
54942
  if (!created) {
54588
- if (readdirSync7(marker).some((name) => name !== "state.json"))
54943
+ if (readdirSync8(marker).some((name) => name !== "state.json"))
54589
54944
  return;
54590
54945
  if (!lstatSync18(state).isFile() || lstatSync18(state).isSymbolicLink() || lstatSync18(state).size > 1024)
54591
54946
  return;
@@ -54593,7 +54948,7 @@ function claimPreparation(skillPath) {
54593
54948
  if (previous.version !== 1 || previous.status !== "failed" || Object.keys(previous).length !== 2)
54594
54949
  return;
54595
54950
  }
54596
- mkdirSync5(active, { mode: 448 });
54951
+ mkdirSync6(active, { mode: 448 });
54597
54952
  fd = openSync10(state, constants11.O_RDWR | constants11.O_NOFOLLOW | (created ? constants11.O_CREAT | constants11.O_EXCL : 0), 384);
54598
54953
  if (!fstatSync10(fd).isFile()) {
54599
54954
  closeSync10(fd);
@@ -54724,7 +55079,7 @@ var init_dependency_preparation = () => {};
54724
55079
 
54725
55080
  // src/lib/codex-native-skill-policy.ts
54726
55081
  import { createHash as createHash20, randomUUID as randomUUID6 } from "crypto";
54727
- import { closeSync as closeSync11, constants as constants12, fstatSync as fstatSync11, fsyncSync as fsyncSync3, lstatSync as lstatSync19, mkdirSync as mkdirSync6, openSync as openSync11, readFileSync as readFileSync15, readSync as readSync8, readlinkSync as readlinkSync4, realpathSync as realpathSync7, renameSync as renameSync3, unlinkSync as unlinkSync4, writeFileSync as writeFileSync4 } from "fs";
55082
+ import { closeSync as closeSync11, constants as constants12, fstatSync as fstatSync11, fsyncSync as fsyncSync3, lstatSync as lstatSync19, mkdirSync as mkdirSync7, openSync as openSync11, readFileSync as readFileSync15, readSync as readSync8, readlinkSync as readlinkSync4, realpathSync as realpathSync7, renameSync as renameSync3, unlinkSync as unlinkSync4, writeFileSync as writeFileSync4 } from "fs";
54728
55083
  import { dirname as dirname17, isAbsolute as isAbsolute19, join as join27, resolve as resolve18 } from "path";
54729
55084
  import { isDeepStrictEqual as isDeepStrictEqual7 } from "util";
54730
55085
  function codexNativeHookEnvelopeFromInput(input, event, inputBytes, inheritedFd) {
@@ -54984,7 +55339,7 @@ function writeExecutableCache(dataDir3, entries) {
54984
55339
  return;
54985
55340
  const existing = lstatSync19(directory2, { throwIfNoEntry: false });
54986
55341
  if (!existing)
54987
- mkdirSync6(directory2, { mode: 448 });
55342
+ mkdirSync7(directory2, { mode: 448 });
54988
55343
  else if (existing.isSymbolicLink() || !existing.isDirectory())
54989
55344
  return;
54990
55345
  const holder = lstatSync19(directory2, { throwIfNoEntry: false, bigint: true });
@@ -55279,7 +55634,7 @@ function recordCodexNativePolicyAcceptance(dataDir3, verification, accepted) {
55279
55634
  ...verification.attestation ? { attestation: { schema: verification.attestation.schema, peerProcessId: verification.attestation.peerProcessId } } : {}
55280
55635
  };
55281
55636
  try {
55282
- mkdirSync6(directory2, { recursive: true, mode: 448 });
55637
+ mkdirSync7(directory2, { recursive: true, mode: 448 });
55283
55638
  const stat2 = lstatSync19(directory2);
55284
55639
  if (stat2.isSymbolicLink() || !stat2.isDirectory())
55285
55640
  throw new Error(`the receipt directory is not a real directory: ${directory2}`);
@@ -55321,7 +55676,7 @@ var init_codex_native_skill_policy = __esm(() => {
55321
55676
 
55322
55677
  // src/lib/codex-semantic-cache-witness.ts
55323
55678
  import { createHash as createHash21 } from "crypto";
55324
- import { constants as constants13, closeSync as closeSync12, fstatSync as fstatSync12, lstatSync as lstatSync20, openSync as openSync12, readSync as readSync9, readdirSync as readdirSync8, realpathSync as realpathSync8 } from "fs";
55679
+ import { constants as constants13, closeSync as closeSync12, fstatSync as fstatSync12, lstatSync as lstatSync20, openSync as openSync12, readSync as readSync9, readdirSync as readdirSync9, realpathSync as realpathSync8 } from "fs";
55325
55680
  import { basename as basename11, dirname as dirname18, isAbsolute as isAbsolute20, join as join28, relative as relative7, resolve as resolve19, sep as sep10 } from "path";
55326
55681
  function codexLocalMarketplaceMapsPlugin(text2, marketplace, plugin) {
55327
55682
  try {
@@ -55478,7 +55833,7 @@ function assertCanonicalDirectory(path) {
55478
55833
  function walkSafeTree(path, state, depth = 0, root = path) {
55479
55834
  if (depth > 64 || ++state.entries > 16384)
55480
55835
  refuse4();
55481
- const names = readdirSync8(path).sort();
55836
+ const names = readdirSync9(path).sort();
55482
55837
  const files = [];
55483
55838
  for (const name of names) {
55484
55839
  if (!name || name === "." || name === ".." || name.includes(sep10) || ++state.entries > 16384)
@@ -55624,7 +55979,7 @@ function appOnlyParentProjection(cacheRoot, parents2, read2) {
55624
55979
  } catch {
55625
55980
  refuse4();
55626
55981
  }
55627
- const versions = readdirSync8(parent.pluginParent).filter((name) => name !== ".codex-remote-plugin-install.json");
55982
+ const versions = readdirSync9(parent.pluginParent).filter((name) => name !== ".codex-remote-plugin-install.json");
55628
55983
  if (!versions.length || versions.length > 4096)
55629
55984
  refuse4();
55630
55985
  const materializations = versions.map((version) => {
@@ -55750,7 +56105,7 @@ function reviewedHookParentProjection(cacheRoot, parents2, read2) {
55750
56105
  if (createHash21("sha256").update(marketplaceText).digest("hex") !== parent.marketplaceSha256 || !codexLocalMarketplaceMapsPlugin(marketplaceText, parts[0], parent.namespace))
55751
56106
  refuse4();
55752
56107
  }
55753
- const materializations = readdirSync8(parent.pluginParent).filter((name) => name !== ".codex-remote-plugin-install.json").map((version) => {
56108
+ const materializations = readdirSync9(parent.pluginParent).filter((name) => name !== ".codex-remote-plugin-install.json").map((version) => {
55754
56109
  if (!/^[A-Za-z0-9][A-Za-z0-9._+-]{0,127}$/.test(version))
55755
56110
  refuse4();
55756
56111
  const root = join28(parent.pluginParent, version), stat2 = lstatSync20(root, { throwIfNoEntry: false });
@@ -55784,14 +56139,14 @@ function assertParents(cacheRoot, controls, appOnlyParents, hookParents, files,
55784
56139
  refuse4();
55785
56140
  actual.add(join28(cacheRoot, parts[0], parts[1]));
55786
56141
  }
55787
- const actualMarkets = readdirSync8(cacheRoot);
56142
+ const actualMarkets = readdirSync9(cacheRoot);
55788
56143
  if (actualMarkets.length !== expectedMarkets.size || actualMarkets.some((market) => !expectedMarkets.has(market)))
55789
56144
  refuse4();
55790
56145
  for (const market of actualMarkets) {
55791
56146
  const marketPath = join28(cacheRoot, market), marketStat = lstatSync20(marketPath);
55792
56147
  if (!identifier5(market) || !marketStat.isDirectory() || marketStat.isSymbolicLink())
55793
56148
  refuse4();
55794
- for (const plugin of readdirSync8(marketPath)) {
56149
+ for (const plugin of readdirSync9(marketPath)) {
55795
56150
  const parent = join28(marketPath, plugin), stat2 = lstatSync20(parent);
55796
56151
  if (!identifier5(plugin) || !stat2.isDirectory() || stat2.isSymbolicLink())
55797
56152
  refuse4();
@@ -55806,14 +56161,23 @@ function assertParents(cacheRoot, controls, appOnlyParents, hookParents, files,
55806
56161
  continue;
55807
56162
  const parent = join28(cacheRoot, parts[0], parts[1]);
55808
56163
  const root = join28(parent, parts[2]);
55809
- const base2 = parts[parts.length - 1];
55810
- if (parts.includes(".codex-plugin") && (parts.length < 4 || parts[3] !== ".codex-plugin" || (parts.length === 4 ? base2 !== ".codex-plugin" : parts.length !== 5 || base2 !== "plugin.json")))
56164
+ const base2 = parts[parts.length - 1], folded = foldCodexPluginEntryName(base2);
56165
+ if (parts.length === 3 && (codexPluginRootCapabilityEntry(base2) !== null || isCodexSkillDocumentName(base2)))
55811
56166
  refuse4();
55812
- if ([".app.json", ".mcp.json"].includes(base2) && (parts.length !== 4 || dirname18(member) !== root))
56167
+ const rootEntry = parts.length >= 4 ? codexPluginRootCapabilityEntry(parts[3]) : null;
56168
+ if (rootEntry !== null && rootEntry !== parts[3])
55813
56169
  refuse4();
55814
- if ([".app.json", ".mcp.json"].includes(base2) && hookParents.some((reviewed) => reviewed.pluginParent === parent))
56170
+ if (rootEntry !== null && !SEMANTIC_BOUND_ROOT_ENTRIES.includes(rootEntry))
55815
56171
  refuse4();
55816
- if ((parts[3] === "hooks" || base2 === "hooks.json") && (![4, 5].includes(parts.length) || parts[3] !== "hooks" || (parts.length === 4 ? base2 !== "hooks" : base2 !== "hooks.json") || !hookParents.some((reviewed) => reviewed.pluginParent === join28(cacheRoot, parts[0], parts[1]))))
56172
+ if (isCodexSkillDocumentName(base2) && base2 !== "SKILL.md")
56173
+ refuse4();
56174
+ if (parts.some((part) => CODEX_PLUGIN_MANIFEST_DIRECTORIES.includes(foldCodexPluginEntryName(part))) && (parts.length < 4 || parts[3] !== ".codex-plugin" || (parts.length === 4 ? base2 !== ".codex-plugin" : parts.length !== 5 || base2 !== "plugin.json")))
56175
+ refuse4();
56176
+ if ([".app.json", ".mcp.json"].includes(folded) && (parts.length !== 4 || dirname18(member) !== root))
56177
+ refuse4();
56178
+ if ([".app.json", ".mcp.json"].includes(folded) && hookParents.some((reviewed) => reviewed.pluginParent === parent))
56179
+ refuse4();
56180
+ if ((rootEntry === "hooks" || folded === "hooks.json") && (![4, 5].includes(parts.length) || parts[3] !== "hooks" || (parts.length === 4 ? base2 !== "hooks" : base2 !== "hooks.json") || !hookParents.some((reviewed) => reviewed.pluginParent === join28(cacheRoot, parts[0], parts[1]))))
55817
56181
  refuse4();
55818
56182
  }
55819
56183
  }
@@ -55843,7 +56207,7 @@ function assertSkillMaterializations(cacheRoot, controls, files, read2) {
55843
56207
  const expectedNames = new Set(rows.map((row) => row.name));
55844
56208
  if (expectedNames.size !== rows.length)
55845
56209
  refuse4();
55846
- const entries = readdirSync8(parent);
56210
+ const entries = readdirSync9(parent);
55847
56211
  let roots = 0;
55848
56212
  for (const entry of entries) {
55849
56213
  if (entry === ".codex-remote-plugin-install.json")
@@ -56035,13 +56399,15 @@ function assertCodexSemanticCacheWitnessUnchanged(previous, current) {
56035
56399
  if (hash2(priorProjection) !== previous.sha256 || hash2(currentProjection) !== current.sha256 || canonical8(comparable(priorProjection)) !== canonical8(comparable(currentProjection)))
56036
56400
  refuse4();
56037
56401
  }
56038
- var CODEX_SEMANTIC_CACHE_WITNESS_SCHEMA = "hasna.codex-semantic-cache-witness.v1", identifier5 = (value) => typeof value === "string" && /^[A-Za-z0-9_-]{1,64}$/.test(value), digest = (value) => typeof value === "string" && /^[a-f0-9]{64}$/.test(value), refuse4 = () => {
56402
+ var CODEX_SEMANTIC_CACHE_WITNESS_SCHEMA = "hasna.codex-semantic-cache-witness.v1", SEMANTIC_BOUND_ROOT_ENTRIES, identifier5 = (value) => typeof value === "string" && /^[A-Za-z0-9_-]{1,64}$/.test(value), digest = (value) => typeof value === "string" && /^[a-f0-9]{64}$/.test(value), refuse4 = () => {
56039
56403
  throw new Error("CODEX_SEMANTIC_CACHE_WITNESS_UNSUPPORTED: review Codex plugin cache identity and controls");
56040
56404
  }, MAX_DOCUMENT_BYTES, MAX_RECEIPT_BYTES, codexHookEvents;
56041
56405
  var init_codex_semantic_cache_witness = __esm(() => {
56042
56406
  init_claude_settings_witness();
56043
56407
  init_codex_plugin_skill_controls();
56044
56408
  init_codex_native_skill_catalog();
56409
+ init_codex_plugin_capability_paths();
56410
+ SEMANTIC_BOUND_ROOT_ENTRIES = Object.freeze([".codex-plugin", ".app.json", ".mcp.json", "hooks"]);
56045
56411
  MAX_DOCUMENT_BYTES = 1024 * 1024;
56046
56412
  MAX_RECEIPT_BYTES = 16 * 1024;
56047
56413
  codexHookEvents = new Set([
@@ -56198,7 +56564,7 @@ var init_managed_policy = __esm(() => {
56198
56564
 
56199
56565
  // src/lib/agent-bridge.ts
56200
56566
  import { createHash as createHash22 } from "crypto";
56201
- import { lstatSync as lstatSync23, readFileSync as readFileSync17, readdirSync as readdirSync9 } from "fs";
56567
+ import { lstatSync as lstatSync23, readFileSync as readFileSync17, readdirSync as readdirSync10 } from "fs";
56202
56568
  import { join as join31 } from "path";
56203
56569
  function isOwnedCliBridge(path, expectedPaths) {
56204
56570
  if (!expectedPaths.includes(path))
@@ -56206,7 +56572,7 @@ function isOwnedCliBridge(path, expectedPaths) {
56206
56572
  try {
56207
56573
  if (!lstatSync23(path).isDirectory())
56208
56574
  return false;
56209
- if (JSON.stringify(readdirSync9(path).sort()) !== JSON.stringify(Object.keys(CLI_BRIDGE_FILES).sort()))
56575
+ if (JSON.stringify(readdirSync10(path).sort()) !== JSON.stringify(Object.keys(CLI_BRIDGE_FILES).sort()))
56210
56576
  return false;
56211
56577
  return Object.entries(CLI_BRIDGE_FILES).every(([name, content]) => {
56212
56578
  const file = join31(path, name), stat2 = lstatSync23(file);
@@ -56641,7 +57007,7 @@ var init_hook_diagnostics = __esm(() => {
56641
57007
  });
56642
57008
 
56643
57009
  // src/lib/agent-sumi.ts
56644
- import { spawnSync as spawnSync3 } from "child_process";
57010
+ import { spawnSync as spawnSync4 } from "child_process";
56645
57011
  import { accessSync as accessSync2, constants as constants15, existsSync as existsSync12, lstatSync as lstatSync24, realpathSync as realpathSync9, statSync as statSync10 } from "fs";
56646
57012
  import { delimiter as delimiter2, isAbsolute as isAbsolute21, join as join32, resolve as resolve21 } from "path";
56647
57013
  function recordWithKeys(value, keys2) {
@@ -56715,7 +57081,7 @@ function sumiPathPlan(home, cwd2 = process.cwd(), env3 = process.env) {
56715
57081
  childEnv[key2] = env3[key2];
56716
57082
  let child2;
56717
57083
  try {
56718
- child2 = spawnSync3(executable2, ["--json", "--home", resolve21(home), "--cwd", resolve21(cwd2)], {
57084
+ child2 = spawnSync4(executable2, ["--json", "--home", resolve21(home), "--cwd", resolve21(cwd2)], {
56719
57085
  cwd: resolve21(cwd2),
56720
57086
  env: childEnv,
56721
57087
  encoding: "buffer",
@@ -57296,8 +57662,8 @@ function assertPinnedLauncherShell() {
57296
57662
  if (!stat2.isFile() || (stat2.mode & 73) === 0)
57297
57663
  throw new Error("LAUNCHER_SHELL_UNSUPPORTED");
57298
57664
  }
57299
- const probe = Bun.spawnSync(["/bin/sh", "-p", "-c", "exit 0"], { env: {}, stdin: "ignore", stdout: "ignore", stderr: "ignore" });
57300
- if (probe.exitCode !== 0)
57665
+ const probe2 = Bun.spawnSync(["/bin/sh", "-p", "-c", "exit 0"], { env: {}, stdin: "ignore", stdout: "ignore", stderr: "ignore" });
57666
+ if (probe2.exitCode !== 0)
57301
57667
  throw new Error("LAUNCHER_SHELL_UNSUPPORTED");
57302
57668
  }
57303
57669
  var PINNED_LAUNCHER_SCHEMA = "hasna-skills-pinned-launcher-v2", LAUNCH_CWD_VARIABLE3 = "HASNA_SKILLS_LAUNCH_CWD", PINNED_LAUNCHER_BUN_FLAGS2, PINNED_LAUNCHER_ENV_NAMES, PINNED_LAUNCHER_ENV_PREFIXES, ENV_NAME, ENV_PREFIX, ENV_EXACT, COMMAND_LINE, PINNED_LAUNCHER_MAX_BYTES;
@@ -57346,7 +57712,7 @@ var init_runtime_launcher = __esm(() => {
57346
57712
 
57347
57713
  // src/lib/retained-review-artifacts.ts
57348
57714
  import { createHash as createHash25 } from "crypto";
57349
- import { constants as constants18, closeSync as closeSync16, fstatSync as fstatSync16, fsyncSync as fsyncSync6, lstatSync as lstatSync27, mkdirSync as mkdirSync7, openSync as openSync16, readSync as readSync12, writeSync as writeSync4 } from "fs";
57715
+ import { constants as constants18, closeSync as closeSync16, fstatSync as fstatSync16, fsyncSync as fsyncSync6, lstatSync as lstatSync27, mkdirSync as mkdirSync8, openSync as openSync16, readSync as readSync12, writeSync as writeSync4 } from "fs";
57350
57716
  import { dirname as dirname21, isAbsolute as isAbsolute24, join as join33, resolve as resolve23, sep as sep12 } from "path";
57351
57717
  function keys2(value, names) {
57352
57718
  return Boolean(value && typeof value === "object" && !Array.isArray(value) && Object.keys(value).length === names.length && names.every((name) => Object.hasOwn(value, name)));
@@ -57467,7 +57833,7 @@ function writeReviewArtifactExclusive(change) {
57467
57833
  for (let parent = dirname21(change.path);!lstatSync27(parent, { throwIfNoEntry: false }); parent = dirname21(parent))
57468
57834
  missing2.push(parent);
57469
57835
  for (const parent of missing2.reverse())
57470
- mkdirSync7(parent, { mode: 448 });
57836
+ mkdirSync8(parent, { mode: 448 });
57471
57837
  safe4(change.path);
57472
57838
  privateStore(change.artifact.storeRoot);
57473
57839
  for (let parent = dirname21(change.path);parent !== change.artifact.storeRoot; parent = dirname21(parent)) {
@@ -57510,7 +57876,7 @@ var init_retained_review_artifacts = __esm(() => {
57510
57876
  // src/lib/agent-integration.ts
57511
57877
  import { createHash as createHash26, randomUUID as randomUUID7 } from "crypto";
57512
57878
  import { isDeepStrictEqual as isDeepStrictEqual9 } from "util";
57513
- import { existsSync as existsSync13, lstatSync as lstatSync28, statSync as statSync11, mkdirSync as mkdirSync8, readFileSync as readFileSync19, readdirSync as readdirSync10, opendirSync as opendirSync4, readlinkSync as readlinkSync7, realpathSync as realpathSync11, renameSync as renameSync4, rmdirSync as rmdirSync3, writeFileSync as writeFileSync6, unlinkSync as unlinkSync5, chmodSync, openSync as openSync17, closeSync as closeSync17, fsyncSync as fsyncSync7, fstatSync as fstatSync17, readSync as readSync13, constants as constants19, linkSync as linkSync3 } from "fs";
57879
+ import { existsSync as existsSync13, lstatSync as lstatSync28, statSync as statSync11, mkdirSync as mkdirSync9, readFileSync as readFileSync19, readdirSync as readdirSync11, opendirSync as opendirSync4, readlinkSync as readlinkSync7, realpathSync as realpathSync11, renameSync as renameSync4, rmdirSync as rmdirSync3, writeFileSync as writeFileSync6, unlinkSync as unlinkSync5, chmodSync, openSync as openSync17, closeSync as closeSync17, fsyncSync as fsyncSync7, fstatSync as fstatSync17, readSync as readSync13, constants as constants19, linkSync as linkSync3 } from "fs";
57514
57880
  import { basename as basename12, dirname as dirname22, join as join34, resolve as resolve24, relative as relative8, isAbsolute as isAbsolute25, sep as sep13 } from "path";
57515
57881
  import { homedir as homedir3 } from "os";
57516
57882
  function nativeAgentRoot(home, agent, cwd2 = process.cwd()) {
@@ -57731,7 +58097,7 @@ function treeHash(root) {
57731
58097
  const rel = relative8(root, path);
57732
58098
  if (stat2.isDirectory()) {
57733
58099
  hash3.update(`d\x00${rel}\x00`);
57734
- for (const name of readdirSync10(path).sort())
58100
+ for (const name of readdirSync11(path).sort())
57735
58101
  visit2(join34(path, name));
57736
58102
  return;
57737
58103
  }
@@ -58592,7 +58958,7 @@ function verifyCoordinatedDiscovery(binding, home, aliases, executable2) {
58592
58958
  }
58593
58959
  function atomicWrite2(path, content) {
58594
58960
  assertSafePath(path);
58595
- mkdirSync8(dirname22(path), { recursive: true, mode: 448 });
58961
+ mkdirSync9(dirname22(path), { recursive: true, mode: 448 });
58596
58962
  const temporary = `${path}.skills-${randomUUID7()}`;
58597
58963
  try {
58598
58964
  writeFileSync6(temporary, content, { mode: 384, flag: "wx" });
@@ -58760,7 +59126,7 @@ function planCodexSemanticCacheWitnessUpgrade(options) {
58760
59126
  throw new Error("Local marketplace hook parent is not enabled in the unchanged Codex settings");
58761
59127
  identity6 = { role: "reviewed-hook", pluginId: pluginId2, namespace: parts[1], pluginParent: parent, installation: "local-marketplace", marketplaceSourcePath: source.path, marketplaceSha256: source.sha256 };
58762
59128
  }
58763
- const versions = readdirSync10(parent).filter((name) => name !== ".codex-remote-plugin-install.json");
59129
+ const versions = readdirSync11(parent).filter((name) => name !== ".codex-remote-plugin-install.json");
58764
59130
  if (!versions.length || versions.length > 4096)
58765
59131
  throw new Error("Reviewed native-hook parent has no bounded materializations");
58766
59132
  for (const version of versions) {
@@ -58854,9 +59220,10 @@ function applyAgentIntegration(plan, options = {}) {
58854
59220
  const alias = plan.rootAliases?.find((item) => item.agent === "codex" && (change.path === item.target || change.path.startsWith(item.target + "/")));
58855
59221
  return lexical ? [lexical] : alias ? [alias.alias] : [];
58856
59222
  });
58857
- return withCodexCorpusWrite(roots, (assertCurrent) => applyAgentIntegrationUnlocked(plan, options, assertCurrent), options);
59223
+ return withCodexCorpusWrite(roots, (assertCurrent, admission) => applyAgentIntegrationUnlocked(plan, options, assertCurrent, admission), options);
58858
59224
  }
58859
- function applyAgentIntegrationUnlocked(plan, options = {}, assertCurrent) {
59225
+ function applyAgentIntegrationUnlocked(plan, options = {}, assertCurrent, admission) {
59226
+ const fallback = codexAdmissionReceipt(admission);
58860
59227
  for (const source of plan.reviewArtifactSources ?? [])
58861
59228
  verifyReviewArtifactOriginal(source.path, source.sha256);
58862
59229
  for (const source of plan.observedNativeSources ?? [])
@@ -58920,10 +59287,10 @@ function applyAgentIntegrationUnlocked(plan, options = {}, assertCurrent) {
58920
59287
  recheckRootAliases(aliases);
58921
59288
  for (const agent of plan.retainedReviewChecks?.agents ?? [])
58922
59289
  assertManagedAgentBridge(agent, { ...plan.retainedReviewChecks, dataDir: plan.dataDir });
58923
- return { changed: [], backups, ...aliases.length ? { rootAliases: aliases } : {} };
59290
+ return { changed: [], backups, ...aliases.length ? { rootAliases: aliases } : {}, ...fallback };
58924
59291
  }
58925
59292
  assertSafePath(backupRoot);
58926
- mkdirSync8(backupRoot, { recursive: true, mode: 448 });
59293
+ mkdirSync9(backupRoot, { recursive: true, mode: 448 });
58927
59294
  chmodSync(backupRoot, 448);
58928
59295
  for (const [index, change] of plan.changes.entries())
58929
59296
  if (change.before !== null) {
@@ -58971,7 +59338,7 @@ function applyAgentIntegrationUnlocked(plan, options = {}, assertCurrent) {
58971
59338
  assertManagedAgentBridge(agent, { home: plan.managedAgentChecks.home, dataDir: plan.dataDir, projectDir: plan.managedAgentChecks.projectDir ?? plan.managedAgentChecks.home });
58972
59339
  for (const agent of plan.retainedReviewChecks?.agents ?? [])
58973
59340
  assertManagedAgentBridge(agent, { ...plan.retainedReviewChecks, dataDir: plan.dataDir });
58974
- atomicWrite2(join34(backupRoot, "receipt.json"), JSON.stringify({ version: 1, changes: written.map((change) => ({ path: change.path, beforeHash: change.before === null ? null : sha4(change.before), afterHash: sha4(change.after) })), backups, ...plan.cacheWitnessUpgrade ? { cacheWitnessUpgrade: plan.cacheWitnessUpgrade } : {}, ...plan.retainedReviewArtifacts?.length ? { retainedReviewArtifacts: plan.retainedReviewArtifacts.map((item) => ({ path: item.path, ...item.artifact })) } : {}, ...aliases.length ? { rootAliases: aliases } : {} }) + `
59341
+ atomicWrite2(join34(backupRoot, "receipt.json"), JSON.stringify({ version: 1, changes: written.map((change) => ({ path: change.path, beforeHash: change.before === null ? null : sha4(change.before), afterHash: sha4(change.after) })), backups, ...plan.cacheWitnessUpgrade ? { cacheWitnessUpgrade: plan.cacheWitnessUpgrade } : {}, ...plan.retainedReviewArtifacts?.length ? { retainedReviewArtifacts: plan.retainedReviewArtifacts.map((item) => ({ path: item.path, ...item.artifact })) } : {}, ...aliases.length ? { rootAliases: aliases } : {}, ...fallback }) + `
58975
59342
  `);
58976
59343
  } catch (error) {
58977
59344
  assertCurrent();
@@ -58999,7 +59366,7 @@ function applyAgentIntegrationUnlocked(plan, options = {}, assertCurrent) {
58999
59366
  }
59000
59367
  throw error;
59001
59368
  }
59002
- return { changed: plan.changes.map((change) => change.path), backups, ...aliases.length ? { rootAliases: aliases } : {} };
59369
+ return { changed: plan.changes.map((change) => change.path), backups, ...aliases.length ? { rootAliases: aliases } : {}, ...fallback };
59003
59370
  }
59004
59371
  function syncArchiveDirectory(path) {
59005
59372
  assertSafePath(path);
@@ -59039,9 +59406,10 @@ function archiveNativeSkills(inventory, options) {
59039
59406
  throw new Error("CODEX_CORPUS_ROOT_UNVERIFIED");
59040
59407
  return [...new Set([root, owner2].filter((value) => value !== undefined))];
59041
59408
  });
59042
- return withCodexCorpusWrite(roots, (assertCurrent) => archiveNativeSkillsUnlocked(inventory, options, assertCurrent), options);
59409
+ return withCodexCorpusWrite(roots, (assertCurrent, admission) => archiveNativeSkillsUnlocked(inventory, options, assertCurrent, admission), options);
59043
59410
  }
59044
- function archiveNativeSkillsUnlocked(inventory, options, assertCurrent) {
59411
+ function archiveNativeSkillsUnlocked(inventory, options, assertCurrent, admission) {
59412
+ const fallback = codexAdmissionReceipt(admission);
59045
59413
  const aliases = [...new Map(inventory.filter((entry) => entry.rootAlias).map((entry) => [entry.rootAlias.alias, entry.rootAlias])).values()];
59046
59414
  if (aliases.length && !options.allowRootAliases)
59047
59415
  throw new Error("Native migration requires explicit allowRootAliases for agent root aliases");
@@ -59059,7 +59427,7 @@ function archiveNativeSkillsUnlocked(inventory, options, assertCurrent) {
59059
59427
  throw new Error(`Native skill changed after planning: ${entry.path}`);
59060
59428
  const targetManifest = options.targetManifest ? { schema: options.targetManifest.schema, digest: options.targetManifest.digest, targetCount: options.targetManifest.targets.length } : undefined;
59061
59429
  if (!selected.length)
59062
- return { entries: [], ...targetManifest ? { targetManifest } : {}, ...aliases.length ? { rootAliases: aliases } : {} };
59430
+ return { entries: [], ...targetManifest ? { targetManifest } : {}, ...aliases.length ? { rootAliases: aliases } : {}, ...fallback };
59063
59431
  const operationId = randomUUID7(), archiveRoot = join34(options.dataDir ?? getDataDir(), "migration", operationId, "native"), receiptPath = join34(archiveRoot, "receipt.json");
59064
59432
  const entries = selected.map((entry, index) => ({
59065
59433
  source: entry.vendor ? join34(entry.path, "SKILL.md") : entry.path,
@@ -59068,7 +59436,7 @@ function archiveNativeSkillsUnlocked(inventory, options, assertCurrent) {
59068
59436
  ...entry.vendor ? { discoveryOnly: true } : {},
59069
59437
  status: "planned"
59070
59438
  }));
59071
- const journal = { version: 2, operationId, status: "planned", entries, ...targetManifest ? { targetManifest } : {}, ...aliases.length ? { rootAliases: aliases } : {} };
59439
+ const journal = { version: 2, operationId, status: "planned", entries, ...targetManifest ? { targetManifest } : {}, ...aliases.length ? { rootAliases: aliases } : {}, ...fallback };
59072
59440
  const moved = [];
59073
59441
  const verifyArchive = (entry) => {
59074
59442
  assertSafePath(entry.archive);
@@ -59082,7 +59450,7 @@ function archiveNativeSkillsUnlocked(inventory, options, assertCurrent) {
59082
59450
  const created = [];
59083
59451
  for (let path = archiveRoot;!existsSync13(path); path = dirname22(path))
59084
59452
  created.push(path);
59085
- mkdirSync8(archiveRoot, { recursive: true, mode: 448 });
59453
+ mkdirSync9(archiveRoot, { recursive: true, mode: 448 });
59086
59454
  try {
59087
59455
  for (const directory2 of created)
59088
59456
  syncArchiveDirectory(directory2);
@@ -59165,7 +59533,7 @@ function archiveNativeSkillsUnlocked(inventory, options, assertCurrent) {
59165
59533
  } catch {}
59166
59534
  throw new Error(`Native archive failed; inspect the recovery journal at ${receiptPath} before retrying.`, { cause: error });
59167
59535
  }
59168
- return { entries: entries.map(({ status, conflict, ...entry }) => entry), receiptPath, ...targetManifest ? { targetManifest } : {}, ...aliases.length ? { rootAliases: aliases } : {} };
59536
+ return { entries: entries.map(({ status, conflict, ...entry }) => entry), receiptPath, ...targetManifest ? { targetManifest } : {}, ...aliases.length ? { rootAliases: aliases } : {}, ...fallback };
59169
59537
  }
59170
59538
  function classifiedCodexPluginCacheCopy(entry, cache3, read2, admit) {
59171
59539
  try {
@@ -59574,7 +59942,7 @@ var init_agent_integration = __esm(() => {
59574
59942
  });
59575
59943
 
59576
59944
  // src/lib/home-migration.ts
59577
- import { existsSync as existsSync14, mkdirSync as mkdirSync9, readdirSync as readdirSync11, renameSync as renameSync5, rmSync as rmSync2, statSync as statSync12, writeFileSync as writeFileSync7 } from "fs";
59945
+ import { existsSync as existsSync14, mkdirSync as mkdirSync10, readdirSync as readdirSync12, renameSync as renameSync5, rmSync as rmSync3, statSync as statSync12, writeFileSync as writeFileSync7 } from "fs";
59578
59946
  import { join as join35 } from "path";
59579
59947
  function layoutMigrationRecordPath(appDir) {
59580
59948
  return join35(appDir, SKILLS_CACHE_DIRNAME, LAYOUT_MIGRATION_RECORD);
@@ -59600,7 +59968,7 @@ function listLegacyFlatSkillDirs(appDir) {
59600
59968
  return legacy;
59601
59969
  let entries = [];
59602
59970
  try {
59603
- entries = readdirSync11(appDir);
59971
+ entries = readdirSync12(appDir);
59604
59972
  } catch {
59605
59973
  return legacy;
59606
59974
  }
@@ -59619,7 +59987,7 @@ function createLazyDirs(appDir, created) {
59619
59987
  for (const name of [LOGS_DIRNAME, OUTPUTS_DIRNAME]) {
59620
59988
  const dir = join35(appDir, name);
59621
59989
  if (!existsSync14(dir)) {
59622
- mkdirSync9(dir, { recursive: true });
59990
+ mkdirSync10(dir, { recursive: true });
59623
59991
  created.push(dir);
59624
59992
  }
59625
59993
  }
@@ -59636,7 +60004,7 @@ function migrateOwnerLayout(options = {}) {
59636
60004
  if (existsSync14(cache3)) {
59637
60005
  let entries = [];
59638
60006
  try {
59639
- entries = readdirSync11(cache3);
60007
+ entries = readdirSync12(cache3);
59640
60008
  } catch {}
59641
60009
  if (entries.length > 0) {
59642
60010
  return {
@@ -59663,7 +60031,7 @@ function migrateOwnerLayout(options = {}) {
59663
60031
  if (!existsSync14(dir))
59664
60032
  continue;
59665
60033
  try {
59666
- for (const entry of readdirSync11(dir))
60034
+ for (const entry of readdirSync12(dir))
59667
60035
  collisionNames.add(entry);
59668
60036
  } catch {}
59669
60037
  }
@@ -59678,13 +60046,13 @@ function migrateOwnerLayout(options = {}) {
59678
60046
  }
59679
60047
  }
59680
60048
  if (existsSync14(cache3)) {
59681
- rmSync2(cache3, { recursive: true, force: true });
60049
+ rmSync3(cache3, { recursive: true, force: true });
59682
60050
  }
59683
60051
  if (installedPresent) {
59684
60052
  renameSync5(installed, cache3);
59685
60053
  moved.push(INSTALLED_SKILLS_DIRNAME);
59686
60054
  } else {
59687
- mkdirSync9(cache3, { recursive: true });
60055
+ mkdirSync10(cache3, { recursive: true });
59688
60056
  }
59689
60057
  for (const name of legacy) {
59690
60058
  renameSync5(join35(appDir, name), join35(cache3, name));
@@ -59713,12 +60081,12 @@ import {
59713
60081
  cpSync as cpSync2,
59714
60082
  existsSync as existsSync15,
59715
60083
  lstatSync as lstatSync29,
59716
- mkdirSync as mkdirSync10,
59717
- mkdtempSync,
60084
+ mkdirSync as mkdirSync11,
60085
+ mkdtempSync as mkdtempSync2,
59718
60086
  readFileSync as readFileSync20,
59719
- readdirSync as readdirSync12,
60087
+ readdirSync as readdirSync13,
59720
60088
  renameSync as renameSync6,
59721
- rmSync as rmSync3,
60089
+ rmSync as rmSync4,
59722
60090
  statSync as statSync13,
59723
60091
  writeFileSync as writeFileSync8
59724
60092
  } from "fs";
@@ -59823,7 +60191,7 @@ function packageSourceRoots(source) {
59823
60191
  function containsSkillDirectories(path) {
59824
60192
  let entries;
59825
60193
  try {
59826
- entries = readdirSync12(path);
60194
+ entries = readdirSync13(path);
59827
60195
  } catch {
59828
60196
  return false;
59829
60197
  }
@@ -59918,12 +60286,16 @@ function writeManagedAgentSkill(params) {
59918
60286
  agent: params.agent,
59919
60287
  path: result2.path,
59920
60288
  action: result2.action,
59921
- ...result2.reason ? { reason: result2.reason } : {}
60289
+ ...result2.reason ? { reason: result2.reason } : {},
60290
+ ...result2.nativeAdmission ? { nativeAdmission: result2.nativeAdmission, nativeAdmissionProbe: result2.nativeAdmissionProbe } : {}
59922
60291
  };
59923
60292
  }
59924
60293
  function writeManagedSkillDir(dir, skillMd, options) {
59925
60294
  const root = options.dryRun ? undefined : codexCorpusRootForPath(dir);
59926
- return withCodexCorpusWrite(root ? [root] : [], (assertCurrent) => writeManagedSkillDirUnlocked(dir, skillMd, options, assertCurrent), options);
60295
+ return withCodexCorpusWrite(root ? [root] : [], (assertCurrent, admission) => {
60296
+ const result2 = writeManagedSkillDirUnlocked(dir, skillMd, options, assertCurrent);
60297
+ return { ...result2, ...codexAdmissionReceipt(admission) };
60298
+ }, options);
59927
60299
  }
59928
60300
  function writeManagedSkillDirUnlocked(dir, skillMd, options, assertCurrent) {
59929
60301
  const skillMdPath = join36(dir, "SKILL.md");
@@ -59964,8 +60336,8 @@ function writeManagedSkillDirUnlocked(dir, skillMd, options, assertCurrent) {
59964
60336
  if (options.dryRun)
59965
60337
  return { action, path: skillMdPath };
59966
60338
  const parentDir = dirname23(dir);
59967
- mkdirSync10(parentDir, { recursive: true });
59968
- const transactionDir = mkdtempSync(join36(parentDir, `.hasna-skills-write-${basename13(dir)}-`));
60339
+ mkdirSync11(parentDir, { recursive: true });
60340
+ const transactionDir = mkdtempSync2(join36(parentDir, `.hasna-skills-write-${basename13(dir)}-`));
59969
60341
  const candidateDir = join36(transactionDir, "candidate");
59970
60342
  const backupDir = join36(transactionDir, "backup");
59971
60343
  const candidateSkillMdPath = join36(candidateDir, "SKILL.md");
@@ -59983,7 +60355,7 @@ function writeManagedSkillDirUnlocked(dir, skillMd, options, assertCurrent) {
59983
60355
  if (options.resourceDir) {
59984
60356
  cpSync2(options.resourceDir, candidateDir, { recursive: true, force: true });
59985
60357
  } else {
59986
- mkdirSync10(candidateDir, { recursive: true });
60358
+ mkdirSync11(candidateDir, { recursive: true });
59987
60359
  }
59988
60360
  writeFileSync8(candidateSkillMdPath, skillMd.endsWith(`
59989
60361
  `) ? skillMd : `${skillMd}
@@ -60007,7 +60379,7 @@ function writeManagedSkillDirUnlocked(dir, skillMd, options, assertCurrent) {
60007
60379
  try {
60008
60380
  assertCurrent();
60009
60381
  if (existsSync15(dir))
60010
- rmSync3(dir, { recursive: true, force: true });
60382
+ rmSync4(dir, { recursive: true, force: true });
60011
60383
  renameDirectory(backupDir, dir);
60012
60384
  originalMoved = false;
60013
60385
  } catch (rollbackError) {
@@ -60020,7 +60392,7 @@ function writeManagedSkillDirUnlocked(dir, skillMd, options, assertCurrent) {
60020
60392
  if (!preserveTransaction) {
60021
60393
  try {
60022
60394
  assertCurrent();
60023
- rmSync3(transactionDir, { recursive: true, force: true });
60395
+ rmSync4(transactionDir, { recursive: true, force: true });
60024
60396
  } catch {}
60025
60397
  }
60026
60398
  }
@@ -60081,7 +60453,7 @@ var init_skill_aliases = __esm(() => {
60081
60453
  });
60082
60454
 
60083
60455
  // src/lib/project-state.ts
60084
- import { existsSync as existsSync16, mkdirSync as mkdirSync11, readFileSync as readFileSync21, writeFileSync as writeFileSync9 } from "fs";
60456
+ import { existsSync as existsSync16, mkdirSync as mkdirSync12, readFileSync as readFileSync21, writeFileSync as writeFileSync9 } from "fs";
60085
60457
  import { join as join37 } from "path";
60086
60458
  function getProjectStateDir(targetDir = process.cwd()) {
60087
60459
  return join37(targetDir, SKILLS_PROJECT_DIR);
@@ -60115,7 +60487,7 @@ function ensureProjectConfig(targetDir = process.cwd()) {
60115
60487
  }
60116
60488
  function saveProjectConfig(config, targetDir = process.cwd()) {
60117
60489
  const dir = getProjectStateDir(targetDir);
60118
- mkdirSync11(dir, { recursive: true });
60490
+ mkdirSync12(dir, { recursive: true });
60119
60491
  const normalized2 = normalizeProjectConfig({ ...config, updatedAt: new Date().toISOString() });
60120
60492
  writeFileSync9(getProjectConfigPath(targetDir), JSON.stringify(normalized2, null, 2) + `
60121
60493
  `);
@@ -60248,7 +60620,7 @@ __export(exports_installer, {
60248
60620
  AGENT_TARGETS: () => AGENT_TARGETS,
60249
60621
  AGENT_LABELS: () => AGENT_LABELS
60250
60622
  });
60251
- import { existsSync as existsSync17, readFileSync as readFileSync23, rmSync as rmSync4 } from "fs";
60623
+ import { existsSync as existsSync17, readFileSync as readFileSync23, rmSync as rmSync5 } from "fs";
60252
60624
  import { join as join38 } from "path";
60253
60625
  import { homedir as homedir5 } from "os";
60254
60626
  function getSkillPath(name) {
@@ -60458,15 +60830,20 @@ function installSkillForAgent(name, options, generateSkillMd) {
60458
60830
  codexCommand: options.codexCommand,
60459
60831
  codexSha256: options.codexSha256
60460
60832
  });
60833
+ const fallback = result2.nativeAdmission ? { nativeAdmission: result2.nativeAdmission, nativeAdmissionProbe: result2.nativeAdmissionProbe } : {};
60461
60834
  if (result2.action === "skip") {
60462
- return { skill: canonicalName, success: false, error: result2.reason ?? "skipped", path: result2.path };
60835
+ return { skill: canonicalName, success: false, error: result2.reason ?? "skipped", path: result2.path, ...fallback };
60463
60836
  }
60464
- return { skill: canonicalName, success: true, path: result2.path };
60837
+ return { skill: canonicalName, success: true, path: result2.path, ...fallback };
60465
60838
  }
60466
60839
  function removeSkillForAgent(name, options) {
60840
+ const record5 = codexAdmissionRecord(options);
60467
60841
  const dir = getAgentSkillPath(name, options.agent, options.scope ?? "global", options.projectDir);
60468
60842
  const root = codexCorpusRootForPath(dir);
60469
- return withCodexCorpusWrite(root ? [root] : [], () => removeSkillForAgentUnlocked(name, options), options);
60843
+ return withCodexCorpusWrite(root ? [root] : [], (_assertCurrent, admission) => {
60844
+ record5.deliver(admission);
60845
+ return removeSkillForAgentUnlocked(name, options);
60846
+ }, options, record5.policy);
60470
60847
  }
60471
60848
  function removeSkillForAgentUnlocked(name, options) {
60472
60849
  const canonicalName = getCanonicalSkillName(name);
@@ -60474,7 +60851,7 @@ function removeSkillForAgentUnlocked(name, options) {
60474
60851
  const dir = getAgentSkillPath(canonicalName, options.agent, scope, options.projectDir);
60475
60852
  if (!hasSkillsOwnershipMarker(dir))
60476
60853
  return false;
60477
- rmSync4(dir, { recursive: true, force: true });
60854
+ rmSync5(dir, { recursive: true, force: true });
60478
60855
  return true;
60479
60856
  }
60480
60857
  function resolveAgentSkillMd(name, generateSkillMd) {
@@ -62322,7 +62699,7 @@ var init_codex_hook_discovery_recovery = __esm(() => {
62322
62699
 
62323
62700
  // src/lib/agent-discovery.ts
62324
62701
  import { createHash as createHash29 } from "crypto";
62325
- import { lstatSync as lstatSync32, readFileSync as readFileSync26, readdirSync as readdirSync13, realpathSync as realpathSync12 } from "fs";
62702
+ import { lstatSync as lstatSync32, readFileSync as readFileSync26, readdirSync as readdirSync14, realpathSync as realpathSync12 } from "fs";
62326
62703
  import { basename as basename16, dirname as dirname26, isAbsolute as isAbsolute30, join as join42, relative as relative9, resolve as resolve28, sep as sep14 } from "path";
62327
62704
  import { isDeepStrictEqual as isDeepStrictEqual13 } from "util";
62328
62705
  function discoveryRootUnresolved(agent, command, detail) {
@@ -63073,13 +63450,13 @@ function assertProjectDiscovery(agent, directories, home, canonical9 = resolve28
63073
63450
  for (const name of ["plugin", "plugins"]) {
63074
63451
  const path = canonical9(join42(directory2, ".sumi", name));
63075
63452
  safe6(path);
63076
- if (lstatSync32(path, { throwIfNoEntry: false })?.isDirectory() && readdirSync13(path).length)
63453
+ if (lstatSync32(path, { throwIfNoEntry: false })?.isDirectory() && readdirSync14(path).length)
63077
63454
  throw new Error(`NATIVE_SKILL_DRIFT: project Sumi plugins require a dedicated discovery review: ${path}`);
63078
63455
  }
63079
63456
  if (agent === "claude") {
63080
63457
  const commands = canonical9(join42(directory2, ".claude/commands"));
63081
63458
  safe6(commands);
63082
- if (lstatSync32(commands, { throwIfNoEntry: false })?.isDirectory() && readdirSync13(commands).length)
63459
+ if (lstatSync32(commands, { throwIfNoEntry: false })?.isDirectory() && readdirSync14(commands).length)
63083
63460
  throw new Error("NATIVE_SKILL_DRIFT: legacy project command discovery requires a dedicated format adapter");
63084
63461
  }
63085
63462
  }
@@ -63228,7 +63605,7 @@ function resolveAgentDiscovery(options) {
63228
63605
  for (const path of plugins) {
63229
63606
  safe6(path);
63230
63607
  if (lstatSync32(path, { throwIfNoEntry: false })?.isDirectory())
63231
- for (const name of readdirSync13(path).sort()) {
63608
+ for (const name of readdirSync14(path).sort()) {
63232
63609
  if (name === "skills-cli.js" && path === plugins[1])
63233
63610
  continue;
63234
63611
  const target = join42(path, name);
@@ -63239,7 +63616,7 @@ function resolveAgentDiscovery(options) {
63239
63616
  }
63240
63617
  for (const root2 of roots) {
63241
63618
  safe6(root2);
63242
- if (lstatSync32(root2, { throwIfNoEntry: false })?.isDirectory() && readdirSync13(root2).some((name) => name.endsWith(".md")))
63619
+ if (lstatSync32(root2, { throwIfNoEntry: false })?.isDirectory() && readdirSync14(root2).some((name) => name.endsWith(".md")))
63243
63620
  unresolved("flat markdown skills require a dedicated native migration adapter");
63244
63621
  }
63245
63622
  }
@@ -63283,7 +63660,7 @@ function resolveAgentDiscovery(options) {
63283
63660
  safe6(builtinRoot);
63284
63661
  if (!lstatSync32(builtinRoot, { throwIfNoEntry: false })?.isDirectory())
63285
63662
  unresolved("installed Gemini builtin root is missing");
63286
- for (const name of readdirSync13(builtinRoot).sort()) {
63663
+ for (const name of readdirSync14(builtinRoot).sort()) {
63287
63664
  const text3 = witness(join42(builtinRoot, name, "SKILL.md"));
63288
63665
  const match = text3?.match(/^---\r?\n[\s\S]*?^name:\s*([a-z0-9][a-z0-9-]*)\s*$/m);
63289
63666
  if (!match?.[1] || builtinNames.includes(match[1]))
@@ -63381,7 +63758,7 @@ function resolveAgentDiscovery(options) {
63381
63758
  unresolved("plugin hooks require a separate no-skill-injection review");
63382
63759
  const commands = join42(root2, "commands");
63383
63760
  safe6(commands);
63384
- if (agent === "claude" && (manifest.commands !== undefined || lstatSync32(commands, { throwIfNoEntry: false })?.isDirectory() && readdirSync13(commands).length))
63761
+ if (agent === "claude" && (manifest.commands !== undefined || lstatSync32(commands, { throwIfNoEntry: false })?.isDirectory() && readdirSync14(commands).length))
63385
63762
  unresolved("legacy command discovery requires retirement or a dedicated format adapter");
63386
63763
  const rootSkill = witness(join42(root2, "SKILL.md"));
63387
63764
  if (rootSkill !== null)
@@ -63403,7 +63780,7 @@ function resolveAgentDiscovery(options) {
63403
63780
  const installed = registrations === null ? {} : parseConfig(registrations, join42(home, ".claude/plugins/installed_plugins.json")).plugins;
63404
63781
  const commands = canonical9(join42(home, ".claude/commands"));
63405
63782
  safe6(commands);
63406
- if (lstatSync32(commands, { throwIfNoEntry: false })?.isDirectory() && readdirSync13(commands).length)
63783
+ if (lstatSync32(commands, { throwIfNoEntry: false })?.isDirectory() && readdirSync14(commands).length)
63407
63784
  unresolved("legacy home command discovery requires a dedicated format adapter");
63408
63785
  for (const [id, enabled] of Object.entries(config.enabledPlugins ?? {})) {
63409
63786
  if (enabled === false)
@@ -63445,7 +63822,7 @@ function resolveAgentDiscovery(options) {
63445
63822
  }
63446
63823
  const localPlugins = join42(home, ".config/opencode/plugins");
63447
63824
  safe6(localPlugins);
63448
- if (lstatSync32(localPlugins, { throwIfNoEntry: false }) && readdirSync13(localPlugins).some((name) => name !== "skills-cli.js"))
63825
+ if (lstatSync32(localPlugins, { throwIfNoEntry: false }) && readdirSync14(localPlugins).some((name) => name !== "skills-cli.js"))
63449
63826
  unresolved("additional local plugin hooks require review");
63450
63827
  } else if (agent === "sumi") {
63451
63828
  if ((config.plugin?.length ?? 0) > 0 || (config.plugins?.length ?? 0) > 0 || sources.some((source) => source.path !== canonical9(configPath) && source.path !== canonical9(join42(sumiConfigDirectory(home), "sumi.jsonc")) && source.sha256 !== null))
@@ -63464,7 +63841,7 @@ function resolveAgentDiscovery(options) {
63464
63841
  const directory2 = join42(home, ".gemini/extensions");
63465
63842
  safe6(directory2);
63466
63843
  if (lstatSync32(directory2, { throwIfNoEntry: false }))
63467
- for (const name of readdirSync13(directory2)) {
63844
+ for (const name of readdirSync14(directory2)) {
63468
63845
  const root2 = join42(directory2, name);
63469
63846
  safe6(root2);
63470
63847
  if (!lstatSync32(root2)?.isDirectory())
@@ -63552,7 +63929,7 @@ function physicalPath(path) {
63552
63929
  }
63553
63930
  return resolve29(realpathSync13(cursor), ...suffix);
63554
63931
  }
63555
- function contains(root2, path) {
63932
+ function contains2(root2, path) {
63556
63933
  return path === root2 || path.startsWith(root2 + sep15);
63557
63934
  }
63558
63935
  function configuredRoots(home, explicitHome) {
@@ -63605,14 +63982,14 @@ function assertPortableAuthoringPath(path, options = {}) {
63605
63982
  const defaults2 = NATIVE_DISCOVERY_ROOTS.map((parts) => join43(home, ...parts));
63606
63983
  defaults2.push(join43(home, ".codex/plugins/cache"), join43(home, ".claude/plugins/cache"), join43(home, ".claude/plugins/synced"), join43(home, ".gemini/extensions"));
63607
63984
  for (const root2 of defaults2) {
63608
- if (candidates.some((candidate2) => contains(resolve29(root2), candidate2) || contains(physicalPath(root2), candidate2)))
63985
+ if (candidates.some((candidate2) => contains2(resolve29(root2), candidate2) || contains2(physicalPath(root2), candidate2)))
63609
63986
  native ??= root2;
63610
63987
  }
63611
63988
  if (native) {
63612
63989
  throw new Error(`Refusing portable Skills authoring below native discovery root '${native}': ${lexical}. Set HASNA_SKILLS_DIR to a private authoring corpus outside native roots.`);
63613
63990
  }
63614
63991
  for (const root2 of configuredRoots(home, options.homeDir !== undefined)) {
63615
- if (candidates.some((candidate2) => contains(resolve29(root2), candidate2) || contains(physicalPath(root2), candidate2))) {
63992
+ if (candidates.some((candidate2) => contains2(resolve29(root2), candidate2) || contains2(physicalPath(root2), candidate2))) {
63616
63993
  throw new Error(`Refusing portable Skills authoring below configured native discovery root: ${lexical}`);
63617
63994
  }
63618
63995
  }
@@ -63630,12 +64007,12 @@ var init_authoring_path = __esm(() => {
63630
64007
  // src/lib/portable-skills.ts
63631
64008
  import {
63632
64009
  existsSync as existsSync19,
63633
- mkdirSync as mkdirSync12,
63634
- mkdtempSync as mkdtempSync2,
63635
- readdirSync as readdirSync14,
64010
+ mkdirSync as mkdirSync13,
64011
+ mkdtempSync as mkdtempSync3,
64012
+ readdirSync as readdirSync15,
63636
64013
  realpathSync as realpathSync14,
63637
64014
  renameSync as renameSync7,
63638
- rmSync as rmSync5,
64015
+ rmSync as rmSync6,
63639
64016
  statSync as statSync14,
63640
64017
  writeFileSync as writeFileSync10
63641
64018
  } from "fs";
@@ -63680,7 +64057,7 @@ function listPortableSkills(options = {}) {
63680
64057
  if (!safeIsDirectory(root2))
63681
64058
  return [];
63682
64059
  const skills = [];
63683
- for (const entry of readdirSync14(root2).sort()) {
64060
+ for (const entry of readdirSync15(root2).sort()) {
63684
64061
  if (entry.startsWith("."))
63685
64062
  continue;
63686
64063
  const path = join44(root2, entry);
@@ -63723,7 +64100,7 @@ function scaffoldPortableSkill(name, options = {}) {
63723
64100
  if (existsSync19(skillPath)) {
63724
64101
  if (!options.overwrite)
63725
64102
  throw new Error(`Skill '${skillName}' already exists at ${skillPath}`);
63726
- rmSync5(skillPath, { recursive: true, force: true });
64103
+ rmSync6(skillPath, { recursive: true, force: true });
63727
64104
  }
63728
64105
  const kind = options.kind ?? "executable";
63729
64106
  const description = options.description ?? `${displayName(skillName)} skill`;
@@ -63750,7 +64127,7 @@ function portPortableSkillDirectory(sourceDir, options = {}) {
63750
64127
  };
63751
64128
  const imported = [];
63752
64129
  const skipped = [];
63753
- const entries = readdirSync14(absoluteSource, { withFileTypes: true }).map((entry) => entry.name).filter((entryName) => !entryName.startsWith(".")).sort();
64130
+ const entries = readdirSync15(absoluteSource, { withFileTypes: true }).map((entry) => entry.name).filter((entryName) => !entryName.startsWith(".")).sort();
63754
64131
  for (const entryName of entries) {
63755
64132
  const childPath = join44(absoluteSource, entryName);
63756
64133
  if (!safeIsDirectory(childPath))
@@ -63795,11 +64172,11 @@ function physicalImportPath(path) {
63795
64172
  function assertDisjointImportPaths(source, destination) {
63796
64173
  const sourcePath = realpathSync14(source);
63797
64174
  const destinationPath = physicalImportPath(destination);
63798
- const contains2 = (parent, child2) => {
64175
+ const contains3 = (parent, child2) => {
63799
64176
  const path = relative10(parent, child2);
63800
64177
  return path === "" || !isAbsolute31(path) && path !== ".." && !path.startsWith(`..${sep16}`);
63801
64178
  };
63802
- if (contains2(sourcePath, destinationPath) || contains2(destinationPath, sourcePath)) {
64179
+ if (contains3(sourcePath, destinationPath) || contains3(destinationPath, sourcePath)) {
63803
64180
  throw new Error("Source and destination skill directories must not overlap");
63804
64181
  }
63805
64182
  }
@@ -63826,9 +64203,9 @@ function portPortableSkill(sourcePath, options = {}) {
63826
64203
  if (existsSync19(destination)) {
63827
64204
  if (!options.overwrite)
63828
64205
  throw new Error(`Skill '${skillName}' already exists at ${destination}`);
63829
- rmSync5(destination, { recursive: true, force: true });
64206
+ rmSync6(destination, { recursive: true, force: true });
63830
64207
  }
63831
- mkdirSync12(dirname28(destination), { recursive: true });
64208
+ mkdirSync13(dirname28(destination), { recursive: true });
63832
64209
  copySkillDirectory(absoluteSource, destination);
63833
64210
  const base2 = {
63834
64211
  ...inferred,
@@ -63870,8 +64247,8 @@ function installCorpusSkillAtomically(input, options = {}) {
63870
64247
  const target = join44(root2, name);
63871
64248
  assertPortableAuthoringPath(target, options);
63872
64249
  const created = !existsSync19(target);
63873
- mkdirSync12(root2, { recursive: true });
63874
- const staging = mkdtempSync2(join44(root2, `.pull-${name}-`));
64250
+ mkdirSync13(root2, { recursive: true });
64251
+ const staging = mkdtempSync3(join44(root2, `.pull-${name}-`));
63875
64252
  let moved = false;
63876
64253
  let backup = null;
63877
64254
  try {
@@ -63879,16 +64256,16 @@ function installCorpusSkillAtomically(input, options = {}) {
63879
64256
  const manifest = buildCorpusManifest(input, name);
63880
64257
  writeSkillJsonWithHash(staging, manifest);
63881
64258
  if (existsSync19(target)) {
63882
- backup = mkdtempSync2(join44(root2, `.pull-backup-${name}-`));
64259
+ backup = mkdtempSync3(join44(root2, `.pull-backup-${name}-`));
63883
64260
  renameSync7(target, join44(backup, name));
63884
64261
  moved = true;
63885
64262
  }
63886
64263
  renameSync7(staging, target);
63887
64264
  if (moved && backup)
63888
- rmSync5(backup, { recursive: true, force: true });
64265
+ rmSync6(backup, { recursive: true, force: true });
63889
64266
  return { name, path: target, manifest, created };
63890
64267
  } catch (error) {
63891
- rmSync5(staging, { recursive: true, force: true });
64268
+ rmSync6(staging, { recursive: true, force: true });
63892
64269
  if (moved && backup && existsSync19(join44(backup, name))) {
63893
64270
  try {
63894
64271
  renameSync7(join44(backup, name), target);
@@ -64133,7 +64510,7 @@ __export(exports_registry, {
64133
64510
  CATEGORIES: () => CATEGORIES,
64134
64511
  BASIC_SKILL_NAMES: () => BASIC_SKILL_NAMES
64135
64512
  });
64136
- import { existsSync as existsSync20, readFileSync as readFileSync27, readdirSync as readdirSync15 } from "fs";
64513
+ import { existsSync as existsSync20, readFileSync as readFileSync27, readdirSync as readdirSync16 } from "fs";
64137
64514
  import { join as join45 } from "path";
64138
64515
  function isBasicSkillName(name) {
64139
64516
  return BASIC_SKILL_NAMES.includes(name);
@@ -64174,7 +64551,7 @@ function discoverSkillsInDir(dir, source = "custom") {
64174
64551
  return [];
64175
64552
  const result2 = [];
64176
64553
  try {
64177
- const entries = readdirSync15(dir, { withFileTypes: true });
64554
+ const entries = readdirSync16(dir, { withFileTypes: true });
64178
64555
  for (const entry of entries) {
64179
64556
  if (!entry.isDirectory())
64180
64557
  continue;
@@ -64210,7 +64587,7 @@ function findExtensionSkillPath(name) {
64210
64587
  if (!config.extensionsDir || !existsSync20(config.extensionsDir))
64211
64588
  return null;
64212
64589
  try {
64213
- const entries = readdirSync15(config.extensionsDir, { withFileTypes: true });
64590
+ const entries = readdirSync16(config.extensionsDir, { withFileTypes: true });
64214
64591
  for (const entry of entries) {
64215
64592
  if (!entry.isDirectory())
64216
64593
  continue;
@@ -65932,7 +66309,7 @@ var require_cli_spinners = __commonJS((exports, module) => {
65932
66309
  });
65933
66310
 
65934
66311
  // src/lib/auth-store.ts
65935
- import { chmodSync as chmodSync2, existsSync as existsSync21, mkdirSync as mkdirSync13, readFileSync as readFileSync28, renameSync as renameSync8, statSync as statSync15, unlinkSync as unlinkSync6, writeFileSync as writeFileSync11 } from "fs";
66312
+ import { chmodSync as chmodSync2, existsSync as existsSync21, mkdirSync as mkdirSync14, readFileSync as readFileSync28, renameSync as renameSync8, statSync as statSync15, unlinkSync as unlinkSync6, writeFileSync as writeFileSync11 } from "fs";
65936
66313
  import { basename as basename19, dirname as dirname29, join as join46 } from "path";
65937
66314
  function getAuthFilePath(env3 = process.env) {
65938
66315
  return skillsCredentialFilePath(env3);
@@ -65971,9 +66348,10 @@ function getAuthConfig(env3 = process.env, options = {}) {
65971
66348
  return null;
65972
66349
  return { apiKey: fleet.apiKey, ...readIdentity(env3) };
65973
66350
  }
65974
- function writeCredentialValues(values2, env3 = process.env) {
66351
+ function writeCredentialValues(values2, env3 = process.env, beforeWrite) {
66352
+ beforeWrite?.();
65975
66353
  const file = skillsCredentialFilePath(env3);
65976
- mkdirSync13(dirname29(file), { recursive: true, mode: 448 });
66354
+ mkdirSync14(dirname29(file), { recursive: true, mode: 448 });
65977
66355
  const lines = [];
65978
66356
  const written = new Set;
65979
66357
  if (existsSync21(file)) {
@@ -66000,9 +66378,16 @@ function writeCredentialValues(values2, env3 = process.env) {
66000
66378
  `) + `
66001
66379
  `;
66002
66380
  const temp = `${file}.tmp-${process.pid}`;
66003
- writeFileSync11(temp, body, { mode: 384 });
66004
- chmodSync2(temp, 384);
66005
- renameSync8(temp, file);
66381
+ writeFileSync11(temp, body, { mode: 384, flag: "wx" });
66382
+ try {
66383
+ chmodSync2(temp, 384);
66384
+ beforeWrite?.();
66385
+ renameSync8(temp, file);
66386
+ } finally {
66387
+ try {
66388
+ unlinkSync6(temp);
66389
+ } catch {}
66390
+ }
66006
66391
  return file;
66007
66392
  }
66008
66393
  function readCredentialValue(key2, env3 = process.env) {
@@ -66046,7 +66431,14 @@ function safeOrigin(url) {
66046
66431
  return null;
66047
66432
  }
66048
66433
  }
66049
- function saveAuthConfig(config, env3 = process.env, authenticatedOrigin, issuedBy) {
66434
+ function saveAuthConfig(config, env3 = process.env, authenticatedOrigin, issuedBy, assertUnchanged) {
66435
+ const unchanged3 = assertUnchanged ?? captureSkillsCredentialFiles(skillsProfileCredentialFiles(env3));
66436
+ const beforeWrite = () => {
66437
+ unchanged3();
66438
+ if (issuedBy)
66439
+ assertSkillsSignInCredentialReplaceable(env3);
66440
+ };
66441
+ beforeWrite();
66050
66442
  const apiKey = config.apiKey.trim();
66051
66443
  if (!apiKey)
66052
66444
  throw new Error("Refusing to store an empty Skills API key.");
@@ -66058,7 +66450,7 @@ function saveAuthConfig(config, env3 = process.env, authenticatedOrigin, issuedB
66058
66450
  const previous = readIdentityRecord(env3);
66059
66451
  const loginWroteBefore = previous?.urlWrittenBy === "login" && typeof previous.apiUrl === "string" && safeOrigin(previous.apiUrl) === apiUrl;
66060
66452
  const urlWrittenByLogin = issuedBy !== undefined && (!previousUrl || safeOrigin(previousUrl) !== apiUrl || loginWroteBefore);
66061
- const file = writeCredentialValues({ SKILLS_API_KEY: null, SKILLS_API_URL: null, [SKILLS_API_KEY_REF]: null, [SKILLS_API_KEY_ENV]: apiKey, [SKILLS_BOUND_API_URL]: apiUrl, [SKILLS_API_URL_ENV]: apiUrl }, env3);
66453
+ const file = writeCredentialValues({ SKILLS_API_KEY: null, SKILLS_API_URL: null, [SKILLS_API_KEY_REF]: null, [SKILLS_API_KEY_ENV]: apiKey, [SKILLS_BOUND_API_URL]: apiUrl, [SKILLS_API_URL_ENV]: apiUrl }, env3, beforeWrite);
66062
66454
  const identity6 = {};
66063
66455
  for (const field3 of ["email", "orgId", "orgSlug", "userId"]) {
66064
66456
  const value = config[field3];
@@ -87962,7 +88354,7 @@ var init_remote_auth = __esm(() => {
87962
88354
 
87963
88355
  // src/lib/sign-in.ts
87964
88356
  import { createHash as createHash32 } from "crypto";
87965
- import { chmodSync as chmodSync3, mkdirSync as mkdirSync14, readFileSync as readFileSync29, readdirSync as readdirSync16, renameSync as renameSync9, unlinkSync as unlinkSync7, writeFileSync as writeFileSync12 } from "fs";
88357
+ import { chmodSync as chmodSync3, mkdirSync as mkdirSync15, readFileSync as readFileSync29, readdirSync as readdirSync17, renameSync as renameSync9, unlinkSync as unlinkSync7, writeFileSync as writeFileSync12 } from "fs";
87966
88358
  import { basename as basename20, dirname as dirname30, join as join47 } from "path";
87967
88359
  function isRecord7(value) {
87968
88360
  return Boolean(value && typeof value === "object" && !Array.isArray(value));
@@ -88116,7 +88508,7 @@ function pendingDeviceSignInPath(origin, env3 = process.env) {
88116
88508
  }
88117
88509
  function savePendingDeviceSignIn(origin, start, env3 = process.env, now3 = Date.now()) {
88118
88510
  const path = pendingDeviceSignInPath(origin, env3);
88119
- mkdirSync14(dirname30(path), { recursive: true, mode: 448 });
88511
+ mkdirSync15(dirname30(path), { recursive: true, mode: 448 });
88120
88512
  const pending = {
88121
88513
  origin,
88122
88514
  deviceCode: start.deviceCode,
@@ -88174,7 +88566,7 @@ function pendingDeviceSignInOrigins(env3 = process.env, now3 = Date.now()) {
88174
88566
  }
88175
88567
  let entries;
88176
88568
  try {
88177
- entries = readdirSync16(location.dir);
88569
+ entries = readdirSync17(location.dir);
88178
88570
  } catch {
88179
88571
  return [];
88180
88572
  }
@@ -88205,7 +88597,7 @@ function clearPendingDeviceSignIn(env3 = process.env, origin) {
88205
88597
  }
88206
88598
  let entries;
88207
88599
  try {
88208
- entries = readdirSync16(location.dir);
88600
+ entries = readdirSync17(location.dir);
88209
88601
  } catch {
88210
88602
  return;
88211
88603
  }
@@ -88218,7 +88610,10 @@ function clearPendingDeviceSignIn(env3 = process.env, origin) {
88218
88610
  }
88219
88611
  }
88220
88612
  }
88221
- async function persistSignIn(result2, origin, env3 = process.env, issuedBy = "sign-in") {
88613
+ async function persistSignIn(result2, origin, env3 = process.env, issuedBy = "sign-in", assertUnchanged) {
88614
+ const unchanged3 = assertUnchanged ?? captureSkillsCredentialFiles(skillsProfileCredentialFiles(env3));
88615
+ unchanged3();
88616
+ assertSkillsSignInCredentialReplaceable(env3);
88222
88617
  let apiKey = typeof result2.apiKey === "string" && result2.apiKey.trim() ? result2.apiKey : undefined;
88223
88618
  if (!apiKey && typeof result2.token === "string" && result2.token) {
88224
88619
  const created = await new RemoteSkillsAuthClient(origin).request("/api/auth/keys", {
@@ -88236,7 +88631,7 @@ async function persistSignIn(result2, origin, env3 = process.env, issuedBy = "si
88236
88631
  ...boundedText(result2.organization?.id) ? { orgId: result2.organization.id } : {},
88237
88632
  ...boundedText(result2.organization?.slug) ? { orgSlug: result2.organization.slug } : {},
88238
88633
  ...boundedText(result2.user?.id) ? { userId: result2.user.id } : {}
88239
- }, env3, origin, issuedBy);
88634
+ }, env3, origin, issuedBy, unchanged3);
88240
88635
  }
88241
88636
  function manualRevocationHint(origin) {
88242
88637
  if (origin === SKILLS_PRODUCT_DEFAULT_ORIGIN) {
@@ -88884,7 +89279,7 @@ var init_skill_bundles = __esm(() => {
88884
89279
  });
88885
89280
 
88886
89281
  // src/lib/pull.ts
88887
- import { existsSync as existsSync22, mkdirSync as mkdirSync15, mkdtempSync as mkdtempSync3, readFileSync as readFileSync30, renameSync as renameSync10, rmSync as rmSync6, writeFileSync as writeFileSync13 } from "fs";
89282
+ import { existsSync as existsSync22, mkdirSync as mkdirSync16, mkdtempSync as mkdtempSync4, readFileSync as readFileSync30, renameSync as renameSync10, rmSync as rmSync7, writeFileSync as writeFileSync13 } from "fs";
88888
89283
  import { dirname as dirname31, join as join48 } from "path";
88889
89284
  async function pullSkills(options = {}) {
88890
89285
  const client2 = options.client !== undefined ? options.client : await createRemoteSkillsClient();
@@ -89041,7 +89436,7 @@ function reconcileTombstone(slug2, corpusOptions) {
89041
89436
  if (!hasSkillsOwnershipMarker(target)) {
89042
89437
  return { name: slug2, success: true, tombstoned: true, removed: false, leftInPlace: true };
89043
89438
  }
89044
- rmSync6(target, { recursive: true, force: true });
89439
+ rmSync7(target, { recursive: true, force: true });
89045
89440
  return { name: slug2, success: true, tombstoned: true, removed: true };
89046
89441
  }
89047
89442
  function readPullMarker(dir) {
@@ -89180,16 +89575,16 @@ function verifyBundleResponseBytes(buffer, response, verify = {}) {
89180
89575
  }
89181
89576
  function installBundleAtomically(name, entries, options = {}, marker = {}) {
89182
89577
  const root2 = getPortableSkillsRoot(options);
89183
- mkdirSync15(root2, { recursive: true });
89578
+ mkdirSync16(root2, { recursive: true });
89184
89579
  const target = join48(root2, name);
89185
89580
  const created = !existsSync22(target);
89186
- const staging = mkdtempSync3(join48(root2, `.pull-${name}-`));
89581
+ const staging = mkdtempSync4(join48(root2, `.pull-${name}-`));
89187
89582
  let moved = false;
89188
89583
  let backup = null;
89189
89584
  try {
89190
89585
  for (const entry of entries) {
89191
89586
  const destination = join48(staging, entry.path);
89192
- mkdirSync15(dirname31(destination), { recursive: true });
89587
+ mkdirSync16(dirname31(destination), { recursive: true });
89193
89588
  writeFileSync13(destination, entry.bytes, { mode: entry.mode });
89194
89589
  }
89195
89590
  writePullMarker(staging, {
@@ -89201,15 +89596,15 @@ function installBundleAtomically(name, entries, options = {}, marker = {}) {
89201
89596
  ...marker.revisionId ? { revisionId: marker.revisionId } : {}
89202
89597
  });
89203
89598
  if (existsSync22(target)) {
89204
- backup = mkdtempSync3(join48(root2, `.pull-backup-${name}-`));
89599
+ backup = mkdtempSync4(join48(root2, `.pull-backup-${name}-`));
89205
89600
  renameSync10(target, join48(backup, name));
89206
89601
  moved = true;
89207
89602
  }
89208
89603
  renameSync10(staging, target);
89209
89604
  if (moved && backup)
89210
- rmSync6(backup, { recursive: true, force: true });
89605
+ rmSync7(backup, { recursive: true, force: true });
89211
89606
  } catch (error61) {
89212
- rmSync6(staging, { recursive: true, force: true });
89607
+ rmSync7(staging, { recursive: true, force: true });
89213
89608
  if (moved && backup && existsSync22(join48(backup, name))) {
89214
89609
  try {
89215
89610
  renameSync10(join48(backup, name), target);
@@ -91889,7 +92284,7 @@ var init_init = __esm(() => {
91889
92284
  });
91890
92285
 
91891
92286
  // src/lib/home-adoption.ts
91892
- import { constants as constants22, closeSync as closeSync20, fstatSync as fstatSync20, lstatSync as lstatSync34, openSync as openSync20, readSync as readSync17, existsSync as existsSync25, mkdirSync as mkdirSync16, readdirSync as readdirSync17, readFileSync as readFileSync33, rmSync as rmSync7, statSync as statSync16, writeFileSync as writeFileSync15 } from "fs";
92287
+ import { constants as constants22, closeSync as closeSync20, fstatSync as fstatSync20, lstatSync as lstatSync34, openSync as openSync20, readSync as readSync17, existsSync as existsSync25, mkdirSync as mkdirSync17, readdirSync as readdirSync18, readFileSync as readFileSync33, rmSync as rmSync8, statSync as statSync16, writeFileSync as writeFileSync15 } from "fs";
91893
92288
  import { homedir as homedir8 } from "os";
91894
92289
  import { join as join52 } from "path";
91895
92290
  function indexCanonicalCorpus(corpusRoot) {
@@ -91898,7 +92293,7 @@ function indexCanonicalCorpus(corpusRoot) {
91898
92293
  return byName;
91899
92294
  let entries = [];
91900
92295
  try {
91901
- entries = readdirSync17(corpusRoot);
92296
+ entries = readdirSync18(corpusRoot);
91902
92297
  } catch {
91903
92298
  return byName;
91904
92299
  }
@@ -91948,7 +92343,7 @@ function scanUnmarkedHomes(options = {}) {
91948
92343
  continue;
91949
92344
  let entries = [];
91950
92345
  try {
91951
- entries = readdirSync17(home);
92346
+ entries = readdirSync18(home);
91952
92347
  } catch {
91953
92348
  continue;
91954
92349
  }
@@ -92008,11 +92403,11 @@ function appendConflictsLedger(appDir, conflicts) {
92008
92403
  writeFileSync15(ledgerPath, `${JSON.stringify(ledger, null, 2)}
92009
92404
  `);
92010
92405
  }
92011
- function writeRollbackRecord(mode, entries, appDir = getDataDir()) {
92406
+ function writeRollbackRecord(mode, entries, appDir = getDataDir(), admission = {}) {
92012
92407
  const dir = join52(appDir, ROLLBACK_DIRNAME);
92013
- mkdirSync16(dir, { recursive: true });
92408
+ mkdirSync17(dir, { recursive: true });
92014
92409
  const file2 = join52(dir, `${mode}-${Date.now()}.json`);
92015
- const record12 = { version: 1, mode, timestamp: new Date().toISOString(), entries };
92410
+ const record12 = { version: 1, mode, timestamp: new Date().toISOString(), entries, ...admission };
92016
92411
  writeFileSync15(file2, `${JSON.stringify(record12, null, 2)}
92017
92412
  `);
92018
92413
  return file2;
@@ -92024,8 +92419,9 @@ function adoptUnmarkedHomes(options = {}) {
92024
92419
  }
92025
92420
  const appDir = options.homeDir ? join52(options.homeDir, ".hasna", "skills") : getDataDir();
92026
92421
  const roots = scan.adoptable.map((entry) => codexCorpusRootForPath(entry.path)).filter((root2) => !!root2);
92027
- return withCodexCorpusWrite(roots, (assertCurrent) => {
92422
+ return withCodexCorpusWrite(roots, (assertCurrent, admission) => {
92028
92423
  assertCurrent();
92424
+ const fallback = codexAdmissionReceipt(admission);
92029
92425
  const canonical9 = indexCanonicalCorpus(resolveCorpusRoot(options));
92030
92426
  const markers = scan.adoptable.map((entry) => {
92031
92427
  const root2 = codexCorpusRootForPath(entry.path);
@@ -92042,7 +92438,7 @@ function adoptUnmarkedHomes(options = {}) {
92042
92438
  assertCurrent();
92043
92439
  let rollbackFile;
92044
92440
  if (markers.length > 0) {
92045
- rollbackFile = writeRollbackRecord("adopt", markers, appDir);
92441
+ rollbackFile = writeRollbackRecord("adopt", markers, appDir, fallback);
92046
92442
  }
92047
92443
  for (const entry of markers) {
92048
92444
  assertCurrent();
@@ -92055,7 +92451,7 @@ function adoptUnmarkedHomes(options = {}) {
92055
92451
  }
92056
92452
  assertCurrent();
92057
92453
  appendConflictsLedger(appDir, scan.conflicts);
92058
- return { ...scan, applied: true, rollbackFile };
92454
+ return { ...scan, applied: true, rollbackFile, ...fallback };
92059
92455
  }, options);
92060
92456
  }
92061
92457
  function pruneOwnership(dir) {
@@ -92107,7 +92503,7 @@ function pruneStrayHomes(options = {}) {
92107
92503
  continue;
92108
92504
  let entries = [];
92109
92505
  try {
92110
- entries = readdirSync17(home);
92506
+ entries = readdirSync18(home);
92111
92507
  } catch {
92112
92508
  continue;
92113
92509
  }
@@ -92140,9 +92536,10 @@ function pruneStrayHomes(options = {}) {
92140
92536
  }
92141
92537
  const appDir = options.homeDir ? join52(options.homeDir, ".hasna", "skills") : getDataDir();
92142
92538
  const roots = candidates.map((candidate2) => codexCorpusRootForPath(candidate2.path)).filter((root2) => !!root2);
92143
- return withCodexCorpusWrite(roots, (assertCurrent) => {
92539
+ return withCodexCorpusWrite(roots, (assertCurrent, admission) => {
92144
92540
  assertCurrent();
92145
- const rollbackFile = writeRollbackRecord("prune", candidates.map(({ agent, skill, path, hash: hash6, marker }) => ({ agent, skill, path, hash: hash6, marker })), appDir);
92541
+ const fallback = codexAdmissionReceipt(admission);
92542
+ const rollbackFile = writeRollbackRecord("prune", candidates.map(({ agent, skill, path, hash: hash6, marker }) => ({ agent, skill, path, hash: hash6, marker })), appDir, fallback);
92146
92543
  let pruned = 0;
92147
92544
  for (const candidate2 of candidates) {
92148
92545
  assertCurrent();
@@ -92156,13 +92553,13 @@ function pruneStrayHomes(options = {}) {
92156
92553
  const skillMd = join52(candidate2.path, "SKILL.md");
92157
92554
  if ((existsSync25(skillMd) ? hashSkillMarkdownFile(skillMd) : "") !== candidate2.hash)
92158
92555
  continue;
92159
- rmSync7(candidate2.path, { recursive: true, force: true });
92556
+ rmSync8(candidate2.path, { recursive: true, force: true });
92160
92557
  assertCurrent();
92161
92558
  if (existsSync25(candidate2.path))
92162
92559
  throw new Error("Skill prune readback failed");
92163
92560
  pruned++;
92164
92561
  }
92165
- return { candidates, pruned, dryRun: false, rollbackFile };
92562
+ return { candidates, pruned, dryRun: false, rollbackFile, ...fallback };
92166
92563
  }, options);
92167
92564
  }
92168
92565
  var CONFLICTS_LEDGER_FILE = "conflicts.json", ROLLBACK_DIRNAME = "rollback";
@@ -92176,7 +92573,7 @@ var init_home_adoption = __esm(() => {
92176
92573
  });
92177
92574
 
92178
92575
  // src/lib/home-census.ts
92179
- import { existsSync as existsSync26, readFileSync as readFileSync34, readdirSync as readdirSync18, statSync as statSync17 } from "fs";
92576
+ import { existsSync as existsSync26, readFileSync as readFileSync34, readdirSync as readdirSync19, statSync as statSync17 } from "fs";
92180
92577
  import { homedir as homedir9 } from "os";
92181
92578
  import { join as join53 } from "path";
92182
92579
  function sortEntries(entries) {
@@ -92210,7 +92607,7 @@ function censusHomeDrift(options = {}) {
92210
92607
  const present2 = new Set;
92211
92608
  let dirEntries = [];
92212
92609
  try {
92213
- dirEntries = readdirSync18(home);
92610
+ dirEntries = readdirSync19(home);
92214
92611
  } catch {
92215
92612
  continue;
92216
92613
  }
@@ -92474,7 +92871,7 @@ var exports_diagnostic = {};
92474
92871
  __export(exports_diagnostic, {
92475
92872
  registerDiagnostic: () => registerDiagnostic
92476
92873
  });
92477
- import { existsSync as existsSync27, readFileSync as readFileSync36, readdirSync as readdirSync19, statSync as statSync18 } from "fs";
92874
+ import { existsSync as existsSync27, readFileSync as readFileSync36, readdirSync as readdirSync20, statSync as statSync18 } from "fs";
92478
92875
  import { join as join54 } from "path";
92479
92876
  import { execSync as execSync2 } from "child_process";
92480
92877
  function registerDiagnostic(parent) {
@@ -92667,7 +93064,7 @@ function handleWhoami(options) {
92667
93064
  let skillCount = 0;
92668
93065
  if (exists)
92669
93066
  try {
92670
- skillCount = readdirSync19(agentSkillsPath).filter((f) => !f.startsWith(".") && statSync18(join54(agentSkillsPath, f)).isDirectory()).length;
93067
+ skillCount = readdirSync20(agentSkillsPath).filter((f) => !f.startsWith(".") && statSync18(join54(agentSkillsPath, f)).isDirectory()).length;
92671
93068
  } catch {}
92672
93069
  agentConfigs.push({ agent, label: AGENT_LABELS[agent], path: agentSkillsPath, exists, skillCount });
92673
93070
  }
@@ -92925,7 +93322,7 @@ var init_cloud_executions = __esm(() => {
92925
93322
 
92926
93323
  // node_modules/@hasna/secrets/dist/sdk.js
92927
93324
  import { isIP as isIP3 } from "net";
92928
- import { spawnSync as spawnSync4 } from "child_process";
93325
+ import { spawnSync as spawnSync5 } from "child_process";
92929
93326
  import { closeSync as closeSync23, fstatSync as fstatSync23, openSync as openSync23, readFileSync as readFileSync37 } from "fs";
92930
93327
  import { O_NOFOLLOW as O_NOFOLLOW3, O_NONBLOCK as O_NONBLOCK3, O_RDONLY as O_RDONLY3 } from "constants";
92931
93328
  import { createRequire as createRequire2 } from "module";
@@ -93200,7 +93597,7 @@ function isAmbientEnvironment2(env3) {
93200
93597
  return env3 === process.env || env3[AMBIENT_ENVIRONMENT2] === true;
93201
93598
  }
93202
93599
  function defaultKeychainRunner2(argv) {
93203
- const result2 = spawnSync4(KEYCHAIN_SECURITY_BIN2, [...argv], {
93600
+ const result2 = spawnSync5(KEYCHAIN_SECURITY_BIN2, [...argv], {
93204
93601
  encoding: "utf8",
93205
93602
  stdio: ["ignore", "pipe", "pipe"],
93206
93603
  timeout: KEYCHAIN_SPAWN_TIMEOUT_MS2
@@ -94581,7 +94978,7 @@ __export(exports_selected_run, {
94581
94978
  });
94582
94979
  import { createHash as createHash36 } from "crypto";
94583
94980
  import { spawn as spawn3 } from "child_process";
94584
- import { mkdirSync as mkdirSync17, mkdtempSync as mkdtempSync4, writeFileSync as writeFileSync16, realpathSync as realpathSync16 } from "fs";
94981
+ import { mkdirSync as mkdirSync18, mkdtempSync as mkdtempSync5, writeFileSync as writeFileSync16, realpathSync as realpathSync16 } from "fs";
94585
94982
  import { dirname as dirname33, join as join56, resolve as resolve33 } from "path";
94586
94983
  import { tmpdir, hostname as stationHostname2 } from "os";
94587
94984
  async function resolveSelectedRun(spec, profileId, options = {}) {
@@ -94705,7 +95102,7 @@ async function executeSelectedLocal(selected, options = {}) {
94705
95102
  throw new SkillSelectionError("INVALID_SECRET_BINDINGS", "Explicit environment values must be bounded strings without NUL bytes.");
94706
95103
  secretEnv[name] = value;
94707
95104
  }
94708
- const runDirectory = mkdtempSync4(join56(tmpdir(), "skills-execution-"));
95105
+ const runDirectory = mkdtempSync5(join56(tmpdir(), "skills-execution-"));
94709
95106
  const paths = new SkillEntryPaths;
94710
95107
  for (const entry of entries) {
94711
95108
  paths.add(entry.path, 100, () => {
@@ -94714,7 +95111,7 @@ async function executeSelectedLocal(selected, options = {}) {
94714
95111
  throw new SkillSelectionError("INVALID_BUNDLE_PATH", "The execution bundle path exceeds its limit.");
94715
95112
  });
94716
95113
  const destination = join56(runDirectory, entry.path);
94717
- mkdirSync17(dirname33(destination), { recursive: true, mode: 448 });
95114
+ mkdirSync18(dirname33(destination), { recursive: true, mode: 448 });
94718
95115
  writeFileSync16(destination, entry.bytes, { flag: "wx", mode: entry.mode & 511 });
94719
95116
  }
94720
95117
  env3.SKILLS_INPUT_JSON = input2;
@@ -98967,7 +99364,7 @@ var init_runs = __esm(() => {
98967
99364
 
98968
99365
  // src/lib/run-state.ts
98969
99366
  import { createHash as createHash37, randomBytes } from "crypto";
98970
- import { existsSync as existsSync28, mkdirSync as mkdirSync18, readFileSync as readFileSync38, readdirSync as readdirSync20, statSync as statSync19, writeFileSync as writeFileSync17 } from "fs";
99367
+ import { existsSync as existsSync28, mkdirSync as mkdirSync19, readFileSync as readFileSync38, readdirSync as readdirSync21, statSync as statSync19, writeFileSync as writeFileSync17 } from "fs";
98971
99368
  import { extname, join as join57, relative as relative11 } from "path";
98972
99369
  function createSkillRun(params, targetDir = process.cwd()) {
98973
99370
  const now3 = new Date;
@@ -98978,9 +99375,9 @@ function createSkillRun(params, targetDir = process.cwd()) {
98978
99375
  const runDir = join57(root2, "runs", day, id2);
98979
99376
  const logsDir = join57(runDir, "logs");
98980
99377
  const exportDir = join57(root2, "exports", skillName, id2);
98981
- mkdirSync18(logsDir, { recursive: true });
98982
- mkdirSync18(exportDir, { recursive: true });
98983
- mkdirSync18(join57(root2, "tmp"), { recursive: true });
99378
+ mkdirSync19(logsDir, { recursive: true });
99379
+ mkdirSync19(exportDir, { recursive: true });
99380
+ mkdirSync19(join57(root2, "tmp"), { recursive: true });
98984
99381
  const record13 = {
98985
99382
  id: id2,
98986
99383
  skill: skillName,
@@ -99047,11 +99444,11 @@ function listSkillRuns(targetDir = process.cwd(), limit = 50) {
99047
99444
  if (!existsSync28(runsRoot))
99048
99445
  return [];
99049
99446
  const records = [];
99050
- for (const day of readdirSync20(runsRoot).sort().reverse()) {
99447
+ for (const day of readdirSync21(runsRoot).sort().reverse()) {
99051
99448
  const dayDir = join57(runsRoot, day);
99052
99449
  if (!statSync19(dayDir).isDirectory())
99053
99450
  continue;
99054
- for (const runId2 of readdirSync20(dayDir).sort().reverse()) {
99451
+ for (const runId2 of readdirSync21(dayDir).sort().reverse()) {
99055
99452
  const record13 = readRunRecord(join57(dayDir, runId2));
99056
99453
  if (record13)
99057
99454
  records.push(record13);
@@ -99065,7 +99462,7 @@ function findSkillRun(runId2, targetDir = process.cwd()) {
99065
99462
  const runsRoot = join57(getProjectStateDir(targetDir), "runs");
99066
99463
  if (!existsSync28(runsRoot))
99067
99464
  return null;
99068
- for (const day of readdirSync20(runsRoot)) {
99465
+ for (const day of readdirSync21(runsRoot)) {
99069
99466
  const record13 = readRunRecord(join57(runsRoot, day, runId2));
99070
99467
  if (record13)
99071
99468
  return record13;
@@ -99121,7 +99518,7 @@ function readRunRecord(runDir) {
99121
99518
  }
99122
99519
  function walkFiles(dir) {
99123
99520
  const files = [];
99124
- for (const entry of readdirSync20(dir)) {
99521
+ for (const entry of readdirSync21(dir)) {
99125
99522
  const full = join57(dir, entry);
99126
99523
  if (statSync19(full).isDirectory())
99127
99524
  files.push(...walkFiles(full));
@@ -111139,7 +111536,7 @@ var init_remote_customer_operations = __esm(() => {
111139
111536
  });
111140
111537
 
111141
111538
  // src/lib/workspace-profile.ts
111142
- import { constants as constants25, closeSync as closeSync26, fstatSync as fstatSync26, lstatSync as lstatSync36, mkdirSync as mkdirSync19, mkdtempSync as mkdtempSync5, openSync as openSync26, readFileSync as readFileSync39, renameSync as renameSync11, rmSync as rmSync8, writeFileSync as writeFileSync18 } from "fs";
111539
+ import { constants as constants25, closeSync as closeSync26, fstatSync as fstatSync26, lstatSync as lstatSync36, mkdirSync as mkdirSync20, mkdtempSync as mkdtempSync6, openSync as openSync26, readFileSync as readFileSync39, renameSync as renameSync11, rmSync as rmSync9, writeFileSync as writeFileSync18 } from "fs";
111143
111540
  import { dirname as dirname34, join as join58 } from "path";
111144
111541
  function stat2(path) {
111145
111542
  try {
@@ -111212,6 +111609,7 @@ async function prepareWorkspaceEnrollment(membershipId, source = process.env) {
111212
111609
  const env3 = { ...source }, profile = selectedSkillsProfile(env3);
111213
111610
  if (!profile)
111214
111611
  return fail4("Workspace login requires an explicit HASNA_PROFILE name.");
111612
+ assertSkillsSignInCredentialReplaceable(env3);
111215
111613
  if (["HASNA_SKILLS_API_KEY_OVERRIDE", "HASNA_SKILLS_API_KEY_REF", "HASNA_SKILLS_API_KEY", "SKILLS_API_KEY"].some((name) => env3[name]?.trim()))
111216
111614
  return fail4("Clear injected API keys before enrolling a named workspace profile.");
111217
111615
  const origin = getApiUrl("Sign in to a workspace", env3);
@@ -111290,8 +111688,8 @@ async function prepareWorkspaceEnrollment(membershipId, source = process.env) {
111290
111688
  return fail4("The new profile exceeds the credential reader size limit.");
111291
111689
  const identity6 = JSON.stringify({ email: verified.user.email, userId: verified.user.id, orgId: verified.organization.id, orgSlug: verified.organization.slug, apiUrl: origin, issuedBy: "sign-in" }, null, 2) + `
111292
111690
  `;
111293
- mkdirSync19(dirname34(file2), { recursive: true, mode: 448 });
111294
- const temp = mkdtempSync5(join58(dirname34(file2), ".workspace-login-"));
111691
+ mkdirSync20(dirname34(file2), { recursive: true, mode: 448 });
111692
+ const temp = mkdtempSync6(join58(dirname34(file2), ".workspace-login-"));
111295
111693
  let identityInstalled = false;
111296
111694
  try {
111297
111695
  writeFileSync18(join58(temp, "credentials"), body, { mode: 384, flag: "wx" });
@@ -111310,7 +111708,7 @@ async function prepareWorkspaceEnrollment(membershipId, source = process.env) {
111310
111708
  } catch (error61) {
111311
111709
  if (identityInstalled) {
111312
111710
  if (oldIdentity === null)
111313
- rmSync8(identityFile, { force: true });
111711
+ rmSync9(identityFile, { force: true });
111314
111712
  else {
111315
111713
  writeFileSync18(join58(temp, "restore"), oldIdentity, { mode: 384, flag: "wx" });
111316
111714
  renameSync11(join58(temp, "restore"), identityFile);
@@ -111318,7 +111716,7 @@ async function prepareWorkspaceEnrollment(membershipId, source = process.env) {
111318
111716
  }
111319
111717
  throw error61;
111320
111718
  } finally {
111321
- rmSync8(temp, { recursive: true, force: true });
111719
+ rmSync9(temp, { recursive: true, force: true });
111322
111720
  }
111323
111721
  return {
111324
111722
  status: "authenticated",
@@ -111507,7 +111905,7 @@ var init_recurring_customer = __esm(() => {
111507
111905
  });
111508
111906
 
111509
111907
  // src/lib/recurring-recovery.ts
111510
- import { constants as constants26, closeSync as closeSync27, fsyncSync as fsyncSync8, fstatSync as fstatSync27, lstatSync as lstatSync37, mkdirSync as mkdirSync20, openSync as openSync27, readSync as readSync19, realpathSync as realpathSync17, renameSync as renameSync12, unlinkSync as unlinkSync8, writeFileSync as writeFileSync19 } from "fs";
111908
+ import { constants as constants26, closeSync as closeSync27, fsyncSync as fsyncSync8, fstatSync as fstatSync27, lstatSync as lstatSync37, mkdirSync as mkdirSync21, openSync as openSync27, readSync as readSync19, realpathSync as realpathSync17, renameSync as renameSync12, unlinkSync as unlinkSync8, writeFileSync as writeFileSync19 } from "fs";
111511
111909
  import { dirname as dirname35, isAbsolute as isAbsolute33, join as join59, resolve as resolve34 } from "path";
111512
111910
  import { randomUUID as randomUUID8 } from "crypto";
111513
111911
 
@@ -111653,7 +112051,7 @@ function base2(customer, organizationId) {
111653
112051
  function create3(directory2, intent) {
111654
112052
  if (!isAbsolute33(directory2) || resolve34(directory2) !== directory2 || realpathSync17(dirname35(directory2)) !== dirname35(directory2))
111655
112053
  invalid6();
111656
- mkdirSync20(directory2, { mode: 448 });
112054
+ mkdirSync21(directory2, { mode: 448 });
111657
112055
  const owner2 = new RecoveryOwner(directory2), checked = intentSchema.parse(intent), intentSha256 = canonicalJsonSha256(checked);
111658
112056
  owner2.write(`intent-${intentSha256}.json`, checked);
111659
112057
  owner2.write("state.json", { contractVersion: 1, intentSha256, phase: "prepared", consentId: null });
@@ -113291,7 +113689,7 @@ var init_run_routing = __esm(() => {
113291
113689
  });
113292
113690
 
113293
113691
  // src/mcp/operation-tools.ts
113294
- import { existsSync as existsSync29, readdirSync as readdirSync21, statSync as statSync20 } from "fs";
113692
+ import { existsSync as existsSync29, readdirSync as readdirSync22, statSync as statSync20 } from "fs";
113295
113693
  import { join as join60 } from "path";
113296
113694
  function registerOperationTools(server) {
113297
113695
  server.registerTool("cloud_skill_eligibility", {
@@ -113773,7 +114171,7 @@ function registerOperationTools(server) {
113773
114171
  let skillCount = 0;
113774
114172
  if (exists) {
113775
114173
  try {
113776
- skillCount = readdirSync21(agentSkillsPath).filter((f) => {
114174
+ skillCount = readdirSync22(agentSkillsPath).filter((f) => {
113777
114175
  const full = join60(agentSkillsPath, f);
113778
114176
  return !f.startsWith(".") && statSync20(full).isDirectory();
113779
114177
  }).length;
@@ -113841,7 +114239,7 @@ var init_operation_tools = __esm(() => {
113841
114239
  });
113842
114240
 
113843
114241
  // src/lib/feedback.ts
113844
- import { appendFileSync as appendFileSync2, existsSync as existsSync30, mkdirSync as mkdirSync21 } from "fs";
114242
+ import { appendFileSync as appendFileSync2, existsSync as existsSync30, mkdirSync as mkdirSync22 } from "fs";
113845
114243
  import { dirname as dirname36, join as join61 } from "path";
113846
114244
  import { Database } from "bun:sqlite";
113847
114245
  function getFeedbackDbPath() {
@@ -113851,7 +114249,7 @@ function getFeedbackDb() {
113851
114249
  const dbPath = getFeedbackDbPath();
113852
114250
  const dir = dirname36(dbPath);
113853
114251
  if (!existsSync30(dir))
113854
- mkdirSync21(dir, { recursive: true });
114252
+ mkdirSync22(dir, { recursive: true });
113855
114253
  const db = new Database(dbPath);
113856
114254
  db.exec("PRAGMA journal_mode = WAL");
113857
114255
  db.exec([
@@ -113880,7 +114278,7 @@ function saveFeedback(input2) {
113880
114278
  const path = join61(getDataDir(), "feedback.jsonl");
113881
114279
  const dir = dirname36(path);
113882
114280
  if (!existsSync30(dir))
113883
- mkdirSync21(dir, { recursive: true });
114281
+ mkdirSync22(dir, { recursive: true });
113884
114282
  appendFileSync2(path, JSON.stringify({ message, category, email: input2.email ?? null, agent: input2.agent ?? null, version: input2.version ?? null, createdAt: new Date().toISOString() }) + `
113885
114283
  `);
113886
114284
  return { saved: true, category, path };
@@ -114041,7 +114439,7 @@ var init_resource_meta_tools = __esm(() => {
114041
114439
  });
114042
114440
 
114043
114441
  // src/lib/scheduler.ts
114044
- import { existsSync as existsSync31, readFileSync as readFileSync40, writeFileSync as writeFileSync20, mkdirSync as mkdirSync22 } from "fs";
114442
+ import { existsSync as existsSync31, readFileSync as readFileSync40, writeFileSync as writeFileSync20, mkdirSync as mkdirSync23 } from "fs";
114045
114443
  import { join as join62 } from "path";
114046
114444
  function getSchedulesPath(targetDir = process.cwd()) {
114047
114445
  return join62(targetDir, ".skills", "schedules.json");
@@ -114059,7 +114457,7 @@ function saveSchedules(data, targetDir = process.cwd()) {
114059
114457
  const path = getSchedulesPath(targetDir);
114060
114458
  const dir = join62(targetDir, ".skills");
114061
114459
  if (!existsSync31(dir))
114062
- mkdirSync22(dir, { recursive: true });
114460
+ mkdirSync23(dir, { recursive: true });
114063
114461
  writeFileSync20(path, JSON.stringify(data, null, 2));
114064
114462
  }
114065
114463
  function validateCronField(expr, min2, max2, label) {
@@ -114359,9 +114757,9 @@ var init_schedule_tools = __esm(() => {
114359
114757
  import { createHash as createHash38, createHmac as createHmac3 } from "crypto";
114360
114758
  import {
114361
114759
  existsSync as existsSync32,
114362
- mkdirSync as mkdirSync23,
114760
+ mkdirSync as mkdirSync24,
114363
114761
  readFileSync as readFileSync41,
114364
- readdirSync as readdirSync22,
114762
+ readdirSync as readdirSync23,
114365
114763
  statSync as statSync21,
114366
114764
  writeFileSync as writeFileSync21
114367
114765
  } from "fs";
@@ -114486,7 +114884,7 @@ function parsePositiveInteger(value) {
114486
114884
  }
114487
114885
  function walkFiles2(dir) {
114488
114886
  const files = [];
114489
- for (const entry of readdirSync22(dir)) {
114887
+ for (const entry of readdirSync23(dir)) {
114490
114888
  const full = join63(dir, entry);
114491
114889
  const stats = statSync21(full);
114492
114890
  if (stats.isDirectory())
@@ -114725,7 +115123,7 @@ var init_private_publication_customer = __esm(() => {
114725
115123
  });
114726
115124
 
114727
115125
  // src/lib/private-publication-recovery.ts
114728
- import { constants as constants27, closeSync as closeSync28, fsyncSync as fsyncSync9, fstatSync as fstatSync28, lstatSync as lstatSync38, mkdirSync as mkdirSync24, openSync as openSync28, readSync as readSync20, realpathSync as realpathSync18, renameSync as renameSync13, unlinkSync as unlinkSync9, writeFileSync as writeFileSync22 } from "fs";
115126
+ import { constants as constants27, closeSync as closeSync28, fsyncSync as fsyncSync9, fstatSync as fstatSync28, lstatSync as lstatSync38, mkdirSync as mkdirSync25, openSync as openSync28, readSync as readSync20, realpathSync as realpathSync18, renameSync as renameSync13, unlinkSync as unlinkSync9, writeFileSync as writeFileSync22 } from "fs";
114729
115127
  import { dirname as dirname38, isAbsolute as isAbsolute35, join as join64, resolve as resolve35 } from "path";
114730
115128
  import { randomUUID as randomUUID9 } from "crypto";
114731
115129
  function safeDirectory(directory3) {
@@ -114869,7 +115267,7 @@ async function preparePrivatePublication(client2, sourceDirectory, recoveryDirec
114869
115267
  };
114870
115268
  if (!isAbsolute35(recoveryDirectory) || resolve35(recoveryDirectory) !== recoveryDirectory || realpathSync18(dirname38(recoveryDirectory)) !== dirname38(recoveryDirectory))
114871
115269
  return fail5();
114872
- mkdirSync24(recoveryDirectory, { mode: 448 });
115270
+ mkdirSync25(recoveryDirectory, { mode: 448 });
114873
115271
  safeDirectory(recoveryDirectory);
114874
115272
  const parent = openSync28(dirname38(recoveryDirectory), constants27.O_RDONLY | constants27.O_NOFOLLOW);
114875
115273
  try {
@@ -115432,7 +115830,7 @@ var exports_runtime_mcp = {};
115432
115830
  __export(exports_runtime_mcp, {
115433
115831
  handleMcp: () => handleMcp
115434
115832
  });
115435
- import { existsSync as existsSync33, mkdirSync as mkdirSync25, readFileSync as readFileSync42, writeFileSync as writeFileSync23 } from "fs";
115833
+ import { existsSync as existsSync33, mkdirSync as mkdirSync26, readFileSync as readFileSync42, writeFileSync as writeFileSync23 } from "fs";
115436
115834
  import { homedir as homedir10 } from "os";
115437
115835
  import { dirname as dirname39, join as join65 } from "path";
115438
115836
  async function handleMcp(options) {
@@ -115608,7 +116006,7 @@ function writeJsonObject(path, data) {
115608
116006
  `);
115609
116007
  }
115610
116008
  function writeTextFile(path, content) {
115611
- mkdirSync25(dirname39(path), { recursive: true });
116009
+ mkdirSync26(dirname39(path), { recursive: true });
115612
116010
  writeFileSync23(path, content.endsWith(`
115613
116011
  `) ? content : `${content}
115614
116012
  `);
@@ -115803,7 +116201,7 @@ async function validateReviewedRuntimeLock(bytes, sha2563, context2) {
115803
116201
  throw new Error("REVIEWED_LOCK_LOCATION_INVALID");
115804
116202
  if (location === `node_modules/${PACKAGE2}`)
115805
116203
  continue;
115806
- if (typeof entry.version !== "string" || !VERSION.test(entry.version) || typeof entry.resolved !== "string" || typeof entry.integrity !== "string" || !INTEGRITY.test(entry.integrity))
116204
+ if (typeof entry.version !== "string" || !VERSION2.test(entry.version) || typeof entry.resolved !== "string" || typeof entry.integrity !== "string" || !INTEGRITY.test(entry.integrity))
115807
116205
  throw new Error("REVIEWED_LOCK_PACKAGE_INVALID");
115808
116206
  let url2;
115809
116207
  try {
@@ -115835,10 +116233,10 @@ async function validateReviewedRuntimeLock(bytes, sha2563, context2) {
115835
116233
  }));
115836
116234
  }
115837
116235
  }
115838
- var PACKAGE2 = "@hasna/skills", NAME2, VERSION, INTEGRITY, MAX_LOCK_BYTES, MAX_METADATA_BYTES;
116236
+ var PACKAGE2 = "@hasna/skills", NAME2, VERSION2, INTEGRITY, MAX_LOCK_BYTES, MAX_METADATA_BYTES;
115839
116237
  var init_reviewed_runtime_lock = __esm(() => {
115840
116238
  NAME2 = /^(?:@[a-z0-9._-]+\/)?[a-z0-9._-]+$/;
115841
- VERSION = /^\d+\.\d+\.\d+(?:-[a-zA-Z0-9.-]+)?(?:\+[a-zA-Z0-9.-]+)?$/;
116239
+ VERSION2 = /^\d+\.\d+\.\d+(?:-[a-zA-Z0-9.-]+)?(?:\+[a-zA-Z0-9.-]+)?$/;
115842
116240
  INTEGRITY = /^sha512-[A-Za-z0-9+/]{86}==$/;
115843
116241
  MAX_LOCK_BYTES = 8 * 1024 * 1024;
115844
116242
  MAX_METADATA_BYTES = 32 * 1024 * 1024;
@@ -115848,15 +116246,15 @@ var init_reviewed_runtime_lock = __esm(() => {
115848
116246
  import { createHash as createHash40, randomUUID as randomUUID10 } from "crypto";
115849
116247
  import { Readable } from "stream";
115850
116248
  import { createGunzip as createGunzip2 } from "zlib";
115851
- import { spawnSync as spawnSync5 } from "child_process";
116249
+ import { spawnSync as spawnSync6 } from "child_process";
115852
116250
  import {
115853
116251
  chmodSync as chmodSync4,
115854
116252
  copyFileSync,
115855
116253
  existsSync as existsSync34,
115856
116254
  lstatSync as lstatSync39,
115857
- mkdirSync as mkdirSync26,
116255
+ mkdirSync as mkdirSync27,
115858
116256
  readFileSync as readFileSync43,
115859
- readdirSync as readdirSync23,
116257
+ readdirSync as readdirSync24,
115860
116258
  readlinkSync as readlinkSync8,
115861
116259
  realpathSync as realpathSync19,
115862
116260
  renameSync as renameSync14,
@@ -115927,7 +116325,7 @@ function verifyTargetPrerequisites(manifest, packageRoot, home, cwd2, pathValue)
115927
116325
  for (const key2 of ["SUMI_CONFIG", "SUMI_CONFIG_CONTENT"])
115928
116326
  if (process.env[key2] !== undefined)
115929
116327
  env3[key2] = "";
115930
- const child2 = spawnSync5(pinnedLauncherRuntime(), [...PINNED_LAUNCHER_BUN_FLAGS2, entry, home, cwd2], {
116328
+ const child2 = spawnSync6(pinnedLauncherRuntime(), [...PINNED_LAUNCHER_BUN_FLAGS2, entry, home, cwd2], {
115931
116329
  cwd: dirname40(packageRoot),
115932
116330
  env: env3,
115933
116331
  encoding: "buffer",
@@ -116001,7 +116399,7 @@ function assertNoSymlinkAncestors(path) {
116001
116399
  function acquireRuntimeLock(runtimeRoot) {
116002
116400
  const lockPath = join66(runtimeRoot, ".copyfile-update-lock");
116003
116401
  try {
116004
- mkdirSync26(lockPath, { mode: 448 });
116402
+ mkdirSync27(lockPath, { mode: 448 });
116005
116403
  } catch {
116006
116404
  throw new Error("RUNTIME_UPDATE_LOCKED");
116007
116405
  }
@@ -116270,7 +116668,7 @@ async function downloadPackage(version2, stagingRoot, registryOrigin, fetcher) {
116270
116668
  throw new Error("TARBALL_PACKAGE_IDENTITY_MISMATCH");
116271
116669
  const bins = packageBins(unpacked);
116272
116670
  const archiveRoot = join66(stagingRoot, "verified-archive");
116273
- mkdirSync26(archiveRoot, { mode: 448 });
116671
+ mkdirSync27(archiveRoot, { mode: 448 });
116274
116672
  await archive.extract(archiveRoot);
116275
116673
  const extractedPackage = join66(archiveRoot, "package");
116276
116674
  const extracted = readTree(extractedPackage, false);
@@ -116321,7 +116719,7 @@ function readTree(root2, includeModes, excludeNpmDependencies = false) {
116321
116719
  const base3 = realpathSync19(root2);
116322
116720
  const entries = [];
116323
116721
  const walk2 = (dir, prefix = "") => {
116324
- for (const item of readdirSync23(dir).sort()) {
116722
+ for (const item of readdirSync24(dir).sort()) {
116325
116723
  const path = join66(dir, item);
116326
116724
  const rel = prefix ? `${prefix}/${item}` : item;
116327
116725
  const stat3 = lstatSync39(path);
@@ -116365,7 +116763,7 @@ function normalizeModes(root2) {
116365
116763
  throw new Error("RUNTIME_ENTRY_TYPE_UNSUPPORTED");
116366
116764
  chmodSync4(root2, rootStat.mode & 493);
116367
116765
  const walk2 = (dir) => {
116368
- for (const item of readdirSync23(dir)) {
116766
+ for (const item of readdirSync24(dir)) {
116369
116767
  const path = join66(dir, item);
116370
116768
  const stat3 = lstatSync39(path);
116371
116769
  if (stat3.isSymbolicLink())
@@ -116426,7 +116824,7 @@ function verifyPreimageManifest(runtimePath, receipt, home) {
116426
116824
  }
116427
116825
  function captureConfigPreimages(home, stage) {
116428
116826
  const root2 = join66(stage, "preimage", "configs");
116429
- mkdirSync26(root2, { recursive: true, mode: 448 });
116827
+ mkdirSync27(root2, { recursive: true, mode: 448 });
116430
116828
  return CONFIG_PREIMAGE_PATHS.map((relativePath) => {
116431
116829
  const sourcePath = join66(home, relativePath);
116432
116830
  if (!entryExists(sourcePath))
@@ -116436,7 +116834,7 @@ function captureConfigPreimages(home, stage) {
116436
116834
  throw new Error("CONFIG_PREIMAGE_NOT_REGULAR_FILE");
116437
116835
  const bytes = readFileSync43(sourcePath);
116438
116836
  const backupPath = join66(root2, relativePath);
116439
- mkdirSync26(dirname40(backupPath), { recursive: true, mode: 448 });
116837
+ mkdirSync27(dirname40(backupPath), { recursive: true, mode: 448 });
116440
116838
  writeFileSync24(backupPath, bytes, { flag: "wx", mode: 384 });
116441
116839
  chmodSync4(backupPath, 384);
116442
116840
  const readback = readFileSync43(backupPath);
@@ -116589,7 +116987,7 @@ function persistReceipt(path, value) {
116589
116987
  return;
116590
116988
  const historyRoot = join66(dirname40(path), "receipt-history");
116591
116989
  if (!entryExists(historyRoot))
116592
- mkdirSync26(historyRoot, { mode: 448 });
116990
+ mkdirSync27(historyRoot, { mode: 448 });
116593
116991
  const historyStat = lstatSync39(historyRoot);
116594
116992
  if (!historyStat.isDirectory() || historyStat.isSymbolicLink() || (historyStat.mode & 63) !== 0)
116595
116993
  throw new Error("RECEIPT_HISTORY_NOT_PRIVATE");
@@ -116613,7 +117011,7 @@ function persistAliasReceipt(path, value) {
116613
117011
  return;
116614
117012
  const history = join66(dirname40(path), "history");
116615
117013
  if (!entryExists(history))
116616
- mkdirSync26(history, { mode: 448 });
117014
+ mkdirSync27(history, { mode: 448 });
116617
117015
  const historyStat = lstatSync39(history);
116618
117016
  if (!historyStat.isDirectory() || historyStat.isSymbolicLink() || (historyStat.mode & 63) !== 0)
116619
117017
  throw new Error("ALIAS_RECEIPT_HISTORY_UNSAFE");
@@ -116770,7 +117168,7 @@ function adoptCopyfileAliases(options = {}) {
116770
117168
  }
116771
117169
  if (!aliases.length)
116772
117170
  return { adopted: true, version: layout.currentVersion, aliasCount: 0 };
116773
- mkdirSync26(receiptDir, { recursive: true, mode: 448 });
117171
+ mkdirSync27(receiptDir, { recursive: true, mode: 448 });
116774
117172
  const receiptDirStat = lstatSync39(receiptDir);
116775
117173
  if (!receiptDirStat.isDirectory() || receiptDirStat.isSymbolicLink() || receiptDirStat.mode & 63)
116776
117174
  throw new Error("ALIAS_RECEIPT_DIRECTORY_UNSAFE");
@@ -116996,7 +117394,7 @@ async function updateCopyfileRuntime(version2, options = {}) {
116996
117394
  try {
116997
117395
  if (entryExists(finalPath))
116998
117396
  throw new Error("TARGET_RUNTIME_ALREADY_EXISTS");
116999
- mkdirSync26(stagePath, { mode: 448 });
117397
+ mkdirSync27(stagePath, { mode: 448 });
117000
117398
  chmodSync4(stagePath, 448);
117001
117399
  const configPreimages = captureConfigPreimages(home, stagePath);
117002
117400
  const fetcher = options.fetcher ?? fetch;
@@ -117005,7 +117403,7 @@ async function updateCopyfileRuntime(version2, options = {}) {
117005
117403
  throw new Error("PACKAGE_BIN_SET_CHANGED");
117006
117404
  }
117007
117405
  const stagePackage = join66(stagePath, "install");
117008
- mkdirSync26(stagePackage, { mode: 448 });
117406
+ mkdirSync27(stagePackage, { mode: 448 });
117009
117407
  copyFileSync(artifact.tarballPath, join66(stagePackage, "verified.tgz"));
117010
117408
  writeFileSync24(join66(stagePackage, "package.json"), JSON.stringify({ name: "skills-runtime-install", version: "0.0.0", private: true, dependencies: { [PACKAGE_NAME]: "file:./verified.tgz" } }, null, 2), { mode: 384, flag: "wx" });
117011
117409
  let npmVersion;
@@ -117175,7 +117573,7 @@ function rollbackCopyfileRuntime(receiptId, options = {}) {
117175
117573
  throw new Error("RUNTIME_ROOT_NOT_PRIVATE");
117176
117574
  const releaseLock = acquireRuntimeLock(runtimeRoot);
117177
117575
  try {
117178
- const matches2 = readdirSync23(runtimeRoot).filter((name) => {
117576
+ const matches2 = readdirSync24(runtimeRoot).filter((name) => {
117179
117577
  if (!/^\d+\.\d+\.\d+-copyfile$/.test(name))
117180
117578
  return false;
117181
117579
  const receipt2 = join66(runtimeRoot, name, "rollout-receipt.json");
@@ -117279,7 +117677,7 @@ __export(exports_runtime, {
117279
117677
  registerRuntime: () => registerRuntime
117280
117678
  });
117281
117679
  import { createHash as createHash41, randomUUID as randomUUID11 } from "crypto";
117282
- import { lstatSync as lstatSync40, mkdirSync as mkdirSync27, readFileSync as readFileSync44, writeFileSync as writeFileSync25 } from "fs";
117680
+ import { lstatSync as lstatSync40, mkdirSync as mkdirSync28, readFileSync as readFileSync44, writeFileSync as writeFileSync25 } from "fs";
117283
117681
  import { basename as basename22, isAbsolute as isAbsolute38, join as join67 } from "path";
117284
117682
  import { createInterface } from "readline";
117285
117683
  function registerRuntime(parent) {
@@ -118196,7 +118594,7 @@ async function handleExportsDownload(runId2, options) {
118196
118594
  const canonicalSkill = typeof remoteRun.skill === "string" ? remoteRun.skill : "remote";
118197
118595
  const requestedSkill = typeof remoteRun.requestedSlug === "string" && remoteRun.requestedSlug.trim() ? remoteRun.requestedSlug : canonicalSkill;
118198
118596
  const exportDir = getRunExportDir(runId2, requestedSkill);
118199
- mkdirSync27(exportDir, { recursive: true });
118597
+ mkdirSync28(exportDir, { recursive: true });
118200
118598
  const downloaded = [];
118201
118599
  for (const artifact of artifacts) {
118202
118600
  const artifactId = String(artifact.id || "");
@@ -118250,7 +118648,7 @@ function ensureSafeExportParent(root2, relativePath) {
118250
118648
  } catch (error61) {
118251
118649
  if (error61.code !== "ENOENT")
118252
118650
  throw error61;
118253
- mkdirSync27(parent, { mode: 448 });
118651
+ mkdirSync28(parent, { mode: 448 });
118254
118652
  }
118255
118653
  }
118256
118654
  }
@@ -118840,7 +119238,7 @@ var init_completion = __esm(() => {
118840
119238
  });
118841
119239
 
118842
119240
  // src/lib/portable-snapshot-filter.ts
118843
- import { readdirSync as readdirSync24, statSync as statSync22 } from "fs";
119241
+ import { readdirSync as readdirSync25, statSync as statSync22 } from "fs";
118844
119242
  import { homedir as homedir11 } from "os";
118845
119243
  import { join as join68, sep as sep19 } from "path";
118846
119244
  function isExcludedSkillFileName(fileName) {
@@ -118879,7 +119277,7 @@ function destinationFor(definition, stationId, relativePath) {
118879
119277
  function walkEntries(absoluteRoot) {
118880
119278
  let entries;
118881
119279
  try {
118882
- entries = readdirSync24(absoluteRoot, { withFileTypes: true });
119280
+ entries = readdirSync25(absoluteRoot, { withFileTypes: true });
118883
119281
  } catch {
118884
119282
  return [];
118885
119283
  }
@@ -118992,7 +119390,7 @@ var init_portable_snapshot_filter = __esm(() => {
118992
119390
  import { createHash as createHash42 } from "crypto";
118993
119391
  import {
118994
119392
  copyFileSync as copyFileSync2,
118995
- mkdirSync as mkdirSync28,
119393
+ mkdirSync as mkdirSync29,
118996
119394
  readFileSync as readFileSync45,
118997
119395
  statSync as statSync23,
118998
119396
  writeFileSync as writeFileSync26
@@ -119125,7 +119523,7 @@ function writeStationSnapshot(options) {
119125
119523
  let written = 0;
119126
119524
  for (const plan of untouched) {
119127
119525
  const destination = resolve37(repoRoot, plan.destination);
119128
- mkdirSync28(dirname42(destination), { recursive: true });
119526
+ mkdirSync29(dirname42(destination), { recursive: true });
119129
119527
  copyFileSync2(plan.source.fullPath, destination);
119130
119528
  written += 1;
119131
119529
  }
@@ -119144,7 +119542,7 @@ function writeStationSnapshot(options) {
119144
119542
  files: manifestFiles
119145
119543
  };
119146
119544
  const manifestPath = resolve37(repoRoot, "resources", options.stationId, "skills", "sync-manifest.json");
119147
- mkdirSync28(dirname42(manifestPath), { recursive: true });
119545
+ mkdirSync29(dirname42(manifestPath), { recursive: true });
119148
119546
  writeFileSync26(manifestPath, `${JSON.stringify(manifest, null, 2)}
119149
119547
  `);
119150
119548
  return {
@@ -119826,7 +120224,7 @@ var init_codex_hook_policy_recovery = __esm(() => {
119826
120224
  });
119827
120225
 
119828
120226
  // src/lib/agent-codex-trust.ts
119829
- import { lstatSync as lstatSync44, mkdirSync as mkdirSync29, readdirSync as readdirSync25, readFileSync as readFileSync46, realpathSync as realpathSync21, statSync as statSync24 } from "fs";
120227
+ import { lstatSync as lstatSync44, mkdirSync as mkdirSync30, readdirSync as readdirSync26, readFileSync as readFileSync46, realpathSync as realpathSync21, statSync as statSync24 } from "fs";
119830
120228
  import { createHash as createHash43, randomUUID as randomUUID12 } from "crypto";
119831
120229
  import { execFileSync as execFileSync2 } from "child_process";
119832
120230
  import { dirname as dirname45, isAbsolute as isAbsolute41, join as join72, resolve as resolve40 } from "path";
@@ -120012,7 +120410,7 @@ async function reconcileCodexNativeHooks(options, connect = connectCodexHookRpc)
120012
120410
  if (recovery?.reviewedPlanDigest !== undefined)
120013
120411
  need8(recovery.reviewedPlanDigest === recoveryPlanDigest, "RECONCILE_RECOVERY_PLAN_CHANGED");
120014
120412
  const preview2 = !!recovery && recovery.reviewedPlanDigest === undefined;
120015
- const receipt = { version: 1, status: preview2 ? "recovery-review-required" : supersededBinding ? "superseded" : "reconciled", reconciled: !preview2, supersededBinding, automaticRollback: false, journal, planDigest: intent.planDigest, nativeVersion: rpc.version, nativeStateVerified: !nativeTrustPending, nativeTrustPending, bindingRefreshRequired: !!configDiscoveryRecovery, nativeExecutionVerified: false, configSha256: currentConfig.sha256, hooksSha256: hooksCurrent.sha256, policySha256: policyBefore.sha256, policyBeforeSha256: policyBefore.sha256, policyCurrentSha256: policyCurrent.sha256, previousSkillsCli: intent.skillsCli, skillsCli: skillsCli.receipt, releaseProof: options.releaseProof, nativeInventoryScope: recordedNativeHooks ? "complete" : "declared-managed-hooks-only", unrelatedNativeHooksPreserved: !!recordedNativeHooks, unrelatedSettingsAndCommentsPreserved: true, ...recoveryPlan ? { recoveryPlan, recoveryPlanDigest } : {} };
120413
+ const receipt = { version: 1, status: preview2 ? "recovery-review-required" : supersededBinding ? "superseded" : "reconciled", reconciled: !preview2, supersededBinding, automaticRollback: false, journal, planDigest: intent.planDigest, nativeVersion: rpc.version, nativeStateVerified: !nativeTrustPending, nativeTrustPending, bindingRefreshRequired: !!configDiscoveryRecovery, nativeExecutionVerified: false, configSha256: currentConfig.sha256, hooksSha256: hooksCurrent.sha256, policySha256: policyBefore.sha256, policyBeforeSha256: policyBefore.sha256, policyCurrentSha256: policyCurrent.sha256, previousSkillsCli: intent.skillsCli, skillsCli: skillsCli.receipt, releaseProof: options.releaseProof, nativeInventoryScope: recordedNativeHooks ? "complete" : "declared-managed-hooks-only", unrelatedNativeHooksPreserved: !!recordedNativeHooks, unrelatedSettingsAndCommentsPreserved: true, ...recoveryPlan ? { recoveryPlan, recoveryPlanDigest } : {}, ...codexAdmissionReceipt(rpc.admission) };
120016
120414
  if (preview2)
120017
120415
  return receipt;
120018
120416
  save(join72(journal, "receipt.json"), json2(receipt));
@@ -120026,9 +120424,9 @@ async function reconcileCodexNativeHooks(options, connect = connectCodexHookRpc)
120026
120424
  }
120027
120425
  async function enrollCodexNativeHooks(options = {}, connect = connectCodexHookRpc) {
120028
120426
  const home = resolve40(options.home ?? homedir13());
120029
- return withCodexCorpusWriteAsync([join72(home, ".codex")], () => enrollCodexNativeHooksUnlocked(options, connect), options);
120427
+ return withCodexCorpusWriteAsync([join72(home, ".codex")], (_assertCurrent, admission) => enrollCodexNativeHooksUnlocked(options, connect, admission), options);
120030
120428
  }
120031
- async function enrollCodexNativeHooksUnlocked(options, connect) {
120429
+ async function enrollCodexNativeHooksUnlocked(options, connect, admission) {
120032
120430
  let rpc, journal;
120033
120431
  try {
120034
120432
  const home = resolve40(options.home ?? homedir13()), dataDir3 = resolve40(options.dataDir ?? getDataDirReadOnly());
@@ -120089,14 +120487,14 @@ async function enrollCodexNativeHooksUnlocked(options, connect) {
120089
120487
  checkInputs();
120090
120488
  const digestInput = { version: 1, home, configPath, ...nativeConfigPath !== configPath ? { nativeConfigPath } : {}, configSha256: configFile.sha256, configVersion: layers[0].version, policySha256: policyFile.sha256, hooksSha256: hooksFile.sha256, skillsCli: skillsCli.receipt, nativeVersion: rpc.version, declarations: expected, admitted };
120091
120489
  const planDigest = makePlanDigest(digestInput);
120092
- const baseReceipt = { planDigest, skillsCli: skillsCli.receipt, nativeVersion: rpc.version, nativeConfigPath, ownedNativeProcessId: rpc.processId, agent: "codex", applied: false, planned, nativeEligible: planned.length === 0, bindingRefreshRequired: false, transport: "owned-stdio-process", existingSessionsReloaded: false, nativeExecutionVerified: false };
120490
+ const baseReceipt = { planDigest, skillsCli: skillsCli.receipt, nativeVersion: rpc.version, nativeConfigPath, ownedNativeProcessId: rpc.processId, agent: "codex", applied: false, planned, nativeEligible: planned.length === 0, bindingRefreshRequired: false, transport: "owned-stdio-process", existingSessionsReloaded: false, nativeExecutionVerified: false, ...codexAdmissionReceipt(admission) };
120093
120491
  if (options.apply)
120094
120492
  need8(options.reviewedPlanDigest === planDigest, "PLAN_CHANGED: run the dry-run again and pass its reviewed --plan-digest with --apply");
120095
120493
  const parent = join72(dataDir3, "native-hook-trust");
120096
120494
  const st = lstatSync44(parent, { throwIfNoEntry: false });
120097
120495
  if (st) {
120098
120496
  need8(st.isDirectory() && !st.isSymbolicLink() && st.uid === process.getuid() && (st.mode & 511) === 448, "UNSAFE_JOURNAL");
120099
- const priorJournals = readdirSync25(parent);
120497
+ const priorJournals = readdirSync26(parent);
120100
120498
  need8(priorJournals.length < 1000, "JOURNAL_BOUND");
120101
120499
  for (const name of priorJournals) {
120102
120500
  need8(/^[a-f0-9-]{36}$/.test(name), "UNSAFE_JOURNAL");
@@ -120106,13 +120504,13 @@ async function enrollCodexNativeHooksUnlocked(options, connect) {
120106
120504
  if (!options.apply || !planned.length)
120107
120505
  return baseReceipt;
120108
120506
  if (!st)
120109
- mkdirSync29(parent, { mode: 448 });
120507
+ mkdirSync30(parent, { mode: 448 });
120110
120508
  journal = join72(parent, randomUUID12());
120111
- mkdirSync29(journal, { mode: 448 });
120509
+ mkdirSync30(journal, { mode: 448 });
120112
120510
  save(join72(journal, "config.before.toml"), configFile.bytes);
120113
120511
  save(join72(journal, "hooks.before.json"), hooksFile.bytes);
120114
120512
  save(join72(journal, "policy.before.json"), policyFile.bytes);
120115
- save(join72(journal, "intent.json"), json2({ ...digestInput, planDigest, hooks: planned, nativeHooks: discovered.map(safeNativeHook) }));
120513
+ save(join72(journal, "intent.json"), json2({ ...digestInput, planDigest, hooks: planned, nativeHooks: discovered.map(safeNativeHook), ...codexAdmissionReceipt(admission) }));
120116
120514
  need8(isDeepStrictEqual19(admit(await list2()), admitted), "NATIVE_DISCOVERY_CHANGED");
120117
120515
  checkInputs();
120118
120516
  let result2;
@@ -120150,7 +120548,7 @@ async function enrollCodexNativeHooksUnlocked(options, connect) {
120150
120548
  const message = error61 instanceof Error && error61.message.startsWith("CODEX_HOOK_TRUST_") ? error61.message : "CODEX_HOOK_TRUST_REFUSED: verify managed bridge installation and native Codex support";
120151
120549
  if (journal) {
120152
120550
  try {
120153
- save(join72(journal, "stopped.json"), json2({ error: message.split(":")[0], automaticRollback: false, reconcileBeforeRetry: true }));
120551
+ save(join72(journal, "stopped.json"), json2({ error: message.split(":")[0], automaticRollback: false, reconcileBeforeRetry: true, ...codexAdmissionReceipt(admission) }));
120154
120552
  } catch {}
120155
120553
  }
120156
120554
  throw new Error(message);
@@ -120269,7 +120667,7 @@ var init_codex_native_trust = __esm(() => {
120269
120667
 
120270
120668
  // src/lib/claude-prospective-review.ts
120271
120669
  import { createHash as createHash45 } from "crypto";
120272
- import { lstatSync as lstatSync45, readFileSync as readFileSync48, readdirSync as readdirSync26, realpathSync as realpathSync22 } from "fs";
120670
+ import { lstatSync as lstatSync45, readFileSync as readFileSync48, readdirSync as readdirSync27, realpathSync as realpathSync22 } from "fs";
120273
120671
  import { basename as basename23, dirname as dirname46, isAbsolute as isAbsolute42, join as join74, relative as relative15, resolve as resolve42, sep as sep21 } from "path";
120274
120672
  import { isDeepStrictEqual as isDeepStrictEqual20 } from "util";
120275
120673
  function hashClaudeDiscoveryBinding(binding) {
@@ -120359,7 +120757,7 @@ function captureClaudeProspectiveCandidateClosure(root2) {
120359
120757
  let bytes = 0;
120360
120758
  const walk2 = (directory3) => {
120361
120759
  const beforeDirectory = lstatSync45(directory3);
120362
- const names = readdirSync26(directory3).sort();
120760
+ const names = readdirSync27(directory3).sort();
120363
120761
  if (new Set(names).size !== names.length)
120364
120762
  refuse8("candidate contains ambiguous directory entries");
120365
120763
  for (const name of names) {
@@ -120514,7 +120912,7 @@ function assertNoUnprojectedSkillPayload(root2, catalogPath, marketplace, plugin
120514
120912
  if (entries[0].skills !== undefined || entries[0].commands !== undefined)
120515
120913
  refuse8("candidate marketplace entry declares native skill or command payloads");
120516
120914
  const walk2 = (directory3) => {
120517
- for (const name of readdirSync26(directory3).sort()) {
120915
+ for (const name of readdirSync27(directory3).sort()) {
120518
120916
  const path = join74(directory3, name), rel = relative15(root2, path).split(sep21).join("/");
120519
120917
  const stat3 = lstatSync45(path);
120520
120918
  if (stat3.isDirectory())
@@ -121468,11 +121866,16 @@ function registerAgentIntegration(parent) {
121468
121866
  throw new Error("CODEX_NATIVE_SKILL_CATALOG_ABSOLUTE_PATH_REQUIRED");
121469
121867
  if (existsSync36(options.output))
121470
121868
  throw new Error("CODEX_NATIVE_SKILL_CATALOG_OUTPUT_EXISTS");
121869
+ let admission;
121471
121870
  const catalog = await captureCodexNativeSkillCatalog({
121472
121871
  command: options.codexCommand,
121473
121872
  home: homedir14(),
121474
121873
  ...process.env.CODEX_HOME === undefined ? {} : { codexHome: process.env.CODEX_HOME },
121475
121874
  cwd: options.cwd
121875
+ }, async (connection) => {
121876
+ const rpc = await connectCodexHookRpc(connection);
121877
+ admission = rpc.admission;
121878
+ return rpc;
121476
121879
  });
121477
121880
  const bytes = JSON.stringify(catalog, null, 2) + `
121478
121881
  `;
@@ -121492,7 +121895,8 @@ function registerAgentIntegration(parent) {
121492
121895
  skillCount: catalog.skills.length,
121493
121896
  output: options.output,
121494
121897
  bytes: Buffer.byteLength(bytes),
121495
- sha256: createHash47("sha256").update(bytes).digest("hex")
121898
+ sha256: createHash47("sha256").update(bytes).digest("hex"),
121899
+ ...codexAdmissionReceipt(admission)
121496
121900
  };
121497
121901
  await writeCliOutput(options.json ? JSON.stringify(receipt) : `Captured ${receipt.skillCount} native Codex skill(s) in ${receipt.output}.`);
121498
121902
  } catch (error61) {
@@ -121836,6 +122240,8 @@ var init_agent_integration2 = __esm(() => {
121836
122240
  init_claude_marketplace_entry_witness();
121837
122241
  init_claude_prospective_review();
121838
122242
  init_codex_native_skill_catalog();
122243
+ init_codex_hook_rpc();
122244
+ init_codex_corpus_write();
121839
122245
  init_self_spawn();
121840
122246
  init_config();
121841
122247
  init_claude_installer_capture();
@@ -122478,8 +122884,8 @@ var init_grants = __esm(() => {
122478
122884
  import { createHash as createHash48 } from "crypto";
122479
122885
  import {
122480
122886
  copyFileSync as copyFileSync3,
122481
- mkdirSync as mkdirSync30,
122482
- readdirSync as readdirSync27,
122887
+ mkdirSync as mkdirSync31,
122888
+ readdirSync as readdirSync28,
122483
122889
  readFileSync as readFileSync50,
122484
122890
  statSync as statSync25,
122485
122891
  writeFileSync as writeFileSync30
@@ -122523,7 +122929,7 @@ function planStationHydration(stationId, repoRoot) {
122523
122929
  const agentRoot = join76(snapshotRoot, "agent-homes", agent);
122524
122930
  let identEntries;
122525
122931
  try {
122526
- identEntries = readdirSync27(agentRoot, { withFileTypes: true });
122932
+ identEntries = readdirSync28(agentRoot, { withFileTypes: true });
122527
122933
  } catch {
122528
122934
  continue;
122529
122935
  }
@@ -122737,7 +123143,7 @@ function writeStationHydration(options) {
122737
123143
  }
122738
123144
  let written = 0;
122739
123145
  for (const entry of toWrite) {
122740
- mkdirSync30(dirname48(entry.destination), { recursive: true });
123146
+ mkdirSync31(dirname48(entry.destination), { recursive: true });
122741
123147
  copyFileSync3(entry.fullPath, entry.destination);
122742
123148
  written += 1;
122743
123149
  }
@@ -122759,7 +123165,7 @@ function writeStationHydration(options) {
122759
123165
  skills: resultSkills
122760
123166
  };
122761
123167
  const hydrationManifestPath = join76(dirname48(cacheRoot), `hydration-${options.stationId}.json`);
122762
- mkdirSync30(dirname48(hydrationManifestPath), { recursive: true });
123168
+ mkdirSync31(dirname48(hydrationManifestPath), { recursive: true });
122763
123169
  writeFileSync30(hydrationManifestPath, `${JSON.stringify(hydration, null, 2)}
122764
123170
  `);
122765
123171
  return {
@@ -122836,7 +123242,7 @@ var init_hydrate = __esm(() => {
122836
123242
 
122837
123243
  // src/lib/prepare-skill.ts
122838
123244
  import { createHash as createHash49, randomUUID as randomUUID13 } from "crypto";
122839
- import { chmodSync as chmodSync5, existsSync as existsSync37, lstatSync as lstatSync48, mkdirSync as mkdirSync31, mkdtempSync as mkdtempSync6, readFileSync as readFileSync51, readdirSync as readdirSync28, renameSync as renameSync15, rmSync as rmSync9, writeFileSync as writeFileSync31 } from "fs";
123245
+ import { chmodSync as chmodSync5, existsSync as existsSync37, lstatSync as lstatSync48, mkdirSync as mkdirSync32, mkdtempSync as mkdtempSync7, readFileSync as readFileSync51, readdirSync as readdirSync29, renameSync as renameSync15, rmSync as rmSync10, writeFileSync as writeFileSync31 } from "fs";
122840
123246
  import { tmpdir as tmpdir2 } from "os";
122841
123247
  import { dirname as dirname49, isAbsolute as isAbsolute46, join as join77, relative as relative16, resolve as resolve46, sep as sep24 } from "path";
122842
123248
  function prepareSkill(name, options) {
@@ -122878,13 +123284,13 @@ function prepareSkill(name, options) {
122878
123284
  throw new Error("skill.json provenance must be an object.");
122879
123285
  const provenance = manifest.provenance;
122880
123286
  const candidate2 = { ...manifest, version: options.version, kind, provenance: { ...provenance } };
122881
- const staging = mkdtempSync6(join77(tmpdir2(), "skills-prepare-"));
123287
+ const staging = mkdtempSync7(join77(tmpdir2(), "skills-prepare-"));
122882
123288
  try {
122883
123289
  for (const directory3 of before2.directories)
122884
- mkdirSync31(join77(staging, directory3), { recursive: true });
123290
+ mkdirSync32(join77(staging, directory3), { recursive: true });
122885
123291
  for (const file2 of before2.files) {
122886
123292
  const destination = join77(staging, file2.path);
122887
- mkdirSync31(dirname49(destination), { recursive: true });
123293
+ mkdirSync32(dirname49(destination), { recursive: true });
122888
123294
  writeFileSync31(destination, file2.bytes, { mode: file2.mode });
122889
123295
  }
122890
123296
  const stagedManifest = join77(staging, "skill.json");
@@ -122916,12 +123322,12 @@ ${validation.issues.map((issue2) => `${issue2.code}: ${issue2.message}`).join(`
122916
123322
  chmodSync5(temporary, manifestFile.mode);
122917
123323
  renameSync15(temporary, join77(path, "skill.json"));
122918
123324
  } finally {
122919
- rmSync9(temporary, { force: true });
123325
+ rmSync10(temporary, { force: true });
122920
123326
  }
122921
123327
  }
122922
123328
  return { name: normalized2, path, previousVersion, version: options.version, kind, contentHash, changed: changed3, written: changed3 && !options.dryRun, warnings: validation.warnings };
122923
123329
  } finally {
122924
- rmSync9(staging, { recursive: true, force: true });
123330
+ rmSync10(staging, { recursive: true, force: true });
122925
123331
  }
122926
123332
  }
122927
123333
  function assertPackedCanonicalCoverage(root2) {
@@ -123037,7 +123443,7 @@ function snapshot2(root2) {
123037
123443
  const hash7 = createHash49("sha256").update(`${rootStat.dev}:${rootStat.ino}\x00`);
123038
123444
  let count = 0, bytes = 0;
123039
123445
  const walk2 = (relative17) => {
123040
- for (const name of readdirSync28(join77(root2, relative17)).sort()) {
123446
+ for (const name of readdirSync29(join77(root2, relative17)).sort()) {
123041
123447
  if (IGNORED.has(name.toLowerCase()) || !relative17 && ROOT_IGNORED.has(name.toLowerCase()))
123042
123448
  continue;
123043
123449
  const path = relative17 ? `${relative17}/${name}` : name;
@@ -123458,7 +123864,7 @@ var init_schedule = __esm(() => {
123458
123864
  });
123459
123865
 
123460
123866
  // src/lib/registry-sync.ts
123461
- import { mkdirSync as mkdirSync32, writeFileSync as writeFileSync32 } from "fs";
123867
+ import { mkdirSync as mkdirSync33, writeFileSync as writeFileSync32 } from "fs";
123462
123868
  import { dirname as dirname50, relative as relative17 } from "path";
123463
123869
  function createRegistrySyncArtifact(options = {}) {
123464
123870
  const profile = options.profile ?? "all";
@@ -123516,7 +123922,7 @@ function createRegistrySyncArtifact(options = {}) {
123516
123922
  };
123517
123923
  }
123518
123924
  function writeRegistrySyncArtifact(path, artifact) {
123519
- mkdirSync32(dirname50(path), { recursive: true });
123925
+ mkdirSync33(dirname50(path), { recursive: true });
123520
123926
  writeFileSync32(path, `${JSON.stringify(artifact, null, 2)}
123521
123927
  `);
123522
123928
  }
@@ -124224,6 +124630,14 @@ async function codeFor(client2, options) {
124224
124630
  return promptCode();
124225
124631
  }
124226
124632
  function errorResult(error61, json3) {
124633
+ if (error61 instanceof SkillsFleetCredentialError) {
124634
+ if (json3)
124635
+ console.log(JSON.stringify({ error: error61.message, code: error61.code, next: error61.next }));
124636
+ else
124637
+ console.error(error61.message);
124638
+ process.exitCode = 1;
124639
+ return;
124640
+ }
124227
124641
  const message = error61 instanceof NameInputError || error61 instanceof WorkspaceProfileError ? error61.message : "Unable to complete workspace sign-in. Check the selected server, profile, account and fresh verification code.";
124228
124642
  if (json3)
124229
124643
  console.log(JSON.stringify({ error: message }));
@@ -124277,6 +124691,7 @@ One workspace key saved. Use HASNA_PROFILE=${result2.profile} for subsequent com
124277
124691
  }
124278
124692
  var init_workspace_selection = __esm(() => {
124279
124693
  init_auth_store();
124694
+ init_fleet_credentials();
124280
124695
  init_remote_auth();
124281
124696
  init_workspace_profile();
124282
124697
  init_customer_verification();
@@ -124422,7 +124837,7 @@ function printWhoami(payload) {
124422
124837
  }
124423
124838
  function signInTarget(url2, json3) {
124424
124839
  try {
124425
- const target = resolveSkillsSignInOrigin(process.env, {}, url2);
124840
+ const target = captureSkillsSignInTarget(process.env, {}, url2);
124426
124841
  const refusal3 = gatewaySignInRefusal(target);
124427
124842
  if (refusal3)
124428
124843
  throw refusal3;
@@ -124433,7 +124848,10 @@ function signInTarget(url2, json3) {
124433
124848
  }
124434
124849
  }
124435
124850
  function targetFlag(target) {
124436
- return target.source === "--url" ? ` --url ${target.origin}` : "";
124851
+ return target.source === "--url" ? ` --url ${skillsShellArgument(target.origin)}` : "";
124852
+ }
124853
+ function skillsCommand(command, target) {
124854
+ return skillsProfileCommand(command, process.env, target.origin);
124437
124855
  }
124438
124856
  async function finishSignIn(result2, target, json3) {
124439
124857
  const email5 = result2.user?.email;
@@ -124445,7 +124863,7 @@ async function finishSignIn(result2, target, json3) {
124445
124863
  ...organization2 ? { organization: organization2 } : {},
124446
124864
  ...result2.firstLogin !== undefined ? { firstLogin: result2.firstLogin } : {},
124447
124865
  apiUrl: target.origin,
124448
- next: ["skills setup agents"]
124866
+ next: [skillsCommand("setup agents", target)]
124449
124867
  }));
124450
124868
  return;
124451
124869
  }
@@ -124455,20 +124873,20 @@ async function finishSignIn(result2, target, json3) {
124455
124873
  console.log(source_default.dim(` Organization: ${result2.organization.name}`));
124456
124874
  console.log(source_default.dim(` Server: ${target.origin}`));
124457
124875
  console.log(source_default.dim(` API key saved to ${getAuthFilePath()}`));
124458
- await offerAgentSetup();
124876
+ await offerAgentSetup(target);
124459
124877
  }
124460
- async function offerAgentSetup() {
124878
+ async function offerAgentSetup(target) {
124461
124879
  const before2 = process.exitCode;
124462
124880
  const answer = await prompt(`
124463
- Register Skills with your coding agents now (skills setup agents)? [Y/n] `);
124881
+ Register Skills with your coding agents now (${skillsCommand("setup agents", target)})? [Y/n] `);
124464
124882
  if (answer === null) {
124465
124883
  process.exitCode = before2 ?? 0;
124466
124884
  console.log(source_default.dim(`
124467
- Skipped. Run it any time: skills setup agents`));
124885
+ Skipped. Run it any time: ${skillsCommand("setup agents", target)}`));
124468
124886
  return;
124469
124887
  }
124470
124888
  if (answer !== "" && !/^y(es)?$/i.test(answer)) {
124471
- console.log(source_default.dim("Skipped. Run it any time: skills setup agents"));
124889
+ console.log(source_default.dim(`Skipped. Run it any time: ${skillsCommand("setup agents", target)}`));
124472
124890
  return;
124473
124891
  }
124474
124892
  const { handleMcp: handleMcp2 } = await Promise.resolve().then(() => (init_runtime_mcp(), exports_runtime_mcp));
@@ -124545,7 +124963,7 @@ async function doLogin(email5, code2, json3, target) {
124545
124963
  if (!json3)
124546
124964
  console.log(source_default.green("\u2713 Code sent to " + email5));
124547
124965
  if (json3 || !isTTY || !process.stderr.isTTY) {
124548
- console.log(JSON.stringify({ status: "code_sent", email: email5, message: `Supply the fresh six-digit code on stdin to: skills login --email ${email5} --code-stdin${targetFlag(target)}` }));
124966
+ console.log(JSON.stringify({ status: "code_sent", email: email5, message: `Supply the fresh six-digit code on stdin to: ${skillsCommand("login", target)} --email ${skillsShellArgument(email5)} --code-stdin${targetFlag(target)}` }));
124549
124967
  return;
124550
124968
  }
124551
124969
  const answer = await promptCode();
@@ -124555,6 +124973,7 @@ async function doLogin(email5, code2, json3, target) {
124555
124973
  }
124556
124974
  let verifyRes;
124557
124975
  try {
124976
+ target.unchanged?.();
124558
124977
  verifyRes = await apiRequest("/api/auth/verify", {
124559
124978
  method: "POST",
124560
124979
  body: JSON.stringify({ email: email5, code: code2 })
@@ -124568,7 +124987,7 @@ async function doLogin(email5, code2, json3, target) {
124568
124987
  return;
124569
124988
  }
124570
124989
  try {
124571
- await persistSignIn(verifyRes, origin, env3, "sign-in");
124990
+ await persistSignIn(verifyRes, origin, env3, "sign-in", target.unchanged);
124572
124991
  } catch (err) {
124573
124992
  writeCommandError(err, "Login succeeded but API key creation failed", json3);
124574
124993
  return;
@@ -124597,6 +125016,7 @@ async function doApiKeyLogin(apiKey, json3, target) {
124597
125016
  }
124598
125017
  let whoami;
124599
125018
  try {
125019
+ target.unchanged?.();
124600
125020
  whoami = await apiRequest("/api/auth/whoami", {
124601
125021
  headers: { Authorization: `Bearer ${trimmed}` }
124602
125022
  }, origin);
@@ -124609,20 +125029,25 @@ async function doApiKeyLogin(apiKey, json3, target) {
124609
125029
  const orgId = stringField2(identity6.orgId);
124610
125030
  const orgSlug = stringField2(identity6.organization);
124611
125031
  const userId = stringField2(identity6.userId);
124612
- saveAuthConfig({
124613
- apiKey: trimmed,
124614
- ...email5 ? { email: email5 } : {},
124615
- ...orgId ? { orgId } : {},
124616
- ...orgSlug ? { orgSlug } : {},
124617
- ...userId ? { userId } : {}
124618
- }, env3, origin, "api-key");
125032
+ try {
125033
+ saveAuthConfig({
125034
+ apiKey: trimmed,
125035
+ ...email5 ? { email: email5 } : {},
125036
+ ...orgId ? { orgId } : {},
125037
+ ...orgSlug ? { orgSlug } : {},
125038
+ ...userId ? { userId } : {}
125039
+ }, env3, origin, "api-key", target.unchanged);
125040
+ } catch (error61) {
125041
+ writeCommandError(error61, "API key verified but the selected profile changed", json3);
125042
+ return;
125043
+ }
124619
125044
  if (json3 || !isTTY) {
124620
- console.log(JSON.stringify({ ...identity6, status: "authenticated", apiUrl: origin, next: ["skills setup agents"] }, null, 2));
125045
+ console.log(JSON.stringify({ ...identity6, status: "authenticated", apiUrl: origin, next: [skillsCommand("setup agents", target)] }, null, 2));
124621
125046
  return;
124622
125047
  }
124623
125048
  printWhoami(identity6);
124624
125049
  console.log(source_default.dim(`Server: ${origin}`));
124625
- await offerAgentSetup();
125050
+ await offerAgentSetup(target);
124626
125051
  }
124627
125052
  function printDeviceCode(session, resumed, write) {
124628
125053
  write(source_default.bold(resumed ? `
@@ -124643,12 +125068,12 @@ async function doDeviceLogin(options, target) {
124643
125068
  const origin = target.origin;
124644
125069
  const json3 = Boolean(options.json);
124645
125070
  const interactive = Boolean(isTTY && !json3);
124646
- const next = `skills login --poll${targetFlag(target)}`;
125071
+ const next = `${skillsCommand("login", target)} --poll${targetFlag(target)}`;
124647
125072
  let session = options.poll ? loadPendingDeviceSignIn(origin, env3) : null;
124648
125073
  if (options.poll && !session) {
124649
125074
  const others = pendingDeviceSignInOrigins(env3).filter((other) => other !== origin);
124650
125075
  if (others.length > 0) {
124651
- writeCommandError(new Error(`No pending sign-in for ${origin}. Pending: ${others.map((other) => `skills login --poll --url ${other}`).join("; ")}`), "No pending sign-in", json3);
125076
+ writeCommandError(new Error(`No pending sign-in for ${origin}. Pending: ${others.map((other) => `${skillsProfileCommand("login", process.env, other)} --poll --url ${skillsShellArgument(other)}`).join("; ")}`), "No pending sign-in", json3);
124652
125077
  return;
124653
125078
  }
124654
125079
  }
@@ -124699,7 +125124,10 @@ Waiting for authentication...`));
124699
125124
  try {
124700
125125
  const deviceCode = session.deviceCode;
124701
125126
  outcome = await pollDeviceAuthorization({
124702
- poll: () => pollDeviceToken(origin, deviceCode),
125127
+ poll: () => {
125128
+ target.unchanged?.();
125129
+ return pollDeviceToken(origin, deviceCode);
125130
+ },
124703
125131
  intervalSeconds: session.interval,
124704
125132
  deadline: Math.min(Date.now() + timeoutMs, session.expiresAt),
124705
125133
  onSlowDown: (intervalMs) => {
@@ -124713,8 +125141,8 @@ Waiting for authentication...`));
124713
125141
  }
124714
125142
  if (outcome.status !== "authorized") {
124715
125143
  const ended = {
124716
- expired: "The sign-in code expired before it was approved. Start again: skills login",
124717
- invalid: "The server no longer recognises this sign-in code. Start again: skills login",
125144
+ expired: `The sign-in code expired before it was approved. Start again: ${skillsCommand("login", target)}${targetFlag(target)}`,
125145
+ invalid: `The server no longer recognises this sign-in code. Start again: ${skillsCommand("login", target)}${targetFlag(target)}`,
124718
125146
  denied: "Sign-in was denied in the browser.",
124719
125147
  timeout: `Device login timed out before browser authentication completed. Resume with: ${next}`,
124720
125148
  cancelled: "Sign-in cancelled."
@@ -124730,7 +125158,7 @@ Waiting for authentication...`));
124730
125158
  return;
124731
125159
  }
124732
125160
  try {
124733
- await persistSignIn(outcome.result, origin, env3, "sign-in");
125161
+ await persistSignIn(outcome.result, origin, env3, "sign-in", target.unchanged);
124734
125162
  } catch (err) {
124735
125163
  writeCommandError(err, "Login succeeded but API key creation failed", json3);
124736
125164
  return;
@@ -124982,6 +125410,7 @@ var init_auth = __esm(() => {
124982
125410
  init_auth_store();
124983
125411
  init_fleet_credentials();
124984
125412
  init_remote_client();
125413
+ init_credential_profile_command();
124985
125414
  init_sign_in();
124986
125415
  init_remote_auth();
124987
125416
  isTTY = process.stdin.isTTY && process.stdout.isTTY;
@@ -133673,6 +134102,7 @@ function InstallProgress({
133673
134102
  // src/cli/components/AccountView.tsx
133674
134103
  var import_react29 = __toESM(require_react(), 1);
133675
134104
  init_fleet_credentials();
134105
+ init_credential_profile_command();
133676
134106
  init_sign_in();
133677
134107
  var jsx_dev_runtime6 = __toESM(require_jsx_dev_runtime(), 1);
133678
134108
  var SLASH_COMMANDS = [
@@ -133732,7 +134162,7 @@ function AccountView({ action, argument, onDone }) {
133732
134162
  });
133733
134163
  return;
133734
134164
  }
133735
- const target = resolveSkillsSignInOrigin(process.env, {}, argument);
134165
+ const target = captureSkillsSignInTarget(process.env, {}, argument);
133736
134166
  const refusal3 = gatewaySignInRefusal(target);
133737
134167
  if (refusal3)
133738
134168
  throw refusal3;
@@ -133743,13 +134173,16 @@ function AccountView({ action, argument, onDone }) {
133743
134173
  update2({ kind: "waiting", userCode: start.userCode, url: url2, origin: target.origin });
133744
134174
  openVerificationPage(url2, target.origin);
133745
134175
  const outcome = await pollDeviceAuthorization({
133746
- poll: () => pollDeviceToken(target.origin, start.deviceCode),
134176
+ poll: () => {
134177
+ target.unchanged?.();
134178
+ return pollDeviceToken(target.origin, start.deviceCode);
134179
+ },
133747
134180
  intervalSeconds: start.interval,
133748
134181
  deadline: Date.now() + start.expiresIn * 1000,
133749
134182
  signal: controller.signal
133750
134183
  });
133751
134184
  if (outcome.status === "authorized") {
133752
- await persistSignIn(outcome.result, target.origin);
134185
+ await persistSignIn(outcome.result, target.origin, process.env, "sign-in", target.unchanged);
133753
134186
  const email4 = outcome.result.user?.email;
133754
134187
  update2({
133755
134188
  kind: "done",
@@ -133757,16 +134190,17 @@ function AccountView({ action, argument, onDone }) {
133757
134190
  lines: [
133758
134191
  { text: email4 ? `Signed in as ${email4}` : "Signed in", tone: "good" },
133759
134192
  { text: `Server: ${target.origin}`, tone: "dim" },
133760
- { text: "Register Skills with your agents from a shell: skills setup agents", tone: "dim" }
134193
+ { text: `Register Skills with your agents from a shell: ${skillsProfileCommand("setup agents", process.env, target.origin)}`, tone: "dim" }
133761
134194
  ]
133762
134195
  });
133763
134196
  return;
133764
134197
  }
134198
+ const retry = argument !== undefined ? `/login ${target.origin}` : "/login";
133765
134199
  const ended = {
133766
- expired: "The sign-in code expired before it was approved. Type /login to start again.",
133767
- invalid: "The server no longer recognises this sign-in code. Type /login to start again.",
134200
+ expired: `The sign-in code expired before it was approved. Type ${retry} to start again.`,
134201
+ invalid: `The server no longer recognises this sign-in code. Type ${retry} to start again.`,
133768
134202
  denied: "Sign-in was denied in the browser.",
133769
- timeout: "Sign-in timed out. Type /login to start again.",
134203
+ timeout: `Sign-in timed out. Type ${retry} to start again.`,
133770
134204
  cancelled: "Sign-in cancelled."
133771
134205
  }[outcome.status];
133772
134206
  update2({ kind: "done", changed: false, lines: [{ text: ended, tone: "bad" }] });