@planu/cli 3.9.13 → 4.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +5 -0
- package/dist/cli/commands/spec.js +20 -1
- package/dist/cli/commands/status.js +18 -1
- package/dist/config/license-plans.json +1 -0
- package/dist/engine/ai-integration/codex/hooks-generator.js +1 -0
- package/dist/engine/ai-integration/gemini/settings-generator.js +4 -1
- package/dist/engine/ai-integration/kiro/hooks-generator.js +2 -1
- package/dist/engine/autopilot/action-registry.js +5 -14
- package/dist/engine/autopilot/state-updater.js +13 -10
- package/dist/engine/cascade-hooks/hooks/git-auto-stage.hook.js +3 -0
- package/dist/engine/cascade-hooks/hooks/html-regen.hook.js +1 -1
- package/dist/engine/cascade-hooks/hooks/status-json.hook.js +1 -1
- package/dist/engine/cascade-hooks/state-drift-detector.d.ts +1 -1
- package/dist/engine/cascade-hooks/state-drift-detector.js +15 -12
- package/dist/engine/git/planu-autocommit.d.ts +1 -0
- package/dist/engine/git/planu-autocommit.js +6 -0
- package/dist/engine/git-hook-injector.js +3 -3
- package/dist/engine/handoff-artifacts/io.js +3 -2
- package/dist/engine/handoff-packager.js +2 -1
- package/dist/engine/hooks/full-spectrum-generator.d.ts +2 -1
- package/dist/engine/hooks/full-spectrum-generator.js +5 -3
- package/dist/engine/release/postmortem-generator.d.ts +1 -1
- package/dist/engine/release/postmortem-generator.js +3 -2
- package/dist/engine/safety/cross-process-lock.js +2 -2
- package/dist/engine/session/checkpoint-writer.js +0 -1
- package/dist/engine/session-context-generator.js +4 -1
- package/dist/engine/spec-audit/index.js +2 -2
- package/dist/engine/spec-audit/report-writer.d.ts +1 -1
- package/dist/engine/spec-audit/report-writer.js +5 -4
- package/dist/engine/spec-migrator/index.d.ts +1 -0
- package/dist/engine/spec-migrator/index.js +1 -0
- package/dist/engine/spec-migrator/planu-canonical-policy.d.ts +9 -0
- package/dist/engine/spec-migrator/planu-canonical-policy.js +62 -0
- package/dist/engine/spec-migrator/planu-root-cleaner.js +18 -94
- package/dist/engine/spec-migrator/strict-planu-cleanup.d.ts +6 -0
- package/dist/engine/spec-migrator/strict-planu-cleanup.js +199 -0
- package/dist/engine/spec-summary-html.d.ts +5 -5
- package/dist/engine/spec-summary-html.js +7 -32
- package/dist/storage/gaps-log.js +4 -4
- package/dist/storage/transition-log.js +3 -2
- package/dist/tools/audit-specs-drift.js +3 -3
- package/dist/tools/create-spec/post-creation.d.ts +2 -1
- package/dist/tools/create-spec/post-creation.js +9 -11
- package/dist/tools/create-spec/spec-builder.js +1 -1
- package/dist/tools/create-spec.js +42 -18
- package/dist/tools/flag-spec-gap.d.ts +1 -1
- package/dist/tools/flag-spec-gap.js +1 -1
- package/dist/tools/generate-dashboard.js +3 -3
- package/dist/tools/housekeeping-sweep.js +16 -0
- package/dist/tools/init-project/git-setup.js +11 -2
- package/dist/tools/init-project/handler.js +1 -27
- package/dist/tools/init-project/migration-runner.js +8 -0
- package/dist/tools/license-gate.d.ts +1 -0
- package/dist/tools/license-gate.js +5 -1
- package/dist/tools/list-specs.js +13 -0
- package/dist/tools/register-sdd-tools.d.ts +1 -1
- package/dist/tools/register-sdd-tools.js +1 -0
- package/dist/tools/register-spec-tools/core-spec-tools.js +16 -0
- package/dist/tools/spec-lock-handler.js +1 -1
- package/dist/tools/sync-spec-state-handler.js +7 -0
- package/dist/tools/tool-registry/group-misc.js +4 -4
- package/dist/tools/update-status/batch.d.ts +3 -0
- package/dist/tools/update-status/batch.js +96 -0
- package/dist/tools/update-status/dod-gates.js +1 -1
- package/dist/tools/update-status/file-sync.js +3 -1
- package/dist/tools/update-status/index.js +15 -2
- package/dist/tools/update-status-actions.js +2 -6
- package/dist/tools/validate.js +27 -0
- package/dist/tools/workspace-dashboard-handler.js +6 -9
- package/dist/types/git.d.ts +1 -1
- package/dist/types/spec-format.d.ts +26 -0
- package/package.json +7 -7
|
@@ -162,22 +162,18 @@ export async function runDoneActions(projectId, specId, gitBranch) {
|
|
|
162
162
|
}
|
|
163
163
|
return null;
|
|
164
164
|
})(),
|
|
165
|
-
//
|
|
166
|
-
// SPEC-575: Auto-commit staged planu/ docs (idempotent, safe-fail)
|
|
165
|
+
// Warn if non-planu changes remain. Planu autocommit/staging is opt-in only.
|
|
167
166
|
(async () => {
|
|
168
167
|
try {
|
|
169
168
|
const { resolveProjectPath, git: gitCmd } = await import('./git/git-helpers.js');
|
|
170
169
|
const projectPath = await resolveProjectPath(projectId);
|
|
171
|
-
|
|
170
|
+
if (process.env.PLANU_ENABLE_AUTOCOMMIT === 'true') {
|
|
172
171
|
await gitCmd(projectPath, ['add', 'planu/']);
|
|
173
172
|
const { planuAutoCommit } = await import('../engine/git/planu-autocommit.js');
|
|
174
173
|
void planuAutoCommit({ projectPath, specId, reason: 'mark-done' }).catch((err) => {
|
|
175
174
|
console.error('[update-status] planuAutoCommit failed:', err instanceof Error ? err.message : String(err));
|
|
176
175
|
});
|
|
177
176
|
}
|
|
178
|
-
catch {
|
|
179
|
-
// git add failed (nothing to stage, or not a git repo) — continue to status check
|
|
180
|
-
}
|
|
181
177
|
const { stdout } = await gitCmd(projectPath, ['status', '--porcelain']);
|
|
182
178
|
const nonPlanuLines = stdout
|
|
183
179
|
.trim()
|
package/dist/tools/validate.js
CHANGED
|
@@ -68,6 +68,33 @@ export async function handleValidate(args, server) {
|
|
|
68
68
|
};
|
|
69
69
|
}
|
|
70
70
|
const projectPath = knowledge.projectPath;
|
|
71
|
+
// SPEC-1017: fail closed when planu/ contains non-canonical artifacts.
|
|
72
|
+
try {
|
|
73
|
+
const { runStrictPlanuCleanup, validateStrictPlanuLayout } = await import('../engine/spec-migrator/index.js');
|
|
74
|
+
await runStrictPlanuCleanup(projectPath);
|
|
75
|
+
const layout = await validateStrictPlanuLayout(projectPath);
|
|
76
|
+
if (!layout.ok) {
|
|
77
|
+
return {
|
|
78
|
+
content: [
|
|
79
|
+
{
|
|
80
|
+
type: 'text',
|
|
81
|
+
text: `Strict Planu layout validation failed for ${specId}.\n\n` +
|
|
82
|
+
`Non-canonical paths:\n${layout.offenders.map((p) => `- ${p}`).join('\n')}\n\n` +
|
|
83
|
+
`Canonical contract:\n${layout.contract}`,
|
|
84
|
+
},
|
|
85
|
+
],
|
|
86
|
+
isError: true,
|
|
87
|
+
structuredContent: {
|
|
88
|
+
error: 'strict_planu_layout_violation',
|
|
89
|
+
offenders: layout.offenders,
|
|
90
|
+
contract: layout.contract,
|
|
91
|
+
},
|
|
92
|
+
};
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
catch {
|
|
96
|
+
/* best-effort — implementation validation still runs if layout check is unavailable */
|
|
97
|
+
}
|
|
71
98
|
// 3. Run validation engine
|
|
72
99
|
const result = await validateSpec(spec, projectPath);
|
|
73
100
|
// 4. Generate DoR and DoD checklists
|
|
@@ -10,6 +10,7 @@ import { readRecentAutopilotAlerts } from '../storage/autopilot-log-store.js';
|
|
|
10
10
|
import { verifyStateFiles } from '../engine/cascade-hooks/state-drift-detector.js';
|
|
11
11
|
import { readFile } from 'node:fs/promises';
|
|
12
12
|
import { join } from 'node:path';
|
|
13
|
+
import { getAsyncAnalysisPath } from './create-spec/post-creation.js';
|
|
13
14
|
export async function handleWorkspaceOverview(args) {
|
|
14
15
|
const result = await buildWorkspaceOverview(args.healthThreshold);
|
|
15
16
|
if (result.projectCount === 0) {
|
|
@@ -126,10 +127,10 @@ export async function handleWorkspaceSearch(args) {
|
|
|
126
127
|
}
|
|
127
128
|
return { content: [{ type: 'text', text: lines.join('\n') }] };
|
|
128
129
|
}
|
|
129
|
-
/** SPEC-781: Check if a spec has
|
|
130
|
-
async function hasPendingAnalysis(projectPath,
|
|
130
|
+
/** SPEC-781: Check if a spec has pending async analysis in external project data. */
|
|
131
|
+
async function hasPendingAnalysis(projectPath, specId) {
|
|
131
132
|
try {
|
|
132
|
-
await readFile(
|
|
133
|
+
await readFile(getAsyncAnalysisPath(projectPath, specId), 'utf-8');
|
|
133
134
|
return false;
|
|
134
135
|
}
|
|
135
136
|
catch {
|
|
@@ -144,7 +145,6 @@ async function collectPendingAnalysisAlerts(projectPath) {
|
|
|
144
145
|
const results = [];
|
|
145
146
|
const PENDING_RE = /^pendingAnalysis:\s*true/m;
|
|
146
147
|
const ID_RE = /^id:\s*(SPEC-\d+)/m;
|
|
147
|
-
const SPEC_DIR_RE = /planu\/specs\/([^/]+)\/spec\.md$/;
|
|
148
148
|
for (const specFile of specFiles) {
|
|
149
149
|
const content = await readFile(specFile, 'utf-8').catch(() => '');
|
|
150
150
|
if (!PENDING_RE.test(content)) {
|
|
@@ -155,11 +155,8 @@ async function collectPendingAnalysisAlerts(projectPath) {
|
|
|
155
155
|
if (specId === undefined) {
|
|
156
156
|
continue;
|
|
157
157
|
}
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
const specDir = dirName !== undefined ? join('planu/specs', dirName) : null;
|
|
161
|
-
if (specDir !== null && !(await hasPendingAnalysis(projectPath, specDir))) {
|
|
162
|
-
continue; // .analysis.json exists — analysis done
|
|
158
|
+
if (!(await hasPendingAnalysis(projectPath, specId))) {
|
|
159
|
+
continue;
|
|
163
160
|
}
|
|
164
161
|
results.push({ specId, message: `Spec ${specId} analysis still running` });
|
|
165
162
|
}
|
package/dist/types/git.d.ts
CHANGED
|
@@ -310,7 +310,7 @@ export interface ListSpecPrsInput {
|
|
|
310
310
|
projectPath: string;
|
|
311
311
|
specId?: string;
|
|
312
312
|
}
|
|
313
|
-
export type PlanuAutocommitSkipReason = 'no-staged-changes' | 'mid-merge' | 'detached-head';
|
|
313
|
+
export type PlanuAutocommitSkipReason = 'disabled' | 'no-staged-changes' | 'mid-merge' | 'detached-head';
|
|
314
314
|
export type PlanuAutocommitReason = 'mark-done' | 'sync-release' | 'status-update' | 'session-checkpoint';
|
|
315
315
|
export interface PlanuAutocommitResult {
|
|
316
316
|
committed: boolean;
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import type { Spec } from './spec/core.js';
|
|
2
2
|
import type { Estimation } from './estimation.js';
|
|
3
|
+
import type { SpecStatus } from './common/index.js';
|
|
3
4
|
/** A criterion in the lean spec frontmatter. */
|
|
4
5
|
export interface LeanCriterion {
|
|
5
6
|
text: string;
|
|
@@ -42,6 +43,31 @@ export interface CleanupResult {
|
|
|
42
43
|
deletedSpecFiles: string[];
|
|
43
44
|
totalDeleted: number;
|
|
44
45
|
}
|
|
46
|
+
export interface PlanuCanonicalPathPolicy {
|
|
47
|
+
readonly canonicalRootFiles: readonly string[];
|
|
48
|
+
readonly canonicalRootDirs: readonly string[];
|
|
49
|
+
readonly canonicalSpecFiles: readonly string[];
|
|
50
|
+
readonly generatedRuntimePatterns: readonly string[];
|
|
51
|
+
readonly legacyMergeBeforeDeleteFiles: readonly string[];
|
|
52
|
+
}
|
|
53
|
+
export interface StrictPlanuCleanupResult {
|
|
54
|
+
deleted: string[];
|
|
55
|
+
merged: string[];
|
|
56
|
+
gitignoreUpdated: boolean;
|
|
57
|
+
}
|
|
58
|
+
export interface StrictPlanuValidationResult {
|
|
59
|
+
ok: boolean;
|
|
60
|
+
offenders: string[];
|
|
61
|
+
contract: string;
|
|
62
|
+
}
|
|
63
|
+
export interface UpdateStatusBatchInput {
|
|
64
|
+
specIds: string[];
|
|
65
|
+
status: SpecStatus;
|
|
66
|
+
projectId?: string;
|
|
67
|
+
projectPath?: string;
|
|
68
|
+
dryRun?: boolean;
|
|
69
|
+
reviewNotes?: string;
|
|
70
|
+
}
|
|
45
71
|
/** Report of detected migration drift (SPEC-715). Read-only — no FS mutations. */
|
|
46
72
|
export interface MigrationDriftReport {
|
|
47
73
|
/** Count of specs that still have a stray technical.md (need unified migration). */
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@planu/cli",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "4.0.0",
|
|
4
4
|
"description": "Planu — MCP Server for Spec Driven Development with native Rust acceleration for hot paths. Cross-platform (Linux/macOS/Windows, x64/arm64, glibc/musl).",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "dist/index.js",
|
|
@@ -32,12 +32,12 @@
|
|
|
32
32
|
"packageName": "@planu/core"
|
|
33
33
|
},
|
|
34
34
|
"optionalDependencies": {
|
|
35
|
-
"@planu/core-darwin-arm64": "3.9.
|
|
36
|
-
"@planu/core-darwin-x64": "3.9.
|
|
37
|
-
"@planu/core-linux-arm64-gnu": "3.9.
|
|
38
|
-
"@planu/core-linux-arm64-musl": "3.9.
|
|
39
|
-
"@planu/core-linux-x64-gnu": "3.9.
|
|
40
|
-
"@planu/core-linux-x64-musl": "3.9.
|
|
35
|
+
"@planu/core-darwin-arm64": "3.9.14",
|
|
36
|
+
"@planu/core-darwin-x64": "3.9.14",
|
|
37
|
+
"@planu/core-linux-arm64-gnu": "3.9.14",
|
|
38
|
+
"@planu/core-linux-arm64-musl": "3.9.14",
|
|
39
|
+
"@planu/core-linux-x64-gnu": "3.9.14",
|
|
40
|
+
"@planu/core-linux-x64-musl": "3.9.14"
|
|
41
41
|
},
|
|
42
42
|
"engines": {
|
|
43
43
|
"node": ">=24.0.0"
|