@sentry/dotagents 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (202) hide show
  1. package/README.md +96 -0
  2. package/dist/cli/commands/add.d.ts +12 -0
  3. package/dist/cli/commands/add.d.ts.map +1 -0
  4. package/dist/cli/commands/add.js +127 -0
  5. package/dist/cli/commands/add.js.map +1 -0
  6. package/dist/cli/commands/init.d.ts +10 -0
  7. package/dist/cli/commands/init.d.ts.map +1 -0
  8. package/dist/cli/commands/init.js +81 -0
  9. package/dist/cli/commands/init.js.map +1 -0
  10. package/dist/cli/commands/init.test.d.ts +2 -0
  11. package/dist/cli/commands/init.test.d.ts.map +1 -0
  12. package/dist/cli/commands/init.test.js +71 -0
  13. package/dist/cli/commands/init.test.js.map +1 -0
  14. package/dist/cli/commands/install.d.ts +15 -0
  15. package/dist/cli/commands/install.d.ts.map +1 -0
  16. package/dist/cli/commands/install.js +139 -0
  17. package/dist/cli/commands/install.js.map +1 -0
  18. package/dist/cli/commands/install.test.d.ts +2 -0
  19. package/dist/cli/commands/install.test.d.ts.map +1 -0
  20. package/dist/cli/commands/install.test.js +94 -0
  21. package/dist/cli/commands/install.test.js.map +1 -0
  22. package/dist/cli/commands/list.d.ts +13 -0
  23. package/dist/cli/commands/list.d.ts.map +1 -0
  24. package/dist/cli/commands/list.js +82 -0
  25. package/dist/cli/commands/list.js.map +1 -0
  26. package/dist/cli/commands/list.test.d.ts +2 -0
  27. package/dist/cli/commands/list.test.d.ts.map +1 -0
  28. package/dist/cli/commands/list.test.js +96 -0
  29. package/dist/cli/commands/list.test.js.map +1 -0
  30. package/dist/cli/commands/remove.d.ts +10 -0
  31. package/dist/cli/commands/remove.d.ts.map +1 -0
  32. package/dist/cli/commands/remove.js +68 -0
  33. package/dist/cli/commands/remove.js.map +1 -0
  34. package/dist/cli/commands/sync.d.ts +16 -0
  35. package/dist/cli/commands/sync.d.ts.map +1 -0
  36. package/dist/cli/commands/sync.js +108 -0
  37. package/dist/cli/commands/sync.js.map +1 -0
  38. package/dist/cli/commands/sync.test.d.ts +2 -0
  39. package/dist/cli/commands/sync.test.d.ts.map +1 -0
  40. package/dist/cli/commands/sync.test.js +100 -0
  41. package/dist/cli/commands/sync.test.js.map +1 -0
  42. package/dist/cli/commands/update.d.ts +15 -0
  43. package/dist/cli/commands/update.d.ts.map +1 -0
  44. package/dist/cli/commands/update.js +113 -0
  45. package/dist/cli/commands/update.js.map +1 -0
  46. package/dist/cli/commands/update.test.d.ts +2 -0
  47. package/dist/cli/commands/update.test.d.ts.map +1 -0
  48. package/dist/cli/commands/update.test.js +90 -0
  49. package/dist/cli/commands/update.test.js.map +1 -0
  50. package/dist/cli/index.d.ts +2 -0
  51. package/dist/cli/index.d.ts.map +1 -0
  52. package/dist/cli/index.js +49 -0
  53. package/dist/cli/index.js.map +1 -0
  54. package/dist/config/index.d.ts +5 -0
  55. package/dist/config/index.d.ts.map +1 -0
  56. package/dist/config/index.js +4 -0
  57. package/dist/config/index.js.map +1 -0
  58. package/dist/config/loader.d.ts +6 -0
  59. package/dist/config/loader.d.ts.map +1 -0
  60. package/dist/config/loader.js +35 -0
  61. package/dist/config/loader.js.map +1 -0
  62. package/dist/config/loader.test.d.ts +2 -0
  63. package/dist/config/loader.test.d.ts.map +1 -0
  64. package/dist/config/loader.test.js +60 -0
  65. package/dist/config/loader.test.js.map +1 -0
  66. package/dist/config/schema.d.ts +37 -0
  67. package/dist/config/schema.d.ts.map +1 -0
  68. package/dist/config/schema.js +43 -0
  69. package/dist/config/schema.js.map +1 -0
  70. package/dist/config/schema.test.d.ts +2 -0
  71. package/dist/config/schema.test.d.ts.map +1 -0
  72. package/dist/config/schema.test.js +138 -0
  73. package/dist/config/schema.test.js.map +1 -0
  74. package/dist/config/writer.d.ts +17 -0
  75. package/dist/config/writer.d.ts.map +1 -0
  76. package/dist/config/writer.js +71 -0
  77. package/dist/config/writer.js.map +1 -0
  78. package/dist/config/writer.test.d.ts +2 -0
  79. package/dist/config/writer.test.d.ts.map +1 -0
  80. package/dist/config/writer.test.js +103 -0
  81. package/dist/config/writer.test.js.map +1 -0
  82. package/dist/gitignore/index.d.ts +2 -0
  83. package/dist/gitignore/index.d.ts.map +1 -0
  84. package/dist/gitignore/index.js +2 -0
  85. package/dist/gitignore/index.js.map +1 -0
  86. package/dist/gitignore/writer.d.ts +16 -0
  87. package/dist/gitignore/writer.d.ts.map +1 -0
  88. package/dist/gitignore/writer.js +40 -0
  89. package/dist/gitignore/writer.js.map +1 -0
  90. package/dist/gitignore/writer.test.d.ts +2 -0
  91. package/dist/gitignore/writer.test.d.ts.map +1 -0
  92. package/dist/gitignore/writer.test.js +99 -0
  93. package/dist/gitignore/writer.test.js.map +1 -0
  94. package/dist/index.d.ts +12 -0
  95. package/dist/index.d.ts.map +1 -0
  96. package/dist/index.js +8 -0
  97. package/dist/index.js.map +1 -0
  98. package/dist/lockfile/index.d.ts +5 -0
  99. package/dist/lockfile/index.d.ts.map +1 -0
  100. package/dist/lockfile/index.js +4 -0
  101. package/dist/lockfile/index.js.map +1 -0
  102. package/dist/lockfile/loader.d.ts +10 -0
  103. package/dist/lockfile/loader.d.ts.map +1 -0
  104. package/dist/lockfile/loader.js +36 -0
  105. package/dist/lockfile/loader.js.map +1 -0
  106. package/dist/lockfile/schema.d.ts +42 -0
  107. package/dist/lockfile/schema.d.ts.map +1 -0
  108. package/dist/lockfile/schema.js +25 -0
  109. package/dist/lockfile/schema.js.map +1 -0
  110. package/dist/lockfile/schema.test.d.ts +2 -0
  111. package/dist/lockfile/schema.test.d.ts.map +1 -0
  112. package/dist/lockfile/schema.test.js +60 -0
  113. package/dist/lockfile/schema.test.js.map +1 -0
  114. package/dist/lockfile/writer.d.ts +7 -0
  115. package/dist/lockfile/writer.d.ts.map +1 -0
  116. package/dist/lockfile/writer.js +17 -0
  117. package/dist/lockfile/writer.js.map +1 -0
  118. package/dist/lockfile/writer.test.d.ts +2 -0
  119. package/dist/lockfile/writer.test.d.ts.map +1 -0
  120. package/dist/lockfile/writer.test.js +73 -0
  121. package/dist/lockfile/writer.test.js.map +1 -0
  122. package/dist/skills/discovery.d.ts +17 -0
  123. package/dist/skills/discovery.d.ts.map +1 -0
  124. package/dist/skills/discovery.js +156 -0
  125. package/dist/skills/discovery.js.map +1 -0
  126. package/dist/skills/discovery.test.d.ts +2 -0
  127. package/dist/skills/discovery.test.d.ts.map +1 -0
  128. package/dist/skills/discovery.test.js +110 -0
  129. package/dist/skills/discovery.test.js.map +1 -0
  130. package/dist/skills/index.d.ts +7 -0
  131. package/dist/skills/index.d.ts.map +1 -0
  132. package/dist/skills/index.js +4 -0
  133. package/dist/skills/index.js.map +1 -0
  134. package/dist/skills/loader.d.ts +14 -0
  135. package/dist/skills/loader.d.ts.map +1 -0
  136. package/dist/skills/loader.js +57 -0
  137. package/dist/skills/loader.js.map +1 -0
  138. package/dist/skills/loader.test.d.ts +2 -0
  139. package/dist/skills/loader.test.d.ts.map +1 -0
  140. package/dist/skills/loader.test.js +69 -0
  141. package/dist/skills/loader.test.js.map +1 -0
  142. package/dist/skills/resolver.d.ts +46 -0
  143. package/dist/skills/resolver.d.ts.map +1 -0
  144. package/dist/skills/resolver.integration.test.d.ts +2 -0
  145. package/dist/skills/resolver.integration.test.d.ts.map +1 -0
  146. package/dist/skills/resolver.integration.test.js +106 -0
  147. package/dist/skills/resolver.integration.test.js.map +1 -0
  148. package/dist/skills/resolver.js +82 -0
  149. package/dist/skills/resolver.js.map +1 -0
  150. package/dist/skills/resolver.test.d.ts +2 -0
  151. package/dist/skills/resolver.test.d.ts.map +1 -0
  152. package/dist/skills/resolver.test.js +36 -0
  153. package/dist/skills/resolver.test.js.map +1 -0
  154. package/dist/sources/cache.d.ts +23 -0
  155. package/dist/sources/cache.d.ts.map +1 -0
  156. package/dist/sources/cache.js +61 -0
  157. package/dist/sources/cache.js.map +1 -0
  158. package/dist/sources/git.d.ts +25 -0
  159. package/dist/sources/git.d.ts.map +1 -0
  160. package/dist/sources/git.js +72 -0
  161. package/dist/sources/git.js.map +1 -0
  162. package/dist/sources/index.d.ts +5 -0
  163. package/dist/sources/index.d.ts.map +1 -0
  164. package/dist/sources/index.js +4 -0
  165. package/dist/sources/index.js.map +1 -0
  166. package/dist/sources/local.d.ts +9 -0
  167. package/dist/sources/local.d.ts.map +1 -0
  168. package/dist/sources/local.js +32 -0
  169. package/dist/sources/local.js.map +1 -0
  170. package/dist/symlinks/index.d.ts +2 -0
  171. package/dist/symlinks/index.d.ts.map +1 -0
  172. package/dist/symlinks/index.js +2 -0
  173. package/dist/symlinks/index.js.map +1 -0
  174. package/dist/symlinks/manager.d.ts +20 -0
  175. package/dist/symlinks/manager.d.ts.map +1 -0
  176. package/dist/symlinks/manager.js +103 -0
  177. package/dist/symlinks/manager.js.map +1 -0
  178. package/dist/symlinks/manager.test.d.ts +2 -0
  179. package/dist/symlinks/manager.test.d.ts.map +1 -0
  180. package/dist/symlinks/manager.test.js +94 -0
  181. package/dist/symlinks/manager.test.js.map +1 -0
  182. package/dist/utils/exec.d.ts +16 -0
  183. package/dist/utils/exec.d.ts.map +1 -0
  184. package/dist/utils/exec.js +37 -0
  185. package/dist/utils/exec.js.map +1 -0
  186. package/dist/utils/fs.d.ts +6 -0
  187. package/dist/utils/fs.d.ts.map +1 -0
  188. package/dist/utils/fs.js +10 -0
  189. package/dist/utils/fs.js.map +1 -0
  190. package/dist/utils/hash.d.ts +16 -0
  191. package/dist/utils/hash.d.ts.map +1 -0
  192. package/dist/utils/hash.js +50 -0
  193. package/dist/utils/hash.js.map +1 -0
  194. package/dist/utils/hash.test.d.ts +2 -0
  195. package/dist/utils/hash.test.d.ts.map +1 -0
  196. package/dist/utils/hash.test.js +61 -0
  197. package/dist/utils/hash.test.js.map +1 -0
  198. package/dist/utils/index.d.ts +4 -0
  199. package/dist/utils/index.d.ts.map +1 -0
  200. package/dist/utils/index.js +4 -0
  201. package/dist/utils/index.js.map +1 -0
  202. package/package.json +56 -0
package/README.md ADDED
@@ -0,0 +1,96 @@
1
+ # dotagents
2
+
3
+ A package manager for `.agents` directories. Declare agent skill dependencies in `agents.toml`, lock versions for reproducibility, and let every tool on your team discover skills from a single place.
4
+
5
+ ## Why dotagents?
6
+
7
+ **One source of truth.** Skills live in `.agents/skills/` and symlink into `.claude/skills/`, `.cursor/skills/`, or wherever your tools expect them. No copy-pasting between directories.
8
+
9
+ **Reproducible.** `agents.lock` pins exact commits and integrity hashes. `dotagents install --frozen` in CI guarantees everyone runs the same skills.
10
+
11
+ **Shareable.** Skills are just directories with a `SKILL.md`. Host them in any git repo, discover them automatically, install with one command.
12
+
13
+ ## Quick Start
14
+
15
+ ```bash
16
+ # Initialize a new project
17
+ npx dotagents init
18
+
19
+ # Add a skill from a GitHub repo
20
+ npx dotagents add getsentry/skills --name find-bugs
21
+
22
+ # Install all declared skills
23
+ npx dotagents install
24
+ ```
25
+
26
+ This creates an `agents.toml`:
27
+
28
+ ```toml
29
+ version = 1
30
+ gitignore = false
31
+
32
+ [[skills]]
33
+ name = "find-bugs"
34
+ source = "getsentry/skills"
35
+ ```
36
+
37
+ And a lockfile (`agents.lock`) pinning the exact commit and integrity hash.
38
+
39
+ ## Commands
40
+
41
+ | Command | Description |
42
+ |---------|-------------|
43
+ | `dotagents init` | Create `agents.toml` and `.agents/skills/` |
44
+ | `dotagents add <source>` | Add a skill dependency |
45
+ | `dotagents remove <name>` | Remove a skill |
46
+ | `dotagents install` | Install all dependencies from `agents.toml` |
47
+ | `dotagents update [name]` | Update skills to latest versions |
48
+ | `dotagents list` | Show installed skills and their status |
49
+ | `dotagents sync` | Reconcile gitignore, symlinks, and verify state |
50
+
51
+ ## Source Formats
52
+
53
+ ```toml
54
+ [[skills]]
55
+ name = "find-bugs"
56
+ source = "getsentry/skills" # GitHub repo (auto-discover)
57
+
58
+ [[skills]]
59
+ name = "review"
60
+ source = "getsentry/skills@v1.0.0" # Pinned to a ref
61
+
62
+ [[skills]]
63
+ name = "internal"
64
+ source = "git:https://git.corp.dev/repo" # Non-GitHub git
65
+
66
+ [[skills]]
67
+ name = "local"
68
+ source = "path:./my-skills/local-skill" # Local directory
69
+ ```
70
+
71
+ ## How It Works
72
+
73
+ 1. Skills are declared in `agents.toml` at the project root
74
+ 2. `dotagents install` clones repos, discovers skills by convention, and copies them into `.agents/skills/`
75
+ 3. `agents.lock` records the resolved commit and a SHA-256 integrity hash
76
+ 4. By default (`gitignore = false`), skills are checked into git so collaborators get them immediately. Set `gitignore = true` to auto-generate `.agents/.gitignore` and exclude managed skills instead.
77
+ 5. Symlinks connect `.agents/skills/` to wherever your tools look (configured via `symlinks.targets`)
78
+
79
+ ## Checking In Skills
80
+
81
+ By default, `dotagents init` sets `gitignore = false` so installed skills are committed to git. This means anyone cloning the repo gets skills immediately — they only need dotagents when adding or updating skills.
82
+
83
+ To gitignore managed skills instead (collaborators must run `dotagents install`), set `gitignore = true` in `agents.toml` or remove the field entirely (it defaults to `true` when absent for backward compatibility).
84
+
85
+ ## Contributing
86
+
87
+ ```bash
88
+ git clone git@github.com:getsentry/dotagents.git
89
+ cd dotagents
90
+ pnpm install
91
+ pnpm check # lint + typecheck + test
92
+ ```
93
+
94
+ ## License
95
+
96
+ MIT
@@ -0,0 +1,12 @@
1
+ export declare class AddError extends Error {
2
+ constructor(message: string);
3
+ }
4
+ export interface AddOptions {
5
+ projectRoot: string;
6
+ specifier: string;
7
+ ref?: string;
8
+ name?: string;
9
+ }
10
+ export declare function runAdd(opts: AddOptions): Promise<string>;
11
+ export default function add(args: string[]): Promise<void>;
12
+ //# sourceMappingURL=add.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"add.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/add.ts"],"names":[],"mappings":"AAUA,qBAAa,QAAS,SAAQ,KAAK;gBACrB,OAAO,EAAE,MAAM;CAI5B;AAED,MAAM,WAAW,UAAU;IACzB,WAAW,EAAE,MAAM,CAAC;IACpB,SAAS,EAAE,MAAM,CAAC;IAClB,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED,wBAAsB,MAAM,CAAC,IAAI,EAAE,UAAU,GAAG,OAAO,CAAC,MAAM,CAAC,CA6F9D;AAED,wBAA8B,GAAG,CAAC,IAAI,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC,CAmC/D"}
@@ -0,0 +1,127 @@
1
+ import { join } from "node:path";
2
+ import { parseArgs } from "node:util";
3
+ import chalk from "chalk";
4
+ import { loadConfig } from "../../config/loader.js";
5
+ import { addSkillToConfig } from "../../config/writer.js";
6
+ import { parseSource, resolveSkill } from "../../skills/resolver.js";
7
+ import { discoverAllSkills } from "../../skills/discovery.js";
8
+ import { ensureCached } from "../../sources/cache.js";
9
+ import { runInstall } from "./install.js";
10
+ export class AddError extends Error {
11
+ constructor(message) {
12
+ super(message);
13
+ this.name = "AddError";
14
+ }
15
+ }
16
+ export async function runAdd(opts) {
17
+ const { projectRoot, specifier, ref, name: nameOverride } = opts;
18
+ const configPath = join(projectRoot, "agents.toml");
19
+ // Parse the specifier
20
+ const parsed = parseSource(specifier);
21
+ // Determine ref (flag overrides inline @ref)
22
+ const effectiveRef = ref ?? parsed.ref;
23
+ // For git sources, resolve to discover the skill name
24
+ let skillName;
25
+ if (parsed.type === "local") {
26
+ // Local source — resolve and read SKILL.md for the name
27
+ const resolved = await resolveSkill(nameOverride ?? "unknown", { source: specifier }, { projectRoot });
28
+ if (resolved.type !== "local")
29
+ throw new AddError("Unexpected resolve type for local source");
30
+ const { loadSkillMd } = await import("../../skills/loader.js");
31
+ const { join: pathJoin } = await import("node:path");
32
+ const meta = await loadSkillMd(pathJoin(resolved.skillDir, "SKILL.md"));
33
+ skillName = nameOverride ?? meta.name;
34
+ }
35
+ else {
36
+ // Git source — clone and discover
37
+ const url = parsed.url;
38
+ const cacheKey = parsed.type === "github"
39
+ ? `${parsed.owner}/${parsed.repo}`
40
+ : url.replace(/^https?:\/\//, "").replace(/\.git$/, "");
41
+ const cached = await ensureCached({ url, cacheKey, ref: effectiveRef });
42
+ if (nameOverride) {
43
+ // User specified name, verify it exists
44
+ const { discoverSkill } = await import("../../skills/discovery.js");
45
+ const found = await discoverSkill(cached.repoDir, nameOverride);
46
+ if (!found) {
47
+ throw new AddError(`Skill "${nameOverride}" not found in ${specifier}. ` +
48
+ `Use 'dotagents add ${specifier}' without --name to see available skills.`);
49
+ }
50
+ skillName = nameOverride;
51
+ }
52
+ else {
53
+ // Discover all skills and pick
54
+ const skills = await discoverAllSkills(cached.repoDir);
55
+ if (skills.length === 0) {
56
+ throw new AddError(`No skills found in ${specifier}.`);
57
+ }
58
+ if (skills.length === 1) {
59
+ skillName = skills[0].meta.name;
60
+ }
61
+ else {
62
+ // Multiple skills found — for now, list them and ask user to pick with --name
63
+ const names = skills.map((s) => s.meta.name).sort();
64
+ throw new AddError(`Multiple skills found in ${specifier}: ${names.join(", ")}. ` +
65
+ `Use --name to specify which one.`);
66
+ }
67
+ }
68
+ }
69
+ // Check if skill already exists in config
70
+ const config = await loadConfig(configPath);
71
+ if (config.skills.some((s) => s.name === skillName)) {
72
+ throw new AddError(`Skill "${skillName}" already exists in agents.toml. Remove it first or use 'dotagents update'.`);
73
+ }
74
+ // Build the source string for agents.toml
75
+ let source = specifier;
76
+ // If ref was provided inline (@ref), strip it from source since we'll use the ref field
77
+ if (parsed.ref && !ref) {
78
+ // Inline ref — keep it in source as-is
79
+ }
80
+ else if (effectiveRef && !specifier.includes("@")) {
81
+ // Ref from --ref flag, not inline
82
+ }
83
+ // Add to config
84
+ await addSkillToConfig(configPath, skillName, {
85
+ source,
86
+ ...(effectiveRef ? { ref: effectiveRef } : {}),
87
+ });
88
+ // Run install to actually fetch and place the skill
89
+ await runInstall({ projectRoot });
90
+ return skillName;
91
+ }
92
+ export default async function add(args) {
93
+ const { positionals, values } = parseArgs({
94
+ args,
95
+ allowPositionals: true,
96
+ options: {
97
+ ref: { type: "string" },
98
+ name: { type: "string" },
99
+ },
100
+ strict: true,
101
+ });
102
+ const specifier = positionals[0];
103
+ if (!specifier) {
104
+ console.error(chalk.red("Usage: dotagents add <specifier> [--ref <ref>] [--name <name>]"));
105
+ process.exitCode = 1;
106
+ return;
107
+ }
108
+ const { resolve } = await import("node:path");
109
+ try {
110
+ const name = await runAdd({
111
+ projectRoot: resolve("."),
112
+ specifier,
113
+ ref: values["ref"],
114
+ name: values["name"],
115
+ });
116
+ console.log(chalk.green(`Added skill: ${name}`));
117
+ }
118
+ catch (err) {
119
+ if (err instanceof AddError) {
120
+ console.error(chalk.red(err.message));
121
+ process.exitCode = 1;
122
+ return;
123
+ }
124
+ throw err;
125
+ }
126
+ }
127
+ //# sourceMappingURL=add.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"add.js","sourceRoot":"","sources":["../../../src/cli/commands/add.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AACjC,OAAO,EAAE,SAAS,EAAE,MAAM,WAAW,CAAC;AACtC,OAAO,KAAK,MAAM,OAAO,CAAC;AAC1B,OAAO,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AACpD,OAAO,EAAE,gBAAgB,EAAE,MAAM,wBAAwB,CAAC;AAC1D,OAAO,EAAE,WAAW,EAAE,YAAY,EAAE,MAAM,0BAA0B,CAAC;AACrE,OAAO,EAAE,iBAAiB,EAAE,MAAM,2BAA2B,CAAC;AAC9D,OAAO,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAC;AACtD,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE1C,MAAM,OAAO,QAAS,SAAQ,KAAK;IACjC,YAAY,OAAe;QACzB,KAAK,CAAC,OAAO,CAAC,CAAC;QACf,IAAI,CAAC,IAAI,GAAG,UAAU,CAAC;IACzB,CAAC;CACF;AASD,MAAM,CAAC,KAAK,UAAU,MAAM,CAAC,IAAgB;IAC3C,MAAM,EAAE,WAAW,EAAE,SAAS,EAAE,GAAG,EAAE,IAAI,EAAE,YAAY,EAAE,GAAG,IAAI,CAAC;IACjE,MAAM,UAAU,GAAG,IAAI,CAAC,WAAW,EAAE,aAAa,CAAC,CAAC;IAEpD,sBAAsB;IACtB,MAAM,MAAM,GAAG,WAAW,CAAC,SAAS,CAAC,CAAC;IAEtC,6CAA6C;IAC7C,MAAM,YAAY,GAAG,GAAG,IAAI,MAAM,CAAC,GAAG,CAAC;IAEvC,sDAAsD;IACtD,IAAI,SAAiB,CAAC;IAEtB,IAAI,MAAM,CAAC,IAAI,KAAK,OAAO,EAAE,CAAC;QAC5B,wDAAwD;QACxD,MAAM,QAAQ,GAAG,MAAM,YAAY,CACjC,YAAY,IAAI,SAAS,EACzB,EAAE,MAAM,EAAE,SAAS,EAAE,EACrB,EAAE,WAAW,EAAE,CAChB,CAAC;QACF,IAAI,QAAQ,CAAC,IAAI,KAAK,OAAO;YAAE,MAAM,IAAI,QAAQ,CAAC,0CAA0C,CAAC,CAAC;QAE9F,MAAM,EAAE,WAAW,EAAE,GAAG,MAAM,MAAM,CAAC,wBAAwB,CAAC,CAAC;QAC/D,MAAM,EAAE,IAAI,EAAE,QAAQ,EAAE,GAAG,MAAM,MAAM,CAAC,WAAW,CAAC,CAAC;QACrD,MAAM,IAAI,GAAG,MAAM,WAAW,CAAC,QAAQ,CAAC,QAAQ,CAAC,QAAQ,EAAE,UAAU,CAAC,CAAC,CAAC;QACxE,SAAS,GAAG,YAAY,IAAI,IAAI,CAAC,IAAI,CAAC;IACxC,CAAC;SAAM,CAAC;QACN,kCAAkC;QAClC,MAAM,GAAG,GAAG,MAAM,CAAC,GAAI,CAAC;QACxB,MAAM,QAAQ,GACZ,MAAM,CAAC,IAAI,KAAK,QAAQ;YACtB,CAAC,CAAC,GAAG,MAAM,CAAC,KAAK,IAAI,MAAM,CAAC,IAAI,EAAE;YAClC,CAAC,CAAC,GAAG,CAAC,OAAO,CAAC,cAAc,EAAE,EAAE,CAAC,CAAC,OAAO,CAAC,QAAQ,EAAE,EAAE,CAAC,CAAC;QAE5D,MAAM,MAAM,GAAG,MAAM,YAAY,CAAC,EAAE,GAAG,EAAE,QAAQ,EAAE,GAAG,EAAE,YAAY,EAAE,CAAC,CAAC;QAExE,IAAI,YAAY,EAAE,CAAC;YACjB,wCAAwC;YACxC,MAAM,EAAE,aAAa,EAAE,GAAG,MAAM,MAAM,CAAC,2BAA2B,CAAC,CAAC;YACpE,MAAM,KAAK,GAAG,MAAM,aAAa,CAAC,MAAM,CAAC,OAAO,EAAE,YAAY,CAAC,CAAC;YAChE,IAAI,CAAC,KAAK,EAAE,CAAC;gBACX,MAAM,IAAI,QAAQ,CAChB,UAAU,YAAY,kBAAkB,SAAS,IAAI;oBACnD,sBAAsB,SAAS,2CAA2C,CAC7E,CAAC;YACJ,CAAC;YACD,SAAS,GAAG,YAAY,CAAC;QAC3B,CAAC;aAAM,CAAC;YACN,+BAA+B;YAC/B,MAAM,MAAM,GAAG,MAAM,iBAAiB,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC;YACvD,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;gBACxB,MAAM,IAAI,QAAQ,CAAC,sBAAsB,SAAS,GAAG,CAAC,CAAC;YACzD,CAAC;YACD,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;gBACxB,SAAS,GAAG,MAAM,CAAC,CAAC,CAAE,CAAC,IAAI,CAAC,IAAI,CAAC;YACnC,CAAC;iBAAM,CAAC;gBACN,8EAA8E;gBAC9E,MAAM,KAAK,GAAG,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,IAAI,EAAE,CAAC;gBACpD,MAAM,IAAI,QAAQ,CAChB,4BAA4B,SAAS,KAAK,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI;oBAC5D,kCAAkC,CACrC,CAAC;YACJ,CAAC;QACH,CAAC;IACH,CAAC;IAED,0CAA0C;IAC1C,MAAM,MAAM,GAAG,MAAM,UAAU,CAAC,UAAU,CAAC,CAAC;IAC5C,IAAI,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,KAAK,SAAS,CAAC,EAAE,CAAC;QACpD,MAAM,IAAI,QAAQ,CAChB,UAAU,SAAS,6EAA6E,CACjG,CAAC;IACJ,CAAC;IAED,0CAA0C;IAC1C,IAAI,MAAM,GAAG,SAAS,CAAC;IACvB,wFAAwF;IACxF,IAAI,MAAM,CAAC,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;QACvB,uCAAuC;IACzC,CAAC;SAAM,IAAI,YAAY,IAAI,CAAC,SAAS,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE,CAAC;QACpD,kCAAkC;IACpC,CAAC;IAED,gBAAgB;IAChB,MAAM,gBAAgB,CAAC,UAAU,EAAE,SAAS,EAAE;QAC5C,MAAM;QACN,GAAG,CAAC,YAAY,CAAC,CAAC,CAAC,EAAE,GAAG,EAAE,YAAY,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;KAC/C,CAAC,CAAC;IAEH,oDAAoD;IACpD,MAAM,UAAU,CAAC,EAAE,WAAW,EAAE,CAAC,CAAC;IAElC,OAAO,SAAS,CAAC;AACnB,CAAC;AAED,MAAM,CAAC,OAAO,CAAC,KAAK,UAAU,GAAG,CAAC,IAAc;IAC9C,MAAM,EAAE,WAAW,EAAE,MAAM,EAAE,GAAG,SAAS,CAAC;QACxC,IAAI;QACJ,gBAAgB,EAAE,IAAI;QACtB,OAAO,EAAE;YACP,GAAG,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;YACvB,IAAI,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;SACzB;QACD,MAAM,EAAE,IAAI;KACb,CAAC,CAAC;IAEH,MAAM,SAAS,GAAG,WAAW,CAAC,CAAC,CAAC,CAAC;IACjC,IAAI,CAAC,SAAS,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,gEAAgE,CAAC,CAAC,CAAC;QAC3F,OAAO,CAAC,QAAQ,GAAG,CAAC,CAAC;QACrB,OAAO;IACT,CAAC;IAED,MAAM,EAAE,OAAO,EAAE,GAAG,MAAM,MAAM,CAAC,WAAW,CAAC,CAAC;IAC9C,IAAI,CAAC;QACH,MAAM,IAAI,GAAG,MAAM,MAAM,CAAC;YACxB,WAAW,EAAE,OAAO,CAAC,GAAG,CAAC;YACzB,SAAS;YACT,GAAG,EAAE,MAAM,CAAC,KAAK,CAAC;YAClB,IAAI,EAAE,MAAM,CAAC,MAAM,CAAC;SACrB,CAAC,CAAC;QACH,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,KAAK,CAAC,gBAAgB,IAAI,EAAE,CAAC,CAAC,CAAC;IACnD,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,IAAI,GAAG,YAAY,QAAQ,EAAE,CAAC;YAC5B,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC,CAAC;YACtC,OAAO,CAAC,QAAQ,GAAG,CAAC,CAAC;YACrB,OAAO;QACT,CAAC;QACD,MAAM,GAAG,CAAC;IACZ,CAAC;AACH,CAAC"}
@@ -0,0 +1,10 @@
1
+ export interface InitOptions {
2
+ force?: boolean;
3
+ projectRoot: string;
4
+ }
5
+ export declare function runInit(opts: InitOptions): Promise<void>;
6
+ export declare class InitError extends Error {
7
+ constructor(message: string);
8
+ }
9
+ export default function init(args: string[]): Promise<void>;
10
+ //# sourceMappingURL=init.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"init.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/init.ts"],"names":[],"mappings":"AAUA,MAAM,WAAW,WAAW;IAC1B,KAAK,CAAC,EAAE,OAAO,CAAC;IAChB,WAAW,EAAE,MAAM,CAAC;CACrB;AAED,wBAAsB,OAAO,CAAC,IAAI,EAAE,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC,CA0B9D;AAoCD,qBAAa,SAAU,SAAQ,KAAK;gBACtB,OAAO,EAAE,MAAM;CAI5B;AAED,wBAA8B,IAAI,CAAC,IAAI,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC,CAoBhE"}
@@ -0,0 +1,81 @@
1
+ import { existsSync } from "node:fs";
2
+ import { mkdir, writeFile } from "node:fs/promises";
3
+ import { join } from "node:path";
4
+ import chalk from "chalk";
5
+ import { generateDefaultConfig } from "../../config/writer.js";
6
+ import { updateAgentsGitignore } from "../../gitignore/writer.js";
7
+ import { ensureSkillsSymlink } from "../../symlinks/manager.js";
8
+ import { loadConfig } from "../../config/loader.js";
9
+ import { parseArgs } from "node:util";
10
+ export async function runInit(opts) {
11
+ const { projectRoot, force } = opts;
12
+ const configPath = join(projectRoot, "agents.toml");
13
+ const agentsDir = join(projectRoot, ".agents");
14
+ const skillsDir = join(agentsDir, "skills");
15
+ if (existsSync(configPath) && !force) {
16
+ throw new InitError("agents.toml already exists. Use --force to overwrite.");
17
+ }
18
+ await writeFile(configPath, generateDefaultConfig(), "utf-8");
19
+ await mkdir(skillsDir, { recursive: true });
20
+ // Set up gitignore and symlinks based on config
21
+ const config = await loadConfig(configPath);
22
+ await updateAgentsGitignore(agentsDir, config.gitignore, []);
23
+ const targets = config.symlinks?.targets ?? [];
24
+ const symlinkResults = [];
25
+ for (const target of targets) {
26
+ const targetDir = join(projectRoot, target);
27
+ const result = await ensureSkillsSymlink(agentsDir, targetDir);
28
+ symlinkResults.push({ target, ...result });
29
+ }
30
+ return printSummary(config.gitignore, symlinkResults);
31
+ }
32
+ function printSummary(gitignore, symlinks) {
33
+ // eslint-disable-next-line no-console
34
+ console.log(chalk.green("Created agents.toml"));
35
+ // eslint-disable-next-line no-console
36
+ console.log(chalk.green("Created .agents/skills/"));
37
+ if (gitignore) {
38
+ // eslint-disable-next-line no-console
39
+ console.log(chalk.green("Created .agents/.gitignore"));
40
+ }
41
+ for (const s of symlinks) {
42
+ if (s.created) {
43
+ // eslint-disable-next-line no-console
44
+ console.log(chalk.green(`Created symlink: ${s.target}/skills/ → .agents/skills/`));
45
+ }
46
+ if (s.migrated.length > 0) {
47
+ // eslint-disable-next-line no-console
48
+ console.log(chalk.yellow(`Migrated ${s.migrated.length} skill(s) from ${s.target}/skills/ to .agents/skills/`));
49
+ }
50
+ }
51
+ // eslint-disable-next-line no-console
52
+ console.log(`\n${chalk.bold("Next steps:")}\n 1. Add skills: dotagents add @anthropics/pdf-processing\n 2. Install: dotagents install`);
53
+ }
54
+ export class InitError extends Error {
55
+ constructor(message) {
56
+ super(message);
57
+ this.name = "InitError";
58
+ }
59
+ }
60
+ export default async function init(args) {
61
+ const { values } = parseArgs({
62
+ args,
63
+ options: {
64
+ force: { type: "boolean" },
65
+ },
66
+ strict: true,
67
+ });
68
+ const { resolve } = await import("node:path");
69
+ try {
70
+ await runInit({ projectRoot: resolve("."), force: values["force"] });
71
+ }
72
+ catch (err) {
73
+ if (err instanceof InitError) {
74
+ console.error(chalk.red(err.message));
75
+ process.exitCode = 1;
76
+ return;
77
+ }
78
+ throw err;
79
+ }
80
+ }
81
+ //# sourceMappingURL=init.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"init.js","sourceRoot":"","sources":["../../../src/cli/commands/init.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=init.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"init.test.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/init.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,71 @@
1
+ import { describe, it, expect, beforeEach, afterEach } from "vitest";
2
+ import { mkdtemp, rm, writeFile, lstat, readdir } from "node:fs/promises";
3
+ import { join } from "node:path";
4
+ import { tmpdir } from "node:os";
5
+ import { existsSync } from "node:fs";
6
+ import { runInit, InitError } from "./init.js";
7
+ import { loadConfig } from "../../config/loader.js";
8
+ describe("runInit", () => {
9
+ let dir;
10
+ beforeEach(async () => {
11
+ dir = await mkdtemp(join(tmpdir(), "dotagents-init-test-"));
12
+ });
13
+ afterEach(async () => {
14
+ await rm(dir, { recursive: true });
15
+ });
16
+ it("creates agents.toml in project root", async () => {
17
+ await runInit({ projectRoot: dir });
18
+ const config = await loadConfig(join(dir, "agents.toml"));
19
+ expect(config.version).toBe(1);
20
+ expect(config.skills).toEqual([]);
21
+ });
22
+ it("creates .agents/skills/ directory", async () => {
23
+ await runInit({ projectRoot: dir });
24
+ const stat = await lstat(join(dir, ".agents", "skills"));
25
+ expect(stat.isDirectory()).toBe(true);
26
+ });
27
+ it("does not create .agents/.gitignore with default config (gitignore = false)", async () => {
28
+ await runInit({ projectRoot: dir });
29
+ expect(existsSync(join(dir, ".agents", ".gitignore"))).toBe(false);
30
+ });
31
+ it("throws InitError if agents.toml exists without --force", async () => {
32
+ await writeFile(join(dir, "agents.toml"), "version = 1\n");
33
+ await expect(runInit({ projectRoot: dir })).rejects.toThrow(InitError);
34
+ await expect(runInit({ projectRoot: dir })).rejects.toThrow("agents.toml already exists");
35
+ });
36
+ it("overwrites agents.toml with --force", async () => {
37
+ await writeFile(join(dir, "agents.toml"), "garbage content");
38
+ await runInit({ projectRoot: dir, force: true });
39
+ const config = await loadConfig(join(dir, "agents.toml"));
40
+ expect(config.version).toBe(1);
41
+ });
42
+ it("is idempotent with --force", async () => {
43
+ await runInit({ projectRoot: dir });
44
+ await runInit({ projectRoot: dir, force: true });
45
+ const config = await loadConfig(join(dir, "agents.toml"));
46
+ expect(config.version).toBe(1);
47
+ expect(existsSync(join(dir, ".agents", "skills"))).toBe(true);
48
+ });
49
+ it("does not create symlinks with default config", async () => {
50
+ await runInit({ projectRoot: dir });
51
+ // Default config has no symlinks configured, so .claude should not exist
52
+ expect(existsSync(join(dir, ".claude"))).toBe(false);
53
+ });
54
+ it("creates all expected files and directories", async () => {
55
+ await runInit({ projectRoot: dir });
56
+ expect(existsSync(join(dir, "agents.toml"))).toBe(true);
57
+ expect(existsSync(join(dir, ".agents"))).toBe(true);
58
+ expect(existsSync(join(dir, ".agents", "skills"))).toBe(true);
59
+ // Default config has gitignore = false, so no .gitignore is created
60
+ expect(existsSync(join(dir, ".agents", ".gitignore"))).toBe(false);
61
+ });
62
+ it("preserves existing .agents/skills/ contents", async () => {
63
+ const { mkdir, writeFile: wf } = await import("node:fs/promises");
64
+ await mkdir(join(dir, ".agents", "skills", "my-skill"), { recursive: true });
65
+ await wf(join(dir, ".agents", "skills", "my-skill", "SKILL.md"), "# test");
66
+ await runInit({ projectRoot: dir });
67
+ const entries = await readdir(join(dir, ".agents", "skills"));
68
+ expect(entries).toContain("my-skill");
69
+ });
70
+ });
71
+ //# sourceMappingURL=init.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"init.test.js","sourceRoot":"","sources":["../../../src/cli/commands/init.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,15 @@
1
+ export declare class InstallError extends Error {
2
+ constructor(message: string);
3
+ }
4
+ export interface InstallOptions {
5
+ projectRoot: string;
6
+ frozen?: boolean;
7
+ force?: boolean;
8
+ }
9
+ export interface InstallResult {
10
+ installed: string[];
11
+ skipped: string[];
12
+ }
13
+ export declare function runInstall(opts: InstallOptions): Promise<InstallResult>;
14
+ export default function install(args: string[]): Promise<void>;
15
+ //# sourceMappingURL=install.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"install.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/install.ts"],"names":[],"mappings":"AAgBA,qBAAa,YAAa,SAAQ,KAAK;gBACzB,OAAO,EAAE,MAAM;CAI5B;AAED,MAAM,WAAW,cAAc;IAC7B,WAAW,EAAE,MAAM,CAAC;IACpB,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB,KAAK,CAAC,EAAE,OAAO,CAAC;CACjB;AAED,MAAM,WAAW,aAAa;IAC5B,SAAS,EAAE,MAAM,EAAE,CAAC;IACpB,OAAO,EAAE,MAAM,EAAE,CAAC;CACnB;AAED,wBAAsB,UAAU,CAAC,IAAI,EAAE,cAAc,GAAG,OAAO,CAAC,aAAa,CAAC,CAiH7E;AAED,wBAA8B,OAAO,CAAC,IAAI,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC,CA+BnE"}
@@ -0,0 +1,139 @@
1
+ import { join } from "node:path";
2
+ import { mkdir } from "node:fs/promises";
3
+ import { parseArgs } from "node:util";
4
+ import chalk from "chalk";
5
+ import { loadConfig } from "../../config/loader.js";
6
+ import { loadLockfile } from "../../lockfile/loader.js";
7
+ import { writeLockfile } from "../../lockfile/writer.js";
8
+ import { isGitLocked } from "../../lockfile/schema.js";
9
+ import { resolveSkill } from "../../skills/resolver.js";
10
+ import { hashDirectory } from "../../utils/hash.js";
11
+ import { copyDir } from "../../utils/fs.js";
12
+ import { updateAgentsGitignore } from "../../gitignore/writer.js";
13
+ import { ensureSkillsSymlink } from "../../symlinks/manager.js";
14
+ export class InstallError extends Error {
15
+ constructor(message) {
16
+ super(message);
17
+ this.name = "InstallError";
18
+ }
19
+ }
20
+ export async function runInstall(opts) {
21
+ const { projectRoot, frozen, force } = opts;
22
+ const configPath = join(projectRoot, "agents.toml");
23
+ const lockPath = join(projectRoot, "agents.lock");
24
+ const agentsDir = join(projectRoot, ".agents");
25
+ const skillsDir = join(agentsDir, "skills");
26
+ // 1. Read config
27
+ const config = await loadConfig(configPath);
28
+ const skillNames = config.skills.map((s) => s.name);
29
+ if (skillNames.length === 0) {
30
+ console.log(chalk.dim("No skills declared in agents.toml."));
31
+ return { installed: [], skipped: [] };
32
+ }
33
+ // 2. Read lockfile
34
+ const lockfile = await loadLockfile(lockPath);
35
+ if (frozen && !lockfile) {
36
+ throw new InstallError("--frozen requires agents.lock to exist.");
37
+ }
38
+ if (frozen) {
39
+ // Verify all skills are in lockfile
40
+ for (const name of skillNames) {
41
+ if (!lockfile.skills[name]) {
42
+ throw new InstallError(`--frozen: skill "${name}" is in agents.toml but missing from agents.lock.`);
43
+ }
44
+ }
45
+ }
46
+ // 3. Ensure directories exist
47
+ await mkdir(skillsDir, { recursive: true });
48
+ // 4. Resolve and install each skill
49
+ const newLock = { version: 1, skills: {} };
50
+ const installed = [];
51
+ const skipped = [];
52
+ for (const name of skillNames) {
53
+ const dep = config.skills.find((s) => s.name === name);
54
+ const locked = lockfile?.skills[name];
55
+ // If locked and not forced, use the locked commit
56
+ const lockedCommit = !force && locked && isGitLocked(locked) ? locked.commit : undefined;
57
+ let resolved;
58
+ try {
59
+ resolved = await resolveSkill(name, dep, {
60
+ projectRoot,
61
+ lockedCommit,
62
+ });
63
+ }
64
+ catch (err) {
65
+ const msg = err instanceof Error ? err.message : String(err);
66
+ throw new InstallError(`Failed to resolve skill "${name}": ${msg}`);
67
+ }
68
+ // Copy skill into .agents/skills/<name>/
69
+ const destDir = join(skillsDir, name);
70
+ await copyDir(resolved.skillDir, destDir);
71
+ // Compute integrity hash
72
+ const integrity = await hashDirectory(destDir);
73
+ // Frozen mode: verify integrity matches lockfile
74
+ if (frozen && locked) {
75
+ if (locked.integrity !== integrity) {
76
+ throw new InstallError(`--frozen: integrity mismatch for "${name}". ` +
77
+ `Expected ${locked.integrity}, got ${integrity}.`);
78
+ }
79
+ }
80
+ // Build lock entry
81
+ const lockEntry = resolved.type === "git"
82
+ ? {
83
+ source: dep.source,
84
+ resolved_url: resolved.resolvedUrl,
85
+ resolved_path: resolved.resolvedPath,
86
+ ...(resolved.resolvedRef ? { resolved_ref: resolved.resolvedRef } : {}),
87
+ commit: resolved.commit,
88
+ integrity,
89
+ }
90
+ : {
91
+ source: dep.source,
92
+ integrity,
93
+ };
94
+ newLock.skills[name] = lockEntry;
95
+ installed.push(name);
96
+ }
97
+ // 5. Write lockfile (unless frozen)
98
+ if (!frozen) {
99
+ await writeLockfile(lockPath, newLock);
100
+ }
101
+ // 6. Regenerate .agents/.gitignore
102
+ await updateAgentsGitignore(agentsDir, config.gitignore, skillNames);
103
+ // 7. Create/verify symlinks
104
+ const targets = config.symlinks?.targets ?? [];
105
+ for (const target of targets) {
106
+ await ensureSkillsSymlink(agentsDir, join(projectRoot, target));
107
+ }
108
+ return { installed, skipped };
109
+ }
110
+ export default async function install(args) {
111
+ const { values } = parseArgs({
112
+ args,
113
+ options: {
114
+ frozen: { type: "boolean" },
115
+ force: { type: "boolean" },
116
+ },
117
+ strict: true,
118
+ });
119
+ const { resolve } = await import("node:path");
120
+ try {
121
+ const result = await runInstall({
122
+ projectRoot: resolve("."),
123
+ frozen: values["frozen"],
124
+ force: values["force"],
125
+ });
126
+ if (result.installed.length > 0) {
127
+ console.log(chalk.green(`Installed ${result.installed.length} skill(s): ${result.installed.join(", ")}`));
128
+ }
129
+ }
130
+ catch (err) {
131
+ if (err instanceof InstallError) {
132
+ console.error(chalk.red(err.message));
133
+ process.exitCode = 1;
134
+ return;
135
+ }
136
+ throw err;
137
+ }
138
+ }
139
+ //# sourceMappingURL=install.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"install.js","sourceRoot":"","sources":["../../../src/cli/commands/install.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=install.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"install.test.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/install.test.ts"],"names":[],"mappings":""}