@productbrain/cli 0.1.0-beta.5916 → 0.1.0-beta.5955
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/dist/__tests__/capture-receipt-spine-floor.test.d.ts +2 -0
- package/dist/__tests__/capture-receipt-spine-floor.test.d.ts.map +1 -0
- package/dist/__tests__/capture-receipt-spine-floor.test.js +45 -0
- package/dist/__tests__/capture-receipt-spine-floor.test.js.map +1 -0
- package/dist/__tests__/capture.test.js +1 -1
- package/dist/__tests__/capture.test.js.map +1 -1
- package/dist/__tests__/repo-detect.test.js +3 -0
- package/dist/__tests__/repo-detect.test.js.map +1 -1
- package/dist/commands/__tests__/quality.test.js +3 -3
- package/dist/commands/__tests__/quality.test.js.map +1 -1
- package/dist/commands/capture.d.ts +1 -2
- package/dist/commands/capture.d.ts.map +1 -1
- package/dist/commands/capture.js +6 -2
- package/dist/commands/capture.js.map +1 -1
- package/dist/formatters/brief.d.ts +2 -1
- package/dist/formatters/brief.d.ts.map +1 -1
- package/dist/formatters/brief.js +5 -2
- package/dist/formatters/brief.js.map +1 -1
- package/dist/formatters/brief.test.d.ts +2 -0
- package/dist/formatters/brief.test.d.ts.map +1 -0
- package/dist/formatters/brief.test.js +20 -0
- package/dist/formatters/brief.test.js.map +1 -0
- package/dist/formatters/capture.d.ts +10 -0
- package/dist/formatters/capture.d.ts.map +1 -1
- package/dist/formatters/capture.js +13 -0
- package/dist/formatters/capture.js.map +1 -1
- package/dist/formatters/orient.d.ts +6 -6
- package/dist/formatters/orient.d.ts.map +1 -1
- package/dist/formatters/orient.js +9 -8
- package/dist/formatters/orient.js.map +1 -1
- package/dist/formatters/orient.rituals.test.js +11 -4
- package/dist/formatters/orient.rituals.test.js.map +1 -1
- package/dist/formatters/spineCheck.d.ts +5 -68
- package/dist/formatters/spineCheck.d.ts.map +1 -1
- package/dist/formatters/spineCheck.js +15 -13
- package/dist/formatters/spineCheck.js.map +1 -1
- package/dist/formatters/spineCheck.test.d.ts +2 -0
- package/dist/formatters/spineCheck.test.d.ts.map +1 -0
- package/dist/formatters/spineCheck.test.js +76 -0
- package/dist/formatters/spineCheck.test.js.map +1 -0
- package/dist/lib/captureGrounding.d.ts +3 -2
- package/dist/lib/captureGrounding.d.ts.map +1 -1
- package/dist/lib/captureGrounding.js +16 -9
- package/dist/lib/captureGrounding.js.map +1 -1
- package/dist/lib/captureGrounding.test.d.ts +2 -0
- package/dist/lib/captureGrounding.test.d.ts.map +1 -0
- package/dist/lib/captureGrounding.test.js +40 -0
- package/dist/lib/captureGrounding.test.js.map +1 -0
- package/dist/lib/readinessNotices.d.ts +15 -0
- package/dist/lib/readinessNotices.d.ts.map +1 -0
- package/dist/lib/readinessNotices.js +15 -0
- package/dist/lib/readinessNotices.js.map +1 -0
- package/dist/lib/repo-detect.d.ts.map +1 -1
- package/dist/lib/repo-detect.js +4 -0
- package/dist/lib/repo-detect.js.map +1 -1
- package/dist/lib/spineVerdictRead.d.ts +65 -0
- package/dist/lib/spineVerdictRead.d.ts.map +1 -0
- package/dist/lib/spineVerdictRead.js +64 -0
- package/dist/lib/spineVerdictRead.js.map +1 -0
- package/package.json +1 -1
|
@@ -1,76 +1,13 @@
|
|
|
1
|
-
/**
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
* Types are local structural mirrors of convex/intelligence/spineCheck.ts's
|
|
5
|
-
* SpineVerdictPayload — the CLI package cannot import convex/ or kernel/
|
|
6
|
-
* (same precedent as formatters/coaching.ts's CoachingVerdict mirror).
|
|
7
|
-
*/
|
|
8
|
-
export interface SpineStructuralFinding {
|
|
9
|
-
passed: boolean;
|
|
10
|
-
missing: Array<'purpose' | 'vision' | 'strategy' | 'objective' | 'key_result'>;
|
|
11
|
-
duplicateSingletons: {
|
|
12
|
-
purpose: string[] | null;
|
|
13
|
-
vision: string[] | null;
|
|
14
|
-
};
|
|
15
|
-
unconnectedStrategyIds: string[];
|
|
16
|
-
/** Truncated relation set means unknown, never inferred disconnected (PR #530 P2). */
|
|
17
|
-
strategiesWithUnknownConnectivity: string[];
|
|
18
|
-
visionConnectedToPurpose: boolean | null;
|
|
19
|
-
visionPurposeConnectivityTruncated: boolean;
|
|
20
|
-
/** TASK-78 (WP-684, doneWhen 12e): objective/key_result layers — optional, since a row
|
|
21
|
-
* persisted BEFORE this slice reads back with these undefined (same back-compat precedent
|
|
22
|
-
* as strategiesWithUnknownConnectivity below — the append-only spineVerdicts table never
|
|
23
|
-
* migrates old rows). */
|
|
24
|
-
unconnectedObjectiveIds?: string[];
|
|
25
|
-
objectivesWithUnknownConnectivity?: string[];
|
|
26
|
-
unconnectedKeyResultIds?: string[];
|
|
27
|
-
keyResultsWithUnknownConnectivity?: string[];
|
|
28
|
-
}
|
|
29
|
-
export interface SpineStrategyResult {
|
|
30
|
-
entryId: string;
|
|
31
|
-
refusal: {
|
|
32
|
-
entryId: string;
|
|
33
|
-
hasRefusalSignal: boolean;
|
|
34
|
-
};
|
|
35
|
-
rogerMartin: {
|
|
36
|
-
isStrategicChoice: boolean;
|
|
37
|
-
oppositeReasonable: boolean;
|
|
38
|
-
reasoning: string;
|
|
39
|
-
suggestion?: string | null;
|
|
40
|
-
} | null;
|
|
41
|
-
}
|
|
42
|
-
export interface SpineStoryVerdict {
|
|
43
|
-
passed: boolean;
|
|
44
|
-
failedCriterion: string | null;
|
|
45
|
-
criteria: Array<{
|
|
46
|
-
id: string;
|
|
47
|
-
passed: boolean;
|
|
48
|
-
reasoning: string;
|
|
49
|
-
}>;
|
|
50
|
-
}
|
|
51
|
-
export interface SpineVerdictPayload {
|
|
52
|
-
structural: SpineStructuralFinding;
|
|
53
|
-
noSpineEntries: boolean;
|
|
54
|
-
perStrategy: SpineStrategyResult[];
|
|
55
|
-
story: SpineStoryVerdict | null;
|
|
56
|
-
/** True iff the strategy fetch hit its cap — the graded set may be incomplete (PR #530 P2). */
|
|
57
|
-
strategiesTruncated: boolean;
|
|
58
|
-
/** True iff the per-strategy LLM evaluation loop stopped on the wall-clock budget — fewer
|
|
59
|
-
* strategies were graded this pass than exist (D1 residue fix). Optional: a row persisted
|
|
60
|
-
* before this field existed reads back with it undefined (same precedent as
|
|
61
|
-
* strategiesWithUnknownConnectivity above). */
|
|
62
|
-
perStrategyEvaluationTruncated?: boolean;
|
|
63
|
-
/** Round 1 P2 (cYO_e): mirrors strategiesTruncated above for the outcome layer — optional,
|
|
64
|
-
* since a row persisted before this field existed reads back with it undefined. */
|
|
65
|
-
objectivesTruncated?: boolean;
|
|
66
|
-
keyResultsTruncated?: boolean;
|
|
67
|
-
}
|
|
1
|
+
/** Spine-check display consumes the shared, generated read contract. */
|
|
2
|
+
import type { GatewayRouteReturnByName } from '@productbrain/kernel-client';
|
|
3
|
+
export type { SpineStructuralRead as SpineStructuralFinding, SpineStrategyRead as SpineStrategyResult, SpineStoryRead as SpineStoryVerdict, GradedSpineVerdict as SpineVerdictPayload, } from '../lib/spineVerdictRead.js';
|
|
68
4
|
export interface SpineVerdictRow {
|
|
69
|
-
verdict:
|
|
5
|
+
verdict: unknown;
|
|
70
6
|
includesStoryPass: boolean;
|
|
71
7
|
createdAt: number;
|
|
72
8
|
stale: boolean;
|
|
73
9
|
staleMemberIds: string[];
|
|
10
|
+
membershipTruncated?: NonNullable<GatewayRouteReturnByName<"quality.getLatestSpineVerdict">>["membershipTruncated"];
|
|
74
11
|
}
|
|
75
12
|
export declare function formatSpineVerdict(row: SpineVerdictRow | null): string;
|
|
76
13
|
//# sourceMappingURL=spineCheck.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"spineCheck.d.ts","sourceRoot":"","sources":["../../src/formatters/spineCheck.ts"],"names":[],"mappings":"AAAA
|
|
1
|
+
{"version":3,"file":"spineCheck.d.ts","sourceRoot":"","sources":["../../src/formatters/spineCheck.ts"],"names":[],"mappings":"AAAA,wEAAwE;AACxE,OAAO,KAAK,EAAE,wBAAwB,EAAE,MAAM,6BAA6B,CAAC;AAE5E,YAAY,EACV,mBAAmB,IAAI,sBAAsB,EAC7C,iBAAiB,IAAI,mBAAmB,EACxC,cAAc,IAAI,iBAAiB,EACnC,kBAAkB,IAAI,mBAAmB,GAC1C,MAAM,4BAA4B,CAAC;AAEpC,MAAM,WAAW,eAAe;IAC9B,OAAO,EAAE,OAAO,CAAC;IACjB,iBAAiB,EAAE,OAAO,CAAC;IAC3B,SAAS,EAAE,MAAM,CAAC;IAClB,KAAK,EAAE,OAAO,CAAC;IACf,cAAc,EAAE,MAAM,EAAE,CAAC;IACzB,mBAAmB,CAAC,EAAE,WAAW,CAAC,wBAAwB,CAAC,+BAA+B,CAAC,CAAC,CAAC,qBAAqB,CAAC,CAAC;CACrH;AAED,wBAAgB,kBAAkB,CAAC,GAAG,EAAE,eAAe,GAAG,IAAI,GAAG,MAAM,CA+GtE"}
|
|
@@ -1,21 +1,23 @@
|
|
|
1
|
-
|
|
2
|
-
* Spine-story check formatter (A2, WP-581/FEAT-1402).
|
|
3
|
-
*
|
|
4
|
-
* Types are local structural mirrors of convex/intelligence/spineCheck.ts's
|
|
5
|
-
* SpineVerdictPayload — the CLI package cannot import convex/ or kernel/
|
|
6
|
-
* (same precedent as formatters/coaching.ts's CoachingVerdict mirror).
|
|
7
|
-
*/
|
|
1
|
+
import { readSpineVerdict, describeSpineStaleness } from '../lib/spineVerdictRead.js';
|
|
8
2
|
export function formatSpineVerdict(row) {
|
|
9
3
|
if (!row) {
|
|
10
4
|
return 'No spine check has been run yet. Run `pb quality spine-check` to compute one.';
|
|
11
5
|
}
|
|
12
|
-
const
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
6
|
+
const parsed = readSpineVerdict(row.verdict);
|
|
7
|
+
if (parsed.kind === 'malformed') {
|
|
8
|
+
return 'Stored spine verdict is malformed — run `pb quality spine-check` to replace it.';
|
|
9
|
+
}
|
|
10
|
+
if (parsed.kind === 'empty') {
|
|
11
|
+
const freshness = row.stale
|
|
12
|
+
? ` Stale: ${describeSpineStaleness(row.staleMemberIds.length, row.membershipTruncated)}. Run \`pb quality spine-check\` to refresh it.`
|
|
13
|
+
: '';
|
|
14
|
+
return `The last spine check found no accepted purpose, vision or strategy.${freshness}`;
|
|
16
15
|
}
|
|
16
|
+
const { verdict } = parsed;
|
|
17
|
+
const lines = [];
|
|
17
18
|
if (row.stale) {
|
|
18
|
-
|
|
19
|
+
const reason = describeSpineStaleness(row.staleMemberIds.length, row.membershipTruncated);
|
|
20
|
+
lines.push(`[stale — ${reason}. Run \`pb quality spine-check\` again.]`);
|
|
19
21
|
lines.push('');
|
|
20
22
|
}
|
|
21
23
|
const s = verdict.structural;
|
|
@@ -100,7 +102,7 @@ export function formatSpineVerdict(row) {
|
|
|
100
102
|
// parse error), not "never requested". Conflating the two reads a failure as
|
|
101
103
|
// a clean skip (review fix, PR #530 P2).
|
|
102
104
|
lines.push('');
|
|
103
|
-
lines.push('One-story judgment: requested, but the LLM pass did not return a usable result (timeout or parse failure). Run
|
|
105
|
+
lines.push('One-story judgment: requested, but the LLM pass did not return a usable result (timeout or parse failure). Run `pb quality spine-check --story` to retry.');
|
|
104
106
|
}
|
|
105
107
|
else {
|
|
106
108
|
lines.push('');
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"spineCheck.js","sourceRoot":"","sources":["../../src/formatters/spineCheck.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"spineCheck.js","sourceRoot":"","sources":["../../src/formatters/spineCheck.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"spineCheck.test.d.ts","sourceRoot":"","sources":["../../src/formatters/spineCheck.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
import { describe, expect, it } from 'vitest';
|
|
2
|
+
import { formatSpineVerdict } from './spineCheck.js';
|
|
3
|
+
const row = {
|
|
4
|
+
verdict: {
|
|
5
|
+
structural: {
|
|
6
|
+
passed: true, missing: [], duplicateSingletons: { purpose: null, vision: null },
|
|
7
|
+
unconnectedStrategyIds: [], strategiesWithUnknownConnectivity: [],
|
|
8
|
+
visionConnectedToPurpose: true, visionPurposeConnectivityTruncated: false,
|
|
9
|
+
},
|
|
10
|
+
noSpineEntries: false, perStrategy: [], story: null, strategiesTruncated: false,
|
|
11
|
+
},
|
|
12
|
+
includesStoryPass: false, createdAt: 1, stale: true, staleMemberIds: [],
|
|
13
|
+
};
|
|
14
|
+
describe('spine verdict freshness disclosure', () => {
|
|
15
|
+
it.each([null, {}, { noSpineEntries: false }, ...[undefined, 'true', 0].map((noSpineEntries) => ({
|
|
16
|
+
...row.verdict, noSpineEntries,
|
|
17
|
+
}))])('renders recovery instead of crashing or grading malformed payload %j', (verdict) => {
|
|
18
|
+
const text = formatSpineVerdict({ ...row, verdict });
|
|
19
|
+
expect(text).toContain('Stored spine verdict is malformed');
|
|
20
|
+
expect(text).toContain('pb quality spine-check');
|
|
21
|
+
expect(text).not.toMatch(/Structural completeness|PASS|FAIL/);
|
|
22
|
+
});
|
|
23
|
+
it.each([false, true])('describes an empty result historically, preserving stale=%s', (stale) => {
|
|
24
|
+
const text = formatSpineVerdict({ ...row, stale, verdict: { noSpineEntries: true, structural: null } });
|
|
25
|
+
expect(text).toContain('The last spine check found no accepted purpose, vision or strategy.');
|
|
26
|
+
expect(text.includes('freshness could not be verified')).toBe(stale);
|
|
27
|
+
expect(text).not.toContain('nothing to check');
|
|
28
|
+
});
|
|
29
|
+
it.each([false, true])('preserves known changes in an empty stale result, capped=%s', (membershipTruncated) => {
|
|
30
|
+
const text = formatSpineVerdict({ ...row, staleMemberIds: ['edited'], membershipTruncated, verdict: { noSpineEntries: true, structural: null } });
|
|
31
|
+
expect(text).toContain('1 entry changed or joined/left the spine');
|
|
32
|
+
expect(text.includes('at least 1')).toBe(membershipTruncated);
|
|
33
|
+
expect(text.includes('membership scan incomplete')).toBe(membershipTruncated);
|
|
34
|
+
expect(text).not.toContain('changed-entry count is unknown');
|
|
35
|
+
});
|
|
36
|
+
it('renders a lower-bound graded count without treating it as a complete count', () => {
|
|
37
|
+
const text = formatSpineVerdict({ ...row, staleMemberIds: ['edited', 'deleted'], membershipTruncated: true });
|
|
38
|
+
expect(text).toContain('at least 2 entries changed');
|
|
39
|
+
expect(text).toContain('membership scan incomplete');
|
|
40
|
+
});
|
|
41
|
+
it('retains detailed findings from the shared validated payload', () => {
|
|
42
|
+
const verdict = row.verdict;
|
|
43
|
+
const text = formatSpineVerdict({ ...row, stale: false, verdict: {
|
|
44
|
+
...verdict,
|
|
45
|
+
structural: { ...verdict.structural, unconnectedObjectiveIds: ['OBJ-1'], keyResultsWithUnknownConnectivity: ['KR-1'] },
|
|
46
|
+
perStrategy: [{ entryId: 'STR-1', refusal: { hasRefusalSignal: true }, rogerMartin: { isStrategicChoice: true, reasoning: 'Selected niche.' } }],
|
|
47
|
+
story: { passed: false, failedCriterion: 'purpose', criteria: [{ id: 'purpose', passed: false, reasoning: 'Missing connection.' }] },
|
|
48
|
+
objectivesTruncated: true,
|
|
49
|
+
} });
|
|
50
|
+
expect(text).toContain('Unconnected objectives (no part_of edge to any strategy): OBJ-1');
|
|
51
|
+
expect(text).toContain('Key result connectivity unknown (relation set truncated): KR-1');
|
|
52
|
+
expect(text).toContain('Selected niche.');
|
|
53
|
+
expect(text).toContain('Failed criterion: purpose — Missing connection.');
|
|
54
|
+
expect(text).toContain('Objective set truncated');
|
|
55
|
+
});
|
|
56
|
+
it('names the story flag when retrying a failed story pass', () => {
|
|
57
|
+
const text = formatSpineVerdict({ ...row, includesStoryPass: true });
|
|
58
|
+
expect(text).toContain('pb quality spine-check --story` to retry');
|
|
59
|
+
});
|
|
60
|
+
it('does not interpret an unknown changed-member count as zero changes', () => {
|
|
61
|
+
const text = formatSpineVerdict(row);
|
|
62
|
+
expect(text).toContain('freshness could not be verified; the changed-entry count is unknown');
|
|
63
|
+
expect(text).not.toMatch(/0 (?:member|spine)/);
|
|
64
|
+
expect(text).toContain('pb quality spine-check');
|
|
65
|
+
});
|
|
66
|
+
it('includes membership changes in the meaning of a known count', () => {
|
|
67
|
+
const text = formatSpineVerdict({ ...row, staleMemberIds: ['unchanged-entry-now-scoped'] });
|
|
68
|
+
expect(text).toContain('1 entry changed or joined/left the spine');
|
|
69
|
+
});
|
|
70
|
+
it('does not add an uncertainty warning to a fresh verdict', () => {
|
|
71
|
+
const text = formatSpineVerdict({ ...row, stale: false });
|
|
72
|
+
expect(text).toContain('Structural completeness: PASS');
|
|
73
|
+
expect(text).not.toContain('freshness could not be verified');
|
|
74
|
+
});
|
|
75
|
+
});
|
|
76
|
+
//# sourceMappingURL=spineCheck.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"spineCheck.test.js","sourceRoot":"","sources":["../../src/formatters/spineCheck.test.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,EAAE,EAAE,EAAE,MAAM,QAAQ,CAAC;AAC9C,OAAO,EAAE,kBAAkB,EAAwB,MAAM,iBAAiB,CAAC;AAE3E,MAAM,GAAG,GAAoB;IAC3B,OAAO,EAAE;QACP,UAAU,EAAE;YACV,MAAM,EAAE,IAAI,EAAE,OAAO,EAAE,EAAE,EAAE,mBAAmB,EAAE,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE;YAC/E,sBAAsB,EAAE,EAAE,EAAE,iCAAiC,EAAE,EAAE;YACjE,wBAAwB,EAAE,IAAI,EAAE,kCAAkC,EAAE,KAAK;SAC1E;QACD,cAAc,EAAE,KAAK,EAAE,WAAW,EAAE,EAAE,EAAE,KAAK,EAAE,IAAI,EAAE,mBAAmB,EAAE,KAAK;KAChF;IACD,iBAAiB,EAAE,KAAK,EAAE,SAAS,EAAE,CAAC,EAAE,KAAK,EAAE,IAAI,EAAE,cAAc,EAAE,EAAE;CACxE,CAAC;AAEF,QAAQ,CAAC,oCAAoC,EAAE,GAAG,EAAE;IACnD,EAAE,CAAC,IAAI,CAAC,CAAC,IAAI,EAAE,EAAE,EAAE,EAAE,cAAc,EAAE,KAAK,EAAE,EAAE,GAAG,CAAC,SAAS,EAAE,MAAM,EAAE,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,cAAc,EAAE,EAAE,CAAC,CAAC;YAChG,GAAI,GAAG,CAAC,OAAmC,EAAE,cAAc;SAC3D,CAAC,CAAC,CAAC,CAAC,CAAC,sEAAsE,EAAE,CAAC,OAAO,EAAE,EAAE;QACzF,MAAM,IAAI,GAAG,kBAAkB,CAAC,EAAE,GAAG,GAAG,EAAE,OAAO,EAAE,CAAC,CAAC;QACrD,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,mCAAmC,CAAC,CAAC;QAC5D,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,wBAAwB,CAAC,CAAC;QACjD,MAAM,CAAC,IAAI,CAAC,CAAC,GAAG,CAAC,OAAO,CAAC,mCAAmC,CAAC,CAAC;IAC/D,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,IAAI,CAAC,CAAC,KAAK,EAAE,IAAI,CAAC,CAAC,CAAC,6DAA6D,EAAE,CAAC,KAAK,EAAE,EAAE;QAC/F,MAAM,IAAI,GAAG,kBAAkB,CAAC,EAAE,GAAG,GAAG,EAAE,KAAK,EAAE,OAAO,EAAE,EAAE,cAAc,EAAE,IAAI,EAAE,UAAU,EAAE,IAAI,EAAE,EAAE,CAAC,CAAC;QACxG,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,qEAAqE,CAAC,CAAC;QAC9F,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,iCAAiC,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QACrE,MAAM,CAAC,IAAI,CAAC,CAAC,GAAG,CAAC,SAAS,CAAC,kBAAkB,CAAC,CAAC;IAChD,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,IAAI,CAAC,CAAC,KAAK,EAAE,IAAI,CAAC,CAAC,CAAC,6DAA6D,EAAE,CAAC,mBAAmB,EAAE,EAAE;QAC7G,MAAM,IAAI,GAAG,kBAAkB,CAAC,EAAE,GAAG,GAAG,EAAE,cAAc,EAAE,CAAC,QAAQ,CAAC,EAAE,mBAAmB,EAAE,OAAO,EAAE,EAAE,cAAc,EAAE,IAAI,EAAE,UAAU,EAAE,IAAI,EAAE,EAAE,CAAC,CAAC;QAClJ,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,0CAA0C,CAAC,CAAC;QACnE,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,YAAY,CAAC,CAAC,CAAC,IAAI,CAAC,mBAAmB,CAAC,CAAC;QAC9D,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,4BAA4B,CAAC,CAAC,CAAC,IAAI,CAAC,mBAAmB,CAAC,CAAC;QAC9E,MAAM,CAAC,IAAI,CAAC,CAAC,GAAG,CAAC,SAAS,CAAC,gCAAgC,CAAC,CAAC;IAC9D,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,4EAA4E,EAAE,GAAG,EAAE;QACrF,MAAM,IAAI,GAAG,kBAAkB,CAAC,EAAE,GAAG,GAAG,EAAE,cAAc,EAAE,CAAC,QAAQ,EAAE,SAAS,CAAC,EAAE,mBAAmB,EAAE,IAAI,EAAE,CAAC,CAAC;QAC9G,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,4BAA4B,CAAC,CAAC;QACrD,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,4BAA4B,CAAC,CAAC;IACtD,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,6DAA6D,EAAE,GAAG,EAAE;QACtE,MAAM,OAAO,GAAG,GAAG,CAAC,OAAkD,CAAC;QACvE,MAAM,IAAI,GAAG,kBAAkB,CAAC,EAAE,GAAG,GAAG,EAAE,KAAK,EAAE,KAAK,EAAE,OAAO,EAAE;gBAChE,GAAG,OAAO;gBACV,UAAU,EAAE,EAAE,GAAG,OAAO,CAAC,UAAU,EAAE,uBAAuB,EAAE,CAAC,OAAO,CAAC,EAAE,iCAAiC,EAAE,CAAC,MAAM,CAAC,EAAE;gBACtH,WAAW,EAAE,CAAC,EAAE,OAAO,EAAE,OAAO,EAAE,OAAO,EAAE,EAAE,gBAAgB,EAAE,IAAI,EAAE,EAAE,WAAW,EAAE,EAAE,iBAAiB,EAAE,IAAI,EAAE,SAAS,EAAE,iBAAiB,EAAE,EAAE,CAAC;gBAChJ,KAAK,EAAE,EAAE,MAAM,EAAE,KAAK,EAAE,eAAe,EAAE,SAAS,EAAE,QAAQ,EAAE,CAAC,EAAE,EAAE,EAAE,SAAS,EAAE,MAAM,EAAE,KAAK,EAAE,SAAS,EAAE,qBAAqB,EAAE,CAAC,EAAE;gBACpI,mBAAmB,EAAE,IAAI;aACzB,EAAE,CAAC,CAAC;QACL,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,iEAAiE,CAAC,CAAC;QAC1F,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,gEAAgE,CAAC,CAAC;QACzF,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,iBAAiB,CAAC,CAAC;QAC1C,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,iDAAiD,CAAC,CAAC;QAC1E,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,yBAAyB,CAAC,CAAC;IACnD,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,wDAAwD,EAAE,GAAG,EAAE;QACjE,MAAM,IAAI,GAAG,kBAAkB,CAAC,EAAE,GAAG,GAAG,EAAE,iBAAiB,EAAE,IAAI,EAAE,CAAC,CAAC;QACrE,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,0CAA0C,CAAC,CAAC;IACpE,CAAC,CAAC,CAAC;IACF,EAAE,CAAC,oEAAoE,EAAE,GAAG,EAAE;QAC5E,MAAM,IAAI,GAAG,kBAAkB,CAAC,GAAG,CAAC,CAAC;QACrC,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,qEAAqE,CAAC,CAAC;QAC9F,MAAM,CAAC,IAAI,CAAC,CAAC,GAAG,CAAC,OAAO,CAAC,oBAAoB,CAAC,CAAC;QAC/C,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,wBAAwB,CAAC,CAAC;IACnD,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,6DAA6D,EAAE,GAAG,EAAE;QACrE,MAAM,IAAI,GAAG,kBAAkB,CAAC,EAAE,GAAG,GAAG,EAAE,cAAc,EAAE,CAAC,4BAA4B,CAAC,EAAE,CAAC,CAAC;QAC5F,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,0CAA0C,CAAC,CAAC;IACrE,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,wDAAwD,EAAE,GAAG,EAAE;QAChE,MAAM,IAAI,GAAG,kBAAkB,CAAC,EAAE,GAAG,GAAG,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC,CAAC;QAC1D,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,+BAA+B,CAAC,CAAC;QACxD,MAAM,CAAC,IAAI,CAAC,CAAC,GAAG,CAAC,SAAS,CAAC,iCAAiC,CAAC,CAAC;IAChE,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
|
|
@@ -4,6 +4,7 @@
|
|
|
4
4
|
* `promptYN` moves here as dead-on-arrival for the `--link-type` refusal path — it stays used
|
|
5
5
|
* only by `--strict`'s existing possible-duplicate confirmation, unchanged.
|
|
6
6
|
*/
|
|
7
|
+
import type { GatewayRouteReturnByName } from '@productbrain/kernel-client';
|
|
7
8
|
/** WP-319 S3: Pre-write grounding result from chain.suggestLinksForCapture */
|
|
8
9
|
export type GroundingRelated = {
|
|
9
10
|
entryId: string;
|
|
@@ -26,7 +27,7 @@ export type GroundingGovernance = {
|
|
|
26
27
|
collectionSlug: string;
|
|
27
28
|
severity: 'block' | 'warn' | 'inform';
|
|
28
29
|
};
|
|
29
|
-
export type GroundingResult = {
|
|
30
|
+
export type GroundingResult = Partial<Pick<GatewayRouteReturnByName<'chain.suggestLinksForCapture'>[number], 'scanTruncated'>> & {
|
|
30
31
|
index: number;
|
|
31
32
|
related: GroundingRelated[];
|
|
32
33
|
duplicates: GroundingDuplicate[];
|
|
@@ -44,7 +45,7 @@ export declare function extractPrefixHint(text: string, prefixMap: Record<string
|
|
|
44
45
|
resolvedCollection: string | null;
|
|
45
46
|
cleanText: string;
|
|
46
47
|
};
|
|
47
|
-
/** Print advisory grounding banner
|
|
48
|
+
/** Print advisory grounding banner; suppress only complete checks with no matches. */
|
|
48
49
|
export declare function printGroundingBanner(grounding: GroundingResult): void;
|
|
49
50
|
/** Print dry-run grounding preview to stdout (--suggest-only). */
|
|
50
51
|
export declare function printGroundingPreview(grounding: GroundingResult | null, entryName: string, collectionSlug: string): void;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"captureGrounding.d.ts","sourceRoot":"","sources":["../../src/lib/captureGrounding.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;
|
|
1
|
+
{"version":3,"file":"captureGrounding.d.ts","sourceRoot":"","sources":["../../src/lib/captureGrounding.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,KAAK,EAAE,wBAAwB,EAAE,MAAM,6BAA6B,CAAC;AAE5E,8EAA8E;AAC9E,MAAM,MAAM,gBAAgB,GAAG;IAC7B,OAAO,EAAE,MAAM,CAAC;IAChB,IAAI,EAAE,MAAM,CAAC;IACb,cAAc,EAAE,MAAM,CAAC;IACvB,YAAY,EAAE,MAAM,CAAC;IACrB,uBAAuB,EAAE,MAAM,CAAC;IAChC,SAAS,EAAE,MAAM,CAAC;CACnB,CAAC;AAEF,MAAM,MAAM,kBAAkB,GAAG;IAC/B,OAAO,EAAE,MAAM,CAAC;IAChB,IAAI,EAAE,MAAM,CAAC;IACb,cAAc,EAAE,MAAM,CAAC;IACvB,SAAS,EAAE,SAAS,GAAG,oBAAoB,CAAC;IAC5C,YAAY,EAAE,MAAM,CAAC;CACtB,CAAC;AAEF,MAAM,MAAM,mBAAmB,GAAG;IAChC,OAAO,EAAE,MAAM,CAAC;IAChB,IAAI,EAAE,MAAM,CAAC;IACb,cAAc,EAAE,MAAM,CAAC;IACvB,QAAQ,EAAE,OAAO,GAAG,MAAM,GAAG,QAAQ,CAAC;CACvC,CAAC;AAEF,MAAM,MAAM,eAAe,GAAG,OAAO,CAAC,IAAI,CAAC,wBAAwB,CAAC,8BAA8B,CAAC,CAAC,MAAM,CAAC,EAAE,eAAe,CAAC,CAAC,GAAG;IAC/H,KAAK,EAAE,MAAM,CAAC;IACd,OAAO,EAAE,gBAAgB,EAAE,CAAC;IAC5B,UAAU,EAAE,kBAAkB,EAAE,CAAC;IACjC,qEAAqE;IACrE,UAAU,CAAC,EAAE,mBAAmB,EAAE,CAAC;IACnC,CAAC,CAAC,EAAE,MAAM,CAAC;CACZ,CAAC;AAEF;;;;;GAKG;AACH,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG;IAAE,kBAAkB,EAAE,MAAM,GAAG,IAAI,CAAC;IAAC,SAAS,EAAE,MAAM,CAAA;CAAE,CAO3I;AAWD,sFAAsF;AACtF,wBAAgB,oBAAoB,CAAC,SAAS,EAAE,eAAe,GAAG,IAAI,CAsCrE;AAED,kEAAkE;AAClE,wBAAgB,qBAAqB,CACnC,SAAS,EAAE,eAAe,GAAG,IAAI,EACjC,SAAS,EAAE,MAAM,EACjB,cAAc,EAAE,MAAM,GACrB,IAAI,CAkDN;AAED,mFAAmF;AACnF,wBAAsB,QAAQ,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAQhE"}
|
|
@@ -1,9 +1,3 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* `pb capture` grounding presentation helpers — extracted from capture.ts (WP-688 S4, TASK-105)
|
|
3
|
-
* purely to fund that file's shrink-only LOC budget (STD-2/DEC-1504); no behavior change.
|
|
4
|
-
* `promptYN` moves here as dead-on-arrival for the `--link-type` refusal path — it stays used
|
|
5
|
-
* only by `--strict`'s existing possible-duplicate confirmation, unchanged.
|
|
6
|
-
*/
|
|
7
1
|
/**
|
|
8
2
|
* Extract a known ID prefix hint from capture text.
|
|
9
3
|
* Pattern: "FLO: description" or "TEN: something broken" — prefix must be uppercase,
|
|
@@ -21,7 +15,14 @@ export function extractPrefixHint(text, prefixMap) {
|
|
|
21
15
|
return { resolvedCollection: slug, cleanText: rest.trim() };
|
|
22
16
|
}
|
|
23
17
|
// WP-319 S3: Grounding helpers — advisory output, stderr only.
|
|
24
|
-
|
|
18
|
+
function groundingCoverageNote(grounding) {
|
|
19
|
+
if (grounding.scanTruncated === false)
|
|
20
|
+
return null;
|
|
21
|
+
return grounding.scanTruncated === true
|
|
22
|
+
? 'Grounding sample omitted accepted entries; additional matching entries may exist.'
|
|
23
|
+
: 'Grounding completeness is unverified; additional matching entries may exist.';
|
|
24
|
+
}
|
|
25
|
+
/** Print advisory grounding banner; suppress only complete checks with no matches. */
|
|
25
26
|
export function printGroundingBanner(grounding) {
|
|
26
27
|
const possibleDuplicates = grounding.duplicates.filter((d) => d.matchType === 'possible_duplicate');
|
|
27
28
|
const related = [
|
|
@@ -30,10 +31,13 @@ export function printGroundingBanner(grounding) {
|
|
|
30
31
|
];
|
|
31
32
|
const governance = grounding.governance ?? [];
|
|
32
33
|
const hasGovernance = governance.length > 0;
|
|
33
|
-
|
|
34
|
+
const coverageNote = groundingCoverageNote(grounding);
|
|
35
|
+
if (possibleDuplicates.length === 0 && related.length === 0 && !hasGovernance && !coverageNote) {
|
|
34
36
|
return; // Zero-noise floor: nothing to show
|
|
35
37
|
}
|
|
36
38
|
const lines = ['\n Grounding:'];
|
|
39
|
+
if (coverageNote)
|
|
40
|
+
lines.push(` ${coverageNote}`);
|
|
37
41
|
if (possibleDuplicates.length > 0) {
|
|
38
42
|
const label = possibleDuplicates.length === 1 ? 'Possible duplicate' : 'Possible duplicates';
|
|
39
43
|
const items = possibleDuplicates.map((d) => `${d.entryId} "${d.name}"`).join(', ');
|
|
@@ -61,6 +65,9 @@ export function printGroundingPreview(grounding, entryName, collectionSlug) {
|
|
|
61
65
|
process.stdout.write(' No grounding data available (timeout or unavailable).\n\n');
|
|
62
66
|
return;
|
|
63
67
|
}
|
|
68
|
+
const coverageNote = groundingCoverageNote(grounding);
|
|
69
|
+
if (coverageNote)
|
|
70
|
+
process.stdout.write(` ${coverageNote}\n\n`);
|
|
64
71
|
const possibleDuplicates = grounding.duplicates.filter((d) => d.matchType === 'possible_duplicate');
|
|
65
72
|
const related = [
|
|
66
73
|
...grounding.related,
|
|
@@ -68,7 +75,7 @@ export function printGroundingPreview(grounding, entryName, collectionSlug) {
|
|
|
68
75
|
];
|
|
69
76
|
const govCandidates = grounding.governance ?? [];
|
|
70
77
|
if (possibleDuplicates.length === 0 && related.length === 0 && govCandidates.length === 0) {
|
|
71
|
-
process.stdout.write(' No matches found
|
|
78
|
+
process.stdout.write(' No matches found in this check.\n\n');
|
|
72
79
|
return;
|
|
73
80
|
}
|
|
74
81
|
if (possibleDuplicates.length > 0) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"captureGrounding.js","sourceRoot":"","sources":["../../src/lib/captureGrounding.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"captureGrounding.js","sourceRoot":"","sources":["../../src/lib/captureGrounding.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"captureGrounding.test.d.ts","sourceRoot":"","sources":["../../src/lib/captureGrounding.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import { afterEach, describe, expect, it, vi } from 'vitest';
|
|
2
|
+
import { printGroundingBanner, printGroundingPreview } from './captureGrounding.js';
|
|
3
|
+
const empty = { index: 0, related: [], duplicates: [], governance: [] };
|
|
4
|
+
afterEach(() => vi.restoreAllMocks());
|
|
5
|
+
describe('capture grounding completeness', () => {
|
|
6
|
+
it.each([true, undefined, false])('preview preserves completeness=%s without claiming uniqueness', (scanTruncated) => {
|
|
7
|
+
const output = vi.spyOn(process.stdout, 'write').mockReturnValue(true);
|
|
8
|
+
printGroundingPreview({ ...empty, scanTruncated }, 'Equipment maintenance', 'decisions');
|
|
9
|
+
const text = output.mock.calls.map(([chunk]) => String(chunk)).join('');
|
|
10
|
+
expect(text).toContain('No matches found in this check.');
|
|
11
|
+
expect(text).not.toContain('looks unique');
|
|
12
|
+
expect(text.includes('additional matching entries may exist')).toBe(scanTruncated !== false);
|
|
13
|
+
if (scanTruncated === undefined)
|
|
14
|
+
expect(text).toContain('completeness is unverified');
|
|
15
|
+
});
|
|
16
|
+
it.each([true, undefined, false])('normal-capture banner preserves completeness=%s', (scanTruncated) => {
|
|
17
|
+
const output = vi.spyOn(process.stderr, 'write').mockReturnValue(true);
|
|
18
|
+
printGroundingBanner({ ...empty, scanTruncated });
|
|
19
|
+
const text = output.mock.calls.map(([chunk]) => String(chunk)).join('');
|
|
20
|
+
expect(text.includes('additional matching entries may exist')).toBe(scanTruncated !== false);
|
|
21
|
+
if (scanTruncated === false)
|
|
22
|
+
expect(output).not.toHaveBeenCalled();
|
|
23
|
+
});
|
|
24
|
+
it('keeps known duplicate evidence alongside the truncation caveat', () => {
|
|
25
|
+
const output = vi.spyOn(process.stdout, 'write').mockReturnValue(true);
|
|
26
|
+
printGroundingPreview({ ...empty, scanTruncated: true, duplicates: [{ entryId: 'DEC-1', name: 'Maintenance plan', collectionSlug: 'decisions', matchType: 'possible_duplicate', overlapRatio: 0.9 }] }, 'Maintenance plan', 'decisions');
|
|
27
|
+
const text = output.mock.calls.map(([chunk]) => String(chunk)).join('');
|
|
28
|
+
expect(text).toContain('additional matching entries may exist');
|
|
29
|
+
expect(text).toContain('DEC-1');
|
|
30
|
+
expect(text).toContain('Possible duplicates:');
|
|
31
|
+
});
|
|
32
|
+
it('reports unavailable grounding without an absence claim', () => {
|
|
33
|
+
const output = vi.spyOn(process.stdout, 'write').mockReturnValue(true);
|
|
34
|
+
printGroundingPreview(null, 'Maintenance plan', 'decisions');
|
|
35
|
+
const text = output.mock.calls.map(([chunk]) => String(chunk)).join('');
|
|
36
|
+
expect(text).toContain('timeout or unavailable');
|
|
37
|
+
expect(text).not.toContain('No matches');
|
|
38
|
+
});
|
|
39
|
+
});
|
|
40
|
+
//# sourceMappingURL=captureGrounding.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"captureGrounding.test.js","sourceRoot":"","sources":["../../src/lib/captureGrounding.test.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,QAAQ,EAAE,MAAM,EAAE,EAAE,EAAE,EAAE,EAAE,MAAM,QAAQ,CAAC;AAC7D,OAAO,EAAE,oBAAoB,EAAE,qBAAqB,EAAwB,MAAM,uBAAuB,CAAC;AAE1G,MAAM,KAAK,GAAoB,EAAE,KAAK,EAAE,CAAC,EAAE,OAAO,EAAE,EAAE,EAAE,UAAU,EAAE,EAAE,EAAE,UAAU,EAAE,EAAE,EAAE,CAAC;AACzF,SAAS,CAAC,GAAG,EAAE,CAAC,EAAE,CAAC,eAAe,EAAE,CAAC,CAAC;AAEtC,QAAQ,CAAC,gCAAgC,EAAE,GAAG,EAAE;IAC9C,EAAE,CAAC,IAAI,CAAC,CAAC,IAAI,EAAE,SAAS,EAAE,KAAK,CAAC,CAAC,CAAC,+DAA+D,EAAE,CAAC,aAAa,EAAE,EAAE;QACnH,MAAM,MAAM,GAAG,EAAE,CAAC,KAAK,CAAC,OAAO,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,eAAe,CAAC,IAAI,CAAC,CAAC;QACvE,qBAAqB,CAAC,EAAE,GAAG,KAAK,EAAE,aAAa,EAAE,EAAE,uBAAuB,EAAE,WAAW,CAAC,CAAC;QACzF,MAAM,IAAI,GAAG,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,EAAE,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QACxE,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,iCAAiC,CAAC,CAAC;QAC1D,MAAM,CAAC,IAAI,CAAC,CAAC,GAAG,CAAC,SAAS,CAAC,cAAc,CAAC,CAAC;QAC3C,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,uCAAuC,CAAC,CAAC,CAAC,IAAI,CAAC,aAAa,KAAK,KAAK,CAAC,CAAC;QAC7F,IAAI,aAAa,KAAK,SAAS;YAAE,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,4BAA4B,CAAC,CAAC;IACxF,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,IAAI,CAAC,CAAC,IAAI,EAAE,SAAS,EAAE,KAAK,CAAC,CAAC,CAAC,iDAAiD,EAAE,CAAC,aAAa,EAAE,EAAE;QACrG,MAAM,MAAM,GAAG,EAAE,CAAC,KAAK,CAAC,OAAO,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,eAAe,CAAC,IAAI,CAAC,CAAC;QACvE,oBAAoB,CAAC,EAAE,GAAG,KAAK,EAAE,aAAa,EAAE,CAAC,CAAC;QAClD,MAAM,IAAI,GAAG,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,EAAE,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QACxE,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,uCAAuC,CAAC,CAAC,CAAC,IAAI,CAAC,aAAa,KAAK,KAAK,CAAC,CAAC;QAC7F,IAAI,aAAa,KAAK,KAAK;YAAE,MAAM,CAAC,MAAM,CAAC,CAAC,GAAG,CAAC,gBAAgB,EAAE,CAAC;IACrE,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,gEAAgE,EAAE,GAAG,EAAE;QACxE,MAAM,MAAM,GAAG,EAAE,CAAC,KAAK,CAAC,OAAO,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,eAAe,CAAC,IAAI,CAAC,CAAC;QACvE,qBAAqB,CAAC,EAAE,GAAG,KAAK,EAAE,aAAa,EAAE,IAAI,EAAE,UAAU,EAAE,CAAC,EAAE,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,kBAAkB,EAAE,cAAc,EAAE,WAAW,EAAE,SAAS,EAAE,oBAAoB,EAAE,YAAY,EAAE,GAAG,EAAE,CAAC,EAAE,EAAE,kBAAkB,EAAE,WAAW,CAAC,CAAC;QACzO,MAAM,IAAI,GAAG,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,EAAE,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QACxE,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,uCAAuC,CAAC,CAAC;QAChE,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC;QAChC,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,sBAAsB,CAAC,CAAC;IACjD,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,wDAAwD,EAAE,GAAG,EAAE;QAChE,MAAM,MAAM,GAAG,EAAE,CAAC,KAAK,CAAC,OAAO,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,eAAe,CAAC,IAAI,CAAC,CAAC;QACvE,qBAAqB,CAAC,IAAI,EAAE,kBAAkB,EAAE,WAAW,CAAC,CAAC;QAC7D,MAAM,IAAI,GAAG,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,EAAE,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QACxE,MAAM,CAAC,IAAI,CAAC,CAAC,SAAS,CAAC,wBAAwB,CAAC,CAAC;QACjD,MAAM,CAAC,IAAI,CAAC,CAAC,GAAG,CAAC,SAAS,CAAC,YAAY,CAAC,CAAC;IAC3C,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The ONE served wording for a capped readiness scan — `chain.workspaceReadiness`'s
|
|
3
|
+
* accepted-entry sample hit its cap, so entry counts are floors, an apparent gap may already be
|
|
4
|
+
* covered, and the stage verdict is unproven. One declaration per package, imported by every
|
|
5
|
+
* surface that discloses it.
|
|
6
|
+
*
|
|
7
|
+
* Byte-identical to the MCP twin (packages/mcp-server/src/lib/readinessNotices.ts) but
|
|
8
|
+
* deliberately a separate constant: mcp-server's isolated Docker build resolves no private
|
|
9
|
+
* workspace package at runtime, the same constraint that keeps FEEDBACK_SUBMIT_HINT duplicated
|
|
10
|
+
* across the two packages (see scripts/check-notice-hint-drift.mjs for that pair's guard).
|
|
11
|
+
*/
|
|
12
|
+
export declare const READINESS_PROVISIONAL_LINE = "Readiness is provisional: its sample omitted accepted entries. Counts are lower bounds, apparent gaps may already be covered, and the overall stage is unverified.";
|
|
13
|
+
/** The same disclosure inline, for surfaces that render the stage on a shared line. */
|
|
14
|
+
export declare const READINESS_PROVISIONAL_STAGE_SUFFIX = " (provisional: readiness sample omitted entries; absence is unverified)";
|
|
15
|
+
//# sourceMappingURL=readinessNotices.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"readinessNotices.d.ts","sourceRoot":"","sources":["../../src/lib/readinessNotices.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AACH,eAAO,MAAM,0BAA0B,uKAC+H,CAAC;AAEvK,uFAAuF;AACvF,eAAO,MAAM,kCAAkC,4EAC4B,CAAC"}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The ONE served wording for a capped readiness scan — `chain.workspaceReadiness`'s
|
|
3
|
+
* accepted-entry sample hit its cap, so entry counts are floors, an apparent gap may already be
|
|
4
|
+
* covered, and the stage verdict is unproven. One declaration per package, imported by every
|
|
5
|
+
* surface that discloses it.
|
|
6
|
+
*
|
|
7
|
+
* Byte-identical to the MCP twin (packages/mcp-server/src/lib/readinessNotices.ts) but
|
|
8
|
+
* deliberately a separate constant: mcp-server's isolated Docker build resolves no private
|
|
9
|
+
* workspace package at runtime, the same constraint that keeps FEEDBACK_SUBMIT_HINT duplicated
|
|
10
|
+
* across the two packages (see scripts/check-notice-hint-drift.mjs for that pair's guard).
|
|
11
|
+
*/
|
|
12
|
+
export const READINESS_PROVISIONAL_LINE = 'Readiness is provisional: its sample omitted accepted entries. Counts are lower bounds, apparent gaps may already be covered, and the overall stage is unverified.';
|
|
13
|
+
/** The same disclosure inline, for surfaces that render the stage on a shared line. */
|
|
14
|
+
export const READINESS_PROVISIONAL_STAGE_SUFFIX = ' (provisional: readiness sample omitted entries; absence is unverified)';
|
|
15
|
+
//# sourceMappingURL=readinessNotices.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"readinessNotices.js","sourceRoot":"","sources":["../../src/lib/readinessNotices.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AACH,MAAM,CAAC,MAAM,0BAA0B,GACrC,oKAAoK,CAAC;AAEvK,uFAAuF;AACvF,MAAM,CAAC,MAAM,kCAAkC,GAC7C,yEAAyE,CAAC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"repo-detect.d.ts","sourceRoot":"","sources":["../../src/lib/repo-detect.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAMH;;;GAGG;AACH,MAAM,WAAW,gBAAgB;IAC/B,KAAK,EAAE,MAAM,CAAC;IACd,YAAY,EAAE,MAAM,CAAC;IACrB,cAAc,EAAE,MAAM,CAAC;IACvB,eAAe,EAAE,MAAM,CAAC;IACxB,WAAW,EAAE,MAAM,CAAC;IACpB,UAAU,EAAE,MAAM,CAAC;IACnB,aAAa,EAAE,MAAM,CAAC;IACtB,cAAc,EAAE,MAAM,CAAC;CACxB;AAED;;;GAGG;AACH,wBAAgB,uBAAuB,CAAC,QAAQ,EAAE,OAAO,GAAG,gBAAgB,GAAG,IAAI,
|
|
1
|
+
{"version":3,"file":"repo-detect.d.ts","sourceRoot":"","sources":["../../src/lib/repo-detect.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAMH;;;GAGG;AACH,MAAM,WAAW,gBAAgB;IAC/B,KAAK,EAAE,MAAM,CAAC;IACd,YAAY,EAAE,MAAM,CAAC;IACrB,cAAc,EAAE,MAAM,CAAC;IACvB,eAAe,EAAE,MAAM,CAAC;IACxB,WAAW,EAAE,MAAM,CAAC;IACpB,UAAU,EAAE,MAAM,CAAC;IACnB,aAAa,EAAE,MAAM,CAAC;IACtB,cAAc,EAAE,MAAM,CAAC;CACxB;AAED;;;GAGG;AACH,wBAAgB,uBAAuB,CAAC,QAAQ,EAAE,OAAO,GAAG,gBAAgB,GAAG,IAAI,CAyBlF;AAED,MAAM,WAAW,WAAW;IAC1B,IAAI,EAAE,MAAM,GAAG,IAAI,CAAC;IACpB,WAAW,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAC;IACxB,aAAa,EAAE,MAAM,EAAE,CAAC;IACxB,UAAU,EAAE,OAAO,CAAC;CACrB;AAED,wBAAgB,UAAU,CAAC,GAAG,SAAgB,GAAG,WAAW,CAiD3D"}
|
package/dist/lib/repo-detect.js
CHANGED
|
@@ -13,6 +13,10 @@ export function extractWorkspaceProfile(response) {
|
|
|
13
13
|
if (!response || typeof response !== 'object')
|
|
14
14
|
return null;
|
|
15
15
|
const r = response;
|
|
16
|
+
// A sampled stage cannot safely exclude portable guidance or describe workspace maturity.
|
|
17
|
+
// Reuse the existing unavailable-profile path instead of promoting it to an exact profile.
|
|
18
|
+
if (r['sampleTruncated'] === true)
|
|
19
|
+
return null;
|
|
16
20
|
const stage = typeof r['stage'] === 'string' ? r['stage'] : null;
|
|
17
21
|
const governanceMode = typeof r['governanceMode'] === 'string' ? r['governanceMode'] : null;
|
|
18
22
|
if (!stage || !governanceMode)
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"repo-detect.js","sourceRoot":"","sources":["../../src/lib/repo-detect.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAE,UAAU,EAAE,YAAY,EAAE,MAAM,IAAI,CAAC;AAC9C,OAAO,EAAE,OAAO,EAAE,QAAQ,EAAE,MAAM,MAAM,CAAC;AACzC,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAiBzC;;;GAGG;AACH,MAAM,UAAU,uBAAuB,CAAC,QAAiB;IACvD,IAAI,CAAC,QAAQ,IAAI,OAAO,QAAQ,KAAK,QAAQ;QAAE,OAAO,IAAI,CAAC;IAC3D,MAAM,CAAC,GAAG,QAAmC,CAAC;
|
|
1
|
+
{"version":3,"file":"repo-detect.js","sourceRoot":"","sources":["../../src/lib/repo-detect.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Read contract for the append-only spine verdict payload (stored as unknown).
|
|
3
|
+
* This validates display data, never regrades the spine. Original producers always wrote
|
|
4
|
+
* noSpineEntries; newer connectivity/truncation fields may be absent on historical rows.
|
|
5
|
+
* Dependency-free: the existing embedded-copy generator ships this same source to both
|
|
6
|
+
* isolated connectors. Edit here, then run `npm run mcp:embedded-copies`.
|
|
7
|
+
*/
|
|
8
|
+
export interface SpineStructuralRead {
|
|
9
|
+
passed: boolean;
|
|
10
|
+
missing: string[];
|
|
11
|
+
duplicateSingletons: {
|
|
12
|
+
purpose: string[] | null;
|
|
13
|
+
vision: string[] | null;
|
|
14
|
+
};
|
|
15
|
+
unconnectedStrategyIds: string[];
|
|
16
|
+
visionConnectedToPurpose: boolean | null;
|
|
17
|
+
strategiesWithUnknownConnectivity?: string[] | null;
|
|
18
|
+
visionPurposeConnectivityTruncated?: boolean;
|
|
19
|
+
unconnectedObjectiveIds?: string[] | null;
|
|
20
|
+
objectivesWithUnknownConnectivity?: string[] | null;
|
|
21
|
+
unconnectedKeyResultIds?: string[] | null;
|
|
22
|
+
keyResultsWithUnknownConnectivity?: string[] | null;
|
|
23
|
+
}
|
|
24
|
+
export interface SpineStrategyRead {
|
|
25
|
+
entryId: string;
|
|
26
|
+
refusal: {
|
|
27
|
+
hasRefusalSignal: boolean;
|
|
28
|
+
};
|
|
29
|
+
rogerMartin: {
|
|
30
|
+
isStrategicChoice: boolean;
|
|
31
|
+
reasoning: string;
|
|
32
|
+
} | null;
|
|
33
|
+
}
|
|
34
|
+
export interface SpineStoryRead {
|
|
35
|
+
passed: boolean;
|
|
36
|
+
failedCriterion: string | null;
|
|
37
|
+
criteria: Array<{
|
|
38
|
+
id: string;
|
|
39
|
+
passed: boolean;
|
|
40
|
+
reasoning: string;
|
|
41
|
+
}>;
|
|
42
|
+
}
|
|
43
|
+
export interface GradedSpineVerdict {
|
|
44
|
+
noSpineEntries: false;
|
|
45
|
+
structural: SpineStructuralRead;
|
|
46
|
+
perStrategy: SpineStrategyRead[];
|
|
47
|
+
story: SpineStoryRead | null;
|
|
48
|
+
strategiesTruncated?: boolean;
|
|
49
|
+
perStrategyEvaluationTruncated?: boolean;
|
|
50
|
+
objectivesTruncated?: boolean;
|
|
51
|
+
keyResultsTruncated?: boolean;
|
|
52
|
+
}
|
|
53
|
+
export type SpineVerdictRead = {
|
|
54
|
+
kind: 'malformed';
|
|
55
|
+
} | {
|
|
56
|
+
kind: 'empty';
|
|
57
|
+
} | {
|
|
58
|
+
kind: 'graded';
|
|
59
|
+
verdict: GradedSpineVerdict;
|
|
60
|
+
};
|
|
61
|
+
/** Branch on the original discriminant before touching optional graded data. */
|
|
62
|
+
export declare function readSpineVerdict(value: unknown): SpineVerdictRead;
|
|
63
|
+
/** A capped membership read preserves positive evidence, never infers removals by absence. */
|
|
64
|
+
export declare function describeSpineStaleness(changedMemberCount: number, membershipTruncated?: boolean): string;
|
|
65
|
+
//# sourceMappingURL=spineVerdictRead.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"spineVerdictRead.d.ts","sourceRoot":"","sources":["../../src/lib/spineVerdictRead.ts"],"names":[],"mappings":"AAIA;;;;;;GAMG;AACH,MAAM,WAAW,mBAAmB;IACnC,MAAM,EAAE,OAAO,CAAC;IAChB,OAAO,EAAE,MAAM,EAAE,CAAC;IAClB,mBAAmB,EAAE;QAAE,OAAO,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;QAAC,MAAM,EAAE,MAAM,EAAE,GAAG,IAAI,CAAA;KAAE,CAAC;IAC3E,sBAAsB,EAAE,MAAM,EAAE,CAAC;IACjC,wBAAwB,EAAE,OAAO,GAAG,IAAI,CAAC;IACzC,iCAAiC,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;IACpD,kCAAkC,CAAC,EAAE,OAAO,CAAC;IAC7C,uBAAuB,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;IAC1C,iCAAiC,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;IACpD,uBAAuB,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;IAC1C,iCAAiC,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;CACpD;AAED,MAAM,WAAW,iBAAiB;IACjC,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE;QAAE,gBAAgB,EAAE,OAAO,CAAA;KAAE,CAAC;IACvC,WAAW,EAAE;QAAE,iBAAiB,EAAE,OAAO,CAAC;QAAC,SAAS,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,CAAC;CACtE;AAED,MAAM,WAAW,cAAc;IAC9B,MAAM,EAAE,OAAO,CAAC;IAChB,eAAe,EAAE,MAAM,GAAG,IAAI,CAAC;IAC/B,QAAQ,EAAE,KAAK,CAAC;QAAE,EAAE,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,OAAO,CAAC;QAAC,SAAS,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;CACpE;AAED,MAAM,WAAW,kBAAkB;IAClC,cAAc,EAAE,KAAK,CAAC;IACtB,UAAU,EAAE,mBAAmB,CAAC;IAChC,WAAW,EAAE,iBAAiB,EAAE,CAAC;IACjC,KAAK,EAAE,cAAc,GAAG,IAAI,CAAC;IAC7B,mBAAmB,CAAC,EAAE,OAAO,CAAC;IAC9B,8BAA8B,CAAC,EAAE,OAAO,CAAC;IACzC,mBAAmB,CAAC,EAAE,OAAO,CAAC;IAC9B,mBAAmB,CAAC,EAAE,OAAO,CAAC;CAC9B;AAED,MAAM,MAAM,gBAAgB,GACzB;IAAE,IAAI,EAAE,WAAW,CAAA;CAAE,GACrB;IAAE,IAAI,EAAE,OAAO,CAAA;CAAE,GACjB;IAAE,IAAI,EAAE,QAAQ,CAAC;IAAC,OAAO,EAAE,kBAAkB,CAAA;CAAE,CAAC;AAuCnD,gFAAgF;AAChF,wBAAgB,gBAAgB,CAAC,KAAK,EAAE,OAAO,GAAG,gBAAgB,CAWjE;AAGD,8FAA8F;AAC9F,wBAAgB,sBAAsB,CAAC,kBAAkB,EAAE,MAAM,EAAE,mBAAmB,UAAQ,GAAG,MAAM,CAKtG"}
|