@unbrained/pm-cli 2026.5.10 → 2026.5.11

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 (124) hide show
  1. package/.claude-plugin/marketplace.json +4 -4
  2. package/.pi/README.md +10 -1
  3. package/.pi/agents/pm-triage-agent.md +19 -0
  4. package/.pi/agents/pm-verification-agent.md +21 -0
  5. package/.pi/chains/pm-native-delivery.chain.md +11 -0
  6. package/.pi/extensions/pm-cli/index.js +276 -36
  7. package/.pi/skills/pm-native/SKILL.md +6 -2
  8. package/CHANGELOG.md +7 -0
  9. package/README.md +9 -1
  10. package/dist/cli/argv-utils.d.ts +5 -0
  11. package/dist/cli/argv-utils.js +34 -0
  12. package/dist/cli/argv-utils.js.map +1 -0
  13. package/dist/cli/bootstrap-args.d.ts +15 -0
  14. package/dist/cli/bootstrap-args.js +211 -0
  15. package/dist/cli/bootstrap-args.js.map +1 -1
  16. package/dist/cli/commander-usage.js +109 -3
  17. package/dist/cli/commander-usage.js.map +1 -1
  18. package/dist/cli/commands/completion.js +7 -3
  19. package/dist/cli/commands/completion.js.map +1 -1
  20. package/dist/cli/commands/contracts.d.ts +19 -0
  21. package/dist/cli/commands/contracts.js +33 -1
  22. package/dist/cli/commands/contracts.js.map +1 -1
  23. package/dist/cli/commands/create.js +112 -51
  24. package/dist/cli/commands/create.js.map +1 -1
  25. package/dist/cli/commands/docs.js +9 -2
  26. package/dist/cli/commands/docs.js.map +1 -1
  27. package/dist/cli/commands/extension.d.ts +3 -1
  28. package/dist/cli/commands/extension.js +174 -2
  29. package/dist/cli/commands/extension.js.map +1 -1
  30. package/dist/cli/commands/files.js +9 -2
  31. package/dist/cli/commands/files.js.map +1 -1
  32. package/dist/cli/commands/init.d.ts +2 -0
  33. package/dist/cli/commands/init.js +21 -1
  34. package/dist/cli/commands/init.js.map +1 -1
  35. package/dist/cli/commands/metadata-normalizers.d.ts +4 -0
  36. package/dist/cli/commands/metadata-normalizers.js +37 -0
  37. package/dist/cli/commands/metadata-normalizers.js.map +1 -0
  38. package/dist/cli/commands/reindex.js +173 -135
  39. package/dist/cli/commands/reindex.js.map +1 -1
  40. package/dist/cli/commands/search.js +16 -6
  41. package/dist/cli/commands/search.js.map +1 -1
  42. package/dist/cli/commands/test.js +9 -2
  43. package/dist/cli/commands/test.js.map +1 -1
  44. package/dist/cli/commands/update.js +70 -39
  45. package/dist/cli/commands/update.js.map +1 -1
  46. package/dist/cli/error-guidance.d.ts +9 -1
  47. package/dist/cli/error-guidance.js +147 -6
  48. package/dist/cli/error-guidance.js.map +1 -1
  49. package/dist/cli/help-json-payload.js +11 -1
  50. package/dist/cli/help-json-payload.js.map +1 -1
  51. package/dist/cli/main.js +69 -6
  52. package/dist/cli/main.js.map +1 -1
  53. package/dist/cli/register-setup.js +14 -0
  54. package/dist/cli/register-setup.js.map +1 -1
  55. package/dist/cli/telemetry-flush.d.ts +2 -0
  56. package/dist/cli/telemetry-flush.js +4 -0
  57. package/dist/cli/telemetry-flush.js.map +1 -0
  58. package/dist/cli.js +1 -2
  59. package/dist/cli.js.map +1 -1
  60. package/dist/core/extensions/extension-types.d.ts +72 -0
  61. package/dist/core/extensions/extension-types.js +24 -0
  62. package/dist/core/extensions/extension-types.js.map +1 -1
  63. package/dist/core/extensions/loader.d.ts +1 -0
  64. package/dist/core/extensions/loader.js +766 -7
  65. package/dist/core/extensions/loader.js.map +1 -1
  66. package/dist/core/lock/lock.js +2 -0
  67. package/dist/core/lock/lock.js.map +1 -1
  68. package/dist/core/sentry/instrument.d.ts +15 -0
  69. package/dist/core/sentry/instrument.js +35 -3
  70. package/dist/core/sentry/instrument.js.map +1 -1
  71. package/dist/core/shared/constants.js +20 -0
  72. package/dist/core/shared/constants.js.map +1 -1
  73. package/dist/core/shared/errors.d.ts +8 -0
  74. package/dist/core/shared/errors.js.map +1 -1
  75. package/dist/core/shared/levenshtein.d.ts +1 -0
  76. package/dist/core/shared/levenshtein.js +37 -0
  77. package/dist/core/shared/levenshtein.js.map +1 -0
  78. package/dist/core/store/paths.js +34 -1
  79. package/dist/core/store/paths.js.map +1 -1
  80. package/dist/core/store/settings.js +210 -1
  81. package/dist/core/store/settings.js.map +1 -1
  82. package/dist/core/telemetry/runtime.d.ts +1 -0
  83. package/dist/core/telemetry/runtime.js +102 -3
  84. package/dist/core/telemetry/runtime.js.map +1 -1
  85. package/dist/mcp/server.js +3 -1
  86. package/dist/mcp/server.js.map +1 -1
  87. package/dist/pi/native.js +57 -4
  88. package/dist/pi/native.js.map +1 -1
  89. package/dist/sdk/cli-contracts.d.ts +21 -1
  90. package/dist/sdk/cli-contracts.js +250 -0
  91. package/dist/sdk/cli-contracts.js.map +1 -1
  92. package/dist/sdk/index.d.ts +12 -1
  93. package/dist/sdk/index.js +8 -1
  94. package/dist/sdk/index.js.map +1 -1
  95. package/dist/types.d.ts +41 -0
  96. package/dist/types.js.map +1 -1
  97. package/docs/CLAUDE_CODE_PLUGIN.md +39 -0
  98. package/docs/EXTENSIONS.md +687 -0
  99. package/docs/MIGRATION_CLI_SIMPLIFICATION.md +64 -0
  100. package/docs/PI_PACKAGE.md +95 -10
  101. package/docs/SDK.md +441 -0
  102. package/docs/examples/ci/github-actions-pm-extension-gate.yml +53 -0
  103. package/docs/examples/ci/gitlab-ci-pm-extension-gate.yml +41 -0
  104. package/docs/examples/ci/jenkins-pm-extension-gate.Jenkinsfile +45 -0
  105. package/docs/examples/policy-restricted-extension/README.md +74 -0
  106. package/docs/examples/policy-restricted-extension/index.js +21 -0
  107. package/docs/examples/policy-restricted-extension/manifest.json +21 -0
  108. package/docs/examples/policy-restricted-extension/package.json +8 -0
  109. package/docs/examples/sdk-app-embedding/README.md +39 -0
  110. package/docs/examples/sdk-app-embedding/package.json +9 -0
  111. package/docs/examples/sdk-app-embedding/run-embedded-pm.mjs +61 -0
  112. package/docs/examples/sdk-contract-consumer/README.md +57 -0
  113. package/docs/examples/sdk-contract-consumer/inspect-contracts.mjs +47 -0
  114. package/docs/examples/sdk-contract-consumer/package.json +10 -0
  115. package/docs/examples/starter-extension/README.md +57 -42
  116. package/docs/examples/starter-extension/manifest.json +15 -0
  117. package/marketplace.json +3 -3
  118. package/package.json +1 -1
  119. package/plugins/pm-cli-claude/.claude-plugin/plugin.json +2 -2
  120. package/plugins/pm-cli-claude/README.md +55 -14
  121. package/plugins/pm-cli-claude/agents/pm-delivery-chain.md +88 -0
  122. package/plugins/pm-cli-claude/agents/pm-triage-agent.md +83 -0
  123. package/plugins/pm-cli-claude/agents/pm-verification-agent.md +88 -0
  124. package/plugins/pm-cli-claude/hooks/session-start.mjs +87 -22
@@ -1,5 +1,692 @@
1
1
  # Extensions
2
2
 
3
+ Extensions let you add or override `pm` runtime behavior without modifying core `pm-cli` sources.
4
+
5
+ This document is the canonical extension reference for manifest contracts, governance policy, trust and sandbox controls, reload workflows, and diagnostics.
6
+
7
+ ## Quick Start
8
+
9
+ ```bash
10
+ # 1) Scaffold an extension
11
+ pm extension --init ./my-extension
12
+
13
+ # 2) Install in project scope
14
+ pm extension --install --project ./my-extension
15
+
16
+ # 3) Run diagnostics
17
+ pm extension --doctor --project --detail summary
18
+
19
+ # 4) Reload runtime modules after local edits
20
+ pm extension --reload --project
21
+ ```
22
+
23
+ ## Extension Locations
24
+
25
+ - project scope: `.agents/pm/extensions/<name>/`
26
+ - global scope: `~/.pm-cli/extensions/<name>/`
27
+ - project entries override global entries for matching command paths
28
+
29
+ Runtime path overrides:
30
+
31
+ - `PM_PATH`: project tracker root override
32
+ - `PM_GLOBAL_PATH`: global profile root override
33
+
34
+ ## Manifest Contract
35
+
36
+ ### Manifest v1 (supported)
37
+
38
+ ```json
39
+ {
40
+ "name": "my-ext",
41
+ "version": "0.1.0",
42
+ "entry": "./index.js",
43
+ "priority": 100,
44
+ "capabilities": ["commands"]
45
+ }
46
+ ```
47
+
48
+ ### Manifest v2 (recommended)
49
+
50
+ ```json
51
+ {
52
+ "name": "my-ext",
53
+ "version": "0.2.0",
54
+ "entry": "./index.js",
55
+ "priority": 100,
56
+ "manifest_version": 2,
57
+ "trusted": true,
58
+ "provenance": {
59
+ "source": "github://org/repo/path",
60
+ "verified": true
61
+ },
62
+ "sandbox_profile": "restricted",
63
+ "permissions": {
64
+ "fs_read": true,
65
+ "fs_write": false,
66
+ "network": false,
67
+ "env_read": true,
68
+ "env_write": false,
69
+ "process_spawn": false
70
+ },
71
+ "capabilities": ["commands", "hooks"]
72
+ }
73
+ ```
74
+
75
+ ### Capability values
76
+
77
+ - `commands`
78
+ - `parser`
79
+ - `preflight`
80
+ - `services`
81
+ - `renderers`
82
+ - `hooks`
83
+ - `schema`
84
+ - `importers`
85
+ - `search`
86
+
87
+ ## Governance Policy (`extensions.policy`)
88
+
89
+ Policy is configured in `settings.json` under `extensions.policy`.
90
+
91
+ ```json
92
+ {
93
+ "extensions": {
94
+ "policy": {
95
+ "mode": "enforce",
96
+ "trust_mode": "warn",
97
+ "require_provenance": true,
98
+ "default_sandbox_profile": "restricted",
99
+ "allowed_extensions": [],
100
+ "blocked_extensions": [],
101
+ "allowed_capabilities": [],
102
+ "blocked_capabilities": ["services"],
103
+ "allowed_surfaces": [],
104
+ "blocked_surfaces": ["commands.override"],
105
+ "allowed_commands": [],
106
+ "blocked_commands": ["dangerous command"],
107
+ "allowed_actions": [],
108
+ "blocked_actions": ["dangerous-command"],
109
+ "allowed_services": [],
110
+ "blocked_services": ["output_format"]
111
+ }
112
+ }
113
+ }
114
+ ```
115
+
116
+ Mode semantics:
117
+
118
+ - `mode`: `off|warn|enforce` for extension/capability/surface/command/action/service checks
119
+ - `trust_mode`: `off|warn|enforce` for trust checks
120
+ - `default_sandbox_profile`: `none|restricted|strict`
121
+
122
+ Sandbox profiles:
123
+
124
+ - `none`: no sandbox permission gating
125
+ - `restricted`: blocks sensitive writes and spawn (`process_spawn`, `env_write`)
126
+ - `strict`: blocks spawn/network/write style permissions (`process_spawn`, `network`, `fs_write`, `env_write`)
127
+
128
+ If profile is non-`none` and manifest permissions are missing, policy emits a deterministic warning or block.
129
+
130
+ ## Supported Surface Tokens
131
+
132
+ Use these values with `allowed_surfaces` and `blocked_surfaces`:
133
+
134
+ - `commands.override`
135
+ - `commands.handler`
136
+ - `hooks.beforecommand`
137
+ - `hooks.aftercommand`
138
+ - `hooks.onwrite`
139
+ - `hooks.onread`
140
+ - `hooks.onindex`
141
+ - `schema.flags`
142
+ - `schema.itemfields`
143
+ - `schema.itemtypes`
144
+ - `schema.migrations`
145
+ - `parser.override`
146
+ - `preflight.override`
147
+ - `services.override`
148
+ - `renderers.override`
149
+ - `importers.importer`
150
+ - `importers.exporter`
151
+ - `search.provider`
152
+ - `search.vectorstore`
153
+
154
+ ## Reload and Watch Workflows
155
+
156
+ Manual reload:
157
+
158
+ ```bash
159
+ pm extension --reload --project
160
+ ```
161
+
162
+ Watch-mode semantics:
163
+
164
+ ```bash
165
+ pm extension --reload --project --watch
166
+ ```
167
+
168
+ In non-interactive automation, `--watch` performs a deterministic single-pass reload and emits a watch-hint warning.
169
+
170
+ ## Diagnostics and Management
171
+
172
+ Basic diagnostics:
173
+
174
+ ```bash
175
+ pm extension --doctor --project --detail summary
176
+ ```
177
+
178
+ Deep diagnostics:
179
+
180
+ ```bash
181
+ pm extension --doctor --project --detail deep --trace
182
+ ```
183
+
184
+ Management commands:
185
+
186
+ ```bash
187
+ pm extension --explore
188
+ pm extension --manage --project
189
+ pm extension --manage --project --probe-runtime
190
+ pm extension --manage --project --adopt-unmanaged
191
+ pm extension --activate my-extension --project
192
+ pm extension --deactivate my-extension --project
193
+ pm extension --uninstall my-extension --project
194
+ ```
195
+
196
+ Common warning prefixes:
197
+
198
+ - `extension_policy_violation_extension`
199
+ - `extension_policy_violation_capability`
200
+ - `extension_policy_violation_registration`
201
+ - `extension_policy_violation_trust`
202
+ - `extension_policy_blocked_extension`
203
+ - `extension_policy_blocked_capability`
204
+ - `extension_policy_blocked_registration`
205
+ - `extension_policy_blocked_trust`
206
+
207
+ ## Migration Checklist (v1 -> v2)
208
+
209
+ 1. Keep existing manifest fields.
210
+ 2. Add `manifest_version: 2`.
211
+ 3. Add `trusted`, `provenance`, `sandbox_profile`, and `permissions`.
212
+ 4. Extend `extensions.policy` with trust/sandbox and command/action/service controls.
213
+ 5. Run:
214
+
215
+ ```bash
216
+ pm contracts --json
217
+ pm extension --doctor --project --detail summary --strict-exit
218
+ ```
219
+
220
+ 6. Resolve warnings before enforcing `mode=enforce` and `trust_mode=enforce`.
221
+
222
+ ## Runnable Examples
223
+
224
+ - `docs/examples/starter-extension/`
225
+ - `docs/examples/policy-restricted-extension/`
226
+ - `docs/examples/sdk-contract-consumer/`
227
+ - `docs/examples/sdk-app-embedding/`
228
+ - `docs/examples/ci/github-actions-pm-extension-gate.yml`
229
+ - `docs/examples/ci/gitlab-ci-pm-extension-gate.yml`
230
+ - `docs/examples/ci/jenkins-pm-extension-gate.Jenkinsfile`
231
+ # Extensions
232
+
233
+ Extensions let you add or override `pm` runtime behavior without modifying core `pm-cli`.
234
+
235
+ This guide is the authoritative reference for:
236
+
237
+ - manifest `v1` and `v2` contracts
238
+ - governance policy (`extensions.policy`) controls
239
+ - trust/provenance and sandbox restrictions
240
+ - manual reload and watch-mode workflows
241
+ - migration from policy-only setups to enterprise controls
242
+
243
+ ## Quick Start
244
+
245
+ ```bash
246
+ # 1) Scaffold an extension
247
+ pm extension --init ./my-extension
248
+
249
+ # 2) Install in project scope
250
+ pm extension --install --project ./my-extension
251
+
252
+ # 3) Run diagnostics
253
+ pm extension --doctor --project --detail summary
254
+
255
+ # 4) Reload runtime modules after local edits
256
+ pm extension --reload --project
257
+ ```
258
+
259
+ ## Delta From Previous Scope
260
+
261
+ Compared to the previous policy-only extension surface, this release adds:
262
+
263
+ - **Manifest v2 metadata** for trust, provenance, sandbox profile, and runtime permission declarations.
264
+ - **Policy v2 controls** for trust mode, provenance requirement, sandbox defaults, and command/action/service allow/block maps.
265
+ - **Registration enforcement upgrades** so command/action/service restrictions are evaluated at registration boundaries.
266
+ - **Hot reload controls** via cache-busted extension reload (`pm extension --reload`) with watch-mode semantics (`--watch`).
267
+ - **Contracts metadata upgrades** for trust/sandbox compatibility information in `pm contracts`.
268
+
269
+ ## Extension Locations
270
+
271
+ - Project scope: `.agents/pm/extensions/<name>/`
272
+ - Global scope: `~/.pm-cli/extensions/<name>/`
273
+ - Project entries override global entries when command paths collide.
274
+
275
+ Overrides:
276
+
277
+ - `PM_PATH`: project tracker root override
278
+ - `PM_GLOBAL_PATH`: global profile root override
279
+
280
+ ## Manifest Contract
281
+
282
+ ### Manifest v1 (still supported)
283
+
284
+ ```json
285
+ {
286
+ "name": "my-ext",
287
+ "version": "0.1.0",
288
+ "entry": "./index.js",
289
+ "priority": 100,
290
+ "capabilities": ["commands"]
291
+ }
292
+ ```
293
+
294
+ ### Manifest v2 (recommended)
295
+
296
+ ```json
297
+ {
298
+ "name": "my-ext",
299
+ "version": "0.2.0",
300
+ "entry": "./index.js",
301
+ "priority": 100,
302
+ "manifest_version": 2,
303
+ "trusted": true,
304
+ "provenance": {
305
+ "source": "github://org/repo/path",
306
+ "verified": true
307
+ },
308
+ "sandbox_profile": "restricted",
309
+ "permissions": {
310
+ "fs_read": true,
311
+ "fs_write": false,
312
+ "network": false,
313
+ "env_read": true,
314
+ "env_write": false,
315
+ "process_spawn": false
316
+ },
317
+ "capabilities": ["commands", "hooks"]
318
+ }
319
+ ```
320
+
321
+ ### Capability Values
322
+
323
+ - `commands`
324
+ - `parser`
325
+ - `preflight`
326
+ - `services`
327
+ - `renderers`
328
+ - `hooks`
329
+ - `schema`
330
+ - `importers`
331
+ - `search`
332
+
333
+ ## Governance Policy v2
334
+
335
+ Policy is configured under `settings.json` -> `extensions.policy`.
336
+
337
+ ```json
338
+ {
339
+ "extensions": {
340
+ "policy": {
341
+ "mode": "enforce",
342
+ "trust_mode": "warn",
343
+ "require_provenance": true,
344
+ "trusted_extensions": ["policy-restricted-extension"],
345
+ "default_sandbox_profile": "restricted",
346
+ "allowed_extensions": [],
347
+ "blocked_extensions": [],
348
+ "allowed_capabilities": [],
349
+ "blocked_capabilities": ["services"],
350
+ "allowed_surfaces": [],
351
+ "blocked_surfaces": ["commands.override"],
352
+ "allowed_commands": [],
353
+ "blocked_commands": ["dangerous command"],
354
+ "allowed_actions": [],
355
+ "blocked_actions": ["dangerous-command"],
356
+ "allowed_services": [],
357
+ "blocked_services": ["output_format"],
358
+ "extension_overrides": [
359
+ {
360
+ "name": "policy-restricted-extension",
361
+ "require_trusted": true,
362
+ "require_provenance": true,
363
+ "sandbox_profile": "strict",
364
+ "allowed_surfaces": ["commands.handler", "hooks.beforecommand"],
365
+ "blocked_surfaces": ["services.override"]
366
+ }
367
+ ]
368
+ }
369
+ }
370
+ }
371
+ ```
372
+
373
+ ### Mode Semantics
374
+
375
+ - `mode`: `off|warn|enforce` for extension/capability/surface/command/action/service restrictions
376
+ - `trust_mode`: `off|warn|enforce` for trust checks
377
+ - `default_sandbox_profile`: `none|restricted|strict`
378
+
379
+ ### Sandbox Profiles
380
+
381
+ Sandbox profiles are policy-driven gates evaluated against manifest permission declarations:
382
+
383
+ - `none`: no sandbox permission gating
384
+ - `restricted`: blocks sensitive writes/spawn (`process_spawn`, `env_write`)
385
+ - `strict`: blocks spawn/network/write-style permissions (`process_spawn`, `network`, `fs_write`, `env_write`)
386
+
387
+ If a non-`none` profile is active and manifest permissions are missing, a deterministic policy warning/block is emitted.
388
+
389
+ ### Surface Tokens
390
+
391
+ Supported `allowed_surfaces` / `blocked_surfaces` values:
392
+
393
+ - `commands.override`
394
+ - `commands.handler`
395
+ - `hooks.beforecommand`
396
+ - `hooks.aftercommand`
397
+ - `hooks.onwrite`
398
+ - `hooks.onread`
399
+ - `hooks.onindex`
400
+ - `schema.flags`
401
+ - `schema.itemfields`
402
+ - `schema.itemtypes`
403
+ - `schema.migrations`
404
+ - `parser.override`
405
+ - `preflight.override`
406
+ - `services.override`
407
+ - `renderers.override`
408
+ - `importers.importer`
409
+ - `importers.exporter`
410
+ - `search.provider`
411
+ - `search.vectorstore`
412
+
413
+ ## Hot Reload
414
+
415
+ ### Manual reload
416
+
417
+ ```bash
418
+ pm extension --reload --project
419
+ ```
420
+
421
+ This runs extension discovery/load with cache-busted import URLs and returns deterministic load/activation diagnostics.
422
+
423
+ ### Watch mode
424
+
425
+ ```bash
426
+ pm extension --reload --project --watch
427
+ ```
428
+
429
+ `--watch` enables watch-mode semantics for reload workflows. In non-interactive automation, it executes a deterministic single-pass reload and emits a watch hint warning.
430
+
431
+ ## Diagnostics and Warning Codes
432
+
433
+ Common warning prefixes:
434
+
435
+ - `extension_policy_violation_extension`
436
+ - `extension_policy_violation_capability`
437
+ - `extension_policy_violation_registration`
438
+ - `extension_policy_violation_trust`
439
+ - `extension_policy_blocked_extension`
440
+ - `extension_policy_blocked_capability`
441
+ - `extension_policy_blocked_registration`
442
+ - `extension_policy_blocked_trust`
443
+
444
+ Use:
445
+
446
+ ```bash
447
+ pm extension --doctor --project --detail deep --trace
448
+ ```
449
+
450
+ for full activation traces.
451
+
452
+ ## Migration (v1 -> v2)
453
+
454
+ 1. Keep existing manifest fields unchanged.
455
+ 2. Add `manifest_version: 2`.
456
+ 3. Add `trusted`, `provenance`, `sandbox_profile`, and `permissions`.
457
+ 4. Extend `extensions.policy` with trust/sandbox/command-action-service fields.
458
+ 5. Run:
459
+
460
+ ```bash
461
+ pm contracts --json
462
+ pm extension --doctor --project --detail summary --strict-exit
463
+ ```
464
+
465
+ 6. Fix any policy warnings before enforcing (`mode=enforce`, `trust_mode=enforce`).
466
+
467
+ ## Runnable Examples
468
+
469
+ - `docs/examples/starter-extension/`
470
+ - `docs/examples/policy-restricted-extension/`
471
+ - `docs/examples/sdk-contract-consumer/`
472
+ - `docs/examples/sdk-app-embedding/`
473
+ - `docs/examples/ci/github-actions-pm-extension-gate.yml`
474
+ - `docs/examples/ci/gitlab-ci-pm-extension-gate.yml`
475
+ - `docs/examples/ci/jenkins-pm-extension-gate.Jenkinsfile`
476
+ # Extensions
477
+
478
+ Extensions let you add or override `pm` runtime behavior without editing core `pm-cli` sources. They are loaded at runtime, gated by manifest capabilities, and now support granular governance policies for capability/surface allow/block controls.
479
+
480
+ ## Quick Start
481
+
482
+ ```bash
483
+ # 1) Scaffold a new extension
484
+ pm extension --init ./my-extension
485
+
486
+ # 2) Install into project scope
487
+ pm extension --install --project ./my-extension
488
+
489
+ # 3) Run extension diagnostics
490
+ pm extension --doctor --project --detail summary
491
+
492
+ # 4) Deep diagnostics with traces
493
+ pm extension --doctor --project --detail deep --trace
494
+ ```
495
+
496
+ Expected summary signals from `extension --doctor`:
497
+
498
+ - `details.summary.status`: `ok` or `warn`
499
+ - `details.summary.warning_codes`: deterministic warning code list
500
+ - `details.summary.policy`: active policy mode and configured counts
501
+ - `details.triage.remediation`: actionable follow-up guidance
502
+
503
+ ## Extension Locations and Precedence
504
+
505
+ - Project extensions: `.agents/pm/extensions/<name>/`
506
+ - Global extensions: `~/.pm-cli/extensions/<name>/`
507
+ - Project takes precedence when both scopes register the same command/surface.
508
+ - Discovery and activation remain deterministic across runs.
509
+
510
+ Environment overrides:
511
+
512
+ - `PM_PATH`: project tracker root override
513
+ - `PM_GLOBAL_PATH`: global profile root override
514
+
515
+ ## Manifest and Capabilities
516
+
517
+ Minimal `manifest.json`:
518
+
519
+ ```json
520
+ {
521
+ "name": "pm-ext-example",
522
+ "version": "0.1.0",
523
+ "entry": "./index.js",
524
+ "priority": 100,
525
+ "capabilities": ["commands"]
526
+ }
527
+ ```
528
+
529
+ Rules:
530
+
531
+ - `entry` must resolve inside extension directory (symlink-safe canonical checks apply).
532
+ - Declare only capabilities actually used.
533
+ - Unknown capabilities produce deterministic warnings with guidance.
534
+ - Legacy aliases (`migration`, `validation`) are remapped to `schema` with guidance warnings.
535
+
536
+ Supported capabilities:
537
+
538
+ - `commands`
539
+ - `parser`
540
+ - `preflight`
541
+ - `services`
542
+ - `renderers`
543
+ - `hooks`
544
+ - `schema`
545
+ - `importers`
546
+ - `search`
547
+
548
+ ## Governance Policy (Granular Controls)
549
+
550
+ Extension governance policy is configured in `settings.json` under `extensions.policy`.
551
+
552
+ Policy modes:
553
+
554
+ - `off`: no policy enforcement/warnings
555
+ - `warn`: allow registrations but emit policy violation warnings
556
+ - `enforce`: block disallowed extensions/capabilities/surfaces
557
+
558
+ Example policy:
559
+
560
+ ```json
561
+ {
562
+ "extensions": {
563
+ "policy": {
564
+ "mode": "enforce",
565
+ "allowed_extensions": ["release-audit-ext"],
566
+ "blocked_extensions": [],
567
+ "allowed_capabilities": [],
568
+ "blocked_capabilities": ["services"],
569
+ "allowed_surfaces": [],
570
+ "blocked_surfaces": ["commands.override"],
571
+ "extension_overrides": [
572
+ {
573
+ "name": "release-audit-ext",
574
+ "allowed_surfaces": ["commands.handler", "hooks.beforecommand"],
575
+ "blocked_surfaces": ["services.override"]
576
+ }
577
+ ]
578
+ }
579
+ }
580
+ }
581
+ ```
582
+
583
+ ### Surface Tokens
584
+
585
+ Use these exact values for `allowed_surfaces` / `blocked_surfaces`:
586
+
587
+ - `commands.override`
588
+ - `commands.handler`
589
+ - `hooks.beforecommand`
590
+ - `hooks.aftercommand`
591
+ - `hooks.onwrite`
592
+ - `hooks.onread`
593
+ - `hooks.onindex`
594
+ - `schema.flags`
595
+ - `schema.itemfields`
596
+ - `schema.itemtypes`
597
+ - `schema.migrations`
598
+ - `parser.override`
599
+ - `preflight.override`
600
+ - `services.override`
601
+ - `renderers.override`
602
+ - `importers.importer`
603
+ - `importers.exporter`
604
+ - `search.provider`
605
+ - `search.vectorstore`
606
+
607
+ Policy diagnostics use deterministic warning codes:
608
+
609
+ - `extension_policy_violation_extension`
610
+ - `extension_policy_violation_capability`
611
+ - `extension_policy_violation_registration`
612
+ - `extension_policy_blocked_extension`
613
+ - `extension_policy_blocked_capability`
614
+ - `extension_policy_blocked_registration`
615
+
616
+ ## Runtime APIs (Public SDK)
617
+
618
+ Use `@unbrained/pm-cli/sdk` only (no internal imports).
619
+
620
+ - `api.registerCommand(def)` -> `commands`
621
+ - `api.registerParser(command, fn)` -> `parser`
622
+ - `api.registerPreflight(fn)` -> `preflight`
623
+ - `api.registerService(name, fn)` -> `services`
624
+ - `api.registerRenderer(format, fn)` -> `renderers`
625
+ - `api.registerFlags(command, flags)` -> `schema`
626
+ - `api.registerItemFields(fields)` -> `schema`
627
+ - `api.registerItemTypes(types)` -> `schema`
628
+ - `api.registerMigration(def)` -> `schema`
629
+ - `api.registerImporter(name, fn)` -> `importers`
630
+ - `api.registerExporter(name, fn)` -> `importers`
631
+ - `api.registerSearchProvider(provider)` -> `search`
632
+ - `api.registerVectorStoreAdapter(adapter)` -> `search`
633
+ - `api.hooks.beforeCommand/afterCommand/onWrite/onRead/onIndex(fn)` -> `hooks`
634
+
635
+ ## Lifecycle Commands
636
+
637
+ ```bash
638
+ # Explore
639
+ pm extension --explore --project
640
+
641
+ # Manage (update checks + managed state diagnostics)
642
+ pm extension --manage --project
643
+
644
+ # Optional runtime probe parity in manage mode
645
+ pm extension --manage --project --runtime-probe
646
+
647
+ # Auto-adopt unmanaged extensions into managed state
648
+ pm extension --manage --project --fix-managed-state
649
+
650
+ # Activation/deactivation
651
+ pm extension --activate my-extension --project
652
+ pm extension --deactivate my-extension --project
653
+
654
+ # Uninstall
655
+ pm extension --uninstall my-extension --project
656
+ ```
657
+
658
+ ## Non-Interactive Automation Patterns
659
+
660
+ For CI/CD and agents:
661
+
662
+ - Prefer `--json` outputs.
663
+ - Use `pm contracts --schema-only --json` before invoking action payloads.
664
+ - Run `pm extension --doctor --detail summary --strict-exit` as a gate.
665
+ - Add `--detail deep --trace` on failure paths for remediation payloads.
666
+ - Use `--no-extensions` as a deterministic fallback for core-only triage.
667
+
668
+ ## Runnable Examples
669
+
670
+ - Full starter extension: `docs/examples/starter-extension/`
671
+ - Capability-restricted policy example: `docs/examples/policy-restricted-extension/`
672
+ - Programmatic contracts consumer: `docs/examples/sdk-contract-consumer/`
673
+ - CI gating workflow: `docs/examples/ci/github-actions-pm-extension-gate.yml`
674
+
675
+ ## Troubleshooting
676
+
677
+ - Manifest/entry failures: run `pm extension --explore --project`
678
+ - Activation failures: run `pm extension --doctor --detail deep --trace`
679
+ - Policy blocks: review `settings.extensions.policy` and `details.summary.policy`
680
+ - Runtime drift suspicion: compare with `pm --no-extensions <command>`
681
+ - Managed-state update-check gaps: run `pm extension --manage --fix-managed-state`
682
+
683
+ ## Related Docs
684
+
685
+ - `docs/SDK.md`
686
+ - `docs/examples/starter-extension/README.md`
687
+ - `docs/CLAUDE_CODE_PLUGIN.md`
688
+ # Extensions
689
+
3
690
  Extensions add commands, schema, renderers, importers/exporters, search adapters, lifecycle hooks, and selected runtime overrides without modifying core `pm-cli`.
4
691
 
5
692
  ## Agent Quick Context