@ktpartners/dgs-platform 2.7.5 → 2.9.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 +30 -0
- package/README.md +15 -12
- package/agents/dgs-executor.md +0 -52
- package/deliver-great-systems/bin/dgs-tools.cjs +66 -10
- package/deliver-great-systems/bin/lib/commands.cjs +1 -8
- package/deliver-great-systems/bin/lib/config.cjs +9 -90
- package/deliver-great-systems/bin/lib/context.cjs +2 -2
- package/deliver-great-systems/bin/lib/context.test.cjs +100 -100
- package/deliver-great-systems/bin/lib/core.cjs +17 -57
- package/deliver-great-systems/bin/lib/core.test.cjs +166 -170
- package/deliver-great-systems/bin/lib/docs.cjs +3 -3
- package/deliver-great-systems/bin/lib/docs.test.cjs +14 -7
- package/deliver-great-systems/bin/lib/execution.cjs +2 -2
- package/deliver-great-systems/bin/lib/execution.test.cjs +65 -67
- package/deliver-great-systems/bin/lib/ideas.cjs +4 -4
- package/deliver-great-systems/bin/lib/ideas.test.cjs +45 -44
- package/deliver-great-systems/bin/lib/init.cjs +9 -4
- package/deliver-great-systems/bin/lib/init.test.cjs +242 -175
- package/deliver-great-systems/bin/lib/jobs.cjs +1 -1
- package/deliver-great-systems/bin/lib/jobs.test.cjs +203 -202
- package/deliver-great-systems/bin/lib/migration.cjs +256 -281
- package/deliver-great-systems/bin/lib/migration.test.cjs +385 -440
- package/deliver-great-systems/bin/lib/milestone.cjs +1 -1
- package/deliver-great-systems/bin/lib/overlap.cjs +4 -4
- package/deliver-great-systems/bin/lib/overlap.test.cjs +45 -44
- package/deliver-great-systems/bin/lib/path-audit.test.cjs +16 -22
- package/deliver-great-systems/bin/lib/paths.cjs +60 -59
- package/deliver-great-systems/bin/lib/paths.test.cjs +192 -225
- package/deliver-great-systems/bin/lib/phase.cjs +5 -4
- package/deliver-great-systems/bin/lib/projects.cjs +8 -8
- package/deliver-great-systems/bin/lib/projects.test.cjs +75 -74
- package/deliver-great-systems/bin/lib/repos.cjs +94 -230
- package/deliver-great-systems/bin/lib/repos.test.cjs +84 -75
- package/deliver-great-systems/bin/lib/search.cjs +4 -4
- package/deliver-great-systems/bin/lib/specs.cjs +2 -2
- package/deliver-great-systems/bin/lib/sync.cjs +1 -1
- package/deliver-great-systems/bin/lib/template.cjs +3 -3
- package/deliver-great-systems/bin/lib/test-helpers.cjs +59 -162
- package/deliver-great-systems/bin/lib/verify.cjs +3 -3
- package/deliver-great-systems/references/planning-config.md +7 -8
- package/deliver-great-systems/workflows/add-tests.md +1 -1
- package/deliver-great-systems/workflows/approve-spec.md +1 -11
- package/deliver-great-systems/workflows/complete-milestone.md +2 -2
- package/deliver-great-systems/workflows/consolidate-ideas.md +1 -1
- package/deliver-great-systems/workflows/create-milestone-job.md +2 -2
- package/deliver-great-systems/workflows/discuss-phase.md +2 -2
- package/deliver-great-systems/workflows/execute-phase.md +63 -4
- package/deliver-great-systems/workflows/execute-plan.md +0 -51
- package/deliver-great-systems/workflows/find-related-ideas.md +1 -1
- package/deliver-great-systems/workflows/help.md +55 -84
- package/deliver-great-systems/workflows/init-product.md +14 -451
- package/deliver-great-systems/workflows/map-codebase.md +109 -0
- package/deliver-great-systems/workflows/new-milestone.md +16 -6
- package/deliver-great-systems/workflows/new-project.md +22 -681
- package/deliver-great-systems/workflows/quick.md +2 -2
- package/deliver-great-systems/workflows/run-job.md +56 -0
- package/package.json +1 -1
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* Shared test helper module for DGS test suite.
|
|
3
3
|
*
|
|
4
|
-
* Provides
|
|
5
|
-
*
|
|
4
|
+
* Provides root-layout fixture creation for DGS test suite.
|
|
5
|
+
* Temp directory management, file writing, and git repo initialization.
|
|
6
6
|
*
|
|
7
7
|
* All functions are synchronous, matching existing test patterns.
|
|
8
8
|
*/
|
|
@@ -11,7 +11,7 @@ const fs = require('fs');
|
|
|
11
11
|
const path = require('path');
|
|
12
12
|
const os = require('os');
|
|
13
13
|
const { execSync } = require('child_process');
|
|
14
|
-
const { initPaths, resetPaths
|
|
14
|
+
const { initPaths, resetPaths } = require('./paths.cjs');
|
|
15
15
|
|
|
16
16
|
// ─── Utility Helpers ─────────────────────────────────────────────────────────
|
|
17
17
|
|
|
@@ -50,7 +50,7 @@ function writeFile(base, relPath, content) {
|
|
|
50
50
|
*/
|
|
51
51
|
function initGitRepo(dir) {
|
|
52
52
|
fs.mkdirSync(dir, { recursive: true });
|
|
53
|
-
execSync('git init', { cwd: dir, stdio: 'pipe' });
|
|
53
|
+
execSync('git init -b main', { cwd: dir, stdio: 'pipe' });
|
|
54
54
|
execSync('git config user.email "test@test.com"', { cwd: dir, stdio: 'pipe' });
|
|
55
55
|
execSync('git config user.name "Test"', { cwd: dir, stdio: 'pipe' });
|
|
56
56
|
fs.writeFileSync(path.join(dir, '.gitkeep'), '');
|
|
@@ -69,13 +69,17 @@ function initGitRepo(dir) {
|
|
|
69
69
|
*
|
|
70
70
|
* Example:
|
|
71
71
|
* createFixture({
|
|
72
|
-
* '
|
|
73
|
-
* '
|
|
74
|
-
* '
|
|
72
|
+
* 'config.json': '{}',
|
|
73
|
+
* 'STATE.md': '# State',
|
|
74
|
+
* 'phases/': null,
|
|
75
75
|
* })
|
|
76
76
|
*/
|
|
77
77
|
function createFixture(structure) {
|
|
78
|
-
|
|
78
|
+
var cwd = fs.mkdtempSync(path.join(os.tmpdir(), 'dgs-test-'));
|
|
79
|
+
cwd = fs.realpathSync(cwd);
|
|
80
|
+
|
|
81
|
+
// Initialize git repo so getPlanningRoot() works (root layout requires git)
|
|
82
|
+
initGitRepo(cwd);
|
|
79
83
|
|
|
80
84
|
for (const [relPath, content] of Object.entries(structure)) {
|
|
81
85
|
const fullPath = path.join(cwd, relPath);
|
|
@@ -100,182 +104,75 @@ function createFixture(structure) {
|
|
|
100
104
|
}
|
|
101
105
|
|
|
102
106
|
/**
|
|
103
|
-
* Creates a temporary project fixture with
|
|
107
|
+
* Creates a temporary project fixture with root-layout directory structure.
|
|
108
|
+
*
|
|
109
|
+
* Root layout means planning files live at the repo root (no .planning/ subdirectory).
|
|
104
110
|
*
|
|
105
111
|
* @param {Object} [options={}]
|
|
106
|
-
* @param {
|
|
107
|
-
* @param {
|
|
108
|
-
* @param {string} [options.projectName] - Display name (defaults to title-casing the slug).
|
|
109
|
-
* @param {boolean} [options.withGit=false] - Initialize as git repo and commit the structure.
|
|
112
|
+
* @param {string} [options.projectName] - Display name (defaults to 'Test Project').
|
|
113
|
+
* @param {boolean} [options.withGit=false] - Commit the fixture structure to git (git always initialized for root layout).
|
|
110
114
|
* @param {Object} [options.withConfig] - Additional config.json fields to merge.
|
|
111
115
|
* @param {boolean} [options.withPhases=true] - Create phases/ directory with sample plan.
|
|
112
116
|
* @param {boolean} [options.withTodos=false] - Create todos/pending/ and todos/completed/.
|
|
113
117
|
* @param {boolean} [options.withResearch=false] - Create research/ directory.
|
|
114
118
|
* @returns {{ cwd: string, cleanup: () => void, planningDir: string, projectRoot: string }}
|
|
119
|
+
* planningDir === cwd (planning dir IS the repo root).
|
|
120
|
+
* projectRoot === '.' (root-relative path to project).
|
|
115
121
|
*/
|
|
116
122
|
function createTempProject(options) {
|
|
117
123
|
const opts = options || {};
|
|
118
|
-
const
|
|
119
|
-
const layout = opts.layout || 'dotplanning';
|
|
120
|
-
const project = opts.project || null;
|
|
121
|
-
const projectName = opts.projectName || titleCase(project || 'Test Project');
|
|
124
|
+
const projectName = opts.projectName || 'Test Project';
|
|
122
125
|
const withGit = opts.withGit || false;
|
|
123
126
|
const withConfig = opts.withConfig || {};
|
|
124
127
|
const withPhases = opts.withPhases !== undefined ? opts.withPhases : true;
|
|
125
128
|
const withTodos = opts.withTodos || false;
|
|
126
129
|
const withResearch = opts.withResearch || false;
|
|
127
130
|
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
// If withGit, initialize repo first
|
|
131
|
-
if (withGit) {
|
|
132
|
-
initGitRepo(cwd);
|
|
133
|
-
}
|
|
134
|
-
|
|
135
|
-
var planningDir;
|
|
136
|
-
var projectRoot;
|
|
137
|
-
|
|
138
|
-
if (layout === 'root') {
|
|
139
|
-
// Root layout: planning files live at repo root
|
|
140
|
-
planningDir = cwd;
|
|
141
|
-
projectRoot = '.';
|
|
142
|
-
|
|
143
|
-
// Split withConfig into shared and local keys
|
|
144
|
-
var rootLocalKeys = { planningRoot: '.' };
|
|
145
|
-
var rootSharedKeys = {};
|
|
146
|
-
var LOCAL_KEY_SET = new Set(['current_project', 'planningRoot', 'v2_hint_shown', 'sync_hint_shown']);
|
|
147
|
-
for (var k in withConfig) {
|
|
148
|
-
if (LOCAL_KEY_SET.has(k)) {
|
|
149
|
-
rootLocalKeys[k] = withConfig[k];
|
|
150
|
-
} else {
|
|
151
|
-
rootSharedKeys[k] = withConfig[k];
|
|
152
|
-
}
|
|
153
|
-
}
|
|
154
|
-
writeFile(cwd, 'config.local.json', JSON.stringify(rootLocalKeys));
|
|
155
|
-
writeFile(cwd, 'config.json', JSON.stringify(rootSharedKeys));
|
|
156
|
-
|
|
157
|
-
// Project files at root
|
|
158
|
-
writeFile(cwd, 'PROJECT.md', '# Project: ' + projectName + '\n');
|
|
159
|
-
writeFile(cwd, 'REQUIREMENTS.md', '# Requirements\n');
|
|
160
|
-
writeFile(cwd, 'ROADMAP.md', '# Roadmap\n\n## Phases\n\n- [ ] **Phase 1: Test Phase** - A test\n');
|
|
161
|
-
writeFile(cwd, 'STATE.md', '# Project State\n\nPhase: 1\nStatus: Ready\nProgress: [░░░░░░░░░░] 0%\n');
|
|
131
|
+
var cwd = fs.mkdtempSync(path.join(os.tmpdir(), 'dgs-test-'));
|
|
132
|
+
cwd = fs.realpathSync(cwd);
|
|
162
133
|
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
writeFile(cwd, 'REPOS.md', '# Repos\n');
|
|
166
|
-
|
|
167
|
-
if (withPhases) {
|
|
168
|
-
writeFile(cwd, 'phases/01-test-phase/01-01-PLAN.md',
|
|
169
|
-
'---\nphase: 01-test-phase\nplan: 01\n---\n# Plan\n');
|
|
170
|
-
}
|
|
171
|
-
|
|
172
|
-
if (withTodos) {
|
|
173
|
-
fs.mkdirSync(path.join(cwd, 'todos', 'pending'), { recursive: true });
|
|
174
|
-
fs.mkdirSync(path.join(cwd, 'todos', 'completed'), { recursive: true });
|
|
175
|
-
}
|
|
176
|
-
|
|
177
|
-
if (withResearch) {
|
|
178
|
-
fs.mkdirSync(path.join(cwd, 'research'), { recursive: true });
|
|
179
|
-
}
|
|
180
|
-
|
|
181
|
-
} else if (version === 2) {
|
|
182
|
-
if (!project) {
|
|
183
|
-
throw new Error('createTempProject: version 2 requires a project slug');
|
|
184
|
-
}
|
|
185
|
-
planningDir = path.join(cwd, '.planning');
|
|
186
|
-
projectRoot = path.join('.planning', PROJECTS_DIR, project);
|
|
187
|
-
var absProjectRoot = path.join(cwd, '.planning', PROJECTS_DIR, project);
|
|
188
|
-
|
|
189
|
-
// Product-level config: split into shared and local
|
|
190
|
-
var v2LocalKeys = { current_project: project };
|
|
191
|
-
var v2SharedKeys = {};
|
|
192
|
-
var LOCAL_KEY_SET_V2 = new Set(['current_project', 'planningRoot', 'v2_hint_shown', 'sync_hint_shown']);
|
|
193
|
-
for (var ck in withConfig) {
|
|
194
|
-
if (LOCAL_KEY_SET_V2.has(ck)) {
|
|
195
|
-
v2LocalKeys[ck] = withConfig[ck];
|
|
196
|
-
} else {
|
|
197
|
-
v2SharedKeys[ck] = withConfig[ck];
|
|
198
|
-
}
|
|
199
|
-
}
|
|
200
|
-
writeFile(cwd, '.planning/config.json', JSON.stringify(v2SharedKeys));
|
|
201
|
-
writeFile(cwd, '.planning/config.local.json', JSON.stringify(v2LocalKeys));
|
|
134
|
+
// Always initialize git repo (root layout requires git for getPlanningRoot)
|
|
135
|
+
initGitRepo(cwd);
|
|
202
136
|
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
projectsMd += '| Project | Status | Repos Touched | Current Phase |\n';
|
|
206
|
-
projectsMd += '|---------|--------|---------------|---------------|\n';
|
|
207
|
-
projectsMd += '| ' + project + ' | Active | | Phase 1 |\n';
|
|
208
|
-
projectsMd += '\n## Completed\n\n';
|
|
209
|
-
projectsMd += '| Project | Completed | Duration |\n';
|
|
210
|
-
projectsMd += '|---------|-----------|----------|\n';
|
|
211
|
-
writeFile(cwd, '.planning/PROJECTS.md', projectsMd);
|
|
137
|
+
const planningDir = cwd;
|
|
138
|
+
const projectRoot = '.';
|
|
212
139
|
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
writeFile(cwd, path.join('.planning', PROJECTS_DIR, project, 'ROADMAP.md'), '# Roadmap\n\n## Phases\n\n- [ ] **Phase 1: Test Phase** - A test\n');
|
|
223
|
-
writeFile(cwd, path.join('.planning', PROJECTS_DIR, project, 'STATE.md'), '# Project State\n\nPhase: 1\nStatus: Ready\nProgress: [░░░░░░░░░░] 0%\n');
|
|
224
|
-
|
|
225
|
-
if (withPhases) {
|
|
226
|
-
writeFile(cwd, path.join('.planning', PROJECTS_DIR, project, 'phases', '01-test-phase', '01-01-PLAN.md'),
|
|
227
|
-
'---\nphase: 01-test-phase\nplan: 01\n---\n# Plan\n');
|
|
228
|
-
}
|
|
229
|
-
|
|
230
|
-
if (withTodos) {
|
|
231
|
-
fs.mkdirSync(path.join(cwd, '.planning', 'todos', 'pending'), { recursive: true });
|
|
232
|
-
fs.mkdirSync(path.join(cwd, '.planning', 'todos', 'completed'), { recursive: true });
|
|
233
|
-
}
|
|
234
|
-
|
|
235
|
-
if (withResearch) {
|
|
236
|
-
fs.mkdirSync(path.join(cwd, '.planning', PROJECTS_DIR, project, 'research'), { recursive: true });
|
|
237
|
-
}
|
|
238
|
-
|
|
239
|
-
} else {
|
|
240
|
-
// v1 mode (dotplanning layout)
|
|
241
|
-
planningDir = path.join(cwd, '.planning');
|
|
242
|
-
projectRoot = '.planning';
|
|
243
|
-
|
|
244
|
-
// Split withConfig into shared and local
|
|
245
|
-
var v1SharedKeys = {};
|
|
246
|
-
var v1LocalKeys = {};
|
|
247
|
-
var LOCAL_KEY_SET_V1 = new Set(['current_project', 'planningRoot', 'v2_hint_shown', 'sync_hint_shown']);
|
|
248
|
-
for (var vk in withConfig) {
|
|
249
|
-
if (LOCAL_KEY_SET_V1.has(vk)) {
|
|
250
|
-
v1LocalKeys[vk] = withConfig[vk];
|
|
251
|
-
} else {
|
|
252
|
-
v1SharedKeys[vk] = withConfig[vk];
|
|
253
|
-
}
|
|
254
|
-
}
|
|
255
|
-
writeFile(cwd, '.planning/config.json', JSON.stringify(v1SharedKeys));
|
|
256
|
-
if (Object.keys(v1LocalKeys).length > 0) {
|
|
257
|
-
writeFile(cwd, '.planning/config.local.json', JSON.stringify(v1LocalKeys));
|
|
258
|
-
}
|
|
259
|
-
|
|
260
|
-
// Project files
|
|
261
|
-
writeFile(cwd, '.planning/PROJECT.md', '# Project: ' + projectName + '\n');
|
|
262
|
-
writeFile(cwd, '.planning/REQUIREMENTS.md', '# Requirements\n');
|
|
263
|
-
writeFile(cwd, '.planning/ROADMAP.md', '# Roadmap\n\n## Phases\n\n- [ ] **Phase 1: Test Phase** - A test\n');
|
|
264
|
-
writeFile(cwd, '.planning/STATE.md', '# Project State\n\nPhase: 1\nStatus: Ready\nProgress: [░░░░░░░░░░] 0%\n');
|
|
265
|
-
|
|
266
|
-
if (withPhases) {
|
|
267
|
-
writeFile(cwd, '.planning/phases/01-test-phase/01-01-PLAN.md',
|
|
268
|
-
'---\nphase: 01-test-phase\nplan: 01\n---\n# Plan\n');
|
|
140
|
+
// Split withConfig into shared and local keys
|
|
141
|
+
var localKeys = { planningRoot: '.' };
|
|
142
|
+
var sharedKeys = {};
|
|
143
|
+
var LOCAL_KEY_SET = new Set(['current_project', 'planningRoot', 'v2_hint_shown', 'sync_hint_shown']);
|
|
144
|
+
for (var k in withConfig) {
|
|
145
|
+
if (LOCAL_KEY_SET.has(k)) {
|
|
146
|
+
localKeys[k] = withConfig[k];
|
|
147
|
+
} else {
|
|
148
|
+
sharedKeys[k] = withConfig[k];
|
|
269
149
|
}
|
|
150
|
+
}
|
|
151
|
+
writeFile(cwd, 'config.local.json', JSON.stringify(localKeys));
|
|
152
|
+
writeFile(cwd, 'config.json', JSON.stringify(sharedKeys));
|
|
153
|
+
|
|
154
|
+
// Project files at root
|
|
155
|
+
writeFile(cwd, 'PROJECT.md', '# Project: ' + titleCase(projectName) + '\n');
|
|
156
|
+
writeFile(cwd, 'REQUIREMENTS.md', '# Requirements\n');
|
|
157
|
+
writeFile(cwd, 'ROADMAP.md', '# Roadmap\n\n## Phases\n\n- [ ] **Phase 1: Test Phase** - A test\n');
|
|
158
|
+
writeFile(cwd, 'STATE.md', '# Project State\n\nPhase: 1\nStatus: Ready\nProgress: [░░░░░░░░░░] 0%\n');
|
|
159
|
+
|
|
160
|
+
// v2 markers at root
|
|
161
|
+
writeFile(cwd, 'PROJECTS.md', '# Projects\n');
|
|
162
|
+
writeFile(cwd, 'REPOS.md', '# Repos\n');
|
|
163
|
+
|
|
164
|
+
if (withPhases) {
|
|
165
|
+
writeFile(cwd, 'phases/01-test-phase/01-01-PLAN.md',
|
|
166
|
+
'---\nphase: 01-test-phase\nplan: 01\n---\n# Plan\n');
|
|
167
|
+
}
|
|
270
168
|
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
169
|
+
if (withTodos) {
|
|
170
|
+
fs.mkdirSync(path.join(cwd, 'todos', 'pending'), { recursive: true });
|
|
171
|
+
fs.mkdirSync(path.join(cwd, 'todos', 'completed'), { recursive: true });
|
|
172
|
+
}
|
|
275
173
|
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
}
|
|
174
|
+
if (withResearch) {
|
|
175
|
+
fs.mkdirSync(path.join(cwd, 'research'), { recursive: true });
|
|
279
176
|
}
|
|
280
177
|
|
|
281
178
|
// If withGit, commit the fixture structure
|
|
@@ -537,9 +537,9 @@ function cmdValidateHealth(cwd, options, raw) {
|
|
|
537
537
|
else info.push(issue);
|
|
538
538
|
};
|
|
539
539
|
|
|
540
|
-
// ─── Check 1:
|
|
540
|
+
// ─── Check 1: Planning files exist ──────────────────────────────────────────
|
|
541
541
|
if (!fs.existsSync(planningDir)) {
|
|
542
|
-
addIssue('error', 'E001', '
|
|
542
|
+
addIssue('error', 'E001', 'Planning files not found at root', 'Run /dgs:new-project to initialize');
|
|
543
543
|
output({
|
|
544
544
|
status: 'broken',
|
|
545
545
|
errors,
|
|
@@ -742,7 +742,7 @@ function cmdValidateHealth(cwd, options, raw) {
|
|
|
742
742
|
const milestone = getMilestoneInfo(cwd);
|
|
743
743
|
let stateContent = `# Session State\n\n`;
|
|
744
744
|
stateContent += `## Project Reference\n\n`;
|
|
745
|
-
stateContent += `See:
|
|
745
|
+
stateContent += `See: PROJECT.md\n\n`;
|
|
746
746
|
stateContent += `## Position\n\n`;
|
|
747
747
|
stateContent += `**Milestone:** ${milestone.version} ${milestone.name}\n`;
|
|
748
748
|
stateContent += `**Current phase:** (determining...)\n`;
|
|
@@ -11,12 +11,10 @@ DGS splits configuration across two files, both resolved via `getPlanningRoot()`
|
|
|
11
11
|
| File | Tracked | Purpose | Keys |
|
|
12
12
|
|------|---------|---------|------|
|
|
13
13
|
| `config.json` | Yes (shared) | Team settings: model profile, workflow flags, git config, sync config, parallelization | All `VALID_CONFIG_KEYS` |
|
|
14
|
-
| `config.local.json` | No (gitignored) | Per-machine state: which project is active
|
|
14
|
+
| `config.local.json` | No (gitignored) | Per-machine state: which project is active | `current_project`, `v2_hint_shown`, `sync_hint_shown` |
|
|
15
15
|
|
|
16
16
|
`loadConfig()` in `core.cjs` merges both files -- local overrides shared. `writeConfigField()` in `config.cjs` routes writes to the correct file based on `isLocalKey()`.
|
|
17
17
|
|
|
18
|
-
**Migration:** On first read, if only `dgs.config.json` exists, `_migrateLegacyConfig()` splits it into the two-file layout automatically.
|
|
19
|
-
|
|
20
18
|
<config_schema>
|
|
21
19
|
|
|
22
20
|
## Config Schema
|
|
@@ -102,7 +100,6 @@ These keys are stored in `config.local.json` (gitignored, per-machine):
|
|
|
102
100
|
| Key | Default | Description |
|
|
103
101
|
|-----|---------|-------------|
|
|
104
102
|
| `current_project` | -- | Active project slug for multi-project setups |
|
|
105
|
-
| `planningRoot` | -- | Absolute path to planning root (when non-standard) |
|
|
106
103
|
| `v2_hint_shown` | -- | Whether the v2 migration hint has been shown |
|
|
107
104
|
| `sync_hint_shown` | -- | Whether the sync first-run hint has been shown |
|
|
108
105
|
|
|
@@ -176,14 +173,16 @@ To use uncommitted mode:
|
|
|
176
173
|
}
|
|
177
174
|
```
|
|
178
175
|
|
|
179
|
-
2. **Add to .gitignore:**
|
|
176
|
+
2. **Add planning paths to .gitignore:**
|
|
180
177
|
```
|
|
181
|
-
|
|
178
|
+
projects/
|
|
179
|
+
config.json
|
|
180
|
+
config.local.json
|
|
182
181
|
```
|
|
183
182
|
|
|
184
|
-
3. **Existing tracked files:** If
|
|
183
|
+
3. **Existing tracked files:** If planning files were previously tracked:
|
|
185
184
|
```bash
|
|
186
|
-
git rm -r --cached
|
|
185
|
+
git rm -r --cached projects/ config.json config.local.json
|
|
187
186
|
git commit -m "chore: stop tracking planning docs"
|
|
188
187
|
```
|
|
189
188
|
|
|
@@ -50,7 +50,7 @@ TIER_FILES=$(node "$HOME/.claude/deliver-great-systems/bin/dgs-tools.cjs" contex
|
|
|
50
50
|
Verify the phase directory exists. If not:
|
|
51
51
|
```
|
|
52
52
|
ERROR: Phase directory not found for phase ${PHASE_ARG}
|
|
53
|
-
Ensure the phase exists in
|
|
53
|
+
Ensure the phase exists in phases/
|
|
54
54
|
```
|
|
55
55
|
Exit.
|
|
56
56
|
|
|
@@ -114,17 +114,7 @@ This enforces APR-02.
|
|
|
114
114
|
</step>
|
|
115
115
|
|
|
116
116
|
<step name="warning_gate">
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
Read the spec's frontmatter for a `milestones` field (array of milestone references). If the field is empty, null, or absent, add an informational warning to the warnings list:
|
|
120
|
-
|
|
121
|
-
```
|
|
122
|
-
- This spec has no roadmap linkage (no milestones field). Consider linking it to a milestone for implementation tracking.
|
|
123
|
-
```
|
|
124
|
-
|
|
125
|
-
This is a warning, not a blocker. It runs after structural validation so it appears alongside other warnings in this gate.
|
|
126
|
-
|
|
127
|
-
If warnings exist (from validate command output, plus any roadmap linkage warning added above):
|
|
117
|
+
If warnings exist (from validate command output):
|
|
128
118
|
- Display each warning clearly:
|
|
129
119
|
```
|
|
130
120
|
## Approval Warnings
|
|
@@ -500,7 +500,7 @@ rm ${project_root}/REQUIREMENTS.md
|
|
|
500
500
|
|
|
501
501
|
Check for existing retrospective:
|
|
502
502
|
```bash
|
|
503
|
-
ls
|
|
503
|
+
ls RETROSPECTIVE.md 2>/dev/null
|
|
504
504
|
```
|
|
505
505
|
|
|
506
506
|
**If exists:** Read the file, append new milestone section before the "## Cross-Milestone Trends" section.
|
|
@@ -550,7 +550,7 @@ If the "## Cross-Milestone Trends" section exists, update the tables with new da
|
|
|
550
550
|
|
|
551
551
|
**Commit:**
|
|
552
552
|
```bash
|
|
553
|
-
node "$HOME/.claude/deliver-great-systems/bin/dgs-tools.cjs" commit "docs: update retrospective for v${VERSION}" --files
|
|
553
|
+
node "$HOME/.claude/deliver-great-systems/bin/dgs-tools.cjs" commit "docs: update retrospective for v${VERSION}" --files RETROSPECTIVE.md
|
|
554
554
|
```
|
|
555
555
|
|
|
556
556
|
</step>
|
|
@@ -307,7 +307,7 @@ Write multi-line parameters (body, discussion, research) to temporary files usin
|
|
|
307
307
|
{
|
|
308
308
|
"id": 5,
|
|
309
309
|
"filename": "005-improve-api-resilience.md",
|
|
310
|
-
"path": "
|
|
310
|
+
"path": "ideas/pending/005-improve-api-resilience.md",
|
|
311
311
|
"title": "Improve API resilience",
|
|
312
312
|
"consolidated_from": ["001", "003", "017"],
|
|
313
313
|
"moved_files": [
|
|
@@ -123,13 +123,13 @@ node ~/.claude/deliver-great-systems/bin/dgs-tools.cjs jobs create-milestone VER
|
|
|
123
123
|
2. Commit the job file:
|
|
124
124
|
|
|
125
125
|
```bash
|
|
126
|
-
node ~/.claude/deliver-great-systems/bin/dgs-tools.cjs commit "docs(50): create milestone job {version}" --files
|
|
126
|
+
node ~/.claude/deliver-great-systems/bin/dgs-tools.cjs commit "docs(50): create milestone job {version}" --files jobs/pending/milestone-{version}.md
|
|
127
127
|
```
|
|
128
128
|
|
|
129
129
|
3. Display success and next steps:
|
|
130
130
|
|
|
131
131
|
```
|
|
132
|
-
Job created:
|
|
132
|
+
Job created: jobs/pending/milestone-{version}.md
|
|
133
133
|
|
|
134
134
|
---
|
|
135
135
|
|
|
@@ -190,7 +190,7 @@ Project-level files (PROJECT.md, REQUIREMENTS.md, STATE.md, ROADMAP.md, REPOS.md
|
|
|
190
190
|
**Step 2: Read all prior CONTEXT.md files**
|
|
191
191
|
```bash
|
|
192
192
|
# Find all CONTEXT.md files from phases before current
|
|
193
|
-
find
|
|
193
|
+
find phases -name "*-CONTEXT.md" 2>/dev/null | sort
|
|
194
194
|
```
|
|
195
195
|
|
|
196
196
|
For each CONTEXT.md where phase number < current phase:
|
|
@@ -230,7 +230,7 @@ Lightweight scan of existing code to inform gray area identification and discuss
|
|
|
230
230
|
|
|
231
231
|
**Step 1: Check for existing codebase maps**
|
|
232
232
|
```bash
|
|
233
|
-
ls
|
|
233
|
+
ls codebase/*.md 2>/dev/null
|
|
234
234
|
```
|
|
235
235
|
|
|
236
236
|
**If codebase maps exist:** Read the most relevant ones (CONVENTIONS.md, STRUCTURE.md, STACK.md based on phase type). Extract:
|
|
@@ -283,7 +283,66 @@ Execute each wave in sequence. Within a wave: parallel if `PARALLELIZATION=true`
|
|
|
283
283
|
- Bad: "Wave 2 complete. Proceeding to Wave 3."
|
|
284
284
|
- Good: "Terrain system complete — 3 biome types, height-based texturing, physics collision meshes. Vehicle physics (Wave 3) can now reference ground surfaces."
|
|
285
285
|
|
|
286
|
-
5. **
|
|
286
|
+
5. **Codereview gate (per-plan, after spot-check passes):**
|
|
287
|
+
|
|
288
|
+
Check if code review is enabled:
|
|
289
|
+
```bash
|
|
290
|
+
CODEREVIEW=$(node "$HOME/.claude/deliver-great-systems/bin/dgs-tools.cjs" config-get workflow.codereview 2>/dev/null || echo "false")
|
|
291
|
+
```
|
|
292
|
+
|
|
293
|
+
If `CODEREVIEW` is not `true`: skip silently, proceed to next step.
|
|
294
|
+
|
|
295
|
+
**If `NON_INTERACTIVE` is true:**
|
|
296
|
+
Log: `[AUTO-RESOLVE] Code review enabled but skipping in non-interactive mode (codereview requires interactive Task spawning)`
|
|
297
|
+
Skip codereview, proceed to next step.
|
|
298
|
+
|
|
299
|
+
**If `NON_INTERACTIVE` is false (interactive mode) AND `CODEREVIEW` is `true`:**
|
|
300
|
+
|
|
301
|
+
For each plan that completed successfully in this wave:
|
|
302
|
+
|
|
303
|
+
Display:
|
|
304
|
+
```
|
|
305
|
+
------------------------------------------------------------
|
|
306
|
+
DGS > SPAWNING CODE REVIEW
|
|
307
|
+
------------------------------------------------------------
|
|
308
|
+
|
|
309
|
+
Reviewing {phase}-{plan} changes across 3 passes...
|
|
310
|
+
```
|
|
311
|
+
|
|
312
|
+
Compute diff reference for the plan's task commits:
|
|
313
|
+
```bash
|
|
314
|
+
FIRST_TASK_COMMIT=$(git log --oneline --grep="feat(${PHASE}-${PLAN}):" --grep="fix(${PHASE}-${PLAN}):" --grep="test(${PHASE}-${PLAN}):" --grep="refactor(${PHASE}-${PLAN}):" --reverse | head -1 | cut -d' ' -f1)
|
|
315
|
+
```
|
|
316
|
+
|
|
317
|
+
If FIRST_TASK_COMMIT is empty (no task commits found), skip codereview for this plan with message: "No task commits found for {phase}-{plan}, skipping code review."
|
|
318
|
+
|
|
319
|
+
Otherwise, spawn the codereview workflow via Task:
|
|
320
|
+
```
|
|
321
|
+
Task(
|
|
322
|
+
prompt="Run code review for plan {phase}-{plan}.
|
|
323
|
+
|
|
324
|
+
@~/.claude/deliver-great-systems/workflows/codereview.md
|
|
325
|
+
|
|
326
|
+
Inputs:
|
|
327
|
+
- PHASE: ${PHASE}
|
|
328
|
+
- PLAN: ${PLAN}
|
|
329
|
+
- PLAN_PATH: ${phase_dir}/{phase}-{plan}-PLAN.md
|
|
330
|
+
- PHASE_DIR: ${phase_dir}
|
|
331
|
+
- DIFF_REF: ${FIRST_TASK_COMMIT}^..HEAD
|
|
332
|
+
",
|
|
333
|
+
model="{executor_model}"
|
|
334
|
+
)
|
|
335
|
+
```
|
|
336
|
+
|
|
337
|
+
After codereview completes for a plan:
|
|
338
|
+
- If auto-fixes were committed, the fix commit hash is noted in the codereview output
|
|
339
|
+
- The SUMMARY.md already has codereview findings appended and CODEREVIEW.md has been created with the full report (both done by codereview workflow)
|
|
340
|
+
- If the codereview workflow committed auto-fixes, amend the plan's metadata commit to include the updated SUMMARY.md and CODEREVIEW.md:
|
|
341
|
+
```bash
|
|
342
|
+
node "$HOME/.claude/deliver-great-systems/bin/dgs-tools.cjs" commit "" --files ${phase_dir}/{phase}-{plan}-SUMMARY.md ${phase_dir}/{phase}-{plan}-CODEREVIEW.md --amend
|
|
343
|
+
```
|
|
344
|
+
|
|
345
|
+
6. **Mid-workflow push (sync_mid_push):**
|
|
287
346
|
|
|
288
347
|
After each wave completes successfully, push if sync is configured.
|
|
289
348
|
|
|
@@ -297,7 +356,7 @@ Execute each wave in sequence. Within a wave: parallel if `PARALLELIZATION=true`
|
|
|
297
356
|
- If `action` is `"pushed"`: continue silently. If `message` mentions new remote branch, log: `Created remote branch: {branch}`
|
|
298
357
|
- Push failure does NOT halt execution -- warnings are accumulated for end-of-workflow summary
|
|
299
358
|
|
|
300
|
-
|
|
359
|
+
7. **Handle failures:**
|
|
301
360
|
|
|
302
361
|
**Known Claude Code bug (classifyHandoffIfNeeded):** If an agent reports "failed" with error containing `classifyHandoffIfNeeded is not defined`, this is a Claude Code runtime bug — not a DGS or agent issue. The error fires in the completion handler AFTER all tool calls finish. In this case: run the same spot-checks as step 4 (SUMMARY.md exists, git commits present, no Self-Check: FAILED). If spot-checks PASS → treat as **successful**. If spot-checks FAIL → treat as real failure below.
|
|
303
362
|
|
|
@@ -308,9 +367,9 @@ Execute each wave in sequence. Within a wave: parallel if `PARALLELIZATION=true`
|
|
|
308
367
|
**If `NON_INTERACTIVE` is false (interactive mode):**
|
|
309
368
|
For real failures: report which plan failed → ask "Continue?" or "Stop?" → if continue, dependent plans may also fail. If stop, partial completion report.
|
|
310
369
|
|
|
311
|
-
|
|
370
|
+
8. **Execute checkpoint plans between waves** — see `<checkpoint_handling>`.
|
|
312
371
|
|
|
313
|
-
|
|
372
|
+
9. **Proceed to next wave.**
|
|
314
373
|
</step>
|
|
315
374
|
|
|
316
375
|
<step name="checkpoint_handling">
|
|
@@ -486,56 +486,6 @@ node "$HOME/.claude/deliver-great-systems/bin/dgs-tools.cjs" commit "docs({phase
|
|
|
486
486
|
```
|
|
487
487
|
</step>
|
|
488
488
|
|
|
489
|
-
<step name="codereview_gate">
|
|
490
|
-
Check if code review is enabled:
|
|
491
|
-
|
|
492
|
-
```bash
|
|
493
|
-
CODEREVIEW=$(node "$HOME/.claude/deliver-great-systems/bin/dgs-tools.cjs" config-get workflow.codereview 2>/dev/null || echo "false")
|
|
494
|
-
```
|
|
495
|
-
|
|
496
|
-
If `CODEREVIEW` is `true`:
|
|
497
|
-
|
|
498
|
-
Display:
|
|
499
|
-
```
|
|
500
|
-
------------------------------------------------------------
|
|
501
|
-
DGS > SPAWNING CODE REVIEW
|
|
502
|
-
------------------------------------------------------------
|
|
503
|
-
|
|
504
|
-
Reviewing {phase}-{plan} changes across 3 passes...
|
|
505
|
-
```
|
|
506
|
-
|
|
507
|
-
Compute diff reference for the plan's task commits:
|
|
508
|
-
|
|
509
|
-
```bash
|
|
510
|
-
FIRST_TASK_COMMIT=$(git log --oneline --grep="feat(${PHASE}-${PLAN}):" --grep="fix(${PHASE}-${PLAN}):" --grep="test(${PHASE}-${PLAN}):" --grep="refactor(${PHASE}-${PLAN}):" --reverse | head -1 | cut -d' ' -f1)
|
|
511
|
-
```
|
|
512
|
-
|
|
513
|
-
If FIRST_TASK_COMMIT is empty (no task commits found), skip codereview with message: "No task commits found for {phase}-{plan}, skipping code review."
|
|
514
|
-
|
|
515
|
-
Otherwise, invoke the codereview workflow:
|
|
516
|
-
|
|
517
|
-
```
|
|
518
|
-
@~/.claude/deliver-great-systems/workflows/codereview.md
|
|
519
|
-
```
|
|
520
|
-
|
|
521
|
-
With inputs:
|
|
522
|
-
- PHASE: ${PHASE}
|
|
523
|
-
- PLAN: ${PLAN}
|
|
524
|
-
- PLAN_PATH: ${phase_dir}/{phase}-{plan}-PLAN.md
|
|
525
|
-
- PHASE_DIR: ${phase_dir}
|
|
526
|
-
- DIFF_REF: ${FIRST_TASK_COMMIT}^..HEAD
|
|
527
|
-
|
|
528
|
-
After codereview completes:
|
|
529
|
-
- If auto-fixes were committed, the fix commit hash is noted in the codereview output
|
|
530
|
-
- The SUMMARY.md already has codereview findings appended and CODEREVIEW.md has been created with the full report (both done by codereview workflow)
|
|
531
|
-
- If the codereview workflow committed auto-fixes, amend the metadata commit to include the updated SUMMARY.md and CODEREVIEW.md:
|
|
532
|
-
```bash
|
|
533
|
-
node "$HOME/.claude/deliver-great-systems/bin/dgs-tools.cjs" commit "" --files ${phase_dir}/{phase}-{plan}-SUMMARY.md ${phase_dir}/{phase}-{plan}-CODEREVIEW.md --amend
|
|
534
|
-
```
|
|
535
|
-
|
|
536
|
-
If `CODEREVIEW` is `false` or absent: skip silently (no output).
|
|
537
|
-
</step>
|
|
538
|
-
|
|
539
489
|
<step name="update_codebase_map">
|
|
540
490
|
If ${project_root}/codebase/ doesn't exist: skip.
|
|
541
491
|
|
|
@@ -588,5 +538,4 @@ All routes: `/clear` first for fresh context.
|
|
|
588
538
|
- ROADMAP.md updated
|
|
589
539
|
- If codebase map exists: map updated with execution changes (or skipped if no significant changes)
|
|
590
540
|
- If USER-SETUP.md created: prominently surfaced in completion output
|
|
591
|
-
- If codereview enabled: code review completed, auto-fixes committed separately, findings logged to SUMMARY, CODEREVIEW.md created with full report
|
|
592
541
|
</success_criteria>
|
|
@@ -115,7 +115,7 @@ ls ${codebase_dir}/*.md 2>/dev/null
|
|
|
115
115
|
ls ${project_root}/docs/product/*.md 2>/dev/null
|
|
116
116
|
```
|
|
117
117
|
|
|
118
|
-
Where `codebase_dir` is
|
|
118
|
+
Where `codebase_dir` is `codebase` (or the project-specific path if in multi-project mode) and `project_root` is the repo root.
|
|
119
119
|
|
|
120
120
|
Read available context files. Prioritise:
|
|
121
121
|
1. `ARCHITECTURE.md` -- system structure and module boundaries
|