argsbarg 6.2.2 → 6.3.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 (40) hide show
  1. package/CHANGELOG.md +14 -1
  2. package/README.md +2 -2
  3. package/docs/README.md +2 -2
  4. package/docs/ai-skills.md +7 -7
  5. package/docs/bundled-docs.md +2 -2
  6. package/docs/cli-program.md +4 -4
  7. package/docs/configure.md +36 -14
  8. package/docs/developing.md +7 -3
  9. package/docs/distribution-homebrew.md +2 -2
  10. package/docs/mcp.md +3 -3
  11. package/examples/full-example/.cursor/hooks/run-tests-on-stop.ts +56 -0
  12. package/examples/full-example/.cursor/hooks.json +12 -0
  13. package/examples/full-example/Formula/full-example.rb +1 -1
  14. package/examples/full-example/docs/cli-schema.json +6 -6
  15. package/examples/full-example/docs/cli.md +6 -6
  16. package/examples/full-example/docs/mcp.md +2 -2
  17. package/examples/full-example/docs/skill.md +1 -1
  18. package/examples/full-example/justfile +12 -12
  19. package/examples/full-example/scripts/formula-shared.ts +1 -1
  20. package/examples/full-example-json/.cursor/hooks/run-tests-on-stop.ts +56 -0
  21. package/examples/full-example-json/.cursor/hooks.json +12 -0
  22. package/examples/full-example-json/Formula/full-example-json.rb +1 -1
  23. package/examples/full-example-json/docs/cli-schema.json +27 -27
  24. package/examples/full-example-json/docs/cli.md +27 -27
  25. package/examples/full-example-json/docs/mcp.md +2 -2
  26. package/examples/full-example-json/docs/skill.md +1 -1
  27. package/examples/full-example-json/justfile +12 -12
  28. package/examples/full-example-json/scripts/formula-shared.ts +1 -1
  29. package/index.d.ts +20 -4
  30. package/package.json +1 -1
  31. package/src/builtins/builtins.test.ts +7 -7
  32. package/src/builtins/configure-copy.ts +2 -2
  33. package/src/builtins/configure.ts +4 -4
  34. package/src/configure/configure.test.ts +85 -12
  35. package/src/configure/index.ts +45 -13
  36. package/src/core/types.ts +21 -4
  37. package/src/docs/docs.test.ts +2 -2
  38. package/src/docs/mcp-guide.ts +2 -2
  39. package/src/index.ts +1 -0
  40. package/src/skill/generate.ts +1 -1
package/CHANGELOG.md CHANGED
@@ -7,6 +7,18 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
7
7
 
8
8
  ## [Unreleased]
9
9
 
10
+ ## [6.3.0] - 2026-08-07
11
+
12
+ ### Added
13
+
14
+ - **Cursor `stop` hook** — `.cursor/hooks.json` runs `just test` after agent edits to `justfile` or `*.{ts,tsx,js,jsx}` (excluding `node_modules/`, `dist/`, `.cursor/`); test failures auto-submit up to 20 follow-ups. Shipped in copy templates and argsbarg repo root (Cursor-only; not in `AGENTS.md`).
15
+ - **`configure` lifecycle hooks** — `program.configure.afterRefresh` and `program.configure.beforeRemoveAll` for app-specific agent artifact setup/teardown around `configure --refresh` and `configure --remove-all`.
16
+
17
+ ### Changed
18
+
19
+ - **Breaking: `configure --sync` → `configure --refresh`** — renames the non-interactive agent-artifact refresh flag (skills, MCP, config bootstrap). `just sync-artifacts` → `just refresh-artifacts`. No `--sync` alias.
20
+ - **Copy-template justfiles** — `install-local` uses `brew install --force`; uninstall/untap recipes prefix `NONINTERACTIVE=1` so agents and CI skip Homebrew confirm prompts (including post-uninstall untap). `install-production` unchanged.
21
+
10
22
  ## [6.2.2] - 2026-08-07
11
23
 
12
24
  ### Changed
@@ -903,7 +915,8 @@ const cli = { ... } satisfies CliProgram; // or : CliProgram
903
915
  - Migrate schemas: rename every `children` property to **`commands`**; move positional definitions to **`CliPositional`** objects on `positionals` and strip `positional` / `argMin` / `argMax` from flag definitions under `options` (flags only carry `name`, `description`, `kind`, and optional `shortName`).
904
916
  - Imports: use `CliPositional` where needed; replace `CliOptionDef` with `CliOption` or `CliPositional` as appropriate.
905
917
 
906
- [Unreleased]: https://github.com/bdombro/bun-argsbarg/compare/v6.2.2...HEAD
918
+ [Unreleased]: https://github.com/bdombro/bun-argsbarg/compare/v6.3.0...HEAD
919
+ [6.3.0]: https://github.com/bdombro/bun-argsbarg/releases/tag/v6.3.0
907
920
  [6.2.2]: https://github.com/bdombro/bun-argsbarg/releases/tag/v6.2.2
908
921
  [6.2.1]: https://github.com/bdombro/bun-argsbarg/releases/tag/v6.2.1
909
922
  [6.2.0]: https://github.com/bdombro/bun-argsbarg/releases/tag/v6.2.0
package/README.md CHANGED
@@ -158,7 +158,7 @@ ArgsBarg automatically integrates several core features into your application. T
158
158
  ### Experimental Integrations (Opt-in)
159
159
 
160
160
  - `mcp` — Run as a Model Context Protocol stdio-based agent server (injected when `mcpServer.enabled` is `true`). See [docs/mcp.md](docs/mcp.md).
161
- - `configure` (`--sync` / `--status` / `--remove-all`) — Interactive environment setup and developer agent credentials sync (enabled by default; opt out with `configure: { enabled: false }`). See [docs/configure.md](docs/configure.md).
161
+ - `configure` (`--refresh` / `--status` / `--remove-all`) — Interactive environment setup and developer agent credentials sync (enabled by default; opt out with `configure: { enabled: false }`). See [docs/configure.md](docs/configure.md).
162
162
 
163
163
  Do not declare top-level commands named `completion`, `version`, or `docs` as they are reserved by default. If their respective features are enabled, `http`, `mcp`, and `configure` are also reserved.
164
164
 
@@ -385,7 +385,7 @@ This refreshes the argsbarg-managed section in `AGENTS.md` while preserving your
385
385
 
386
386
  ### 3. Generated Skills & Workspace Configuration
387
387
 
388
- Running `myapp configure --sync` installs a compact `SKILL.md` index and full-reference `reference.md` to `~/.agents/skills/<key>/` when `program.skill: { enabled: true }`.
388
+ Running `myapp configure --refresh` installs a compact `SKILL.md` index and full-reference `reference.md` to `~/.agents/skills/<key>/` when `program.skill: { enabled: true }`.
389
389
 
390
390
  See **[docs/configure.md](docs/configure.md)** and **[docs/ai-skills.md](docs/ai-skills.md)** for developer setup and automated Homebrew pipeline integration.
391
391
 
package/docs/README.md CHANGED
@@ -9,10 +9,10 @@ Start here to pick the right guide.
9
9
  | **JSON stdout / `outputSchema`** | [output-schema.md](output-schema.md) — codegen pipeline, JSDoc, narrowing |
10
10
  | **App config / `program.appConfig`** | [config-schema.md](config-schema.md) — flat JSON file, `ctx.appConfig`, codegen |
11
11
  | **JSON Schema validation** | [json-schema-subset.md](json-schema-subset.md) — Draft-07 / 2019-09 / 2020-12 (`$schema` on each schema; default Draft-07) |
12
- | **Exposing MCP tools** | [mcp.md](mcp.md) — stdio server, `inputSchema`, varargs, `configure --sync` |
12
+ | **Exposing MCP tools** | [mcp.md](mcp.md) — stdio server, `inputSchema`, varargs, `configure --refresh` |
13
13
  | **HTTP tool server** | [http-server.md](http-server.md) — `myapp http`, endpoints, curl examples |
14
14
  | **Server logging** (`program.log`, `enrich`, `serialize`) | [logging.md](logging.md) — ECS JSON lines, trace headers, custom formats |
15
- | **Shipping configure / agent artifacts** | [configure.md](configure.md) — Homebrew + `myapp configure --sync` |
15
+ | **Shipping configure / agent artifacts** | [configure.md](configure.md) — Homebrew + `myapp configure --refresh` |
16
16
  | **Homebrew tap-from-repo distribution** | [distribution-homebrew.md](distribution-homebrew.md) — formula pattern, `argsbarg create` |
17
17
  | **Bundling `myapp docs` topics** | [bundled-docs.md](bundled-docs.md) — consumer docgen vs framework docs |
18
18
  | **Agent skills** | [ai-skills.md](ai-skills.md) — `configure`, `docs skill` |
package/docs/ai-skills.md CHANGED
@@ -14,17 +14,17 @@ export const program = {
14
14
  } satisfies CliProgram;
15
15
  ```
16
16
 
17
- When `skill.enabled` is `true`, Homebrew `post_install` (`configure --sync --yes`) installs and refreshes the skill. When omitted or `enabled` is not `true`, no skill is installed.
17
+ When `skill.enabled` is `true`, Homebrew `post_install` (`configure --refresh --yes`) installs and refreshes the skill. When omitted or `enabled` is not `true`, no skill is installed.
18
18
 
19
19
  The skill directory name is the program `key` with `/`, `\`, and spaces replaced by `_` (e.g. `sqsp-qa`, `full-example`).
20
20
 
21
- ## Install via `configure --sync`
21
+ ## Install via `configure --refresh`
22
22
 
23
23
  ```bash
24
- myapp configure --sync --yes
24
+ myapp configure --refresh --yes
25
25
  ```
26
26
 
27
- Skills are not prompted during interactive `configure` — install and uninstall are automatic when `skill.enabled` is set (brew install/uninstall and `--sync` / `--remove-all`).
27
+ Skills are not prompted during interactive `configure` — install and uninstall are automatic when `skill.enabled` is set (brew install/uninstall and `--refresh` / `--remove-all`).
28
28
 
29
29
  ## Programmatic install
30
30
 
@@ -46,7 +46,7 @@ Installed files include an HTML comment hint (`Generated by myapp configure; do
46
46
 
47
47
  | Client | Skill path |
48
48
  | --- | --- |
49
- | Cursor, Codex, Copilot, most agents | `~/.agents/skills/<key>/` (auto via `configure --sync`) |
49
+ | Cursor, Codex, Copilot, most agents | `~/.agents/skills/<key>/` (auto via `configure --refresh`) |
50
50
  | Claude Code | Manual symlink to `~/.claude/skills/<key>/` |
51
51
 
52
52
  ```bash
@@ -61,10 +61,10 @@ Skills describe **shell invocation only** — no MCP setup or `tools/call` guida
61
61
  | Mechanism | Role |
62
62
  | --- | --- |
63
63
  | **`myapp mcp`** (requires `mcpServer`) | Runtime tool execution over MCP |
64
- | **`program.skill.enabled`** + **`configure --sync`** | Persists optimized skill bundle at `~/.agents/skills/<key>/` |
64
+ | **`program.skill.enabled`** + **`configure --refresh`** | Persists optimized skill bundle at `~/.agents/skills/<key>/` |
65
65
  | **`myapp docs`** (requires `docs`) | Bundled markdown on stdout (`docs mcp` when MCP enabled) |
66
66
 
67
- `skill.md` is the routing index; `reference.md` matches `docs cli`. Prefer `configure --sync` over `docs skill` for installed agents. See [cli-program.md](cli-program.md).
67
+ `skill.md` is the routing index; `reference.md` matches `docs cli`. Prefer `configure --refresh` over `docs skill` for installed agents. See [cli-program.md](cli-program.md).
68
68
 
69
69
  **Claude Code plugin** (`mcpServer.claudePlugin: true` → `mcp bundle` writes `dist/claude-plugin/<name>.zip`) ships a separate MCP pointer skill (`SKILL.md` only) that routes agents to the bundled MCP server. This is a **dist artifact**, not installed via `configure`.
70
70
 
@@ -97,11 +97,11 @@ By default (unless `docs.enabled: false`):
97
97
 
98
98
  - **`docs cli-schema`** — same JSON as the former root `--schema` flag (handlers omitted; built-in subtrees included for leaf roots).
99
99
  - **`docs cli`** — markdown rendering of the same command tree (options, positionals, subcommands, fallback routing).
100
- - **`docs skill`** — prints the compact `SKILL.md` index. Prefer `configure --sync --yes` for agents (persists index + full API in `reference.md`).
100
+ - **`docs skill`** — prints the compact `SKILL.md` index. Prefer `configure --refresh --yes` for agents (persists index + full API in `reference.md`).
101
101
 
102
102
  ## MCP guide (`docs mcp`)
103
103
 
104
- When both docs (default) and `mcpServer.enabled` are `true`, ArgsBarg injects a **`docs mcp`** topic with an auto-generated guide: tool list, `program.appConfig`, schema resource URI, `configure --sync`, and protocol notes.
104
+ When both docs (default) and `mcpServer.enabled` are `true`, ArgsBarg injects a **`docs mcp`** topic with an auto-generated guide: tool list, `program.appConfig`, schema resource URI, `configure --refresh`, and protocol notes.
105
105
 
106
106
  There is no override API in v1 — customize behavior via `mcpTool.description` on leaf commands.
107
107
 
@@ -541,9 +541,9 @@ await cli.run();
541
541
  - **Strict:** unknown keys rejected on load.
542
542
  - **CLI:** missing required config exits 1 before the leaf handler (TTY prompt when interactive). Built-in `docs` and `configure get`/`set` skip this exit.
543
543
  - **MCP:** server stays up; missing config returns `isError: true` at `tools/call`.
544
- - **Configure:** interactive `configure` runs the app config wizard; **`configure --sync`** refreshes agent artifacts to `~/.agents/` (see https://dotagentsprotocol.com).
545
- - **Agent skill:** `program.skill: { enabled: true }` installs to `~/.agents/skills/<key>/` on `configure --sync`; see [configure.md](configure.md) and [ai-skills.md](ai-skills.md).
546
- - **MCP install:** `mcpServer: { enabled: true }` merges into `~/.agents/mcp.json` on `configure --sync`; manual Cursor/Claude setup in [mcp.md](mcp.md).
544
+ - **Configure:** interactive `configure` runs the app config wizard; **`configure --refresh`** refreshes agent artifacts to `~/.agents/` (see https://dotagentsprotocol.com). Optional `configure.afterRefresh` / `configure.beforeRemoveAll` for app-specific agent setup; see [configure.md](configure.md).
545
+ - **Agent skill:** `program.skill: { enabled: true }` installs to `~/.agents/skills/<key>/` on `configure --refresh`; see [configure.md](configure.md) and [ai-skills.md](ai-skills.md).
546
+ - **MCP install:** `mcpServer: { enabled: true }` merges into `~/.agents/mcp.json` on `configure --refresh`; manual Cursor/Claude setup in [mcp.md](mcp.md).
547
547
 
548
548
  See [config-schema.md](config-schema.md) for codegen, [configure.md](configure.md) (`configure.targets`), and [mcp.md](mcp.md).
549
549
 
@@ -582,7 +582,7 @@ If you maintain argsbarg from a sibling checkout, `just consumers-dev` / `just c
582
582
 
583
583
  3. **Optional:** add consumer-specific sections above the `<!-- argsbarg:managed -->` marker in `AGENTS.md` (project context, Ink patterns, domain notes).
584
584
 
585
- - **Not this file:** `myapp configure --sync` writes the **app** skill (`SKILL.md` under `~/.agents/skills/<key>/`) from your command schema — how to *invoke* the CLI. `AGENTS.md` is for *authoring* argsbarg schema.
585
+ - **Not this file:** `myapp configure --refresh` writes the **app** skill (`SKILL.md` under `~/.agents/skills/<key>/`) from your command schema — how to *invoke* the CLI. `AGENTS.md` is for *authoring* argsbarg schema.
586
586
 
587
587
  ## See also
588
588
 
package/docs/configure.md CHANGED
@@ -35,13 +35,13 @@ just build
35
35
  just install-local # same formula as production; temporary file:// URL during brew install (`just install` is an alias)
36
36
  ```
37
37
 
38
- Dev flow matches release: formula `install` copies the binary and generates completions; `post_install` runs `<key> configure --sync --yes` for skills/MCP. Use `just reinstall-local` to swap the binary into Cellar during tight edit cycles (skips completions and `post_install`). Use `just sync-artifacts` to refresh agent artifacts without touching the binary.
38
+ Dev flow matches release: formula `install` copies the binary and generates completions; `post_install` runs `<key> configure --refresh --yes` for skills/MCP. Use `just reinstall-local` to swap the binary into Cellar during tight edit cycles (skips completions and `post_install`). Use `just refresh-artifacts` to refresh agent artifacts without touching the binary.
39
39
 
40
40
  ## Quick reference
41
41
 
42
42
  ```bash
43
43
  # Refresh skills/MCP after upgrade (Homebrew post_install runs this automatically)
44
- <key> configure --sync --yes
44
+ <key> configure --refresh --yes
45
45
 
46
46
  # See what is installed
47
47
  <key> configure --status
@@ -60,7 +60,7 @@ Dev flow matches release: formula `install` copies the binary and generates comp
60
60
  <key> configure set <key> <value> [--json] [--from-env]
61
61
  ```
62
62
 
63
- Non-interactive / CI: pass **`--yes`** (or **`--json`**, **`--sync`**, **`--remove-all`**, **`--remove-config`**) — see [Confirmation](#confirmation).
63
+ Non-interactive / CI: pass **`--yes`** (or **`--json`**, **`--refresh`**, **`--remove-all`**, **`--remove-config`**) — see [Confirmation](#confirmation).
64
64
 
65
65
  ## What gets configured
66
66
 
@@ -70,35 +70,35 @@ Non-interactive / CI: pass **`--yes`** (or **`--json`**, **`--sync`**, **`--remo
70
70
  | Shell completions | skipped | Homebrew `generate_completions_from_executable` |
71
71
  | Agent skill | skipped (automatic) | `~/.agents/skills/<key>/` when `program.skill.enabled` |
72
72
  | MCP config | skipped (automatic) | `~/.agents/mcp.json` when `mcpServer.enabled` (see https://dotagentsprotocol.com) |
73
- | App config | auto-runs wizard | Interactive wizard may update `~/.local/lib/<key>/config.json` when values change; `--sync` bootstraps an empty file on install |
73
+ | App config | auto-runs wizard | Interactive wizard may update `~/.local/lib/<key>/config.json` when values change; `--refresh` bootstraps an empty file on install |
74
74
 
75
75
  ### Externally managed binary (Homebrew)
76
76
 
77
77
  When **`PATH`** resolves the program key to the **running executable** (e.g. after `brew install`):
78
78
 
79
79
  - **`configure --status`** shows `app: system (PATH)`
80
- - **`configure --sync`** refreshes the agent skill (when `program.skill.enabled`) and merges MCP into `~/.agents/mcp.json` (when `mcpServer.enabled`); also creates `~/.local/lib/<key>/config.json` as `{}` when missing (all apps)
80
+ - **`configure --refresh`** refreshes the agent skill (when `program.skill.enabled`) and merges MCP into `~/.agents/mcp.json` (when `mcpServer.enabled`); also creates `~/.local/lib/<key>/config.json` as `{}` when missing (all apps)
81
81
 
82
82
  MCP config uses the command name on **`PATH`**, not a Cellar path. For Cursor, Claude Code, and Claude Desktop, copy the `mcpServers` entry manually — see [mcp.md](mcp.md) and `docs mcp`.
83
83
 
84
84
  ### Interactive default
85
85
 
86
- Bare **`configure`** (TTY required) runs the app config wizard when `program.appConfig` has entries. Agent skills and MCP are **not** prompted — they install automatically via brew `post_install` / `--sync` when `program.skill.enabled` or `mcpServer.enabled` respectively.
86
+ Bare **`configure`** (TTY required) runs the app config wizard when `program.appConfig` has entries. Agent skills and MCP are **not** prompted — they install automatically via brew `post_install` / `--refresh` when `program.skill.enabled` or `mcpServer.enabled` respectively.
87
87
 
88
88
  Remove the config file with **`configure --remove-config --yes`**.
89
89
 
90
- The **`app`** and **`skill`** / **`agentsMcp`** targets are shown in `--status` only — never mutated by interactive `configure` (use `--sync` / brew hooks).
90
+ The **`app`** and **`skill`** / **`agentsMcp`** targets are shown in `--status` only — never mutated by interactive `configure` (use `--refresh` / brew hooks).
91
91
 
92
92
  ### `configure.targets`
93
93
 
94
- Optional gates for app binary status and app-config wizard participation in `--sync`:
94
+ Optional gates for app binary status and app-config wizard participation in `--refresh`:
95
95
 
96
96
  ```typescript
97
97
  skill: { enabled: true },
98
98
  mcpServer: { enabled: true },
99
99
  configure: {
100
100
  targets: {
101
- configure: { includedInAll: true }, // optional: app config wizard on --sync
101
+ configure: { includedInAll: true }, // optional: app config wizard on --refresh
102
102
  },
103
103
  },
104
104
  ```
@@ -107,15 +107,37 @@ configure: {
107
107
 
108
108
  Artifact keys: `app`, `configure`. Legacy `configure.targets.*Mcp` keys are rejected — MCP installs to `~/.agents/mcp.json` when `mcpServer.enabled`.
109
109
 
110
+ ### Lifecycle hooks
111
+
112
+ Optional callbacks on `program.configure` for app-specific agent setup beyond the `.agents` protocol (e.g. Cursor or Claude Desktop config). Framework artifacts are installed/refreshed first; hooks extend or retract custom files.
113
+
114
+ ```typescript
115
+ configure: {
116
+ afterRefresh: async (ctx) => {
117
+ if (ctx.dry) return;
118
+ // e.g. symlink skill, merge Cursor mcp.json — ctx.paths has agentsSkillDir, agentsMcpPath, mcpName
119
+ },
120
+ beforeRemoveAll: async (ctx) => {
121
+ if (ctx.dry) return;
122
+ // undo custom installs before framework removes ~/.agents/ artifacts
123
+ },
124
+ },
125
+ ```
126
+
127
+ | Hook | When |
128
+ | --- | --- |
129
+ | `afterRefresh` | After `configure --refresh` installs framework artifacts |
130
+ | `beforeRemoveAll` | Before `configure --remove-all` removes framework artifacts (not `--remove-config`) |
131
+
110
132
  ## App config (`program.appConfig`)
111
133
 
112
- Every app gets `~/.local/lib/<sanitized-key>/config.json` on first **`configure --sync`** (Homebrew `post_install`), even without `program.appConfig`.
134
+ Every app gets `~/.local/lib/<sanitized-key>/config.json` on first **`configure --refresh`** (Homebrew `post_install`), even without `program.appConfig`.
113
135
 
114
136
  When `program.appConfig` is set, ArgsBarg manages schema-driven values in that file.
115
137
 
116
138
  | Mode | Description |
117
139
  | --- | --- |
118
- | `configure --sync` | Bootstraps `config.json` as `{}` when missing |
140
+ | `configure --refresh` | Bootstraps `config.json` as `{}` when missing |
119
141
  | Interactive `configure` | Config wizard when `entries` is non-empty; re-prompts every entry (Enter keeps current); writes only when values or `_bindings` change |
120
142
  | `--status` | Shows config path, required keys (`set` / `missing`), and binding hints (`env`, `file`, `skip`) |
121
143
  | `--remove-config --yes` | Removes the config directory |
@@ -132,7 +154,7 @@ Export helpers from `argsbarg`: `resolveAppConfigPath`, `displayAppConfigPath`.
132
154
  | Flag | Description |
133
155
  | --- | --- |
134
156
  | `--status` | Read-only inventory |
135
- | `--sync` | Refresh installed agent artifacts; bootstrap `config.json` when missing (Homebrew `post_install`; greenfield → full sync plan) |
157
+ | `--refresh` | Refresh installed agent artifacts; bootstrap `config.json` when missing (Homebrew `post_install`; greenfield → full install plan) |
136
158
  | `--remove-all` | Remove all detected agent artifacts |
137
159
  | `--remove-config` | Remove app config directory only |
138
160
 
@@ -146,7 +168,7 @@ Export helpers from `argsbarg`: `resolveAppConfigPath`, `displayAppConfigPath`.
146
168
 
147
169
  ## Confirmation
148
170
 
149
- Interactive `configure` prints a **`{app} Setup`** banner and per-target prompts. Non-interactive modes (`--sync`, `--remove-all`, `--remove-config`) require **`--yes`** unless `--dry`.
171
+ Interactive `configure` prints a **`{app} Setup`** banner and per-target prompts. Non-interactive modes (`--refresh`, `--remove-all`, `--remove-config`) require **`--yes`** unless `--dry`.
150
172
 
151
173
  ## MCP merge behavior
152
174
 
@@ -164,7 +186,7 @@ Release formulae should run:
164
186
 
165
187
  ```ruby
166
188
  def post_install
167
- system bin/"myapp", "configure", "--sync", "--yes"
189
+ system bin/"myapp", "configure", "--refresh", "--yes"
168
190
  end
169
191
  ```
170
192
 
@@ -26,6 +26,10 @@ The release script bumps `package.json`, promotes `[Unreleased]` in `CHANGELOG.m
26
26
 
27
27
  Update `CHANGELOG.md` under `[Unreleased]` before releasing.
28
28
 
29
+ ## Cursor test hook (optional)
30
+
31
+ Copy templates and the argsbarg repo root include `.cursor/hooks.json` plus `.cursor/hooks/run-tests-on-stop.ts`. On agent **stop** (completed turn), when git shows changes to `justfile` or `*.{ts,tsx,js,jsx}` (excluding `node_modules/`, `dist/`, `.cursor/`), the hook runs `just test`. Failures return a `followup_message` (up to **20** auto-retries via `loop_limit`). Requires [Cursor hooks](https://cursor.com/docs/hooks); not part of `AGENTS.md`. New projects get hooks via `argsbarg create`.
32
+
29
33
  ## Local consumer apps
30
34
 
31
35
  Sibling consumer repos (machine-specific paths in the root `justfile` `consumer_apps` variable, e.g. `~/dev/ss/sqsp-workspaces`):
@@ -33,7 +37,7 @@ Sibling consumer repos (machine-specific paths in the root `justfile` `consumer_
33
37
  | Recipe | When | Effect |
34
38
  | --- | --- | --- |
35
39
  | `just consumers-dev` | Before publish; hacking on argsbarg locally | `bun add argsbarg@file:<relative>`; refresh `AGENTS.md` from template (keeps app-specific prefix and conventions footer) |
36
- | `just consumers-sync` | After release | Sets `"argsbarg": "^<this package.json version>"`, `bun install`, merge **cli-program** + **code** Cursor rules, `just build`, `just docgen`, `just install-local` (Homebrew dev formula + agent artifacts; `just install` is an alias) |
40
+ | `just consumers-sync` | After release | Sets `"argsbarg": "^<this package.json version>"`, `bun install`, merge `AGENTS.md`, `just build`, `just docgen`, `just install-local` (Homebrew dev formula + agent artifacts; `just install` is an alias) |
37
41
  | `just consumers-schemagen` | After `@sg` type changes in consumers | Runs `argsbarg schemagen` in each `consumer_apps` path (fails if missing) |
38
42
 
39
43
  `consumers-sync` reads the version from **this repo’s** `package.json` — not npm. Run it **after** `just release` so consumers pin a version that exists on the registry.
@@ -55,7 +59,7 @@ Breaking changes (no backward compat). See [CHANGELOG.md](../CHANGELOG.md) `[Unr
55
59
  7. **Agent instructions:** `just consumers-dev` merges `AGENTS.md` + `CLAUDE.md` (includes **Abstractions** needless-extraction rule).
56
60
  8. **Verify:** `just test` and `just docgen` in each consumer repo.
57
61
 
58
- **Consumer app skill** — `just install-local` in each consumer (part of `consumers-sync`) runs Homebrew dev install then `myapp configure --sync --yes`, which updates `~/.agents/skills/<app>/` when `program.skill.enabled` — not the argsbarg framework rule.
62
+ **Consumer app skill** — `just install-local` in each consumer (part of `consumers-sync`) runs Homebrew dev install then `myapp configure --refresh --yes`, which updates `~/.agents/skills/<app>/` when `program.skill.enabled` — not the argsbarg framework rule.
59
63
 
60
64
  ## npm package contents
61
65
 
@@ -95,7 +99,7 @@ import { runSchemagen } from "argsbarg/schemagen";
95
99
  | `schema.ts`, `parse.ts`, `context.ts` | Transport-agnostic CLI core |
96
100
  | `http/` | HTTP tool server (`httpServer` capability) |
97
101
  | `mcp/` | MCP stdio server and bundle (`mcpServer` capability) |
98
- | `configure/artifacts/` | Agent artifact sync (`configure` capability) |
102
+ | `configure/artifacts/` | Agent artifact install/refresh (`configure` capability) |
99
103
  | `docs/` | Built-in documentation generators |
100
104
 
101
105
  Capabilities are declared on `CliProgram`; builtins wire them in [`src/builtins/`](../src/builtins/).
@@ -11,7 +11,7 @@ ArgsBarg maps the lifecycle of your application directly to standard Homebrew ho
11
11
  | Layer | Mechanism | Role in Lifecycle |
12
12
  | --- | --- | --- |
13
13
  | **Binary & Autocompletions** | Formula `install` block | Installs compiled binary and registers native shell autocompletions. |
14
- | **Telemetry & Agent Synclinks** | Formula `post_install` | Automatically runs `{key} configure --sync --yes` to bootstrap configuration files and sync developer tools. |
14
+ | **Agent artifacts** | Formula `post_install` | Automatically runs `{key} configure --refresh --yes` to bootstrap configuration files and refresh agent artifacts. |
15
15
  | **Application Configuration** | User-facing `{key} configure` | Runs an interactive TTY setup wizard (only when `program.appConfig` defines required parameters). |
16
16
  | **Clean Uninstall** | Formula `uninstall` | Automatically runs `{key} configure --remove-all --yes` to clean up local configurations and symlinks. |
17
17
 
@@ -87,7 +87,7 @@ class Myapp < Formula
87
87
 
88
88
  def post_install
89
89
  # Non-interactive bootstrap of config files and developer links
90
- system bin/"myapp", "configure", "--sync", "--yes"
90
+ system bin/"myapp", "configure", "--refresh", "--yes"
91
91
  end
92
92
 
93
93
  def uninstall
package/docs/mcp.md CHANGED
@@ -46,10 +46,10 @@ bun run examples/nested.ts mcp
46
46
 
47
47
  ### `.agents` auto-install
48
48
 
49
- When `mcpServer.enabled` is set, `configure --sync` merges a `mcpServers` entry into `~/.agents/mcp.json` per the https://dotagentsprotocol.com:
49
+ When `mcpServer.enabled` is set, `configure --refresh` merges a `mcpServers` entry into `~/.agents/mcp.json` per the https://dotagentsprotocol.com:
50
50
 
51
51
  ```bash
52
- myapp configure --sync --yes
52
+ myapp configure --refresh --yes
53
53
  ```
54
54
 
55
55
  ### Manual client setup
@@ -381,7 +381,7 @@ The bundled `SKILL.md` is an **MCP routing stub** — it tells Claude to use the
381
381
 
382
382
  Load locally with `claude --plugin-dir ./dist/claude-plugin/myapp.zip`.
383
383
 
384
- Bare **`myapp mcp`** still runs the stdio MCP server (unchanged for `configure` MCP targets and MCP hosts). Use **`configure --sync --yes`** for Cursor, Claude Code, Claude Desktop, and OpenCode JSON config.
384
+ Bare **`myapp mcp`** still runs the stdio MCP server (unchanged for `configure` MCP targets and MCP hosts). Use **`configure --refresh --yes`** for Cursor, Claude Code, Claude Desktop, and OpenCode JSON config.
385
385
 
386
386
  ## Hidden commands and options
387
387
 
@@ -0,0 +1,56 @@
1
+ #!/usr/bin/env bun
2
+ /* Cursor stop hook: run `just test` on agent completion; follow up if it fails. */
3
+
4
+ try {
5
+ const empty = () => {
6
+ console.log("{}");
7
+ process.exit(0);
8
+ };
9
+
10
+ const input = JSON.parse(await Bun.stdin.text()) as {
11
+ status?: string;
12
+ loop_count?: number;
13
+ workspace_roots?: string[];
14
+ };
15
+
16
+ if (input.status !== "completed") empty();
17
+
18
+ const cwd = input.workspace_roots?.[0] ?? process.cwd();
19
+ if (!(await Bun.file(`${cwd}/justfile`).exists())) empty();
20
+
21
+ const diff = Bun.spawnSync(["git", "diff", "--name-only", "HEAD"], { cwd, stdout: "pipe" });
22
+ const CODE_FILE = /\.(t|j)sx?$/i;
23
+ const SKIP_PREFIX = /^(node_modules|dist|\.cursor)\//;
24
+ const changed = new TextDecoder()
25
+ .decode(diff.stdout)
26
+ .split("\n")
27
+ .some(
28
+ (path) =>
29
+ path &&
30
+ (path === "justfile" || (CODE_FILE.test(path) && !SKIP_PREFIX.test(path))),
31
+ );
32
+ if (!changed) empty();
33
+
34
+ const proc = Bun.spawnSync(["just", "test"], {
35
+ cwd,
36
+ env: { ...process.env, FORCE_COLOR: "0" },
37
+ stderr: "pipe",
38
+ stdout: "pipe",
39
+ });
40
+ const output =
41
+ new TextDecoder().decode(proc.stdout) + new TextDecoder().decode(proc.stderr);
42
+
43
+ if (proc.exitCode === 0) empty();
44
+
45
+ const lines = output.trimEnd().split("\n");
46
+ const tail = lines.length > 80 ? lines.slice(-80).join("\n") : output.trimEnd();
47
+ const n = (input.loop_count ?? 0) + 1;
48
+
49
+ console.log(
50
+ JSON.stringify({
51
+ followup_message: `Tests failed (auto-retry ${n}/20). Fix and ensure \`just test\` passes.\n\n\`\`\`\n${tail}\n\`\`\``,
52
+ }),
53
+ );
54
+ } catch {
55
+ console.log("{}");
56
+ }
@@ -0,0 +1,12 @@
1
+ {
2
+ "version": 1,
3
+ "hooks": {
4
+ "stop": [
5
+ {
6
+ "command": "bun .cursor/hooks/run-tests-on-stop.ts",
7
+ "loop_limit": 20,
8
+ "timeout": 180
9
+ }
10
+ ]
11
+ }
12
+ }
@@ -11,7 +11,7 @@ class FullExample < Formula
11
11
  end
12
12
 
13
13
  def post_install
14
- system bin/"full-example", "configure", "--sync", "--yes"
14
+ system bin/"full-example", "configure", "--refresh", "--yes"
15
15
  end
16
16
 
17
17
  def uninstall
@@ -21,10 +21,10 @@
21
21
  {
22
22
  "key": "configure",
23
23
  "description": "Set up agent skills and MCP config for this app (binary via Homebrew).",
24
- "notes": "Set up agent artifacts after the binary is installed via Homebrew (see README for tap install).\n\nHomebrew post_install runs:\n full-example configure --sync --yes\n\nInteractive setup (per target):\n full-example configure\n\nUpgrade:\n brew upgrade full-example\n\nShell completions are installed by Homebrew during brew install.\nSee: https://docs.brew.sh/Shell-Completion\n\nSee what is installed:\n full-example configure --status\n\nUninstall:\n brew uninstall <tap>/full-example\n\nThe formula uninstall hook runs `configure --remove-all --yes` (skills, MCP, and app config).\n\nUse --dry to preview changes without writing files.\nUse --json for machine-readable output.",
24
+ "notes": "Set up agent artifacts after the binary is installed via Homebrew (see README for tap install).\n\nHomebrew post_install runs:\n full-example configure --refresh --yes\n\nInteractive setup (per target):\n full-example configure\n\nUpgrade:\n brew upgrade full-example\n\nShell completions are installed by Homebrew during brew install.\nSee: https://docs.brew.sh/Shell-Completion\n\nSee what is installed:\n full-example configure --status\n\nUninstall:\n brew uninstall <tap>/full-example\n\nThe formula uninstall hook runs `configure --remove-all --yes` (skills, MCP, and app config).\n\nUse --dry to preview changes without writing files.\nUse --json for machine-readable output.",
25
25
  "options": [
26
26
  {
27
- "name": "sync",
27
+ "name": "refresh",
28
28
  "description": "Refresh installed skills and MCP. Used by Homebrew post_install.",
29
29
  "kind": "presence"
30
30
  },
@@ -40,7 +40,7 @@
40
40
  },
41
41
  {
42
42
  "name": "yes",
43
- "description": "Skip confirmation (required for --sync, --remove-all, --remove-config).",
43
+ "description": "Skip confirmation (required for --refresh, --remove-all, --remove-config).",
44
44
  "kind": "presence",
45
45
  "shortName": "y"
46
46
  },
@@ -261,10 +261,10 @@
261
261
  {
262
262
  "key": "configure",
263
263
  "description": "Set up agent skills and MCP config for this app (binary via Homebrew).",
264
- "notes": "Set up agent artifacts after the binary is installed via Homebrew (see README for tap install).\n\nHomebrew post_install runs:\n full-example configure --sync --yes\n\nInteractive setup (per target):\n full-example configure\n\nUpgrade:\n brew upgrade full-example\n\nShell completions are installed by Homebrew during brew install.\nSee: https://docs.brew.sh/Shell-Completion\n\nSee what is installed:\n full-example configure --status\n\nUninstall:\n brew uninstall <tap>/full-example\n\nThe formula uninstall hook runs `configure --remove-all --yes` (skills, MCP, and app config).\n\nUse --dry to preview changes without writing files.\nUse --json for machine-readable output.",
264
+ "notes": "Set up agent artifacts after the binary is installed via Homebrew (see README for tap install).\n\nHomebrew post_install runs:\n full-example configure --refresh --yes\n\nInteractive setup (per target):\n full-example configure\n\nUpgrade:\n brew upgrade full-example\n\nShell completions are installed by Homebrew during brew install.\nSee: https://docs.brew.sh/Shell-Completion\n\nSee what is installed:\n full-example configure --status\n\nUninstall:\n brew uninstall <tap>/full-example\n\nThe formula uninstall hook runs `configure --remove-all --yes` (skills, MCP, and app config).\n\nUse --dry to preview changes without writing files.\nUse --json for machine-readable output.",
265
265
  "options": [
266
266
  {
267
- "name": "sync",
267
+ "name": "refresh",
268
268
  "description": "Refresh installed skills and MCP. Used by Homebrew post_install.",
269
269
  "kind": "presence"
270
270
  },
@@ -280,7 +280,7 @@
280
280
  },
281
281
  {
282
282
  "name": "yes",
283
- "description": "Skip confirmation (required for --sync, --remove-all, --remove-config).",
283
+ "description": "Skip confirmation (required for --refresh, --remove-all, --remove-config).",
284
284
  "kind": "presence",
285
285
  "shortName": "y"
286
286
  },
@@ -44,7 +44,7 @@ Set up agent skills and MCP config for this app (binary via Homebrew).
44
44
  > Set up agent artifacts after the binary is installed via Homebrew (see README for tap install).
45
45
  >
46
46
  > Homebrew post_install runs:
47
- > full-example configure --sync --yes
47
+ > full-example configure --refresh --yes
48
48
  >
49
49
  > Interactive setup (per target):
50
50
  > full-example configure
@@ -72,10 +72,10 @@ Set up agent skills and MCP config for this app (binary via Homebrew).
72
72
 
73
73
  | Option | Type | Required | Format / default | Description |
74
74
  | --- | --- | --- | --- | --- |
75
- | `--sync` | flag | optional | — | Refresh installed skills and MCP. Used by Homebrew post_install. |
75
+ | `--refresh` | flag | optional | — | Refresh installed skills and MCP. Used by Homebrew post_install. |
76
76
  | `--remove-all` | flag | optional | — | Remove all detected agent artifacts (skills and MCP). |
77
77
  | `--status` | flag | optional | — | Print what is currently installed (read-only). |
78
- | `--yes` (`-y`) | flag | optional | — | Skip confirmation (required for --sync, --remove-all, --remove-config). |
78
+ | `--yes` (`-y`) | flag | optional | — | Skip confirmation (required for --refresh, --remove-all, --remove-config). |
79
79
  | `--dry` | flag | optional | — | Show what would change without writing files. |
80
80
  | `--json` | flag | optional | — | Print changed paths or status JSON on stdout. |
81
81
 
@@ -263,7 +263,7 @@ Set up agent skills and MCP config for this app (binary via Homebrew).
263
263
  > Set up agent artifacts after the binary is installed via Homebrew (see README for tap install).
264
264
  >
265
265
  > Homebrew post_install runs:
266
- > full-example configure --sync --yes
266
+ > full-example configure --refresh --yes
267
267
  >
268
268
  > Interactive setup (per target):
269
269
  > full-example configure
@@ -291,10 +291,10 @@ Set up agent skills and MCP config for this app (binary via Homebrew).
291
291
 
292
292
  | Option | Type | Required | Format / default | Description |
293
293
  | --- | --- | --- | --- | --- |
294
- | `--sync` | flag | optional | — | Refresh installed skills and MCP. Used by Homebrew post_install. |
294
+ | `--refresh` | flag | optional | — | Refresh installed skills and MCP. Used by Homebrew post_install. |
295
295
  | `--remove-all` | flag | optional | — | Remove all detected agent artifacts (skills and MCP). |
296
296
  | `--status` | flag | optional | — | Print what is currently installed (read-only). |
297
- | `--yes` (`-y`) | flag | optional | — | Skip confirmation (required for --sync, --remove-all, --remove-config). |
297
+ | `--yes` (`-y`) | flag | optional | — | Skip confirmation (required for --refresh, --remove-all, --remove-config). |
298
298
  | `--dry` | flag | optional | — | Show what would change without writing files. |
299
299
  | `--json` | flag | optional | — | Print changed paths or status JSON on stdout. |
300
300
 
@@ -8,12 +8,12 @@ full-example exposes an MCP server with features similar to the CLI.
8
8
 
9
9
  ### `.agents` auto-install
10
10
 
11
- When `mcpServer.enabled` is set, `configure --sync` merges this server into `~/.agents/mcp.json` per the https://dotagentsprotocol.com.
11
+ When `mcpServer.enabled` is set, `configure --refresh` merges this server into `~/.agents/mcp.json` per the https://dotagentsprotocol.com.
12
12
 
13
13
  Install the CLI first so `full-example` is on your PATH (e.g. `brew install full-example`).
14
14
 
15
15
  ```bash
16
- full-example configure --sync --yes
16
+ full-example configure --refresh --yes
17
17
  ```
18
18
 
19
19
  Writes or updates `~/.agents/mcp.json` with a `mcpServers` entry for this app.
@@ -36,7 +36,7 @@ For full detail, open `reference.md` in this skill directory (same as `full-exam
36
36
 
37
37
  Install follows the https://dotagentsprotocol.com:
38
38
 
39
- - Auto-install: `full-example configure --sync --yes` when `skill.enabled` → `~/.agents/skills/full-example/`
39
+ - Auto-install: `full-example configure --refresh --yes` when `skill.enabled` → `~/.agents/skills/full-example/`
40
40
  - Cursor and most coding agents read `~/.agents/skills/` natively
41
41
 
42
42
  **Claude Code (manual):** symlink or copy into Claude's skill directory:
@@ -67,16 +67,16 @@ http:
67
67
  install: install-local
68
68
 
69
69
  # Refresh skills and MCP without reinstalling the formula
70
- sync-artifacts:
71
- just run configure --sync --yes
70
+ refresh-artifacts:
71
+ just run configure --refresh --yes
72
72
 
73
73
  # Dev install: build, stage dev formula, brew install, restore release formula
74
74
  install-local: build
75
- @brew untap {{tap}} 2>/dev/null || true
75
+ @NONINTERACTIVE=1 brew untap {{tap}} 2>/dev/null || true
76
76
  mkdir -p {{tap_parent}}
77
77
  ln -sfn '{{justfile_directory()}}' {{tap_path}}
78
78
  bun scripts/dev-formula.ts install
79
- brew install --formula {{tap}}/{{cli_key}}
79
+ brew install --force --formula {{tap}}/{{cli_key}}
80
80
  bun scripts/dev-formula.ts reset
81
81
  @echo ""
82
82
  @echo "Next: {{cli_key}} configure"
@@ -121,10 +121,10 @@ release *ARGS:
121
121
 
122
122
  # Install release formula from tap and run formula test
123
123
  test-release:
124
- brew untap {{tap}} 2>/dev/null || true
124
+ NONINTERACTIVE=1 brew untap {{tap}} 2>/dev/null || true
125
125
  mkdir -p {{tap_parent}}
126
126
  ln -sfn '{{justfile_directory()}}' {{tap_path}}
127
- brew uninstall --formula {{tap}}/{{cli_key}} 2>/dev/null || true
127
+ NONINTERACTIVE=1 brew uninstall --formula {{tap}}/{{cli_key}} 2>/dev/null || true
128
128
  brew install --formula {{tap}}/{{cli_key}}
129
129
  brew test {{cli_key}}
130
130
 
@@ -145,15 +145,15 @@ uninstall-config:
145
145
 
146
146
  # Remove formula and untap
147
147
  uninstall-formula:
148
- @brew uninstall --formula {{tap}}/{{cli_key}} 2>/dev/null || true
149
- @brew uninstall --formula {{tap}}/{{cli_key}}-local 2>/dev/null || true
150
- @brew untap {{tap}} 2>/dev/null || true
148
+ @NONINTERACTIVE=1 brew uninstall --formula {{tap}}/{{cli_key}} 2>/dev/null || true
149
+ @NONINTERACTIVE=1 brew uninstall --formula {{tap}}/{{cli_key}}-local 2>/dev/null || true
150
+ @NONINTERACTIVE=1 brew untap {{tap}} 2>/dev/null || true
151
151
 
152
152
  # Remove release formula (does not untap)
153
153
  uninstall-release:
154
- @brew uninstall --formula {{tap}}/{{cli_key}} 2>/dev/null || true
154
+ @NONINTERACTIVE=1 brew uninstall --formula {{tap}}/{{cli_key}} 2>/dev/null || true
155
155
 
156
156
  # Remove release formula and untap
157
157
  uninstall-release-tap:
158
- @brew uninstall --formula {{tap}}/{{cli_key}} 2>/dev/null || true
159
- @brew untap {{tap}} 2>/dev/null || true
158
+ @NONINTERACTIVE=1 brew uninstall --formula {{tap}}/{{cli_key}} 2>/dev/null || true
159
+ @NONINTERACTIVE=1 brew untap {{tap}} 2>/dev/null || true
@@ -20,7 +20,7 @@ export const formulaInstallRuby = `def install
20
20
  end`;
21
21
 
22
22
  export const formulaPostInstallRuby = `def post_install
23
- system bin/"${key}", "configure", "--sync", "--yes"
23
+ system bin/"${key}", "configure", "--refresh", "--yes"
24
24
  end`;
25
25
 
26
26
  export const formulaUninstallRuby = `def uninstall