@unbrained/pm-cli 2026.8.27 → 2026.8.29
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.claude-plugin/marketplace.json +2 -2
- package/CHANGELOG.md +49 -1
- package/dist/cli/error-guidance.js +61 -7
- package/dist/cli/register-annotations.js +58 -41
- package/dist/cli-bundle/bundle-manifest.json +142 -142
- package/dist/cli-bundle/chunks/{chunk-TNX6HC54.js → chunk-2MKLQL2E.js} +2 -2
- package/dist/cli-bundle/chunks/{chunk-SKXLJIEK.js → chunk-2UETTHY6.js} +49 -49
- package/dist/cli-bundle/chunks/{chunk-SHMDY36D.js → chunk-3TEF3HM5.js} +2 -2
- package/dist/cli-bundle/chunks/{chunk-SH6P7FXI.js → chunk-7SKMLSMX.js} +2 -2
- package/dist/cli-bundle/chunks/chunk-7X6OZEIV.js +34 -0
- package/dist/cli-bundle/chunks/{chunk-CVBBGWW5.js → chunk-CMIEDWAY.js} +54 -50
- package/dist/cli-bundle/chunks/{chunk-3OO3W6FW.js → chunk-GNWPTEBW.js} +64 -61
- package/dist/cli-bundle/chunks/chunk-MTTKAUBX.js +2 -0
- package/dist/cli-bundle/chunks/chunk-N6OR6FAR.js +13 -0
- package/dist/cli-bundle/chunks/{chunk-R4ETAOJC.js → chunk-TGNAA66W.js} +2 -2
- package/dist/cli-bundle/chunks/{chunk-52EKTW6V.js → chunk-WS2GJQVG.js} +2 -2
- package/dist/cli-bundle/chunks/{register-list-query-EUWM6VII.js → register-list-query-OMKJ5ONN.js} +2 -2
- package/dist/cli-bundle/chunks/{register-mutation-FD4HSAVU.js → register-mutation-QBSNCOY3.js} +4 -4
- package/dist/cli-bundle/chunks/{register-operations-HRMNFEC3.js → register-operations-UC77FQZC.js} +2 -2
- package/dist/cli-bundle/chunks/{register-setup-33GNICLX.js → register-setup-GLQ5SYV3.js} +2 -2
- package/dist/cli-bundle/focused-chunks/{chunk-HC7ODMH3.js → chunk-3AVAWVZA.js} +2 -2
- package/dist/cli-bundle/focused-chunks/chunk-3UMBF26I.js +158 -0
- package/dist/cli-bundle/focused-chunks/{chunk-YVVZ3LQ6.js → chunk-73EDXGYE.js} +16 -15
- package/dist/cli-bundle/focused-chunks/{chunk-4BR5UU52.js → chunk-AXZ5AJAF.js} +45 -45
- package/dist/cli-bundle/focused-chunks/{chunk-MXTYGECH.js → chunk-G6PATS5E.js} +3 -3
- package/dist/cli-bundle/focused-chunks/{chunk-SUBSWYW3.js → chunk-JZYPPMXF.js} +2 -2
- package/dist/cli-bundle/focused-chunks/chunk-LLNTHF5X.js +2 -0
- package/dist/cli-bundle/focused-chunks/chunk-LYFWQMVC.js +2 -0
- package/dist/cli-bundle/focused-chunks/chunk-RKOKG43G.js +2 -0
- package/dist/cli-bundle/focused-chunks/chunk-TDK3OCX3.js +2 -0
- package/dist/cli-bundle/focused-chunks/{chunk-EKX37ZHA.js → chunk-THEPQMLX.js} +2 -2
- package/dist/cli-bundle/focused-chunks/{chunk-FC2AXLB5.js → chunk-XXOWRJZ5.js} +2 -2
- package/dist/cli-bundle/main.js +14 -14
- package/dist/cli-bundle/sdk-authoring.js +1 -1
- package/dist/cli-bundle/sdk-contracts.js +2 -2
- package/dist/cli-bundle/sdk-core.js +31 -32
- package/dist/cli-bundle/sdk-governance.js +1 -1
- package/dist/cli-bundle/sdk-graph.js +1 -1
- package/dist/cli-bundle/sdk-merge.js +34 -32
- package/dist/cli-bundle/sdk-query.js +1 -1
- package/dist/cli-bundle/sdk-runtime.js +1 -1
- package/dist/cli-bundle/sdk-testing.js +1 -1
- package/dist/cli-bundle/sdk.js +10 -10
- package/dist/core/diagnostics/remediation.js +16 -6
- package/dist/core/history/drift-scan.d.ts +2 -0
- package/dist/core/history/drift-scan.js +72 -36
- package/dist/core/history/history.d.ts +3 -3
- package/dist/core/history/history.js +5 -5
- package/dist/core/history/replay.d.ts +1 -1
- package/dist/core/history/replay.js +50 -19
- package/dist/core/item/actionability.d.ts +7 -1
- package/dist/core/item/actionability.js +44 -11
- package/dist/core/item/dependency-reference.d.ts +10 -0
- package/dist/core/item/dependency-reference.js +21 -0
- package/dist/core/item/parse.d.ts +4 -0
- package/dist/core/item/parse.js +38 -16
- package/dist/core/shared/author.js +69 -17
- package/dist/mcp/tool-definitions.js +5 -5
- package/dist/sdk/agent/command-recovery.js +3 -3
- package/dist/sdk/agent/task-transcript-contracts.d.ts +52 -0
- package/dist/sdk/agent/task-transcript-contracts.js +198 -0
- package/dist/sdk/annotations.d.ts +5 -2
- package/dist/sdk/annotations.js +66 -36
- package/dist/sdk/cli-bootstrap.d.ts +2 -8
- package/dist/sdk/cli-bootstrap.js +7 -67
- package/dist/sdk/cli-contracts/bootstrap-command-scanner.d.ts +23 -0
- package/dist/sdk/cli-contracts/bootstrap-command-scanner.js +80 -0
- package/dist/sdk/cli-contracts/flag-contracts.js +5 -2
- package/dist/sdk/cli-contracts/flag-lexicon-contracts.js +5 -5
- package/dist/sdk/cli-contracts/tool-parameter-tables.js +15 -2
- package/dist/sdk/cli-contracts/tool-schema.d.ts +1 -1
- package/dist/sdk/cli-contracts/tool-schema.js +16 -3
- package/dist/sdk/comments.d.ts +4 -0
- package/dist/sdk/comments.js +2 -2
- package/dist/sdk/completion.js +9 -5
- package/dist/sdk/contracts.d.ts +1 -0
- package/dist/sdk/contracts.js +3 -2
- package/dist/sdk/dependency-provenance.d.ts +51 -2
- package/dist/sdk/dependency-provenance.js +91 -7
- package/dist/sdk/extension/install-sources.d.ts +8 -1
- package/dist/sdk/extension/install-sources.js +132 -39
- package/dist/sdk/generated/generated-error-code-catalog-part-1.js +74 -14
- package/dist/sdk/generated/generated-error-code-catalog-part-2.js +86 -38
- package/dist/sdk/governance/health.js +86 -22
- package/dist/sdk/governance/validate-history-drift.js +5 -2
- package/dist/sdk/graph/assembly.js +51 -22
- package/dist/sdk/history-repair.d.ts +1 -1
- package/dist/sdk/history-repair.js +20 -10
- package/dist/sdk/index.d.ts +1 -0
- package/dist/sdk/index.js +3 -2
- package/dist/sdk/learnings.d.ts +4 -0
- package/dist/sdk/learnings.js +7 -4
- package/dist/sdk/lifecycle/close.js +4 -3
- package/dist/sdk/lifecycle/create.js +43 -19
- package/dist/sdk/linked-artifacts.js +21 -31
- package/dist/sdk/merge/reconcile.js +3 -16
- package/dist/sdk/notes.d.ts +4 -0
- package/dist/sdk/notes.js +2 -2
- package/dist/sdk/query/next.d.ts +6 -0
- package/dist/sdk/query/next.js +7 -2
- package/dist/sdk/runtime-input.js +5 -2
- package/dist/sdk/runtime.d.ts +6 -6
- package/dist/sdk/runtime.js +8 -8
- package/dist/sdk/test/entry.d.ts +1 -1
- package/dist/sdk/test/entry.js +5 -9
- package/dist/sdk/test/execution.d.ts +3 -0
- package/dist/sdk/test/execution.js +54 -13
- package/docs/COMMANDS.md +4 -3
- package/docs/CONTEXT_RECOVERY_PRIMITIVES.md +67 -0
- package/docs/MERGE_SAFETY.md +23 -10
- package/docs/OUTPUT_TOKEN_ACCOUNTING.md +20 -7
- package/docs/README.md +1 -0
- package/docs/RELEASING.md +9 -1
- package/docs/SDK.md +12 -0
- package/docs/SDK_CONTEXT_INTEGRITY.md +12 -1
- package/docs/SDK_RUNTIME_BOUNDARIES.md +10 -0
- package/docs/TESTING.md +6 -2
- package/docs/agent-task-token-baseline.json +97 -11
- package/docs/agent-task-transcripts.json +211 -0
- package/docs/generated/FLAG_LEXICON_BUDGETS.md +3 -3
- package/docs/generated/REFUSAL_CLOSURE_CENSUS.md +13 -4
- package/docs/performance/cli-transport-overhead.md +10 -2
- package/marketplace.json +2 -2
- package/package.json +8 -8
- package/packages/pm-beads/package.json +1 -1
- package/packages/pm-calendar/package.json +1 -1
- package/packages/pm-command-kit/package.json +1 -1
- package/packages/pm-digital-twin/package.json +1 -1
- package/packages/pm-governance-audit/package.json +1 -1
- package/packages/pm-guide-shell/package.json +1 -1
- package/packages/pm-kanban/package.json +1 -1
- package/packages/pm-lifecycle-hooks/package.json +1 -1
- package/packages/pm-linked-test-adapters/package.json +1 -1
- package/packages/pm-search-advanced/package.json +1 -1
- package/packages/pm-templates/package.json +1 -1
- package/packages/pm-todos/package.json +1 -1
- package/packages/pm-vcs/package.json +1 -1
- package/plugins/pm-claude/.claude-plugin/plugin.json +1 -1
- package/plugins/pm-codex/.codex-plugin/plugin.json +1 -1
- package/sdk/public-surface.json +297 -36
- package/dist/cli-bundle/chunks/chunk-MFNTKMTI.js +0 -13
- package/dist/cli-bundle/chunks/chunk-OS27HHBN.js +0 -35
- package/dist/cli-bundle/chunks/chunk-QTO7USTH.js +0 -2
- package/dist/cli-bundle/focused-chunks/chunk-2AGZ5BRT.js +0 -2
- package/dist/cli-bundle/focused-chunks/chunk-AQ5IYEZZ.js +0 -2
- package/dist/cli-bundle/focused-chunks/chunk-XDPYBQCF.js +0 -156
- package/dist/cli-bundle/focused-chunks/chunk-Y5A7SJJ7.js +0 -2
- package/dist/cli-bundle/focused-chunks/chunk-YHWHX6YY.js +0 -2
|
@@ -6,14 +6,14 @@
|
|
|
6
6
|
},
|
|
7
7
|
"metadata": {
|
|
8
8
|
"description": "Official marketplace for pm CLI — native git-based project management for Claude Code and AI coding agents.",
|
|
9
|
-
"version": "2026.8.
|
|
9
|
+
"version": "2026.8.29"
|
|
10
10
|
},
|
|
11
11
|
"plugins": [
|
|
12
12
|
{
|
|
13
13
|
"name": "pm-claude",
|
|
14
14
|
"source": "./plugins/pm-claude",
|
|
15
15
|
"description": "Native pm CLI integration for Claude Code — 28 MCP tools, 5 workflow skills, 14 slash commands, 4 subagents, hybrid TUI task tracking, session context injection, and coordination subagents for git-based project management without leaving Claude Code.",
|
|
16
|
-
"version": "2026.8.
|
|
16
|
+
"version": "2026.8.29",
|
|
17
17
|
"author": {
|
|
18
18
|
"name": "unbrained",
|
|
19
19
|
"url": "https://github.com/unbraind/pm-cli"
|
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,53 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## 2026.8.29 - 2026-08-29
|
|
4
|
+
|
|
5
|
+
### Fixed
|
|
6
|
+
|
|
7
|
+
- GH-1144: hash-only merge receipts contradict report output and cannot reconcile truthfully ([pm-z1z96w](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-z1z96w.toon))
|
|
8
|
+
- GH-1146/1147: external blockers remain stale and validation recommends deleting them ([pm-yhle2e](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-yhle2e.toon))
|
|
9
|
+
- GH-1140: reject ambiguous bare comma tuples for linked file and test mutations ([pm-nc94mk](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-nc94mk.toon))
|
|
10
|
+
- GH-1148: cached drift mismatch can falsely report tracker corruption ([pm-sxg7wl](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-sxg7wl.toon))
|
|
11
|
+
- GH-1138: linked test name filters can pass after executing zero tests ([pm-ntnv4k](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-ntnv4k.toon))
|
|
12
|
+
- GH-1136: npm 12 object-form npm pack receipts break registry package installs ([pm-xrjy8o](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-xrjy8o.toon))
|
|
13
|
+
- GH-1135: item_hash_version 2 still masks writer hash divergence as corruption ([pm-2qahia](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-2qahia.toon))
|
|
14
|
+
- The annotation key=value grammar has three divergent comma behaviours, two of which silently corrupt the evidence text before it is made immutable ([pm-hu92i3](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-hu92i3.toon))
|
|
15
|
+
- GH-1150: health remediation for pending merge receipts must perform the repair ([pm-r0p3at](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-r0p3at.toon))
|
|
16
|
+
- GH-1134: required collection recovery omits truthful --clear-\* intent ([pm-t7wl00](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-t7wl00.toon))
|
|
17
|
+
- GH-1143: Claude session-file provenance resolver ignores real nested stream fields ([pm-f60039](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-f60039.toon))
|
|
18
|
+
- GH-1137: linked docs writes silently persist nonexistent workspace paths ([pm-hiqlkh](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-hiqlkh.toon))
|
|
19
|
+
- Sentry release gate aborts valid API queries at a fixed 15-second deadline ([pm-b9g2cs](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-b9g2cs.toon))
|
|
20
|
+
|
|
21
|
+
### Other
|
|
22
|
+
|
|
23
|
+
- Refresh @sentry/node 10.72 with packed SDK and release proof ([pm-mwhv33](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/chores/pm-mwhv33.toon))
|
|
24
|
+
- Refresh compatible 2026-08-29 dependency releases ([pm-vwuidf](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/chores/pm-vwuidf.toon))
|
|
25
|
+
- Close the jscpd/CodeFactor sensitivity gap: minTokens 115 misses low-token table clones the CodeFactor bot still files ([pm-xspd](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/chores/pm-xspd.toon))
|
|
26
|
+
|
|
27
|
+
## 2026.8.28 - 2026-08-28
|
|
28
|
+
|
|
29
|
+
### Fixed
|
|
30
|
+
|
|
31
|
+
- Repository test runner inherits production Sentry and turns negative CLI fixtures into release-blocking incidents ([pm-5ug5xq](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-5ug5xq.toon))
|
|
32
|
+
- Broad squash commits overflow hosted-analysis tree lookup and falsely lose reviewed PR provenance ([pm-gactwj](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-gactwj.toon))
|
|
33
|
+
- Golden agent-transcript replay: measure tokens-per-completed-task as a CI-visible DX regression gate ([pm-8pnj](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/features/pm-8pnj.toon))
|
|
34
|
+
- Unknown-option refusal textual flags bypass structured global-option filtering ([pm-x4wbui](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-x4wbui.toon))
|
|
35
|
+
- Agent-task transcript recovery accepts a refusal as a successful retry ([pm-o360q6](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-o360q6.toon))
|
|
36
|
+
- Close lifecycle bypasses reproducible process clock ([pm-hmpu4p](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-hmpu4p.toon))
|
|
37
|
+
- GH-1132: opt-in idempotent annotation append (ifAbsent/--if-absent) prevents retry-driven context duplication; duplicate appends remain available by default ([pm-ea1yh2](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-ea1yh2.toon))
|
|
38
|
+
- Agent-task transcripts accept declared no-effect and partial-effect successful exits ([pm-wanwyc](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-wanwyc.toon))
|
|
39
|
+
- Agent-task baselines accept missing task and composite token ceilings ([pm-aksavu](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-aksavu.toon))
|
|
40
|
+
- Agent-task closeout claims lack linked full-verification commands ([pm-ervmsc](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-ervmsc.toon))
|
|
41
|
+
- CLI transport-floor RSS admission false-fails on single-sample page noise ([pm-pz49xc](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-pz49xc.toon))
|
|
42
|
+
- Unknown-option refusals identify the actual rejected flag and fail closed at delimiters ([pm-fo8g7j](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-fo8g7j.toon))
|
|
43
|
+
- Agent-task gate accepts incidental substrings as required-field completeness ([pm-o7u08u](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-o7u08u.toon))
|
|
44
|
+
- Completed-task transcripts require terminal success, exclusive refusal metadata, and complete recovery ([pm-wa39rl](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-wa39rl.toon))
|
|
45
|
+
- Agent-task token replay trusts missing or incorrect accounting estimates ([pm-ok2kdn](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-ok2kdn.toon))
|
|
46
|
+
|
|
47
|
+
### Security
|
|
48
|
+
|
|
49
|
+
- GH-1131: macOS Node 24 nightly cannot create the Skills-over-MCP special-file socket fixture ([pm-k23c4c](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/issues/pm-k23c4c.toon))
|
|
50
|
+
|
|
3
51
|
## 2026.8.27 - 2026-08-27
|
|
4
52
|
|
|
5
53
|
### Added
|
|
@@ -887,10 +935,10 @@
|
|
|
887
935
|
|
|
888
936
|
### Other
|
|
889
937
|
|
|
938
|
+
- CLI transport overhead budget: gate the per-invocation bootstrap floor and the CLI-vs-SDK delta, not just absolute scale numbers ([pm-yse5dt](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/tasks/pm-yse5dt.toon))
|
|
890
939
|
- CI/CD + test-suite performance: in-process CLI runner and dedupe redundant matrix legs ([pm-7rlp](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/chores/pm-7rlp.toon))
|
|
891
940
|
- ADR: agent identity model — stable author namespace plus structured harness, model, and session provenance ([pm-qwuber](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/decisions/pm-qwuber.toon))
|
|
892
941
|
- Public SDK surface shape: 881 exports behind one flat entrypoint with no capability tiering and a 250ms eager import cost ([pm-38bskj](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/tasks/pm-38bskj.toon))
|
|
893
|
-
- CLI transport overhead budget: gate the per-invocation bootstrap floor and the CLI-vs-SDK delta, not just absolute scale numbers ([pm-yse5dt](https://github.com/unbraind/pm-cli/blob/main/.agents/pm/tasks/pm-yse5dt.toon))
|
|
894
942
|
|
|
895
943
|
## 2026.7.25 - 2026-07-25
|
|
896
944
|
|
|
@@ -1,9 +1,10 @@
|
|
|
1
1
|
|
|
2
|
-
!function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="
|
|
2
|
+
!function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="ca79853d-468c-5522-b5f9-6509c66e3d9b")}catch(e){}}();
|
|
3
3
|
import { resolveRecoveryCommandName } from "../sdk/agent/command-recovery.js";
|
|
4
4
|
import { projectPmDiagnosticOutput, projectPmDiagnosticText, } from "../sdk/cli-contracts/agent-output-contracts.js";
|
|
5
5
|
import { renderPmCommand } from "./argv-utils.js";
|
|
6
6
|
import { discoverNearbyPmRoot } from "../sdk/tracker-root-discovery.js";
|
|
7
|
+
import { stripGlobalBootstrapTokens } from "../sdk/cli-bootstrap.js";
|
|
7
8
|
/** Compact an error envelope to fields that change the caller's next action. */
|
|
8
9
|
export function projectLeanErrorEnvelope(envelope) {
|
|
9
10
|
const { why: _why, title: _title, ...actionable } = envelope;
|
|
@@ -307,15 +308,36 @@ function attachStructuredGuidanceDetails(payload, message) {
|
|
|
307
308
|
function resolveRefusalCandidateFlag(message, normalizedArgs) {
|
|
308
309
|
if (message.flag)
|
|
309
310
|
return message.flag;
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
311
|
+
const isAdmissibleCandidate = (flag) => {
|
|
312
|
+
const canonicalFlag = flag.split("=", 1)[0];
|
|
313
|
+
return (stripGlobalBootstrapTokens([canonicalFlag]).length > 0 &&
|
|
314
|
+
!["--help", "--no-changed-fields", "--version"].includes(canonicalFlag) &&
|
|
315
|
+
normalizedArgs.some((argument) => argument === canonicalFlag ||
|
|
316
|
+
argument.startsWith(`${canonicalFlag}=`)));
|
|
317
|
+
};
|
|
318
|
+
const mentionedFlag = [
|
|
319
|
+
...`${message.title} ${message.happened}`.matchAll(/--[A-Za-z0-9][A-Za-z0-9_-]*/gu),
|
|
320
|
+
]
|
|
321
|
+
.map((match) => match[0])
|
|
322
|
+
.find((flag) => isAdmissibleCandidate(flag));
|
|
323
|
+
if (mentionedFlag)
|
|
324
|
+
return mentionedFlag;
|
|
325
|
+
return message.recovery?.provided_fields
|
|
326
|
+
?.map((field) => field.split("=", 1)[0])
|
|
327
|
+
.find((field) => isAdmissibleCandidate(field));
|
|
313
328
|
}
|
|
314
329
|
function resolveRefusalRejectedValue(message, normalizedArgs, candidateFlag) {
|
|
315
330
|
if (message.value !== undefined)
|
|
316
331
|
return message.value;
|
|
317
332
|
if (candidateFlag) {
|
|
318
|
-
|
|
333
|
+
const candidateArgument = normalizedArgs.find((argument) => argument === candidateFlag || argument.startsWith(`${candidateFlag}=`));
|
|
334
|
+
if (candidateArgument?.startsWith(`${candidateFlag}=`)) {
|
|
335
|
+
return candidateArgument.slice(candidateFlag.length + 1);
|
|
336
|
+
}
|
|
337
|
+
const candidateIndex = normalizedArgs.indexOf(candidateFlag);
|
|
338
|
+
return candidateIndex >= 0
|
|
339
|
+
? normalizedArgs[candidateIndex + 1]
|
|
340
|
+
: undefined;
|
|
319
341
|
}
|
|
320
342
|
const allowedValues = message.recovery?.allowed_values;
|
|
321
343
|
if (!allowedValues?.length)
|
|
@@ -941,6 +963,34 @@ function buildUnknownOptionNextSteps(optionName, commandName, suggestions, candi
|
|
|
941
963
|
: undefined,
|
|
942
964
|
].filter((entry) => typeof entry === "string");
|
|
943
965
|
}
|
|
966
|
+
/**
|
|
967
|
+
* Publish a shell-free correction only when removing the unknown token leaves
|
|
968
|
+
* positional ownership unambiguous; explicit producer guidance stays authoritative.
|
|
969
|
+
*/
|
|
970
|
+
function resolveUnknownOptionRetry(context, optionName) {
|
|
971
|
+
if (context.suggestedRetryCommand !== undefined) {
|
|
972
|
+
return { retryCommand: context.suggestedRetryCommand };
|
|
973
|
+
}
|
|
974
|
+
const normalizedArgs = context.normalizedInvocationArgs;
|
|
975
|
+
if (normalizedArgs === undefined)
|
|
976
|
+
return {};
|
|
977
|
+
if (normalizedArgs.filter((argument) => argument === optionName || argument.startsWith(`${optionName}=`)).length !== 1) {
|
|
978
|
+
return {};
|
|
979
|
+
}
|
|
980
|
+
const optionIndex = normalizedArgs.findIndex((argument) => argument === optionName || argument.startsWith(`${optionName}=`));
|
|
981
|
+
if (optionIndex < 0 ||
|
|
982
|
+
normalizedArgs.includes("--") ||
|
|
983
|
+
(!normalizedArgs[optionIndex]?.includes("=") &&
|
|
984
|
+
optionIndex !== normalizedArgs.length - 1 &&
|
|
985
|
+
normalizedArgs[optionIndex + 1]?.startsWith("-") !== true)) {
|
|
986
|
+
return {};
|
|
987
|
+
}
|
|
988
|
+
const suggestedRetryArgs = stripGlobalBootstrapTokens(normalizedArgs.filter((_, index) => index !== optionIndex));
|
|
989
|
+
return {
|
|
990
|
+
retryCommand: renderPmCommand(suggestedRetryArgs),
|
|
991
|
+
suggestedRetryArgs,
|
|
992
|
+
};
|
|
993
|
+
}
|
|
944
994
|
function buildUnknownOptionGuidance(message, commandName, context) {
|
|
945
995
|
const unknownOption = message.match(/unknown option '([^']+)'/);
|
|
946
996
|
if (!unknownOption) {
|
|
@@ -949,7 +999,7 @@ function buildUnknownOptionGuidance(message, commandName, context) {
|
|
|
949
999
|
const guidanceContext = context ?? {};
|
|
950
1000
|
const optionName = unknownOption[1];
|
|
951
1001
|
const suggestions = normalizeOptionFlags(guidanceContext.unknownOptionSuggestions) ?? [];
|
|
952
|
-
const retryCommand = guidanceContext
|
|
1002
|
+
const { retryCommand, suggestedRetryArgs } = resolveUnknownOptionRetry(guidanceContext, optionName);
|
|
953
1003
|
if (commandName === "update" &&
|
|
954
1004
|
(optionName === "--file" || optionName === "--doc")) {
|
|
955
1005
|
return buildUnsupportedUpdateOptionGuidance(optionName, context, suggestions);
|
|
@@ -966,10 +1016,14 @@ function buildUnknownOptionGuidance(message, commandName, context) {
|
|
|
966
1016
|
happened: `Commander does not recognize option ${optionName} for this command path.`,
|
|
967
1017
|
required: UNKNOWN_OPTION_REQUIRED_BY_SCOPE[candidateContext.optionScope],
|
|
968
1018
|
why: "Option contracts are command-specific and intentionally validated.",
|
|
1019
|
+
flag: optionName,
|
|
1020
|
+
value: optionName,
|
|
969
1021
|
examples,
|
|
970
1022
|
nextSteps,
|
|
971
1023
|
recovery: buildCommanderRecoveryPayload(context, {
|
|
972
1024
|
suggested_flags: suggestions.length > 0 ? suggestions : undefined,
|
|
1025
|
+
suggested_retry: retryCommand,
|
|
1026
|
+
suggested_retry_args: suggestedRetryArgs,
|
|
973
1027
|
candidate_commands: candidateContext.otherCommands,
|
|
974
1028
|
candidate_commands_total: candidateContext.candidateTotal || undefined,
|
|
975
1029
|
candidate_commands_truncated: guidanceContext.unknownOptionOtherCommandsTruncated,
|
|
@@ -1297,4 +1351,4 @@ export const _testOnly = {
|
|
|
1297
1351
|
resolveKnownPackageCommandHint,
|
|
1298
1352
|
};
|
|
1299
1353
|
//# sourceMappingURL=error-guidance.js.map
|
|
1300
|
-
//# debugId=
|
|
1354
|
+
//# debugId=ca79853d-468c-5522-b5f9-6509c66e3d9b
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
|
|
2
|
-
!function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="
|
|
2
|
+
!function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="775518a4-ff3e-5a54-8fbd-b2c4863e23db")}catch(e){}}();
|
|
3
3
|
import { EXIT_CODE, PmCliError, } from "../sdk/runtime-primitives.js";
|
|
4
4
|
import { renderPmCommand } from "../sdk/command-line.js";
|
|
5
5
|
import { runComments } from "./commands/comments.js";
|
|
@@ -93,13 +93,33 @@ function resolveCommentSources(text, options) {
|
|
|
93
93
|
deleteIndex !== undefined,
|
|
94
94
|
};
|
|
95
95
|
}
|
|
96
|
-
|
|
96
|
+
/** Resolves every mutation-bearing source for notes and learnings once. */
|
|
97
|
+
function resolveSingleAnnotationSources(label, positional, options) {
|
|
97
98
|
const addFromOption = resolveAnnotationTextAliases(label, options, label === "note" ? ["add", "text", "note"] : ["add", "text"]);
|
|
98
99
|
const addFromPositional = typeof positional === "string" ? positional : undefined;
|
|
99
100
|
if (addFromOption !== undefined && addFromPositional !== undefined) {
|
|
100
101
|
throw new PmCliError(`Specify ${label} text either as positional [text] or with --add, not both`, EXIT_CODE.USAGE);
|
|
101
102
|
}
|
|
102
|
-
|
|
103
|
+
const add = addFromOption ?? addFromPositional;
|
|
104
|
+
const addJson = label === "note" ? readOptionString(options, "addJson") : undefined;
|
|
105
|
+
const readFromStdin = options.stdin === true;
|
|
106
|
+
const readFromFile = readOptionString(options, "file");
|
|
107
|
+
const editIndex = typeof options.edit === "number" ? options.edit : undefined;
|
|
108
|
+
const deleteIndex = typeof options.delete === "number" ? options.delete : undefined;
|
|
109
|
+
return {
|
|
110
|
+
add,
|
|
111
|
+
addJson,
|
|
112
|
+
readFromStdin,
|
|
113
|
+
readFromFile,
|
|
114
|
+
editIndex,
|
|
115
|
+
deleteIndex,
|
|
116
|
+
isMutation: typeof add === "string" ||
|
|
117
|
+
addJson !== undefined ||
|
|
118
|
+
readFromStdin ||
|
|
119
|
+
readFromFile !== undefined ||
|
|
120
|
+
editIndex !== undefined ||
|
|
121
|
+
deleteIndex !== undefined,
|
|
122
|
+
};
|
|
103
123
|
}
|
|
104
124
|
async function runCommentsAction(id, text, options, command) {
|
|
105
125
|
const globalOptions = getGlobalOptions(command);
|
|
@@ -114,12 +134,13 @@ async function runCommentsAction(id, text, options, command) {
|
|
|
114
134
|
delete: sources.deleteIndex,
|
|
115
135
|
limit: readOptionString(options, "limit"),
|
|
116
136
|
fullHistory: options.fullHistory === true,
|
|
137
|
+
ifAbsent: options.ifAbsent === true,
|
|
117
138
|
author: readOptionString(options, "author"),
|
|
118
139
|
message: readOptionString(options, "message"),
|
|
119
140
|
ownershipAppendBypass: options.ownershipAppendBypass === true,
|
|
120
141
|
force: Boolean(options.force),
|
|
121
142
|
}, globalOptions);
|
|
122
|
-
if (sources.isMutation) {
|
|
143
|
+
if (sources.isMutation && result.changed !== false) {
|
|
123
144
|
await invalidateSearchCachesForMutation(globalOptions, result);
|
|
124
145
|
}
|
|
125
146
|
printAnnotationResult("comments", result, globalOptions, startedAt);
|
|
@@ -128,30 +149,26 @@ async function runNotesAction(id, text, options, command) {
|
|
|
128
149
|
const globalOptions = getGlobalOptions(command);
|
|
129
150
|
const startedAt = Date.now();
|
|
130
151
|
assertNoTransposedAnnotationAction("notes", id, text, options);
|
|
131
|
-
const
|
|
152
|
+
const sources = resolveSingleAnnotationSources("note", text, options);
|
|
132
153
|
const result = await runNotes(id, {
|
|
133
|
-
add,
|
|
134
|
-
addJson:
|
|
135
|
-
stdin:
|
|
136
|
-
file:
|
|
137
|
-
edit:
|
|
138
|
-
delete:
|
|
154
|
+
add: sources.add,
|
|
155
|
+
addJson: sources.addJson,
|
|
156
|
+
stdin: sources.readFromStdin,
|
|
157
|
+
file: sources.readFromFile,
|
|
158
|
+
edit: sources.editIndex,
|
|
159
|
+
delete: sources.deleteIndex,
|
|
139
160
|
limit: readOptionString(options, "limit"),
|
|
140
161
|
since: readOptionString(options, "since"),
|
|
141
162
|
eventType: readOptionString(options, "eventType"),
|
|
142
163
|
includeMeta: options.includeMeta === true,
|
|
143
164
|
fullHistory: options.fullHistory === true,
|
|
165
|
+
ifAbsent: options.ifAbsent === true,
|
|
144
166
|
author: readOptionString(options, "author"),
|
|
145
167
|
message: readOptionString(options, "message"),
|
|
146
168
|
ownershipAppendBypass: options.ownershipAppendBypass === true,
|
|
147
169
|
force: Boolean(options.force),
|
|
148
170
|
}, globalOptions);
|
|
149
|
-
if (
|
|
150
|
-
typeof options.addJson === "string" ||
|
|
151
|
-
options.stdin === true ||
|
|
152
|
-
typeof options.file === "string" ||
|
|
153
|
-
typeof options.edit === "number" ||
|
|
154
|
-
typeof options.delete === "number") {
|
|
171
|
+
if (sources.isMutation && result.changed !== false) {
|
|
155
172
|
await invalidateSearchCachesForMutation(globalOptions, result);
|
|
156
173
|
}
|
|
157
174
|
printAnnotationResult("notes", result, globalOptions, startedAt);
|
|
@@ -160,25 +177,22 @@ async function runLearningsAction(id, text, options, command) {
|
|
|
160
177
|
const globalOptions = getGlobalOptions(command);
|
|
161
178
|
const startedAt = Date.now();
|
|
162
179
|
assertNoTransposedAnnotationAction("learnings", id, text, options);
|
|
163
|
-
const
|
|
180
|
+
const sources = resolveSingleAnnotationSources("learning", text, options);
|
|
164
181
|
const result = await runLearnings(id, {
|
|
165
|
-
add,
|
|
166
|
-
stdin:
|
|
167
|
-
file:
|
|
168
|
-
edit:
|
|
169
|
-
delete:
|
|
182
|
+
add: sources.add,
|
|
183
|
+
stdin: sources.readFromStdin,
|
|
184
|
+
file: sources.readFromFile,
|
|
185
|
+
edit: sources.editIndex,
|
|
186
|
+
delete: sources.deleteIndex,
|
|
170
187
|
limit: readOptionString(options, "limit"),
|
|
171
188
|
fullHistory: options.fullHistory === true,
|
|
189
|
+
ifAbsent: options.ifAbsent === true,
|
|
172
190
|
author: readOptionString(options, "author"),
|
|
173
191
|
message: readOptionString(options, "message"),
|
|
174
192
|
ownershipAppendBypass: options.ownershipAppendBypass === true,
|
|
175
193
|
force: Boolean(options.force),
|
|
176
194
|
}, globalOptions);
|
|
177
|
-
if (
|
|
178
|
-
options.stdin === true ||
|
|
179
|
-
typeof options.file === "string" ||
|
|
180
|
-
typeof options.edit === "number" ||
|
|
181
|
-
typeof options.delete === "number") {
|
|
195
|
+
if (sources.isMutation && result.changed !== false) {
|
|
182
196
|
await invalidateSearchCachesForMutation(globalOptions, result);
|
|
183
197
|
}
|
|
184
198
|
printAnnotationResult("learnings", result, globalOptions, startedAt);
|
|
@@ -195,14 +209,15 @@ export function registerAnnotationCommands(program, parsePositiveInteger) {
|
|
|
195
209
|
.command("comments")
|
|
196
210
|
.argument("<id>", "Item id")
|
|
197
211
|
.argument("[text]", "Optional comment text shorthand (equivalent to --add)")
|
|
198
|
-
.option("--add <text>", "
|
|
212
|
+
.option("--add <text>", "Append comment text; use text=<value> for structured input or - for stdin")
|
|
199
213
|
.option("--stdin", "Read comment text from stdin (supports multiline markdown)")
|
|
200
214
|
.option("--file <path>", "Read comment text from a file or stdin (-)")
|
|
201
|
-
.option("--edit <index>", "Replace
|
|
215
|
+
.option("--edit <index>", "Replace one comment using positional text, --add, --stdin, or --file", parsePositiveInteger("--edit"))
|
|
202
216
|
.option("--delete <index>", "Delete the comment at 1-based <index>", parsePositiveInteger("--delete"))
|
|
203
217
|
.option("--limit <n>", "Return only latest n comments")
|
|
204
|
-
.option("--full-history", "Return
|
|
205
|
-
.option("--
|
|
218
|
+
.option("--full-history", "Return complete comment history instead of a bounded mutation receipt")
|
|
219
|
+
.option("--if-absent", "Append only when resolved author and text are absent")
|
|
220
|
+
.option("--author [value]", "Comment author; defaults to PM_AUTHOR or settings")
|
|
206
221
|
.option("--message <value>", "History message")
|
|
207
222
|
.option("--force", "Force ownership override")
|
|
208
223
|
.description("List, add, edit, or delete comments for an item.")
|
|
@@ -213,10 +228,10 @@ export function registerAnnotationCommands(program, parsePositiveInteger) {
|
|
|
213
228
|
const notesCommand = program
|
|
214
229
|
.command("notes")
|
|
215
230
|
.argument("<id>", "Item id")
|
|
216
|
-
.argument("[text]", "Optional note text shorthand
|
|
231
|
+
.argument("[text]", "Optional note text shorthand for --add")
|
|
217
232
|
.option("--add <text>", "Add a text note (- reads stdin)")
|
|
218
233
|
.option("--note <text>", "Alias for --add")
|
|
219
|
-
.option("--add-json <json>", "Append a
|
|
234
|
+
.option("--add-json <json>", "Append a JSON event")
|
|
220
235
|
.option("--stdin", "Read note text from stdin")
|
|
221
236
|
.option("--file <path>", "Read note from file or stdin (-)")
|
|
222
237
|
.option("--edit <index>", "Replace a 1-based note using the selected text input", parsePositiveInteger("--edit"))
|
|
@@ -225,7 +240,8 @@ export function registerAnnotationCommands(program, parsePositiveInteger) {
|
|
|
225
240
|
.option("--since <timestamp>", "Filter JSON events from this ISO time")
|
|
226
241
|
.option("--event-type <value>", "Filter JSON events by top-level type")
|
|
227
242
|
.option("--include-meta", "Include count and truncation metadata")
|
|
228
|
-
.option("--full-history", "Return
|
|
243
|
+
.option("--full-history", "Return complete note history instead of a bounded receipt")
|
|
244
|
+
.option("--if-absent", "Append only when resolved author and text are absent")
|
|
229
245
|
.option("--author [value]", "Author; defaults to PM_AUTHOR/settings")
|
|
230
246
|
.option("--message <value>", "History message")
|
|
231
247
|
.option("--force", "Force ownership override")
|
|
@@ -235,14 +251,15 @@ export function registerAnnotationCommands(program, parsePositiveInteger) {
|
|
|
235
251
|
const learningsCommand = program
|
|
236
252
|
.command("learnings")
|
|
237
253
|
.argument("<id>", "Item id")
|
|
238
|
-
.argument("[text]", "Optional learning text shorthand
|
|
239
|
-
.option("--add <text>", "
|
|
240
|
-
.option("--stdin", "Read learning text from stdin
|
|
254
|
+
.argument("[text]", "Optional learning text shorthand for --add")
|
|
255
|
+
.option("--add <text>", "Append learning text; use text=<value> or - for stdin")
|
|
256
|
+
.option("--stdin", "Read learning text from stdin")
|
|
241
257
|
.option("--file <path>", "Read learning text from a file or stdin (-)")
|
|
242
|
-
.option("--edit <index>", "Replace
|
|
258
|
+
.option("--edit <index>", "Replace one learning using positional text, --add, --stdin, or --file", parsePositiveInteger("--edit"))
|
|
243
259
|
.option("--delete <index>", "Delete the learning at 1-based <index>", parsePositiveInteger("--delete"))
|
|
244
260
|
.option("--limit <n>", "Return only latest n learnings")
|
|
245
|
-
.option("--full-history", "Return
|
|
261
|
+
.option("--full-history", "Return complete learning history instead of a bounded receipt")
|
|
262
|
+
.option("--if-absent", "Append only when resolved author and text are absent")
|
|
246
263
|
.option("--author [value]", "Learning author (optional; falls back to PM_AUTHOR/settings)")
|
|
247
264
|
.option("--message <value>", "History message")
|
|
248
265
|
.option("--force", "Force ownership override")
|
|
@@ -251,4 +268,4 @@ export function registerAnnotationCommands(program, parsePositiveInteger) {
|
|
|
251
268
|
addHiddenOption(learningsCommand, "--text <text>", "Alias for --add", false);
|
|
252
269
|
}
|
|
253
270
|
//# sourceMappingURL=register-annotations.js.map
|
|
254
|
-
//# debugId=
|
|
271
|
+
//# debugId=775518a4-ff3e-5a54-8fbd-b2c4863e23db
|