agents-inc 0.172.0 → 0.173.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +14 -0
- package/dist/{chunk-MBIOZ5LW.js → chunk-2RTBSLSR.js} +2 -2
- package/dist/{chunk-255DGUCH.js → chunk-3N4FSTVX.js} +12 -6
- package/dist/{chunk-255DGUCH.js.map → chunk-3N4FSTVX.js.map} +1 -1
- package/dist/{chunk-5MGRHS2G.js → chunk-AARQBW5L.js} +22 -12
- package/dist/chunk-AARQBW5L.js.map +1 -0
- package/dist/{chunk-NISWBQNS.js → chunk-BRZA7ZCX.js} +3 -3
- package/dist/{chunk-LUKDDHSI.js → chunk-EHJIQDXR.js} +2 -2
- package/dist/{chunk-MOL2J5HS.js → chunk-F437ICEG.js} +2 -2
- package/dist/{chunk-KCLBLK3F.js → chunk-ITQF35UQ.js} +3 -3
- package/dist/{chunk-7ZOWSCAO.js → chunk-LJQXQTFC.js} +2 -2
- package/dist/{chunk-6LUTY35Q.js → chunk-Q4UNHVPX.js} +4 -4
- package/dist/{chunk-33JICQD5.js → chunk-Q6WRR4BN.js} +4 -5
- package/dist/{chunk-33JICQD5.js.map → chunk-Q6WRR4BN.js.map} +1 -1
- package/dist/{chunk-5PPB6HT6.js → chunk-SPQSNZMM.js} +2 -2
- package/dist/{chunk-Y23MP2OC.js → chunk-VR6QTK5Z.js} +3 -3
- package/dist/{chunk-6CRA46YO.js → chunk-VSPC74SS.js} +41 -19
- package/dist/chunk-VSPC74SS.js.map +1 -0
- package/dist/{chunk-VILFCMRN.js → chunk-WVFBBZEP.js} +252 -102
- package/dist/chunk-WVFBBZEP.js.map +1 -0
- package/dist/commands/build/marketplace.js +2 -2
- package/dist/commands/build/plugins.js +4 -4
- package/dist/commands/compile.js +10 -10
- package/dist/commands/doctor.js +31 -13
- package/dist/commands/doctor.js.map +1 -1
- package/dist/commands/edit.js +13 -13
- package/dist/commands/eject.js +23 -28
- package/dist/commands/eject.js.map +1 -1
- package/dist/commands/init.js +12 -12
- package/dist/commands/list.js +3 -3
- package/dist/commands/new/marketplace.js +2 -2
- package/dist/commands/search.js +7 -7
- package/dist/commands/share.js +6 -6
- package/dist/commands/uninstall.js +45 -41
- package/dist/commands/uninstall.js.map +1 -1
- package/dist/commands/update.js +4 -4
- package/dist/components/common/summary-panel.js +1 -1
- package/dist/hooks/init.js +29 -20
- package/dist/hooks/init.js.map +1 -1
- package/dist/load-agent-defs-E67DSYTN.js +14 -0
- package/dist/{recompile-project-agents-5A44NJRD.js → recompile-project-agents-6G6M2RS6.js} +6 -6
- package/dist/{source-loader-LQNRI5UZ.js → source-loader-W7XCNKNA.js} +2 -2
- package/package.json +1 -1
- package/dist/chunk-5MGRHS2G.js.map +0 -1
- package/dist/chunk-6CRA46YO.js.map +0 -1
- package/dist/chunk-VILFCMRN.js.map +0 -1
- package/dist/load-agent-defs-54VIKN4T.js +0 -14
- /package/dist/{chunk-MBIOZ5LW.js.map → chunk-2RTBSLSR.js.map} +0 -0
- /package/dist/{chunk-NISWBQNS.js.map → chunk-BRZA7ZCX.js.map} +0 -0
- /package/dist/{chunk-LUKDDHSI.js.map → chunk-EHJIQDXR.js.map} +0 -0
- /package/dist/{chunk-MOL2J5HS.js.map → chunk-F437ICEG.js.map} +0 -0
- /package/dist/{chunk-KCLBLK3F.js.map → chunk-ITQF35UQ.js.map} +0 -0
- /package/dist/{chunk-7ZOWSCAO.js.map → chunk-LJQXQTFC.js.map} +0 -0
- /package/dist/{chunk-6LUTY35Q.js.map → chunk-Q4UNHVPX.js.map} +0 -0
- /package/dist/{chunk-5PPB6HT6.js.map → chunk-SPQSNZMM.js.map} +0 -0
- /package/dist/{chunk-Y23MP2OC.js.map → chunk-VR6QTK5Z.js.map} +0 -0
- /package/dist/{load-agent-defs-54VIKN4T.js.map → load-agent-defs-E67DSYTN.js.map} +0 -0
- /package/dist/{recompile-project-agents-5A44NJRD.js.map → recompile-project-agents-6G6M2RS6.js.map} +0 -0
- /package/dist/{source-loader-LQNRI5UZ.js.map → source-loader-W7XCNKNA.js.map} +0 -0
package/CHANGELOG.md
CHANGED
|
@@ -7,6 +7,20 @@ Each release has detailed notes in its own file under [`changelogs/`](./changelo
|
|
|
7
7
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
|
|
8
8
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
9
9
|
|
|
10
|
+
## [0.173.0] - 2026-10-23
|
|
11
|
+
|
|
12
|
+
**`doctor` downloads each marketplace on every run, the editor keeps a saved configuration per marketplace and its stack-switch question waits for the stack, and a sub-agent goes off with its last skill**
|
|
13
|
+
|
|
14
|
+
- REPO-44:
|
|
15
|
+
- The editor keeps a saved configuration per marketplace: loading another opens its own and leaves the one on screen saved with its marketplace, and a saved stack built on another marketplace loads that marketplace first.
|
|
16
|
+
- The question before an account's saved stack replaces changes waits for the stack and offers Retry when it cannot load. A sub-agent whose last skill goes switches off with the toast on a link the CLI minted.
|
|
17
|
+
- `doctor` passes a project holding a Claude and a Codex installation, and `doctor` and `uninstall` use the project's own provider's global where a home holds both. A marketplace skill with no `displayName` is skipped with a warning and the rest of the marketplace loads.
|
|
18
|
+
- CLI-925: `doctor` downloads each marketplace on every run, fails its row when only giget's saved tarball came back, and says when it replaced a saved copy that differed.
|
|
19
|
+
- CLI-915: the editor's preview shows a link's own description over its stack's, as the install does.
|
|
20
|
+
- CLI-865: the panel and terminal-poll specs wait for their settled result instead of sampling once after a fixed delay.
|
|
21
|
+
|
|
22
|
+
See [changelogs/0.173.0.md](./changelogs/0.173.0.md) for full details.
|
|
23
|
+
|
|
10
24
|
## [0.172.0] - 2026-10-22
|
|
11
25
|
|
|
12
26
|
**`init --from`, `edit --from` and `uninstall` show the summary panel at the question, the editor names the sub-agents a skill switches and holds a project link's global entries, links are version 7, and agentsinc.sh/ opens the editor**
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
import {
|
|
3
3
|
chooseProviderForThisRun,
|
|
4
4
|
detectInstallations
|
|
5
|
-
} from "./chunk-
|
|
5
|
+
} from "./chunk-WVFBBZEP.js";
|
|
6
6
|
import {
|
|
7
7
|
CLI_INVOKE_COMMAND,
|
|
8
8
|
EDITOR_URL,
|
|
@@ -79,4 +79,4 @@ export {
|
|
|
79
79
|
ambiguityFinding,
|
|
80
80
|
otherInstallationsInThisScope
|
|
81
81
|
};
|
|
82
|
-
//# sourceMappingURL=chunk-
|
|
82
|
+
//# sourceMappingURL=chunk-2RTBSLSR.js.map
|
|
@@ -14,7 +14,7 @@ import {
|
|
|
14
14
|
readFileOptional,
|
|
15
15
|
unexpressibleOnCodexMessage,
|
|
16
16
|
writeFile
|
|
17
|
-
} from "./chunk-
|
|
17
|
+
} from "./chunk-WVFBBZEP.js";
|
|
18
18
|
|
|
19
19
|
// src/cli/lib/hosts/claude-project-trust.ts
|
|
20
20
|
import path from "path";
|
|
@@ -226,13 +226,19 @@ async function holdsProjectRoles(projectDir) {
|
|
|
226
226
|
|
|
227
227
|
// src/cli/lib/hosts/host-compile-notices.ts
|
|
228
228
|
async function hostCompileNotices(provider, projectDir) {
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
229
|
+
switch (provider) {
|
|
230
|
+
case "claude":
|
|
231
|
+
return claudeCompileNotices(provider, projectDir);
|
|
232
|
+
case "codex":
|
|
233
|
+
return codexCompileNotices(provider, projectDir);
|
|
234
|
+
default: {
|
|
235
|
+
const _exhaustive = provider;
|
|
236
|
+
return _exhaustive;
|
|
237
|
+
}
|
|
238
|
+
}
|
|
233
239
|
}
|
|
234
240
|
|
|
235
241
|
export {
|
|
236
242
|
hostCompileNotices
|
|
237
243
|
};
|
|
238
|
-
//# sourceMappingURL=chunk-
|
|
244
|
+
//# sourceMappingURL=chunk-3N4FSTVX.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/cli/lib/hosts/claude-project-trust.ts","../src/cli/lib/hosts/codex-project-trust.ts","../src/cli/lib/hosts/codex-compile-notices.ts","../src/cli/lib/hosts/host-compile-notices.ts"],"sourcesContent":["import path from \"path\";\nimport { realpath } from \"fs/promises\";\n\nimport { z } from \"zod\";\n\nimport { agentCodec, agentsDir, claudeStateFile } from \"../installation/install-layout.js\";\nimport { isHomeDirectory } from \"../installation/is-home-directory.js\";\nimport { fileExists, glob, readFile, readFileOptional } from \"../../utils/fs.js\";\nimport { extractFrontmatter } from \"../../utils/frontmatter.js\";\nimport type { Provider } from \"../../consts.js\";\n\n/**\n * Warns when Claude Code will drop a project sub-agent's hooks, on every event: project hooks run\n * only once `~/.claude.json` records `projects[<key>].hasTrustDialogAccepted`, keyed by the git\n * repository root (a linked worktree's main checkout). Reads that state, never writes it.\n */\n\nconst claudeStateSchema = z.object({ projects: z.record(z.string(), z.unknown()) });\n\nconst trustedProjectSchema = z.object({ hasTrustDialogAccepted: z.literal(true) });\n\n/** Claude Code reads only a top-level `hooks:` key: event name to its definitions. */\nconst declaredHooksSchema = z.object({ hooks: z.record(z.string(), z.array(z.unknown())) });\n\nconst GIT_ENTRY = \".git\";\nconst GITDIR_PREFIX = \"gitdir:\";\nconst COMMONDIR_FILE = \"commondir\";\nconst BACK_LINK_FILE = \"gitdir\";\nconst WORKTREES_DIR = \"worktrees\";\n\n/** \"never asks\": a folder above is trusted, so no prompt appears and only the record can fix it. */\ntype ClaudeTrust =\n | { readonly kind: \"trusted\" }\n | { readonly kind: \"asks\" }\n | { readonly kind: \"never asks\"; readonly recordKey: string };\n\ntype TrustRecord = (folder: string) => boolean;\n\n/** Empty from the home directory: `~/.claude/agents/` is trusted unconditionally. */\nexport async function claudeCompileNotices(\n provider: Provider,\n projectDir: string,\n): Promise<string[]> {\n if (provider !== \"claude\") return [];\n if (isHomeDirectory(projectDir)) return [];\n\n const agentsWithHooks = await countProjectAgentsDeclaringHooks(projectDir);\n if (agentsWithHooks === 0) return [];\n\n const trust = await claudeTrustOf(projectDir);\n switch (trust.kind) {\n case \"trusted\":\n return [];\n case \"asks\":\n return [claudeProjectNeedsTrustMessage(projectDir, agentsWithHooks)];\n case \"never asks\":\n return [claudeProjectNeverAskedMessage(trust.recordKey, agentsWithHooks)];\n default: {\n const _exhaustive: never = trust;\n return _exhaustive;\n }\n }\n}\n\nexport function claudeProjectNeedsTrustMessage(projectDir: string, count: number): string {\n return (\n `Claude Code runs a project sub-agent's hooks only once you trust the folder: open Claude ` +\n `Code in ${projectDir} and accept the trust prompt. Until then, ${hooksOf(count)} will not ` +\n `run, and nothing will say so.`\n );\n}\n\nexport function claudeProjectNeverAskedMessage(recordKey: string, count: number): string {\n return (\n `Claude Code runs ${hooksOf(count)} only once you trust the folder, and will not ask here: ` +\n `set projects[${JSON.stringify(recordKey)}].hasTrustDialogAccepted to true in ` +\n `${claudeStateFile()}.`\n );\n}\n\nfunction hooksOf(count: number): string {\n return count === 1 ? \"1 sub-agent's hooks\" : `${count} sub-agents' hooks`;\n}\n\nasync function claudeTrustOf(projectDir: string): Promise<ClaudeTrust> {\n const [isTrusted, repositoryRoot] = await Promise.all([\n trustRecord(),\n gitRepositoryRoot(projectDir),\n ]);\n const recordKey =\n repositoryRoot === undefined ? projectDir : await canonicalRepositoryRoot(repositoryRoot);\n if (isTrusted(recordKey)) return { kind: \"trusted\" };\n\n const promptSuppressed = foldersUpTo(projectDir, repositoryRoot).some(isTrusted);\n return promptSuppressed ? { kind: \"never asks\", recordKey } : { kind: \"asks\" };\n}\n\n/** Unreadable counts as untrusted: a wrong \"untrusted\" costs one line of advice. */\nasync function trustRecord(): Promise<TrustRecord> {\n const stateFile = claudeStateFile();\n if (!(await fileExists(stateFile))) return () => false;\n\n const state = claudeStateSchema.safeParse(parsedOrUndefined(await readFile(stateFile)));\n if (!state.success) return () => false;\n\n const { projects } = state.data;\n return (folder) => trustedProjectSchema.safeParse(projects[folder]).success;\n}\n\nfunction parsedOrUndefined(json: string): unknown {\n try {\n return JSON.parse(json);\n } catch {\n return undefined;\n }\n}\n\nfunction foldersUpTo(folder: string, top?: string): string[] {\n const parent = path.dirname(folder);\n if (folder === top || parent === folder) return [folder];\n return [folder, ...foldersUpTo(parent, top)];\n}\n\nasync function gitRepositoryRoot(folder: string): Promise<string | undefined> {\n const candidates = foldersUpTo(folder);\n const holdsGit = await Promise.all(\n candidates.map((candidate) => fileExists(path.join(candidate, GIT_ENTRY))),\n );\n return candidates.find((_, index) => holdsGit[index]);\n}\n\n/**\n * A linked worktree (`.git` file pointing into `<main>/.git/worktrees/`, which points back) is\n * keyed by its main checkout; anything else by `root` itself.\n */\nasync function canonicalRepositoryRoot(root: string): Promise<string> {\n // A `.git` directory reads as empty, as a missing file does.\n const pointer = (await readFileOptional(path.join(root, GIT_ENTRY))).trim();\n if (!pointer.startsWith(GITDIR_PREFIX)) return root;\n\n const gitDir = path.resolve(root, pointer.slice(GITDIR_PREFIX.length).trim());\n const [commonDir, backLink] = await Promise.all([\n pathRecordedIn(gitDir, COMMONDIR_FILE),\n pathRecordedIn(gitDir, BACK_LINK_FILE),\n ]);\n const isLinkedWorktree =\n path.dirname(gitDir) === path.join(commonDir, WORKTREES_DIR) &&\n (await pointsBackAt(backLink, root));\n if (!isLinkedWorktree) return root;\n\n // A worktree of a bare repository is keyed by the bare repository's own folder.\n return path.basename(commonDir) === GIT_ENTRY ? path.dirname(commonDir) : commonDir;\n}\n\nasync function pathRecordedIn(dir: string, file: string): Promise<string> {\n return path.resolve(dir, (await readFileOptional(path.join(dir, file))).trim());\n}\n\nasync function pointsBackAt(backLink: string, root: string): Promise<boolean> {\n const [linked, realRoot] = await Promise.all([\n realpathOrUndefined(backLink),\n realpathOrUndefined(root),\n ]);\n return realRoot !== undefined && linked === path.join(realRoot, GIT_ENTRY);\n}\n\nasync function realpathOrUndefined(file: string): Promise<string | undefined> {\n try {\n return await realpath(file);\n } catch {\n return undefined;\n }\n}\n\nasync function countProjectAgentsDeclaringHooks(projectDir: string): Promise<number> {\n const dir = agentsDir(\"claude\", \"project\", projectDir);\n const files = await glob(agentCodec(\"claude\").listGlob, dir);\n const agents = await Promise.all(files.map((file) => readFile(path.join(dir, file))));\n return agents.filter(declaresAHook).length;\n}\n\n/** An event with no definition runs nothing, so it is not a hook to warn about. */\nfunction declaresAHook(agentMarkdown: string): boolean {\n const frontmatter = declaredHooksSchema.safeParse(extractFrontmatter(agentMarkdown));\n return (\n frontmatter.success &&\n Object.values(frontmatter.data.hooks).some((definitions) => definitions.length > 0)\n );\n}\n","import path from \"path\";\n\nimport { codexGlobalConfigFile } from \"../installation/install-layout.js\";\nimport { ensureDir, fileExists, readFile, writeFile } from \"../../utils/fs.js\";\n\n/**\n * Codex reads `<project>/.codex/agents/*.toml` only while the GLOBAL `config.toml` holds\n * `[projects.\"<abs path>\"] trust_level = \"trusted\"`, failing silently otherwise. The install writes\n * that entry and says so, but never overrides a level the user already set.\n */\n\nconst TRUST_KEY = \"trust_level\";\nconst TRUSTED = \"trusted\";\nconst TRUST_ASSIGNMENT = `${TRUST_KEY} = \"${TRUSTED}\"`;\n\nexport type CodexProjectTrust =\n | { readonly kind: \"already trusted\" }\n | { readonly kind: \"trusted now\"; readonly configFile: string }\n | {\n readonly kind: \"left as the user set it\";\n readonly configFile: string;\n readonly level: string;\n };\n\n/**\n * Merged into the user's file, never rewritten: a second table for the same path would make Codex\n * refuse the whole file. `path.resolve` gives the one spelling Codex matches (no trailing slash).\n */\nexport async function trustCodexProject(projectDir: string): Promise<CodexProjectTrust> {\n const configFile = codexGlobalConfigFile();\n const dir = path.resolve(projectDir);\n const config = (await fileExists(configFile)) ? await readFile(configFile) : \"\";\n\n if (declaresTrust(config, dir)) return { kind: \"already trusted\" };\n\n const level = declaredLevel(config, dir);\n if (level !== undefined) return { kind: \"left as the user set it\", configFile, level };\n\n await ensureDir(path.dirname(configFile));\n await writeFile(configFile, withTrustFor(config, dir));\n return { kind: \"trusted now\", configFile };\n}\n\nexport function codexProjectTrustMessage(\n projectDir: string,\n trust: CodexProjectTrust,\n): string | undefined {\n const table = projectTableHeader(path.resolve(projectDir));\n\n switch (trust.kind) {\n case \"already trusted\":\n return undefined;\n case \"trusted now\":\n return (\n `Trusted this project in your Codex configuration, so Codex reads its sub-agents: added ` +\n `${table} with ${TRUST_KEY} = \"${TRUSTED}\" to ${trust.configFile}.`\n );\n case \"left as the user set it\":\n return (\n `Codex reads this project's sub-agents only once it is trusted, and ${trust.configFile} ` +\n `sets ${TRUST_KEY} = \"${trust.level}\" under ${table}. Left as you set it — change it to ` +\n `\"${TRUSTED}\" for Codex to read them.`\n );\n default: {\n const _exhaustive: never = trust;\n return _exhaustive;\n }\n }\n}\n\n/** Hand-read, not TOML-parsed; any other spelling reads as untrusted, the safe direction. */\nfunction declaresTrust(config: string, projectDir: string): boolean {\n return linesForProject(config, projectDir).includes(TRUST_ASSIGNMENT);\n}\n\nconst TRUST_LEVEL_LINE = new RegExp(`^${TRUST_KEY}\\\\s*=\\\\s*\"([^\"]*)\"$`);\n\n/** The user's own `trust_level` for this project, which is never overwritten. */\nfunction declaredLevel(config: string, projectDir: string): string | undefined {\n return linesForProject(config, projectDir)\n .map((line) => TRUST_LEVEL_LINE.exec(line)?.[1])\n .find((level) => level !== undefined);\n}\n\n/** Trimmed: the lines under the project's table header, then its dotted keys with the prefix cut. */\nfunction linesForProject(config: string, projectDir: string): string[] {\n const lines = config.split(\"\\n\").map((line) => line.trim());\n const dottedPrefix = `projects.\"${projectDir}\".`;\n const dotted = lines\n .filter((line) => line.startsWith(dottedPrefix))\n .map((line) => line.slice(dottedPrefix.length));\n\n return [...linesUnderProjectTable(lines, projectDir), ...dotted];\n}\n\nfunction linesUnderProjectTable(lines: readonly string[], projectDir: string): readonly string[] {\n const header = lines.indexOf(projectTableHeader(projectDir));\n if (header === -1) return [];\n\n const after = lines.slice(header + 1);\n const nextTable = after.findIndex(opensATable);\n return nextTable === -1 ? after : after.slice(0, nextTable);\n}\n\nfunction opensATable(line: string): boolean {\n return line.startsWith(\"[\");\n}\n\nfunction projectTableHeader(projectDir: string): string {\n return `[projects.\"${projectDir}\"]`;\n}\n\nfunction withTrustFor(config: string, projectDir: string): string {\n const lines = config.split(\"\\n\");\n const header = lines.findIndex((line) => line.trim() === projectTableHeader(projectDir));\n\n if (header !== -1) {\n return [...lines.slice(0, header + 1), TRUST_ASSIGNMENT, ...lines.slice(header + 1)].join(\"\\n\");\n }\n\n const theirs = config.trimEnd();\n const table = `${projectTableHeader(projectDir)}\\n${TRUST_ASSIGNMENT}\\n`;\n return theirs === \"\" ? table : `${theirs}\\n\\n${table}`;\n}\n","import {\n agentsLeftOutOfCodexMessage,\n unexpressibleOnCodexMessage,\n} from \"@workspace/compile/agent-source\";\n\nimport { codexProjectTrustMessage, trustCodexProject } from \"./codex-project-trust.js\";\nimport { agentCodec, agentsDir } from \"../installation/install-layout.js\";\nimport { glob } from \"../../utils/fs.js\";\nimport type { Provider } from \"../../consts.js\";\n\n/** Once per run, not per sub-agent or scope: each notice is true of the whole installation. */\nexport async function codexCompileNotices(\n provider: Provider,\n projectDir: string,\n): Promise<string[]> {\n if (provider !== \"codex\") return [];\n\n return [\n agentsLeftOutOfCodexMessage(),\n unexpressibleOnCodexMessage(),\n ...(await trustNotice(projectDir)),\n ];\n}\n\n/** Only when role files exist: trusting a project with nothing for Codex to read grants nothing. */\nasync function trustNotice(projectDir: string): Promise<string[]> {\n if (!(await holdsProjectRoles(projectDir))) return [];\n\n const said = codexProjectTrustMessage(projectDir, await trustCodexProject(projectDir));\n return said === undefined ? [] : [said];\n}\n\nasync function holdsProjectRoles(projectDir: string): Promise<boolean> {\n const roles = await glob(agentCodec(\"codex\").listGlob, agentsDir(\"codex\", \"project\", projectDir));\n\n return roles.length > 0;\n}\n","import { claudeCompileNotices } from \"./claude-project-trust.js\";\nimport { codexCompileNotices } from \"./codex-compile-notices.js\";\nimport type { Provider } from \"../../consts.js\";\n\n/** The one source `init` and `compile` share, so they cannot say different things. */\nexport async function hostCompileNotices(\n provider: Provider,\n projectDir: string,\n): Promise<string[]> {\n return [\n ...(await codexCompileNotices(provider, projectDir)),\n ...(await claudeCompileNotices(provider, projectDir)),\n ];\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;AAAA,OAAO,UAAU;AACjB,SAAS,gBAAgB;AAEzB,SAAS,SAAS;AAclB,IAAM,oBAAoB,EAAE,OAAO,EAAE,UAAU,EAAE,OAAO,EAAE,OAAO,GAAG,EAAE,QAAQ,CAAC,EAAE,CAAC;AAElF,IAAM,uBAAuB,EAAE,OAAO,EAAE,wBAAwB,EAAE,QAAQ,IAAI,EAAE,CAAC;AAGjF,IAAM,sBAAsB,EAAE,OAAO,EAAE,OAAO,EAAE,OAAO,EAAE,OAAO,GAAG,EAAE,MAAM,EAAE,QAAQ,CAAC,CAAC,EAAE,CAAC;AAE1F,IAAM,YAAY;AAClB,IAAM,gBAAgB;AACtB,IAAM,iBAAiB;AACvB,IAAM,iBAAiB;AACvB,IAAM,gBAAgB;AAWtB,eAAsB,qBACpB,UACA,YACmB;AACnB,MAAI,aAAa,SAAU,QAAO,CAAC;AACnC,MAAI,gBAAgB,UAAU,EAAG,QAAO,CAAC;AAEzC,QAAM,kBAAkB,MAAM,iCAAiC,UAAU;AACzE,MAAI,oBAAoB,EAAG,QAAO,CAAC;AAEnC,QAAM,QAAQ,MAAM,cAAc,UAAU;AAC5C,UAAQ,MAAM,MAAM;AAAA,IAClB,KAAK;AACH,aAAO,CAAC;AAAA,IACV,KAAK;AACH,aAAO,CAAC,+BAA+B,YAAY,eAAe,CAAC;AAAA,IACrE,KAAK;AACH,aAAO,CAAC,+BAA+B,MAAM,WAAW,eAAe,CAAC;AAAA,IAC1E,SAAS;AACP,YAAM,cAAqB;AAC3B,aAAO;AAAA,IACT;AAAA,EACF;AACF;AAEO,SAAS,+BAA+B,YAAoB,OAAuB;AACxF,SACE,oGACW,UAAU,6CAA6C,QAAQ,KAAK,CAAC;AAGpF;AAEO,SAAS,+BAA+B,WAAmB,OAAuB;AACvF,SACE,oBAAoB,QAAQ,KAAK,CAAC,wEAClB,KAAK,UAAU,SAAS,CAAC,uCACtC,gBAAgB,CAAC;AAExB;AAEA,SAAS,QAAQ,OAAuB;AACtC,SAAO,UAAU,IAAI,wBAAwB,GAAG,KAAK;AACvD;AAEA,eAAe,cAAc,YAA0C;AACrE,QAAM,CAAC,WAAW,cAAc,IAAI,MAAM,QAAQ,IAAI;AAAA,IACpD,YAAY;AAAA,IACZ,kBAAkB,UAAU;AAAA,EAC9B,CAAC;AACD,QAAM,YACJ,mBAAmB,SAAY,aAAa,MAAM,wBAAwB,cAAc;AAC1F,MAAI,UAAU,SAAS,EAAG,QAAO,EAAE,MAAM,UAAU;AAEnD,QAAM,mBAAmB,YAAY,YAAY,cAAc,EAAE,KAAK,SAAS;AAC/E,SAAO,mBAAmB,EAAE,MAAM,cAAc,UAAU,IAAI,EAAE,MAAM,OAAO;AAC/E;AAGA,eAAe,cAAoC;AACjD,QAAM,YAAY,gBAAgB;AAClC,MAAI,CAAE,MAAM,WAAW,SAAS,EAAI,QAAO,MAAM;AAEjD,QAAM,QAAQ,kBAAkB,UAAU,kBAAkB,MAAM,SAAS,SAAS,CAAC,CAAC;AACtF,MAAI,CAAC,MAAM,QAAS,QAAO,MAAM;AAEjC,QAAM,EAAE,SAAS,IAAI,MAAM;AAC3B,SAAO,CAAC,WAAW,qBAAqB,UAAU,SAAS,MAAM,CAAC,EAAE;AACtE;AAEA,SAAS,kBAAkB,MAAuB;AAChD,MAAI;AACF,WAAO,KAAK,MAAM,IAAI;AAAA,EACxB,QAAQ;AACN,WAAO;AAAA,EACT;AACF;AAEA,SAAS,YAAY,QAAgB,KAAwB;AAC3D,QAAM,SAAS,KAAK,QAAQ,MAAM;AAClC,MAAI,WAAW,OAAO,WAAW,OAAQ,QAAO,CAAC,MAAM;AACvD,SAAO,CAAC,QAAQ,GAAG,YAAY,QAAQ,GAAG,CAAC;AAC7C;AAEA,eAAe,kBAAkB,QAA6C;AAC5E,QAAM,aAAa,YAAY,MAAM;AACrC,QAAM,WAAW,MAAM,QAAQ;AAAA,IAC7B,WAAW,IAAI,CAAC,cAAc,WAAW,KAAK,KAAK,WAAW,SAAS,CAAC,CAAC;AAAA,EAC3E;AACA,SAAO,WAAW,KAAK,CAAC,GAAG,UAAU,SAAS,KAAK,CAAC;AACtD;AAMA,eAAe,wBAAwB,MAA+B;AAEpE,QAAM,WAAW,MAAM,iBAAiB,KAAK,KAAK,MAAM,SAAS,CAAC,GAAG,KAAK;AAC1E,MAAI,CAAC,QAAQ,WAAW,aAAa,EAAG,QAAO;AAE/C,QAAM,SAAS,KAAK,QAAQ,MAAM,QAAQ,MAAM,cAAc,MAAM,EAAE,KAAK,CAAC;AAC5E,QAAM,CAAC,WAAW,QAAQ,IAAI,MAAM,QAAQ,IAAI;AAAA,IAC9C,eAAe,QAAQ,cAAc;AAAA,IACrC,eAAe,QAAQ,cAAc;AAAA,EACvC,CAAC;AACD,QAAM,mBACJ,KAAK,QAAQ,MAAM,MAAM,KAAK,KAAK,WAAW,aAAa,KAC1D,MAAM,aAAa,UAAU,IAAI;AACpC,MAAI,CAAC,iBAAkB,QAAO;AAG9B,SAAO,KAAK,SAAS,SAAS,MAAM,YAAY,KAAK,QAAQ,SAAS,IAAI;AAC5E;AAEA,eAAe,eAAe,KAAa,MAA+B;AACxE,SAAO,KAAK,QAAQ,MAAM,MAAM,iBAAiB,KAAK,KAAK,KAAK,IAAI,CAAC,GAAG,KAAK,CAAC;AAChF;AAEA,eAAe,aAAa,UAAkB,MAAgC;AAC5E,QAAM,CAAC,QAAQ,QAAQ,IAAI,MAAM,QAAQ,IAAI;AAAA,IAC3C,oBAAoB,QAAQ;AAAA,IAC5B,oBAAoB,IAAI;AAAA,EAC1B,CAAC;AACD,SAAO,aAAa,UAAa,WAAW,KAAK,KAAK,UAAU,SAAS;AAC3E;AAEA,eAAe,oBAAoB,MAA2C;AAC5E,MAAI;AACF,WAAO,MAAM,SAAS,IAAI;AAAA,EAC5B,QAAQ;AACN,WAAO;AAAA,EACT;AACF;AAEA,eAAe,iCAAiC,YAAqC;AACnF,QAAM,MAAM,UAAU,UAAU,WAAW,UAAU;AACrD,QAAM,QAAQ,MAAM,KAAK,WAAW,QAAQ,EAAE,UAAU,GAAG;AAC3D,QAAM,SAAS,MAAM,QAAQ,IAAI,MAAM,IAAI,CAAC,SAAS,SAAS,KAAK,KAAK,KAAK,IAAI,CAAC,CAAC,CAAC;AACpF,SAAO,OAAO,OAAO,aAAa,EAAE;AACtC;AAGA,SAAS,cAAc,eAAgC;AACrD,QAAM,cAAc,oBAAoB,UAAU,mBAAmB,aAAa,CAAC;AACnF,SACE,YAAY,WACZ,OAAO,OAAO,YAAY,KAAK,KAAK,EAAE,KAAK,CAAC,gBAAgB,YAAY,SAAS,CAAC;AAEtF;;;AC5LA,OAAOA,WAAU;AAWjB,IAAM,YAAY;AAClB,IAAM,UAAU;AAChB,IAAM,mBAAmB,GAAG,SAAS,OAAO,OAAO;AAenD,eAAsB,kBAAkB,YAAgD;AACtF,QAAM,aAAa,sBAAsB;AACzC,QAAM,MAAMC,MAAK,QAAQ,UAAU;AACnC,QAAM,SAAU,MAAM,WAAW,UAAU,IAAK,MAAM,SAAS,UAAU,IAAI;AAE7E,MAAI,cAAc,QAAQ,GAAG,EAAG,QAAO,EAAE,MAAM,kBAAkB;AAEjE,QAAM,QAAQ,cAAc,QAAQ,GAAG;AACvC,MAAI,UAAU,OAAW,QAAO,EAAE,MAAM,2BAA2B,YAAY,MAAM;AAErF,QAAM,UAAUA,MAAK,QAAQ,UAAU,CAAC;AACxC,QAAM,UAAU,YAAY,aAAa,QAAQ,GAAG,CAAC;AACrD,SAAO,EAAE,MAAM,eAAe,WAAW;AAC3C;AAEO,SAAS,yBACd,YACA,OACoB;AACpB,QAAM,QAAQ,mBAAmBA,MAAK,QAAQ,UAAU,CAAC;AAEzD,UAAQ,MAAM,MAAM;AAAA,IAClB,KAAK;AACH,aAAO;AAAA,IACT,KAAK;AACH,aACE,0FACG,KAAK,SAAS,SAAS,OAAO,OAAO,QAAQ,MAAM,UAAU;AAAA,IAEpE,KAAK;AACH,aACE,sEAAsE,MAAM,UAAU,SAC9E,SAAS,OAAO,MAAM,KAAK,WAAW,KAAK,6CAC/C,OAAO;AAAA,IAEf,SAAS;AACP,YAAM,cAAqB;AAC3B,aAAO;AAAA,IACT;AAAA,EACF;AACF;AAGA,SAAS,cAAc,QAAgB,YAA6B;AAClE,SAAO,gBAAgB,QAAQ,UAAU,EAAE,SAAS,gBAAgB;AACtE;AAEA,IAAM,mBAAmB,IAAI,OAAO,IAAI,SAAS,qBAAqB;AAGtE,SAAS,cAAc,QAAgB,YAAwC;AAC7E,SAAO,gBAAgB,QAAQ,UAAU,EACtC,IAAI,CAAC,SAAS,iBAAiB,KAAK,IAAI,IAAI,CAAC,CAAC,EAC9C,KAAK,CAAC,UAAU,UAAU,MAAS;AACxC;AAGA,SAAS,gBAAgB,QAAgB,YAA8B;AACrE,QAAM,QAAQ,OAAO,MAAM,IAAI,EAAE,IAAI,CAAC,SAAS,KAAK,KAAK,CAAC;AAC1D,QAAM,eAAe,aAAa,UAAU;AAC5C,QAAM,SAAS,MACZ,OAAO,CAAC,SAAS,KAAK,WAAW,YAAY,CAAC,EAC9C,IAAI,CAAC,SAAS,KAAK,MAAM,aAAa,MAAM,CAAC;AAEhD,SAAO,CAAC,GAAG,uBAAuB,OAAO,UAAU,GAAG,GAAG,MAAM;AACjE;AAEA,SAAS,uBAAuB,OAA0B,YAAuC;AAC/F,QAAM,SAAS,MAAM,QAAQ,mBAAmB,UAAU,CAAC;AAC3D,MAAI,WAAW,GAAI,QAAO,CAAC;AAE3B,QAAM,QAAQ,MAAM,MAAM,SAAS,CAAC;AACpC,QAAM,YAAY,MAAM,UAAU,WAAW;AAC7C,SAAO,cAAc,KAAK,QAAQ,MAAM,MAAM,GAAG,SAAS;AAC5D;AAEA,SAAS,YAAY,MAAuB;AAC1C,SAAO,KAAK,WAAW,GAAG;AAC5B;AAEA,SAAS,mBAAmB,YAA4B;AACtD,SAAO,cAAc,UAAU;AACjC;AAEA,SAAS,aAAa,QAAgB,YAA4B;AAChE,QAAM,QAAQ,OAAO,MAAM,IAAI;AAC/B,QAAM,SAAS,MAAM,UAAU,CAAC,SAAS,KAAK,KAAK,MAAM,mBAAmB,UAAU,CAAC;AAEvF,MAAI,WAAW,IAAI;AACjB,WAAO,CAAC,GAAG,MAAM,MAAM,GAAG,SAAS,CAAC,GAAG,kBAAkB,GAAG,MAAM,MAAM,SAAS,CAAC,CAAC,EAAE,KAAK,IAAI;AAAA,EAChG;AAEA,QAAM,SAAS,OAAO,QAAQ;AAC9B,QAAM,QAAQ,GAAG,mBAAmB,UAAU,CAAC;AAAA,EAAK,gBAAgB;AAAA;AACpE,SAAO,WAAW,KAAK,QAAQ,GAAG,MAAM;AAAA;AAAA,EAAO,KAAK;AACtD;;;AChHA,eAAsB,oBACpB,UACA,YACmB;AACnB,MAAI,aAAa,QAAS,QAAO,CAAC;AAElC,SAAO;AAAA,IACL,4BAA4B;AAAA,IAC5B,4BAA4B;AAAA,IAC5B,GAAI,MAAM,YAAY,UAAU;AAAA,EAClC;AACF;AAGA,eAAe,YAAY,YAAuC;AAChE,MAAI,CAAE,MAAM,kBAAkB,UAAU,EAAI,QAAO,CAAC;AAEpD,QAAM,OAAO,yBAAyB,YAAY,MAAM,kBAAkB,UAAU,CAAC;AACrF,SAAO,SAAS,SAAY,CAAC,IAAI,CAAC,IAAI;AACxC;AAEA,eAAe,kBAAkB,YAAsC;AACrE,QAAM,QAAQ,MAAM,KAAK,WAAW,OAAO,EAAE,UAAU,UAAU,SAAS,WAAW,UAAU,CAAC;AAEhG,SAAO,MAAM,SAAS;AACxB;;;AC/BA,eAAsB,mBACpB,UACA,YACmB;AACnB,SAAO;AAAA,IACL,GAAI,MAAM,oBAAoB,UAAU,UAAU;AAAA,IAClD,GAAI,MAAM,qBAAqB,UAAU,UAAU;AAAA,EACrD;AACF;","names":["path","path"]}
|
|
1
|
+
{"version":3,"sources":["../src/cli/lib/hosts/claude-project-trust.ts","../src/cli/lib/hosts/codex-project-trust.ts","../src/cli/lib/hosts/codex-compile-notices.ts","../src/cli/lib/hosts/host-compile-notices.ts"],"sourcesContent":["import path from \"path\";\nimport { realpath } from \"fs/promises\";\n\nimport { z } from \"zod\";\n\nimport { agentCodec, agentsDir, claudeStateFile } from \"../installation/install-layout.js\";\nimport { isHomeDirectory } from \"../installation/is-home-directory.js\";\nimport { fileExists, glob, readFile, readFileOptional } from \"../../utils/fs.js\";\nimport { extractFrontmatter } from \"../../utils/frontmatter.js\";\nimport type { Provider } from \"../../consts.js\";\n\n/**\n * Warns when Claude Code will drop a project sub-agent's hooks, on every event: project hooks run\n * only once `~/.claude.json` records `projects[<key>].hasTrustDialogAccepted`, keyed by the git\n * repository root (a linked worktree's main checkout). Reads that state, never writes it.\n */\n\nconst claudeStateSchema = z.object({ projects: z.record(z.string(), z.unknown()) });\n\nconst trustedProjectSchema = z.object({ hasTrustDialogAccepted: z.literal(true) });\n\n/** Claude Code reads only a top-level `hooks:` key: event name to its definitions. */\nconst declaredHooksSchema = z.object({ hooks: z.record(z.string(), z.array(z.unknown())) });\n\nconst GIT_ENTRY = \".git\";\nconst GITDIR_PREFIX = \"gitdir:\";\nconst COMMONDIR_FILE = \"commondir\";\nconst BACK_LINK_FILE = \"gitdir\";\nconst WORKTREES_DIR = \"worktrees\";\n\n/** \"never asks\": a folder above is trusted, so no prompt appears and only the record can fix it. */\ntype ClaudeTrust =\n | { readonly kind: \"trusted\" }\n | { readonly kind: \"asks\" }\n | { readonly kind: \"never asks\"; readonly recordKey: string };\n\ntype TrustRecord = (folder: string) => boolean;\n\n/** Empty from the home directory: `~/.claude/agents/` is trusted unconditionally. */\nexport async function claudeCompileNotices(\n provider: Provider,\n projectDir: string,\n): Promise<string[]> {\n if (provider !== \"claude\") return [];\n if (isHomeDirectory(projectDir)) return [];\n\n const agentsWithHooks = await countProjectAgentsDeclaringHooks(projectDir);\n if (agentsWithHooks === 0) return [];\n\n const trust = await claudeTrustOf(projectDir);\n switch (trust.kind) {\n case \"trusted\":\n return [];\n case \"asks\":\n return [claudeProjectNeedsTrustMessage(projectDir, agentsWithHooks)];\n case \"never asks\":\n return [claudeProjectNeverAskedMessage(trust.recordKey, agentsWithHooks)];\n default: {\n const _exhaustive: never = trust;\n return _exhaustive;\n }\n }\n}\n\nexport function claudeProjectNeedsTrustMessage(projectDir: string, count: number): string {\n return (\n `Claude Code runs a project sub-agent's hooks only once you trust the folder: open Claude ` +\n `Code in ${projectDir} and accept the trust prompt. Until then, ${hooksOf(count)} will not ` +\n `run, and nothing will say so.`\n );\n}\n\nexport function claudeProjectNeverAskedMessage(recordKey: string, count: number): string {\n return (\n `Claude Code runs ${hooksOf(count)} only once you trust the folder, and will not ask here: ` +\n `set projects[${JSON.stringify(recordKey)}].hasTrustDialogAccepted to true in ` +\n `${claudeStateFile()}.`\n );\n}\n\nfunction hooksOf(count: number): string {\n return count === 1 ? \"1 sub-agent's hooks\" : `${count} sub-agents' hooks`;\n}\n\nasync function claudeTrustOf(projectDir: string): Promise<ClaudeTrust> {\n const [isTrusted, repositoryRoot] = await Promise.all([\n trustRecord(),\n gitRepositoryRoot(projectDir),\n ]);\n const recordKey =\n repositoryRoot === undefined ? projectDir : await canonicalRepositoryRoot(repositoryRoot);\n if (isTrusted(recordKey)) return { kind: \"trusted\" };\n\n const promptSuppressed = foldersUpTo(projectDir, repositoryRoot).some(isTrusted);\n return promptSuppressed ? { kind: \"never asks\", recordKey } : { kind: \"asks\" };\n}\n\n/** Unreadable counts as untrusted: a wrong \"untrusted\" costs one line of advice. */\nasync function trustRecord(): Promise<TrustRecord> {\n const stateFile = claudeStateFile();\n if (!(await fileExists(stateFile))) return () => false;\n\n const state = claudeStateSchema.safeParse(parsedOrUndefined(await readFile(stateFile)));\n if (!state.success) return () => false;\n\n const { projects } = state.data;\n return (folder) => trustedProjectSchema.safeParse(projects[folder]).success;\n}\n\nfunction parsedOrUndefined(json: string): unknown {\n try {\n return JSON.parse(json);\n } catch {\n return undefined;\n }\n}\n\nfunction foldersUpTo(folder: string, top?: string): string[] {\n const parent = path.dirname(folder);\n if (folder === top || parent === folder) return [folder];\n return [folder, ...foldersUpTo(parent, top)];\n}\n\nasync function gitRepositoryRoot(folder: string): Promise<string | undefined> {\n const candidates = foldersUpTo(folder);\n const holdsGit = await Promise.all(\n candidates.map((candidate) => fileExists(path.join(candidate, GIT_ENTRY))),\n );\n return candidates.find((_, index) => holdsGit[index]);\n}\n\n/**\n * A linked worktree (`.git` file pointing into `<main>/.git/worktrees/`, which points back) is\n * keyed by its main checkout; anything else by `root` itself.\n */\nasync function canonicalRepositoryRoot(root: string): Promise<string> {\n // A `.git` directory reads as empty, as a missing file does.\n const pointer = (await readFileOptional(path.join(root, GIT_ENTRY))).trim();\n if (!pointer.startsWith(GITDIR_PREFIX)) return root;\n\n const gitDir = path.resolve(root, pointer.slice(GITDIR_PREFIX.length).trim());\n const [commonDir, backLink] = await Promise.all([\n pathRecordedIn(gitDir, COMMONDIR_FILE),\n pathRecordedIn(gitDir, BACK_LINK_FILE),\n ]);\n const isLinkedWorktree =\n path.dirname(gitDir) === path.join(commonDir, WORKTREES_DIR) &&\n (await pointsBackAt(backLink, root));\n if (!isLinkedWorktree) return root;\n\n // A worktree of a bare repository is keyed by the bare repository's own folder.\n return path.basename(commonDir) === GIT_ENTRY ? path.dirname(commonDir) : commonDir;\n}\n\nasync function pathRecordedIn(dir: string, file: string): Promise<string> {\n return path.resolve(dir, (await readFileOptional(path.join(dir, file))).trim());\n}\n\nasync function pointsBackAt(backLink: string, root: string): Promise<boolean> {\n const [linked, realRoot] = await Promise.all([\n realpathOrUndefined(backLink),\n realpathOrUndefined(root),\n ]);\n return realRoot !== undefined && linked === path.join(realRoot, GIT_ENTRY);\n}\n\nasync function realpathOrUndefined(file: string): Promise<string | undefined> {\n try {\n return await realpath(file);\n } catch {\n return undefined;\n }\n}\n\nasync function countProjectAgentsDeclaringHooks(projectDir: string): Promise<number> {\n const dir = agentsDir(\"claude\", \"project\", projectDir);\n const files = await glob(agentCodec(\"claude\").listGlob, dir);\n const agents = await Promise.all(files.map((file) => readFile(path.join(dir, file))));\n return agents.filter(declaresAHook).length;\n}\n\n/** An event with no definition runs nothing, so it is not a hook to warn about. */\nfunction declaresAHook(agentMarkdown: string): boolean {\n const frontmatter = declaredHooksSchema.safeParse(extractFrontmatter(agentMarkdown));\n return (\n frontmatter.success &&\n Object.values(frontmatter.data.hooks).some((definitions) => definitions.length > 0)\n );\n}\n","import path from \"path\";\n\nimport { codexGlobalConfigFile } from \"../installation/install-layout.js\";\nimport { ensureDir, fileExists, readFile, writeFile } from \"../../utils/fs.js\";\n\n/**\n * Codex reads `<project>/.codex/agents/*.toml` only while the GLOBAL `config.toml` holds\n * `[projects.\"<abs path>\"] trust_level = \"trusted\"`, failing silently otherwise. The install writes\n * that entry and says so, but never overrides a level the user already set.\n */\n\nconst TRUST_KEY = \"trust_level\";\nconst TRUSTED = \"trusted\";\nconst TRUST_ASSIGNMENT = `${TRUST_KEY} = \"${TRUSTED}\"`;\n\nexport type CodexProjectTrust =\n | { readonly kind: \"already trusted\" }\n | { readonly kind: \"trusted now\"; readonly configFile: string }\n | {\n readonly kind: \"left as the user set it\";\n readonly configFile: string;\n readonly level: string;\n };\n\n/**\n * Merged into the user's file, never rewritten: a second table for the same path would make Codex\n * refuse the whole file. `path.resolve` gives the one spelling Codex matches (no trailing slash).\n */\nexport async function trustCodexProject(projectDir: string): Promise<CodexProjectTrust> {\n const configFile = codexGlobalConfigFile();\n const dir = path.resolve(projectDir);\n const config = (await fileExists(configFile)) ? await readFile(configFile) : \"\";\n\n if (declaresTrust(config, dir)) return { kind: \"already trusted\" };\n\n const level = declaredLevel(config, dir);\n if (level !== undefined) return { kind: \"left as the user set it\", configFile, level };\n\n await ensureDir(path.dirname(configFile));\n await writeFile(configFile, withTrustFor(config, dir));\n return { kind: \"trusted now\", configFile };\n}\n\nexport function codexProjectTrustMessage(\n projectDir: string,\n trust: CodexProjectTrust,\n): string | undefined {\n const table = projectTableHeader(path.resolve(projectDir));\n\n switch (trust.kind) {\n case \"already trusted\":\n return undefined;\n case \"trusted now\":\n return (\n `Trusted this project in your Codex configuration, so Codex reads its sub-agents: added ` +\n `${table} with ${TRUST_KEY} = \"${TRUSTED}\" to ${trust.configFile}.`\n );\n case \"left as the user set it\":\n return (\n `Codex reads this project's sub-agents only once it is trusted, and ${trust.configFile} ` +\n `sets ${TRUST_KEY} = \"${trust.level}\" under ${table}. Left as you set it — change it to ` +\n `\"${TRUSTED}\" for Codex to read them.`\n );\n default: {\n const _exhaustive: never = trust;\n return _exhaustive;\n }\n }\n}\n\n/** Hand-read, not TOML-parsed; any other spelling reads as untrusted, the safe direction. */\nfunction declaresTrust(config: string, projectDir: string): boolean {\n return linesForProject(config, projectDir).includes(TRUST_ASSIGNMENT);\n}\n\nconst TRUST_LEVEL_LINE = new RegExp(`^${TRUST_KEY}\\\\s*=\\\\s*\"([^\"]*)\"$`);\n\n/** The user's own `trust_level` for this project, which is never overwritten. */\nfunction declaredLevel(config: string, projectDir: string): string | undefined {\n return linesForProject(config, projectDir)\n .map((line) => TRUST_LEVEL_LINE.exec(line)?.[1])\n .find((level) => level !== undefined);\n}\n\n/** Trimmed: the lines under the project's table header, then its dotted keys with the prefix cut. */\nfunction linesForProject(config: string, projectDir: string): string[] {\n const lines = config.split(\"\\n\").map((line) => line.trim());\n const dottedPrefix = `projects.\"${projectDir}\".`;\n const dotted = lines\n .filter((line) => line.startsWith(dottedPrefix))\n .map((line) => line.slice(dottedPrefix.length));\n\n return [...linesUnderProjectTable(lines, projectDir), ...dotted];\n}\n\nfunction linesUnderProjectTable(lines: readonly string[], projectDir: string): readonly string[] {\n const header = lines.indexOf(projectTableHeader(projectDir));\n if (header === -1) return [];\n\n const after = lines.slice(header + 1);\n const nextTable = after.findIndex(opensATable);\n return nextTable === -1 ? after : after.slice(0, nextTable);\n}\n\nfunction opensATable(line: string): boolean {\n return line.startsWith(\"[\");\n}\n\nfunction projectTableHeader(projectDir: string): string {\n return `[projects.\"${projectDir}\"]`;\n}\n\nfunction withTrustFor(config: string, projectDir: string): string {\n const lines = config.split(\"\\n\");\n const header = lines.findIndex((line) => line.trim() === projectTableHeader(projectDir));\n\n if (header !== -1) {\n return [...lines.slice(0, header + 1), TRUST_ASSIGNMENT, ...lines.slice(header + 1)].join(\"\\n\");\n }\n\n const theirs = config.trimEnd();\n const table = `${projectTableHeader(projectDir)}\\n${TRUST_ASSIGNMENT}\\n`;\n return theirs === \"\" ? table : `${theirs}\\n\\n${table}`;\n}\n","import {\n agentsLeftOutOfCodexMessage,\n unexpressibleOnCodexMessage,\n} from \"@workspace/compile/agent-source\";\n\nimport { codexProjectTrustMessage, trustCodexProject } from \"./codex-project-trust.js\";\nimport { agentCodec, agentsDir } from \"../installation/install-layout.js\";\nimport { glob } from \"../../utils/fs.js\";\nimport type { Provider } from \"../../consts.js\";\n\n/** Once per run, not per sub-agent or scope: each notice is true of the whole installation. */\nexport async function codexCompileNotices(\n provider: Provider,\n projectDir: string,\n): Promise<string[]> {\n if (provider !== \"codex\") return [];\n\n return [\n agentsLeftOutOfCodexMessage(),\n unexpressibleOnCodexMessage(),\n ...(await trustNotice(projectDir)),\n ];\n}\n\n/** Only when role files exist: trusting a project with nothing for Codex to read grants nothing. */\nasync function trustNotice(projectDir: string): Promise<string[]> {\n if (!(await holdsProjectRoles(projectDir))) return [];\n\n const said = codexProjectTrustMessage(projectDir, await trustCodexProject(projectDir));\n return said === undefined ? [] : [said];\n}\n\nasync function holdsProjectRoles(projectDir: string): Promise<boolean> {\n const roles = await glob(agentCodec(\"codex\").listGlob, agentsDir(\"codex\", \"project\", projectDir));\n\n return roles.length > 0;\n}\n","import { claudeCompileNotices } from \"./claude-project-trust.js\";\nimport { codexCompileNotices } from \"./codex-compile-notices.js\";\nimport type { Provider } from \"../../consts.js\";\n\n/** The one source `init` and `compile` share, so they cannot say different things. */\nexport async function hostCompileNotices(\n provider: Provider,\n projectDir: string,\n): Promise<string[]> {\n switch (provider) {\n case \"claude\":\n return claudeCompileNotices(provider, projectDir);\n case \"codex\":\n return codexCompileNotices(provider, projectDir);\n default: {\n const _exhaustive: never = provider;\n return _exhaustive;\n }\n }\n}\n"],"mappings":"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","names":["path","path"]}
|
|
@@ -4,7 +4,7 @@ import {
|
|
|
4
4
|
} from "./chunk-3R3LHA4Q.js";
|
|
5
5
|
import {
|
|
6
6
|
openUrl
|
|
7
|
-
} from "./chunk-
|
|
7
|
+
} from "./chunk-SPQSNZMM.js";
|
|
8
8
|
import {
|
|
9
9
|
fetchSeedConfig
|
|
10
10
|
} from "./chunk-A3ZAXL5T.js";
|
|
@@ -18,10 +18,10 @@ import {
|
|
|
18
18
|
import {
|
|
19
19
|
summaryPanelBlock,
|
|
20
20
|
useTerminalDimensions
|
|
21
|
-
} from "./chunk-
|
|
21
|
+
} from "./chunk-Q6WRR4BN.js";
|
|
22
22
|
import {
|
|
23
23
|
hostCompileNotices
|
|
24
|
-
} from "./chunk-
|
|
24
|
+
} from "./chunk-3N4FSTVX.js";
|
|
25
25
|
import {
|
|
26
26
|
compileAgentsAllScopes,
|
|
27
27
|
compileProjectScope,
|
|
@@ -29,14 +29,14 @@ import {
|
|
|
29
29
|
movedGlobalAgentInputs,
|
|
30
30
|
sayCapturedWarnings,
|
|
31
31
|
writeProjectConfig
|
|
32
|
-
} from "./chunk-
|
|
32
|
+
} from "./chunk-VSPC74SS.js";
|
|
33
33
|
import {
|
|
34
34
|
copyLocalSkills,
|
|
35
35
|
discoverInstalledSkills
|
|
36
|
-
} from "./chunk-
|
|
36
|
+
} from "./chunk-VR6QTK5Z.js";
|
|
37
37
|
import {
|
|
38
38
|
loadAgentDefs
|
|
39
|
-
} from "./chunk-
|
|
39
|
+
} from "./chunk-ITQF35UQ.js";
|
|
40
40
|
import {
|
|
41
41
|
render
|
|
42
42
|
} from "./chunk-KIK5EZYD.js";
|
|
@@ -48,7 +48,7 @@ import {
|
|
|
48
48
|
providerFlag,
|
|
49
49
|
providerNamedBy,
|
|
50
50
|
providerNeedsAConfigurationToInstall
|
|
51
|
-
} from "./chunk-
|
|
51
|
+
} from "./chunk-2RTBSLSR.js";
|
|
52
52
|
import {
|
|
53
53
|
BaseCommand,
|
|
54
54
|
EXIT_CODES,
|
|
@@ -60,7 +60,7 @@ import {
|
|
|
60
60
|
readInstalledGlobal,
|
|
61
61
|
registerExternalSkills,
|
|
62
62
|
writeExternalSkills
|
|
63
|
-
} from "./chunk-
|
|
63
|
+
} from "./chunk-LJQXQTFC.js";
|
|
64
64
|
import {
|
|
65
65
|
ERROR_MESSAGES,
|
|
66
66
|
INCOMPLETE_WORK_RECOVERY,
|
|
@@ -103,7 +103,7 @@ import {
|
|
|
103
103
|
sharedConfigExistingInstall,
|
|
104
104
|
subAgentChanged,
|
|
105
105
|
warn
|
|
106
|
-
} from "./chunk-
|
|
106
|
+
} from "./chunk-WVFBBZEP.js";
|
|
107
107
|
import {
|
|
108
108
|
plural
|
|
109
109
|
} from "./chunk-7OG635DK.js";
|
|
@@ -373,8 +373,18 @@ var Init = class _Init extends BaseCommand {
|
|
|
373
373
|
}
|
|
374
374
|
async showDashboardOrOpenEditor(projectDir) {
|
|
375
375
|
const dashboard = await runDashboardFlow(projectDir, this.config, (msg) => this.log(msg));
|
|
376
|
-
|
|
377
|
-
|
|
376
|
+
switch (dashboard) {
|
|
377
|
+
case "cancelled":
|
|
378
|
+
return this.error("Cancelled", { exit: EXIT_CODES.CANCELLED });
|
|
379
|
+
case "not-installed":
|
|
380
|
+
return this.openEditor(projectDir, void 0);
|
|
381
|
+
case "shown":
|
|
382
|
+
return;
|
|
383
|
+
default: {
|
|
384
|
+
const _exhaustive = dashboard;
|
|
385
|
+
return _exhaustive;
|
|
386
|
+
}
|
|
387
|
+
}
|
|
378
388
|
}
|
|
379
389
|
/** Refused as the install route refuses it, since the line echoes the ref it was given. */
|
|
380
390
|
addMarketplaceLineOrFail(ref) {
|
|
@@ -851,4 +861,4 @@ export {
|
|
|
851
861
|
runDashboardFlow,
|
|
852
862
|
Init
|
|
853
863
|
};
|
|
854
|
-
//# sourceMappingURL=chunk-
|
|
864
|
+
//# sourceMappingURL=chunk-AARQBW5L.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/cli/commands/init.tsx","../src/cli/lib/permission-checker.tsx"],"sourcesContent":["import os from \"os\";\nimport React from \"react\";\n\nimport { Flags, type Interfaces } from \"@oclif/core\";\nimport { Box, Text, useApp } from \"ink\";\nimport { partition } from \"remeda\";\nimport { render } from \"../components/render.js\";\n\nimport { BaseCommand } from \"../base-command.js\";\nimport type { InstallSelection } from \"@workspace/compile/seed-to-config\";\nimport { useTerminalDimensions } from \"../components/hooks/use-terminal-dimensions.js\";\nimport { type SourceLoadResult } from \"../lib/loading/index.js\";\nimport {\n loadSource,\n sayCapturedWarnings,\n loadAgentDefs,\n copyLocalSkills,\n writeProjectConfig,\n compileAgentsAllScopes,\n compileProjectScope,\n type CompilationResult,\n type ConfigWriteResult,\n type SkillCopyResult,\n discoverInstalledSkills,\n} from \"../lib/operations/index.js\";\nimport { movedGlobalAgentInputs, type GateReport } from \"../lib/config-gate/index.js\";\nimport { fetchSeedConfig } from \"../lib/seed/fetch-seed.js\";\nimport {\n registerExternalSkills,\n writeExternalSkills,\n type ExternalSkillInstall,\n} from \"../lib/seed/external-skills.js\";\nimport { seedToInstallSelection, type SeedMapping } from \"../lib/seed/seed-to-selection.js\";\nimport {\n holdInstalledGlobal,\n installsAtHome,\n joinedStatement,\n notInstalledGlobally,\n readInstalledGlobal,\n type HeldGlobal,\n type InstalledGlobal,\n} from \"../lib/seed/seed-apply.js\";\nimport { agentChangesAmong, type AgentChange } from \"../lib/configuration/scope-diff.js\";\nimport { isActiveAt } from \"../lib/configuration/scope-predicates.js\";\nimport { summaryPanelBlock, type SummaryPanelProps } from \"../components/common/summary-panel.js\";\nimport {\n getInstallationsByProvider,\n type ProviderInstallation,\n} from \"../lib/plugins/plugin-info.js\";\nimport {\n assertNamedSourceUsable,\n isLocalSource,\n resolveBranding,\n} from \"../lib/configuration/config.js\";\nimport {\n type InstallMode,\n detectInstallation,\n detectProjectInstallation,\n deriveInstallMode,\n holdsItsOwnInstallation,\n installBaseDir,\n resolveInstallPaths,\n buildAgentScopeMap,\n isHomeDirectory,\n INSTALL_MODE_LABELS,\n INSTALL_MODE_DESCRIPTIONS,\n} from \"../lib/installation/index.js\";\nimport { hostAt } from \"../lib/hosts/host-for.js\";\nimport {\n agentCodec,\n chooseProviderForThisRun,\n providerInUse,\n relativeConfigPath,\n} from \"../lib/installation/install-layout.js\";\nimport { providerToNameAt } from \"../lib/installation/provider-to-name.js\";\nimport { hostCompileNotices } from \"../lib/hosts/host-compile-notices.js\";\nimport {\n installationToName,\n providerFlag,\n providerNamedBy,\n providerNeedsAConfigurationToInstall,\n} from \"../lib/installation/provider-flag.js\";\nimport { checkPermissions } from \"../lib/permission-checker.js\";\nimport {\n ASCII_LOGO,\n CLI_INVOKE_COMMAND,\n DEFAULT_BRANDING,\n EDITOR_ADDRESS,\n EDITOR_URL,\n EJECT_SOURCE,\n editorConfigUrl,\n type Provider,\n} from \"../consts.js\";\nimport { clearTerminalScreen } from \"../utils/terminal.js\";\nimport { SelectList, type SelectListItem } from \"../components/common/select-list.js\";\nimport { promptConfirm, promptValue } from \"../components/common/prompt-confirm.js\";\nimport { Confirm } from \"../components/common/confirm.js\";\nimport { getErrorMessage } from \"../utils/errors.js\";\nimport { EXIT_CODES } from \"../lib/exit-codes.js\";\nimport { openUrl } from \"../utils/open-url.js\";\nimport { plural } from \"../utils/string.js\";\nimport type {\n AgentName,\n AgentScopeConfig,\n MergedSkillsMatrix,\n SkillConfig,\n SkillId,\n SkillScope,\n} from \"../types/index.js\";\nimport { type StartupMessage } from \"../utils/logger.js\";\nimport {\n ERROR_MESSAGES,\n INCOMPLETE_WORK_RECOVERY,\n SHARED_CONFIG_ARRIVALS,\n STATUS_MESSAGES,\n addMarketplaceInTheEditor,\n agentsNotCompiled,\n applySharedConfigHere,\n carriedSkillsWritten,\n globalScopedAgentsHint,\n initSucceeded,\n keptAsInstalledGlobally,\n sharedConfigExistingInstall,\n subAgentChanged,\n} from \"../utils/messages.js\";\nimport type { SeedPayload } from \"@workspace/matrix/seed\";\n\nconst DASHBOARD_OPTIONS = [\n { label: \"Edit in the web editor\", value: \"edit\" },\n { label: \"Compile\", value: \"compile\" },\n { label: \"Doctor\", value: \"doctor\" },\n { label: \"List\", value: \"list\" },\n] as const satisfies readonly SelectListItem<string>[];\n\nconst DASHBOARD_OPTIONS_LINE = ` ${DASHBOARD_OPTIONS.map(({ label }) => `[${label}]`).join(\" \")}`;\n\ntype DashboardCommand = (typeof DASHBOARD_OPTIONS)[number][\"value\"];\n\n/** A white-labelled name replaces the logo, because the logo spells the shipped name. */\nconst DashboardTitle: React.FC<{ name: string }> = ({ name }) =>\n name === DEFAULT_BRANDING.NAME ? <Text>{ASCII_LOGO}</Text> : <Text bold>{name}</Text>;\n\ntype DashboardProps = {\n data: DashboardData;\n onSelect: (command: DashboardCommand) => void;\n onCancel: () => void;\n};\n\nexport const Dashboard: React.FC<DashboardProps> = ({ data, onSelect, onCancel }) => {\n const { exit } = useApp();\n const { rows: terminalHeight } = useTerminalDimensions();\n\n return (\n <Box flexDirection=\"column\" height={terminalHeight}>\n <Box marginBottom={1}>\n <DashboardTitle name={data.name} />\n </Box>\n <Box marginBottom={1}>\n <Text>{dashboardCountLines(data).join(\"\\n\")}</Text>\n </Box>\n <SelectList\n items={DASHBOARD_OPTIONS}\n onSelect={(command) => {\n onSelect(command);\n exit();\n }}\n onCancel={() => {\n onCancel();\n exit();\n }}\n />\n </Box>\n );\n};\n\n/**\n * Shared by the TTY and piped dashboards so the two cannot drift apart. A scope holding two\n * installations gets a named block for each, a blank line apart.\n */\nfunction dashboardCountLines({ installations }: DashboardData): string[] {\n const named = installations.length > 1;\n const blocks = installations.map((installation) => [\n ...(named ? [` Provider: ${installation.provider}`] : []),\n ...installationCountLines(installation),\n ]);\n return blankLineBetween(blocks);\n}\n\nfunction blankLineBetween(blocks: string[][]): string[] {\n return blocks.flatMap((block, index) => (index === 0 ? block : [\"\", ...block]));\n}\n\nfunction installationCountLines(installation: ProviderInstallation): string[] {\n return [\n ` Skills: ${installation.skillCount} installed`,\n ` Agents: ${installation.agentCount} compiled`,\n ` Mode: ${INSTALL_MODE_LABELS[installation.mode]}`,\n ...(installation.marketplace ? [` Marketplace: ${installation.marketplace}`] : []),\n ];\n}\n\nexport function formatDashboardText(data: DashboardData): string {\n return [data.name, \"\", ...dashboardCountLines(data), \"\", DASHBOARD_OPTIONS_LINE].join(\"\\n\");\n}\n\n/** Ctrl+C cancels the run; Escape (null) only leaves the dashboard. */\nconst DASHBOARD_INTERRUPTED = \"interrupted\";\n\ntype DashboardAnswer = DashboardCommand | typeof DASHBOARD_INTERRUPTED | null;\n\nasync function showDashboard(\n projectDir: string,\n log?: (message: string) => void,\n): Promise<DashboardAnswer> {\n const data = await getDashboardData(projectDir);\n\n if (!process.stdin.isTTY) {\n const output = log ?? console.log;\n output(formatDashboardText(data));\n return null;\n }\n\n // clearOnResolve repaints a clean terminal before unmount: the dashboard fills the height.\n const selectedCommand = await promptValue<DashboardAnswer>(\n (resolve) => (\n <Dashboard\n data={data}\n onSelect={(command) => resolve(command)}\n onCancel={() => resolve(null)}\n />\n ),\n { onExit: DASHBOARD_INTERRUPTED, clearOnResolve: true },\n );\n\n clearTerminalScreen();\n\n return selectedCommand;\n}\n\nfunction dashboardCommandArgv(command: DashboardCommand): string[] {\n return command === \"edit\" ? [\"--ui\"] : [];\n}\n\nexport type DashboardFlow = \"not-installed\" | \"shown\" | \"cancelled\";\n\n/** Never exits the process: callers decide from the {@link DashboardFlow} it answers. */\nexport async function runDashboardFlow(\n projectDir: string,\n config: Interfaces.Config,\n log?: (message: string) => void,\n): Promise<DashboardFlow> {\n const installation = await detectInstallation(projectDir);\n if (!installation) return \"not-installed\";\n\n const selectedCommand = await showDashboard(projectDir, log);\n if (selectedCommand === DASHBOARD_INTERRUPTED) return \"cancelled\";\n if (selectedCommand) {\n await config.runCommand(selectedCommand, dashboardCommandArgv(selectedCommand));\n }\n return \"shown\";\n}\n\n/** A required key, not `?`: oclif writes the key as `undefined` when the flag is not passed. */\ntype SourceFlags = { marketplace: string | undefined };\n\ntype Selection = {\n result: InstallSelection;\n sourceResult: SourceLoadResult;\n /** Where the selection was actually loaded from; a shared id may name a marketplace. */\n sourceFlags: SourceFlags;\n /** A global install's own skills, recorded as they are and never installed over. */\n installedAlready: ReadonlySet<SkillId>;\n};\n\n/** The payload names the marketplace because a skill id never says where its repository lives. */\nfunction sharedConfigSourceFlags(flags: SourceFlags, payload: SeedPayload): SourceFlags {\n return { marketplace: flags.marketplace ?? payload.marketplace };\n}\n\nexport default class Init extends BaseCommand {\n /** Resolved once in {@link install}; the closing line is printed several calls below. */\n private brandingName: string = DEFAULT_BRANDING.NAME;\n\n static summary = `Initialize ${DEFAULT_BRANDING.NAME} in this project`;\n static description = `Build a configuration in ${EDITOR_ADDRESS}, or install one by id with --from. Over an existing installation, shows its dashboard.`;\n\n static examples = [\n {\n description: \"Open the editor to build a configuration\",\n command: \"<%= config.bin %> <%= command.id %>\",\n },\n {\n description: \"Install a configuration built in the editor\",\n command: \"<%= config.bin %> <%= command.id %> --from <id>\",\n },\n {\n description: \"Test local marketplace changes against a configuration built in the editor\",\n command: \"<%= config.bin %> <%= command.id %> --from <id> --marketplace ./my-marketplace\",\n },\n ];\n\n static flags = {\n marketplace: Flags.string({\n char: \"m\",\n description:\n \"With --from, install from this marketplace instead of the one the configuration names. Without --from, open the editor and say how to add it there\",\n required: false,\n }),\n from: Flags.string({\n description: \"Install a configuration shared from agentsinc.sh by its id\",\n helpValue: \"<id>\",\n }),\n ui: Flags.boolean({\n description: `Open ${EDITOR_ADDRESS} on the id --from names, or on the catalogue — what a bare init does where nothing is installed`,\n default: false,\n }),\n provider: providerFlag(),\n };\n\n /** The exit code is decided once, after every path through {@link install} has ended. */\n async run(): Promise<void> {\n await this.install();\n this.exitIfWorkIncomplete();\n }\n\n /** The link is printed before it is opened, so it still works where no browser can open. */\n private async openEditor(\n projectDir: string,\n provider: Provider | undefined,\n id?: string,\n marketplace?: string,\n ): Promise<void> {\n const url = id === undefined ? EDITOR_URL : editorConfigUrl(id);\n // Above the first line, so a ref the install route would refuse is refused before any output.\n const marketplaceLine =\n marketplace === undefined ? undefined : this.addMarketplaceLineOrFail(marketplace);\n\n const installedHere = await holdsItsOwnInstallation(projectDir);\n const toName = installedHere ? await installationToName(projectDir, provider) : provider;\n\n this.log(id === undefined ? `Build it at ${url}` : `Open it at ${url}`);\n if (marketplaceLine !== undefined) this.log(marketplaceLine);\n this.log(applySharedConfigHere(id, installedHere, toName));\n\n if (!process.stdin.isTTY) return;\n\n const opened = await openUrl(url);\n if (!opened.ok) this.warn(opened.error);\n }\n\n private async install(): Promise<void> {\n const { flags } = await this.parse(Init);\n const projectDir = process.cwd();\n\n // First, so a refused `--provider` leaves the filesystem untouched at both scopes.\n this.settleTheProviderForThisRun(flags);\n\n // Before `ensureConfigReadable`: a broken config must not block the editor route.\n if (opensTheEditor(flags)) {\n return this.openEditor(\n projectDir,\n providerNamedBy(flags.provider),\n flags.from,\n flags.marketplace,\n );\n }\n\n // ABORT: an unreadable config is refused here, before any route reads it.\n await this.ensureConfigReadable(projectDir);\n\n if (flags.from === undefined) return this.showDashboardOrOpenEditor(projectDir);\n\n // Its degrade arm cannot fire: `ensureConfigReadable` already refused every unreadable config.\n this.brandingName = await this.resolveBrandingName(projectDir);\n\n const selection = await this.selectionFromSharedConfig(flags.from, flags, projectDir);\n if (!selection) this.exit(EXIT_CODES.CANCELLED);\n\n this.reportValidationErrors(selection.result.validation);\n\n await this.handleInstallation(selection, projectDir);\n }\n\n private async showDashboardOrOpenEditor(projectDir: string): Promise<void> {\n const dashboard = await runDashboardFlow(projectDir, this.config, (msg) => this.log(msg));\n switch (dashboard) {\n case \"cancelled\":\n return this.error(\"Cancelled\", { exit: EXIT_CODES.CANCELLED });\n case \"not-installed\":\n return this.openEditor(projectDir, undefined);\n case \"shown\":\n return;\n default: {\n const _exhaustive: never = dashboard;\n return _exhaustive;\n }\n }\n }\n\n /** Refused as the install route refuses it, since the line echoes the ref it was given. */\n private addMarketplaceLineOrFail(ref: string): string {\n try {\n assertNamedSourceUsable(ref);\n return addMarketplaceInTheEditor(ref, isLocalSource(ref));\n } catch (error) {\n this.handleError(error);\n }\n }\n\n /** `--provider` only picks which folder an install creates, so it needs `--from`. */\n private settleTheProviderForThisRun(flags: Interfaces.InferredFlags<typeof Init.flags>): void {\n const named = providerNamedBy(flags.provider);\n if (named === undefined) return;\n\n if (flags.from === undefined) {\n this.error(providerNeedsAConfigurationToInstall(), { exit: EXIT_CODES.INVALID_ARGS });\n }\n\n chooseProviderForThisRun(named);\n }\n\n /** Every refusal fires before anything is written. */\n private async selectionFromSharedConfig(\n id: string,\n flags: SourceFlags,\n projectDir: string,\n ): Promise<Selection | null> {\n await this.refuseInstalledProject(projectDir, id);\n\n const payload = await this.fetchSharedConfigOrFail(id);\n const sourceFlags = sharedConfigSourceFlags(flags, payload);\n const { sourceResult, startupMessages } = await this.loadSourceOrFail(sourceFlags, projectDir);\n // Before the decode, which would otherwise skip carried skills as unknown ids.\n const carriedSkills = this.registerExternalSkillsOrFail(\n payload,\n sourceResult.matrix,\n projectDir,\n );\n const mapping = this.decodeSeedOrFail(payload, sourceResult.matrix);\n const { result } = mapping;\n\n // Nothing is installed here: `refuseInstalledProject` has already refused a home that holds one.\n this.refuseProjectScopedContentAtHome(result, projectDir, false);\n\n const installedGlobal = await installedGlobalToHold(projectDir);\n const held = holdInstalledGlobal(result, installedGlobal);\n const arrivingCarried = notInstalledGlobally(carriedSkills, held);\n\n // Above the lists: a yes installs what was listed, so nothing listed may then be refused.\n await this.refuseSharedConfigBeforeAsking(\n held.result,\n arrivingCarried,\n projectDir,\n sourceResult,\n );\n\n // Above the skips: an \"unknown\" skill is often one whose file failed to parse.\n sayCapturedWarnings(startupMessages);\n this.warnOfSkippedEntries(mapping);\n this.refuseAnEmptySelection(held.result, id);\n\n const stackName = await this.stackNameOf(result.selectedStackId, sourceResult);\n this.logWhatGoesWhere(held, installedGlobal, stackName, {\n id: installsAtHome(result) ? id : undefined,\n provider: providerToNameAt(os.homedir(), providerInUse(projectDir)),\n });\n if (process.stdin.isTTY && !(await this.confirmInstall())) {\n this.log(\"Setup cancelled\");\n return null;\n }\n\n // After the question, so a refusal or a no leaves nothing written.\n await this.writeCarriedSkills(arrivingCarried);\n this.announceArrivingSkills(held, result.selectedAgents.length);\n\n return {\n result: held.result,\n sourceResult,\n sourceFlags,\n installedAlready: new Set(held.installed.skillIds),\n };\n }\n\n /**\n * The panel where the question is asked, or where it would be: the project against the whole\n * global install it inherits. `runFromHome.id` is the id only where home would take it.\n */\n private logWhatGoesWhere(\n held: HeldGlobal,\n installedGlobal: InstalledGlobal | null,\n stackName: string | undefined,\n runFromHome: RunFromHome,\n ): void {\n const joined = joinedGlobalAgents(held, installedGlobal);\n const lines = summaryPanelBlock(\n installPanel(held, installedGlobal, joined, stackName),\n joined.map(subAgentChanged),\n [...joinedStatement(held), ...keptAsInstalledStatement(held, runFromHome)],\n );\n for (const line of lines) {\n this.log(line);\n }\n }\n\n private refuseAnEmptySelection(result: InstallSelection, id: string): void {\n if (!selectsNothing(result)) return;\n\n this.error(`Configuration '${id}' contains no skills this catalog can install.`, {\n exit: EXIT_CODES.ERROR,\n });\n }\n\n private announceArrivingSkills(held: HeldGlobal, agentCount: number): void {\n const arriving = notInstalledGlobally(held.result.skills, held);\n if (arriving.length === 0) return;\n\n this.log(`Installing ${arriving.length} skill(s) across ${agentCount} sub-agent(s)\\n`);\n }\n\n private async confirmInstall(): Promise<boolean> {\n const outcome = await promptConfirm(({ onConfirm, onCancel }) => (\n <Confirm\n message={SHARED_CONFIG_ARRIVALS.INSTALL_CONFIRM}\n onConfirm={onConfirm}\n onCancel={onCancel}\n />\n ));\n return outcome === \"confirmed\";\n }\n\n /** Project-scoped: `detectInstallation`'s global fallback would refuse every clean project. */\n private async refuseInstalledProject(projectDir: string, id: string): Promise<void> {\n const installation = await detectProjectInstallation(projectDir);\n if (!installation) return;\n\n const provider = providerToNameAt(projectDir, providerInUse(projectDir));\n this.error(sharedConfigExistingInstall(installation.configPath, id, provider), {\n exit: EXIT_CODES.ERROR,\n });\n }\n\n private async fetchSharedConfigOrFail(id: string): Promise<SeedPayload> {\n this.log(`Fetching configuration ${id}...`);\n const fetched = await fetchSeedConfig(id);\n if (!fetched.ok) {\n this.error(fetched.error, { exit: EXIT_CODES.ERROR });\n }\n return fetched.payload;\n }\n\n private decodeSeedOrFail(payload: SeedPayload, matrix: MergedSkillsMatrix): SeedMapping {\n try {\n return seedToInstallSelection(payload, matrix);\n } catch (error) {\n this.handleError(error);\n }\n }\n\n private registerExternalSkillsOrFail(\n payload: SeedPayload,\n matrix: MergedSkillsMatrix,\n projectDir: string,\n ): ExternalSkillInstall[] {\n try {\n return registerExternalSkills(payload, matrix, projectDir);\n } catch (error) {\n this.handleError(error);\n }\n }\n\n private async writeCarriedSkills(carried: ExternalSkillInstall[]): Promise<void> {\n if (carried.length === 0) return;\n\n await writeExternalSkills(carried);\n this.log(carriedSkillsWritten(carried.map((skill) => skill.id)));\n }\n\n private async loadSourceOrFail(\n flags: SourceFlags,\n projectDir: string,\n ): Promise<{ sourceResult: SourceLoadResult; startupMessages: StartupMessage[] }> {\n try {\n const loaded = await loadSource({\n // The one load that may choose a marketplace rather than read the stored one.\n caller: \"init\",\n ...(flags.marketplace !== undefined && { sourceFlag: flags.marketplace }),\n projectDir,\n captureStartupMessages: true,\n });\n return { sourceResult: loaded.sourceResult, startupMessages: loaded.startupMessages };\n } catch (error) {\n this.error(getErrorMessage(error), {\n exit: EXIT_CODES.ERROR,\n });\n }\n }\n\n private async handleInstallation(\n { result, sourceResult, sourceFlags, installedAlready }: Selection,\n projectDir: string,\n ): Promise<void> {\n const plan = planInstall(result, installedAlready);\n this.logInstallPlan(plan);\n\n // Before any copy, so a failed resolution cannot leave a half-install with no config.ts.\n const resolvedMarketplace = await this.marketplaceForPluginSkills(\n plan.pluginSkills,\n sourceResult,\n projectDir,\n );\n\n const copyResult = await this.copyEjectedSkills(plan, projectDir, sourceResult);\n\n if (resolvedMarketplace !== null) {\n await this.installPluginSkillsReported(\n plan.pluginSkills,\n resolvedMarketplace,\n projectDir,\n sourceResult.matrix,\n );\n }\n\n try {\n const written = await this.writeConfigAndCompile(\n result,\n sourceResult,\n sourceFlags,\n projectDir,\n );\n this.reportSuccess(written, copyResult, projectDir);\n\n await this.showPermissionNotice(projectDir);\n } catch (error) {\n this.handleError(error);\n }\n }\n\n private async marketplaceForPluginSkills(\n pluginSkills: InstallSelection[\"skills\"],\n sourceResult: SourceLoadResult,\n projectDir: string,\n ): Promise<string | null> {\n if (pluginSkills.length === 0) return null;\n\n return this.requireMarketplaceOrExit(\n sourceResult,\n \"install plugin skills\",\n hostAt(projectDir),\n (marketplace) => this.log(`Registering marketplace \"${marketplace}\"...`),\n );\n }\n\n /** One frame, then unmount: the notice has no exit of its own and `--from` must run headless. */\n private async showPermissionNotice(projectDir: string): Promise<void> {\n const permissionWarning = await checkPermissions(projectDir);\n if (!permissionWarning) return;\n\n const { unmount } = render(permissionWarning);\n unmount();\n }\n\n private logInstallPlan(plan: InstallPlan): void {\n this.log(\"\\n\");\n this.log(`Selected ${plural(plan.ejectedSkills.length + plan.pluginSkills.length, \"skill\")}`);\n this.log(`Install mode: ${installModeDescription(plan)}`);\n }\n\n private async copyEjectedSkills(\n { ejectedSkills, installMode }: InstallPlan,\n projectDir: string,\n sourceResult: SourceLoadResult,\n ): Promise<SkillCopyResult | null> {\n if (ejectedSkills.length === 0) return null;\n\n this.log(\"Copying skills to local directory...\");\n const copyResult = await copyLocalSkills(ejectedSkills, projectDir, sourceResult);\n this.log(skillsCopiedLine(copyResult, installMode, projectDir));\n return copyResult;\n }\n\n private async writeConfigAndCompile(\n result: InstallSelection,\n sourceResult: SourceLoadResult,\n flags: SourceFlags,\n projectDir: string,\n ): Promise<WrittenInstall> {\n const configResult = await this.writeConfigReported(result, sourceResult, flags, projectDir);\n const agentScopeMap = buildAgentScopeMap(configResult.config);\n const compileResult = await this.compileInstalledAgents(\n configResult.propagation,\n agentScopeMap,\n projectDir,\n );\n this.reportCompilation(compileResult);\n await this.reportWhatThisHostCannotCarry(projectDir);\n\n this.reportFanOut(configResult.propagation);\n\n return { configResult, compileResult, agentScopeMap };\n }\n\n private async writeConfigReported(\n result: InstallSelection,\n sourceResult: SourceLoadResult,\n flags: SourceFlags,\n projectDir: string,\n ): Promise<ConfigWriteResult> {\n this.log(\"Generating configuration...\");\n const configResult = await writeProjectConfig({\n selection: result,\n sourceResult,\n projectDir,\n ...(flags.marketplace !== undefined && { sourceFlag: flags.marketplace }),\n });\n\n if (configResult.wasMerged) {\n this.log(`Merged with existing config at ${configResult.existingConfigPath}`);\n }\n\n this.log(`Configuration saved (${plural(configResult.config.agents.length, \"agent\")})\\n`);\n this.reportUnassignedSkills(configResult.config, result.skills);\n return configResult;\n }\n\n private async compileInstalledAgents(\n written: GateReport,\n agentScopeMap: Map<AgentName, SkillScope>,\n projectDir: string,\n ): Promise<CompilationResult> {\n this.log(STATUS_MESSAGES.COMPILING_AGENTS);\n // Sequential: both can reject and discovery warns, so the order decides what the user reads.\n const agentDefs = await loadAgentDefs();\n const { allSkills } = await discoverInstalledSkills(projectDir);\n const compile = compilesGlobalScope(projectDir, written)\n ? compileAgentsAllScopes\n : compileProjectScope;\n return compile({\n projectDir,\n sourcePath: agentDefs.sourcePath,\n skills: allSkills,\n agentScopeMap,\n });\n }\n\n private async reportWhatThisHostCannotCarry(projectDir: string): Promise<void> {\n for (const notice of await hostCompileNotices(providerInUse(projectDir), projectDir)) {\n this.log(notice);\n }\n }\n\n /**\n * Failures are recorded rather than aborted on: the skills and config are already written, and\n * {@link BaseCommand.exitIfWorkIncomplete} answers for them.\n */\n private reportCompilation(compileResult: CompilationResult): void {\n const { compiled, failed, warnings } = compileResult;\n const summary = `Compiled ${plural(compiled.length, \"agent\")}`;\n\n if (failed.length === 0) {\n this.log(`${summary}\\n`);\n return;\n }\n\n this.log(`${summary} (${failed.length} failed)\\n`);\n for (const warning of warnings) {\n this.warn(warning);\n }\n // Off `failed`, not `warnings`: warnings also carry entries that are not failures.\n this.recordIncompleteWork(agentsNotCompiled(failed), INCOMPLETE_WORK_RECOVERY.RECOMPILE);\n }\n\n private reportSuccess(\n { configResult, compileResult, agentScopeMap }: WrittenInstall,\n copyResult: SkillCopyResult | null,\n projectDir: string,\n ): void {\n // A run with work owed ends on the failure account instead of claiming success.\n if (!this.hasIncompleteWork) this.log(`${initSucceeded(this.brandingName)}\\n`);\n\n if (copyResult !== null && copyResult.totalCopied > 0) {\n this.logDirectoryBlocks(\"Skills copied to:\", skillsCopiedBlocks(projectDir, copyResult));\n }\n this.logDirectoryBlocks(\n \"Agents compiled to:\",\n agentsCompiledBlocks(projectDir, compileResult.compiled, agentScopeMap),\n );\n this.reportConfiguration(configResult, agentScopeMap, projectDir);\n }\n\n private reportConfiguration(\n { configPath, propagation }: ConfigWriteResult,\n agentScopeMap: Map<AgentName, SkillScope>,\n projectDir: string,\n ): void {\n const paths = {\n global: resolveInstallPaths(projectDir, \"global\").configPath,\n project: configPath,\n };\n const split = splitAgentScopes(projectDir, agentScopeMap);\n\n this.log(\"Configuration:\");\n for (const written of configsWritten(projectDir, paths, propagation.globalWritten)) {\n this.log(` ${written}`);\n }\n this.log(\"\");\n\n this.log(\"To customize agent-skill assignments:\");\n for (const [index, step] of customizationSteps(split, paths.global, projectDir).entries()) {\n this.log(` ${index + 1}. ${step}`);\n }\n this.log(\"\");\n }\n\n private logDirectoryBlocks(heading: string, blocks: DirectoryBlock[]): void {\n for (const { dir, entries } of blocks) {\n this.log(heading);\n this.log(` ${dir}`);\n for (const entry of entries) {\n this.log(` ${entry}`);\n }\n this.log(\"\");\n }\n }\n}\n\n/** The editor is where a marketplace is added, so `--marketplace` without `--from` opens it. */\nfunction opensTheEditor(\n flags: Pick<Interfaces.InferredFlags<typeof Init.flags>, \"ui\" | \"from\" | \"marketplace\">,\n): boolean {\n return flags.ui || (flags.from === undefined && flags.marketplace !== undefined);\n}\n\n/** A sub-agent is installable without skills, so only a selection with neither is empty. */\nfunction selectsNothing(result: InstallSelection): boolean {\n return result.skills.length === 0 && result.selectedAgents.length === 0;\n}\n\n/** At the home root the global config is the project's own, so there is no global install apart. */\nasync function installedGlobalToHold(projectDir: string): Promise<InstalledGlobal | null> {\n if (isHomeDirectory(projectDir)) return null;\n return await readInstalledGlobal(projectDir);\n}\n\n/** The run from home that changes what a project run keeps, where home would take it. */\ntype RunFromHome = { id: string | undefined; provider: Provider | undefined };\n\nfunction keptAsInstalledStatement(held: HeldGlobal, runFromHome: RunFromHome): string[] {\n const { skillIds, agentNames } = held.keptAsInstalled;\n if (skillIds.length === 0 && agentNames.length === 0) return [];\n return [keptAsInstalledGlobally(skillIds, agentNames, runFromHome.id, runFromHome.provider)];\n}\n\ntype GlobalEntries = { skills: SkillConfig[]; agents: AgentScopeConfig[] };\n\n/** What the project inherits that the configuration leaves unnamed: a project config copies it all. */\nfunction inheritedGlobal(held: HeldGlobal, installedGlobal: InstalledGlobal | null): GlobalEntries {\n if (installedGlobal === null) return { skills: [], agents: [] };\n\n const namedSkills = new Set(held.result.skills.filter(isGlobal).map(({ id }) => id));\n const namedAgents = new Set(held.result.agentConfigs.filter(isGlobal).map(({ name }) => name));\n return {\n skills: installedGlobal.skills.filter((skill) => isGlobal(skill) && !namedSkills.has(skill.id)),\n agents: installedGlobal.agents.filter(\n (agent) => isGlobal(agent) && !namedAgents.has(agent.name),\n ),\n };\n}\n\nfunction isGlobal(entry: SkillConfig | AgentScopeConfig): boolean {\n return isActiveAt(entry, \"global\");\n}\n\n/** Measured against the global install: the project changes nothing else of it. */\nfunction installPanel(\n held: HeldGlobal,\n installedGlobal: InstalledGlobal | null,\n joined: AgentChange[],\n stackName: string | undefined,\n): SummaryPanelProps {\n const inherited = inheritedGlobal(held, installedGlobal);\n return {\n skillConfigs: [...held.result.skills, ...inherited.skills],\n agentConfigs: [...held.result.agentConfigs, ...inherited.agents],\n installedSkillConfigs: installedGlobal?.skills ?? null,\n installedAgentConfigs: installedGlobal?.agents ?? null,\n isInitMode: true,\n changedAgentNames: new Set(joined.map(({ name }) => name)),\n stackName,\n };\n}\n\n/** The held global sub-agents an arriving skill's row joins, against their installed rows. */\nfunction joinedGlobalAgents(\n held: HeldGlobal,\n installedGlobal: InstalledGlobal | null,\n): AgentChange[] {\n if (installedGlobal === null) return [];\n\n return agentChangesAmong(\n held.joined.map(({ agentName }) => agentName),\n installedGlobal,\n { agents: held.result.agentConfigs, stack: held.result.assignedStack },\n );\n}\n\ntype InstallPlan = {\n installMode: InstallMode;\n ejectedSkills: InstallSelection[\"skills\"];\n pluginSkills: InstallSelection[\"skills\"];\n};\n\nfunction planInstall(\n result: InstallSelection,\n installedAlready: ReadonlySet<SkillId>,\n): InstallPlan {\n const toInstall = result.skills.filter(\n (skill) => !skill.excluded && !installedAlready.has(skill.id),\n );\n const [ejectedSkills, pluginSkills] = partition(\n toInstall,\n (skill) => skill.origin === EJECT_SOURCE,\n );\n return { installMode: deriveInstallMode(toInstall), ejectedSkills, pluginSkills };\n}\n\nfunction installModeDescription({ installMode, ejectedSkills, pluginSkills }: InstallPlan): string {\n if (installMode !== \"mixed\") return INSTALL_MODE_DESCRIPTIONS[installMode];\n return `${INSTALL_MODE_LABELS.mixed} (${ejectedSkills.length} eject, ${pluginSkills.length} plugin)`;\n}\n\ntype WrittenInstall = {\n configResult: ConfigWriteResult;\n compileResult: CompilationResult;\n agentScopeMap: Map<AgentName, SkillScope>;\n};\n\n/**\n * From a project, global sub-agents recompile only when the write changed their inputs;\n * otherwise they would be rebuilt from this run's catalogue, not the one they were made from.\n */\nfunction compilesGlobalScope(cwd: string, written: GateReport): boolean {\n return isHomeDirectory(cwd) || movedGlobalAgentInputs(written);\n}\n\n/** Names the directory only when every skill landed at one scope; the block beneath lists both. */\nfunction skillsCopiedLine(\n copyResult: SkillCopyResult,\n installMode: InstallMode,\n projectDir: string,\n): string {\n const isMixed = installMode === \"mixed\";\n const copied = plural(copyResult.totalCopied, isMixed ? \"local skill\" : \"skill\");\n const lineEnd = isMixed ? \"\" : \"\\n\";\n const projectCount = copyResult.projectCopied.length;\n const globalCount = copyResult.globalCopied.length;\n const landedAtBothScopes = projectCount > 0 && globalCount > 0;\n\n if (landedAtBothScopes) {\n return `Copied ${copied} (${projectCount} project, ${globalCount} global)${lineEnd}`;\n }\n const landedAt: SkillScope = globalCount > 0 ? \"global\" : \"project\";\n return `Copied ${copied} to ${resolveInstallPaths(projectDir, landedAt).skillsDir}/${lineEnd}`;\n}\n\n/** Entries are on-disk names, so ids, never display names. */\ntype DirectoryBlock = { dir: string; entries: string[] };\n\nfunction hasEntries(block: DirectoryBlock): boolean {\n return block.entries.length > 0;\n}\n\n/** At home a Claude install's two scopes are one folder, which is named once. */\nfunction oneBlockPerDir(blocks: DirectoryBlock[]): DirectoryBlock[] {\n const dirs = [...new Set(blocks.map((block) => block.dir))];\n return dirs.map((dir) => ({\n dir,\n entries: blocks.filter((block) => block.dir === dir).flatMap((block) => block.entries),\n }));\n}\n\nfunction skillsCopiedBlocks(projectDir: string, copyResult: SkillCopyResult): DirectoryBlock[] {\n return oneBlockPerDir(\n [\n copiedSkillsBlock(projectDir, \"global\", copyResult.globalCopied),\n copiedSkillsBlock(projectDir, \"project\", copyResult.projectCopied),\n ].filter(hasEntries),\n );\n}\n\nfunction copiedSkillsBlock(\n projectDir: string,\n scope: SkillScope,\n copied: SkillCopyResult[\"projectCopied\"],\n): DirectoryBlock {\n return {\n dir: resolveInstallPaths(projectDir, scope).skillsDir,\n entries: copied.map(({ skillId }) => `${skillId}/`),\n };\n}\n\n/** Mirrors `writeCompiledAgentsByScope`' routing. */\nfunction agentsCompiledBlocks(\n projectDir: string,\n compiled: AgentName[],\n agentScopeMap: Map<AgentName, SkillScope>,\n): DirectoryBlock[] {\n const [globalAgents, projectAgents] = partition(\n compiled,\n (name) => agentScopeMap.get(name) === \"global\",\n );\n return oneBlockPerDir(\n [\n compiledAgentsBlock(projectDir, \"global\", globalAgents),\n compiledAgentsBlock(projectDir, \"project\", projectAgents),\n ].filter(hasEntries),\n );\n}\n\n/** Per scope, because the project and global installs can be on different hosts. */\nfunction compiledAgentsBlock(\n projectDir: string,\n scope: SkillScope,\n agents: AgentName[],\n): DirectoryBlock {\n const { extension } = agentCodec(providerInUse(installBaseDir(projectDir, scope)));\n return {\n dir: resolveInstallPaths(projectDir, scope).agentsDir,\n entries: agents.map((name) => `${name}${extension}`),\n };\n}\n\ntype ConfigPaths = { global: string; project: string };\n\ntype AgentScopeSplit = { globalAgentCount: number; isGlobalOnly: boolean };\n\n/** At the home root both scopes are one config and one pass, so there is no split. */\nfunction splitAgentScopes(cwd: string, agentScopeMap: Map<AgentName, SkillScope>): AgentScopeSplit {\n if (isHomeDirectory(cwd)) return { globalAgentCount: 0, isGlobalOnly: false };\n\n const scopes = [...agentScopeMap.values()];\n const globalAgentCount = scopes.filter((scope) => scope === \"global\").length;\n return {\n globalAgentCount,\n isGlobalOnly: globalAgentCount > 0 && globalAgentCount === scopes.length,\n };\n}\n\n/**\n * From a project its own config is always written, and the global one whenever the run changed it,\n * if only to register the project. At home the two are one file.\n */\nfunction configsWritten(projectDir: string, paths: ConfigPaths, globalWritten: boolean): string[] {\n if (isHomeDirectory(projectDir)) return [paths.project];\n return globalWritten ? [paths.global, paths.project] : [paths.project];\n}\n\n/** `compile` in a project recompiles no global agent, hence the global hint. */\nfunction customizationSteps(\n split: AgentScopeSplit,\n globalConfigPath: string,\n projectDir: string,\n): string[] {\n if (split.isGlobalOnly) {\n return [`Edit ${globalConfigPath}`, globalScopedAgentsHint(split.globalAgentCount)];\n }\n\n return [\n `Edit ${relativeConfigPath(projectDir, providerInUse(projectDir))}`,\n `Run '${CLI_INVOKE_COMMAND} compile' to regenerate agents`,\n ...(split.globalAgentCount > 0 ? [globalScopedAgentsHint(split.globalAgentCount)] : []),\n ];\n}\n\nexport type DashboardData = {\n name: string;\n installations: ProviderInstallation[];\n};\n\n/** Each installation's counts come from its own scope-aware read, so project and global never mix. */\nasync function getDashboardData(projectDir: string): Promise<DashboardData> {\n // ABORT: an unloadable config throws here, as the installation check before it already would.\n const [installations, branding] = await Promise.all([\n getInstallationsByProvider(projectDir),\n resolveBranding(projectDir),\n ]);\n // Every caller found an installation before drawing the dashboard.\n if (installations.length === 0) throw new Error(ERROR_MESSAGES.NO_INSTALLATION);\n\n return { name: branding.name, installations };\n}\n","import React from \"react\";\nimport { z } from \"zod\";\n\nimport { Text, Box } from \"ink\";\nimport path from \"path\";\n\nimport { CLI_COLORS, MAX_CONFIG_FILE_SIZE } from \"../consts\";\nimport {\n advisesOnPermissions,\n permissionFiles,\n providerInUse,\n} from \"./installation/install-layout.js\";\nimport { fileExists, readFileSafe } from \"../utils/fs\";\nimport { warn } from \"../utils/logger\";\nimport { settingsFileSchema } from \"./schemas\";\n\ntype SettingsFile = z.infer<typeof settingsFileSchema>;\ntype PermissionConfig = NonNullable<SettingsFile[\"permissions\"]>;\n\n/** Undefined when absent, malformed or empty; silent about every other field (Claude Code's). */\nasync function readSettingsPermissions(filePath: string): Promise<PermissionConfig | undefined> {\n if (!(await fileExists(filePath))) return undefined;\n try {\n const content = await readFileSafe(filePath, MAX_CONFIG_FILE_SIZE);\n const raw: unknown = JSON.parse(content);\n const result = settingsFileSchema.safeParse(raw);\n const parsed: SettingsFile = result.success ? result.data : {};\n return parsed.permissions;\n } catch {\n warn(`Malformed settings file at '${filePath}' — skipping`);\n return undefined;\n }\n}\n\nfunction settingsFilesFor(projectRoot: string): string[] {\n return permissionFiles(providerInUse(projectRoot), \"project\", projectRoot);\n}\n\n/** Permissions from the highest-precedence settings file that defines them — the overlay wins. */\nasync function loadPermissions(files: readonly string[]): Promise<PermissionConfig | undefined> {\n for (const filePath of [...files].reverse()) {\n const permissions = await readSettingsPermissions(filePath);\n if (permissions) return permissions;\n }\n return undefined;\n}\n\n/** Relative to the project and POSIX-separated: a name shown to a person, not a path to open. */\nfunction asUserWritesIt(projectRoot: string, file: string): string {\n return path.relative(projectRoot, file).split(path.sep).join(\"/\");\n}\n\n/** `null` for a host whose permission model this release cannot advise on. */\nexport async function checkPermissions(projectRoot: string): Promise<React.ReactElement | null> {\n if (!advisesOnPermissions(providerInUse(projectRoot))) return null;\n\n const files = settingsFilesFor(projectRoot);\n // The base file: the one this CLI writes and a user with neither is asked to create.\n const [base] = files;\n if (base === undefined) return null;\n\n const permissions = await loadPermissions(files);\n const settingsFile = asUserWritesIt(projectRoot, base);\n\n if (!permissions) {\n return (\n <Box flexDirection=\"column\" borderStyle=\"round\" borderColor={CLI_COLORS.WARNING} padding={1}>\n <Text bold color={CLI_COLORS.WARNING}>\n Permission Notice\n </Text>\n <Text>No permissions configured in {settingsFile}</Text>\n <Text>Agents will prompt for approval on each tool use.</Text>\n <Text> </Text>\n <Text>For autonomous operation, add to {settingsFile}:</Text>\n <Text> </Text>\n <Text color={CLI_COLORS.DIM}>{\"{\"}</Text>\n <Text color={CLI_COLORS.DIM}>{' \"permissions\": {'}</Text>\n <Text color={CLI_COLORS.DIM}>{' \"allow\": ['}</Text>\n <Text color={CLI_COLORS.DIM}>{' \"Read(*)\",'}</Text>\n <Text color={CLI_COLORS.DIM}>{' \"Bash(git *)\",'}</Text>\n <Text color={CLI_COLORS.DIM}>{' \"Bash(bun *)\"'}</Text>\n <Text color={CLI_COLORS.DIM}>{\" ]\"}</Text>\n <Text color={CLI_COLORS.DIM}>{\" }\"}</Text>\n <Text color={CLI_COLORS.DIM}>{\"}\"}</Text>\n </Box>\n );\n }\n\n const hasRestrictiveBash = permissions.deny?.some(\n (rule) => rule === \"Bash(*)\" || rule === \"Bash\",\n );\n const hasNoAllows = !permissions.allow || permissions.allow.length === 0;\n\n if (hasRestrictiveBash || hasNoAllows) {\n return (\n <Box flexDirection=\"column\" borderStyle=\"round\" borderColor={CLI_COLORS.WARNING} padding={1}>\n <Text bold color={CLI_COLORS.WARNING}>\n Permission Warnings\n </Text>\n {hasRestrictiveBash && (\n <Text>\n ⚠ Bash is denied in permissions. Some agents require Bash for git, testing, and build\n commands.\n </Text>\n )}\n {hasNoAllows && (\n <Text>⚠ No allow rules configured. Agents will prompt for each tool use.</Text>\n )}\n </Box>\n );\n }\n\n return null;\n}\n"],"mappings":"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","names":["Box","Text","jsx","jsxs","Text","Box"]}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import {
|
|
3
3
|
listAgentMdFiles
|
|
4
|
-
} from "./chunk-
|
|
4
|
+
} from "./chunk-EHJIQDXR.js";
|
|
5
5
|
import {
|
|
6
6
|
agentCodec,
|
|
7
7
|
agentFrontmatterValidationSchema,
|
|
@@ -27,7 +27,7 @@ import {
|
|
|
27
27
|
warn,
|
|
28
28
|
writeContentHash,
|
|
29
29
|
writePluginManifest
|
|
30
|
-
} from "./chunk-
|
|
30
|
+
} from "./chunk-WVFBBZEP.js";
|
|
31
31
|
import {
|
|
32
32
|
plural
|
|
33
33
|
} from "./chunk-7OG635DK.js";
|
|
@@ -157,4 +157,4 @@ export {
|
|
|
157
157
|
compileAllAgentPlugins,
|
|
158
158
|
printAgentCompilationSummary
|
|
159
159
|
};
|
|
160
|
-
//# sourceMappingURL=chunk-
|
|
160
|
+
//# sourceMappingURL=chunk-BRZA7ZCX.js.map
|
|
@@ -29,7 +29,7 @@ import {
|
|
|
29
29
|
sourceFolderName,
|
|
30
30
|
verbose,
|
|
31
31
|
writeFile
|
|
32
|
-
} from "./chunk-
|
|
32
|
+
} from "./chunk-WVFBBZEP.js";
|
|
33
33
|
import {
|
|
34
34
|
typedEntries,
|
|
35
35
|
typedFromEntries,
|
|
@@ -374,4 +374,4 @@ export {
|
|
|
374
374
|
withoutExcludedAssignments,
|
|
375
375
|
recompileAgents
|
|
376
376
|
};
|
|
377
|
-
//# sourceMappingURL=chunk-
|
|
377
|
+
//# sourceMappingURL=chunk-EHJIQDXR.js.map
|
|
@@ -6,7 +6,7 @@ import {
|
|
|
6
6
|
hostAt,
|
|
7
7
|
loadInstalledConfig,
|
|
8
8
|
refuseUnofferedPlacements
|
|
9
|
-
} from "./chunk-
|
|
9
|
+
} from "./chunk-WVFBBZEP.js";
|
|
10
10
|
|
|
11
11
|
// src/cli/lib/hosts/configured-placements.ts
|
|
12
12
|
async function unofferablePlacementsFound(cwd) {
|
|
@@ -36,4 +36,4 @@ async function configuredSkillsAt(root) {
|
|
|
36
36
|
export {
|
|
37
37
|
unofferablePlacementsFound
|
|
38
38
|
};
|
|
39
|
-
//# sourceMappingURL=chunk-
|
|
39
|
+
//# sourceMappingURL=chunk-F437ICEG.js.map
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import {
|
|
3
3
|
getLocalAgentDefinitions
|
|
4
|
-
} from "./chunk-
|
|
4
|
+
} from "./chunk-BRZA7ZCX.js";
|
|
5
5
|
import {
|
|
6
6
|
loadMergedAgents
|
|
7
|
-
} from "./chunk-
|
|
7
|
+
} from "./chunk-WVFBBZEP.js";
|
|
8
8
|
|
|
9
9
|
// src/cli/lib/operations/project/load-agent-defs.ts
|
|
10
10
|
async function loadAgentDefs() {
|
|
@@ -20,4 +20,4 @@ async function loadAgentDefs() {
|
|
|
20
20
|
export {
|
|
21
21
|
loadAgentDefs
|
|
22
22
|
};
|
|
23
|
-
//# sourceMappingURL=chunk-
|
|
23
|
+
//# sourceMappingURL=chunk-ITQF35UQ.js.map
|
|
@@ -50,7 +50,7 @@ import {
|
|
|
50
50
|
verbose,
|
|
51
51
|
warn,
|
|
52
52
|
writeFile
|
|
53
|
-
} from "./chunk-
|
|
53
|
+
} from "./chunk-WVFBBZEP.js";
|
|
54
54
|
import {
|
|
55
55
|
BUILT_IN_MATRIX,
|
|
56
56
|
getCategoryDomain,
|
|
@@ -1093,4 +1093,4 @@ export {
|
|
|
1093
1093
|
installsAtHome,
|
|
1094
1094
|
BaseCommand
|
|
1095
1095
|
};
|
|
1096
|
-
//# sourceMappingURL=chunk-
|
|
1096
|
+
//# sourceMappingURL=chunk-LJQXQTFC.js.map
|
|
@@ -7,10 +7,10 @@ import {
|
|
|
7
7
|
} from "./chunk-A3ZAXL5T.js";
|
|
8
8
|
import {
|
|
9
9
|
withoutExcludedAssignments
|
|
10
|
-
} from "./chunk-
|
|
10
|
+
} from "./chunk-EHJIQDXR.js";
|
|
11
11
|
import {
|
|
12
12
|
readCarriedSkills
|
|
13
|
-
} from "./chunk-
|
|
13
|
+
} from "./chunk-LJQXQTFC.js";
|
|
14
14
|
import {
|
|
15
15
|
ERROR_MESSAGES,
|
|
16
16
|
directoryExists,
|
|
@@ -21,7 +21,7 @@ import {
|
|
|
21
21
|
loadProjectConfigFromDir,
|
|
22
22
|
readForkedFromMetadata,
|
|
23
23
|
resolveInstallPaths
|
|
24
|
-
} from "./chunk-
|
|
24
|
+
} from "./chunk-WVFBBZEP.js";
|
|
25
25
|
import {
|
|
26
26
|
plural,
|
|
27
27
|
truncateText,
|
|
@@ -371,4 +371,4 @@ export {
|
|
|
371
371
|
skillsAuthoredHere,
|
|
372
372
|
publishSeedConfig
|
|
373
373
|
};
|
|
374
|
-
//# sourceMappingURL=chunk-
|
|
374
|
+
//# sourceMappingURL=chunk-Q4UNHVPX.js.map
|
|
@@ -30,10 +30,9 @@ function useMeasuredHeight() {
|
|
|
30
30
|
const [measuredHeight, setMeasuredHeight] = useState(0);
|
|
31
31
|
const { stdout } = useStdout();
|
|
32
32
|
const measure = () => {
|
|
33
|
-
if (ref.current)
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
}
|
|
33
|
+
if (!ref.current) return;
|
|
34
|
+
const { height } = measureElement(ref.current);
|
|
35
|
+
setMeasuredHeight((prev) => prev !== height ? height : prev);
|
|
37
36
|
};
|
|
38
37
|
useEffect(() => {
|
|
39
38
|
measure();
|
|
@@ -193,4 +192,4 @@ export {
|
|
|
193
192
|
summaryPanelText,
|
|
194
193
|
summaryPanelBlock
|
|
195
194
|
};
|
|
196
|
-
//# sourceMappingURL=chunk-
|
|
195
|
+
//# sourceMappingURL=chunk-Q6WRR4BN.js.map
|