scrumrun 2.6.3 → 2.6.4
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/README.md +1 -1
- package/lib/commands/repair.js +39 -5
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
|
|
5
5
|
ScrumRun gives an agent a small command surface and a precise project memory: what should be done, how each attempt happened, which decisions constrain the code, and why the architecture exists in its current form.
|
|
6
6
|
|
|
7
|
-
**Package:** `2.6.
|
|
7
|
+
**Package:** `2.6.4` · **Method target:** `2.0.0` · **Runtime:** Node.js `>=22.13.0` · **License:** MIT
|
|
8
8
|
|
|
9
9
|
**New here?** Read the [Quickstart](docs/QUICKSTART.md) — first Run in under 10 minutes, no `SPEC.md` reading required. Full docs map in [`docs/INDEX.md`](docs/INDEX.md).
|
|
10
10
|
|
package/lib/commands/repair.js
CHANGED
|
@@ -29,16 +29,24 @@ const path = require("node:path");
|
|
|
29
29
|
const TASK_FILE = /^TASK-\d{3,}\.md$/;
|
|
30
30
|
const RUN_FILE = /^RUN-\d{3,}\.md$/;
|
|
31
31
|
const FEAT_FILE = /^FEAT-\d{3,}\.md$/;
|
|
32
|
+
const SPRINT_FILE = /^SPRINT-\d{3,}\.md$/;
|
|
33
|
+
const MEMORY_FILE = /^(K|DEC|INS|DOS)-\d{3,}\.md$/;
|
|
32
34
|
const FEAT_REF = /^FEAT-\d{3,}$/;
|
|
33
35
|
const SLUG_REF = /^[a-z0-9][a-z0-9-]*$/;
|
|
34
36
|
|
|
35
|
-
const
|
|
37
|
+
const TASK_STATUS_ALIAS = {
|
|
36
38
|
done: "completed",
|
|
37
39
|
todo: "backlog",
|
|
38
40
|
complete: "completed",
|
|
39
41
|
in_progress: "executing"
|
|
40
42
|
};
|
|
41
43
|
|
|
44
|
+
const RUN_STATUS_ALIAS = {
|
|
45
|
+
complete: "completed",
|
|
46
|
+
in_progress: "executing",
|
|
47
|
+
done: "completed"
|
|
48
|
+
};
|
|
49
|
+
|
|
42
50
|
function readIf(file) {
|
|
43
51
|
try {
|
|
44
52
|
return fs.readFileSync(file, "utf8");
|
|
@@ -98,7 +106,15 @@ function planFile(file, kind, ctx) {
|
|
|
98
106
|
const changes = [];
|
|
99
107
|
|
|
100
108
|
const method = extractField(header, "method");
|
|
101
|
-
if (method
|
|
109
|
+
if (method === undefined) {
|
|
110
|
+
if (hasField(header, "id")) {
|
|
111
|
+
const next = insertFieldAfter(header, "id", "method", "2.0.0");
|
|
112
|
+
if (next !== header) {
|
|
113
|
+
changes.push({ field: "method", from: "(missing)", to: "2.0.0" });
|
|
114
|
+
header = next;
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
} else if (method !== "2.0.0" && method !== "null") {
|
|
102
118
|
const next = replaceField(header, "method", "2.0.0");
|
|
103
119
|
if (next !== header) {
|
|
104
120
|
changes.push({ field: "method", from: method, to: "2.0.0" });
|
|
@@ -119,16 +135,24 @@ function planFile(file, kind, ctx) {
|
|
|
119
135
|
}
|
|
120
136
|
|
|
121
137
|
const status = extractField(header, "status");
|
|
122
|
-
if (status &&
|
|
123
|
-
const next = replaceField(header, "status",
|
|
138
|
+
if (status && TASK_STATUS_ALIAS[status]) {
|
|
139
|
+
const next = replaceField(header, "status", TASK_STATUS_ALIAS[status]);
|
|
124
140
|
if (next !== header) {
|
|
125
|
-
changes.push({ field: "status", from: status, to:
|
|
141
|
+
changes.push({ field: "status", from: status, to: TASK_STATUS_ALIAS[status] });
|
|
126
142
|
header = next;
|
|
127
143
|
}
|
|
128
144
|
}
|
|
129
145
|
}
|
|
130
146
|
|
|
131
147
|
if (kind === "run") {
|
|
148
|
+
const status = extractField(header, "status");
|
|
149
|
+
if (status && RUN_STATUS_ALIAS[status]) {
|
|
150
|
+
const next = replaceField(header, "status", RUN_STATUS_ALIAS[status]);
|
|
151
|
+
if (next !== header) {
|
|
152
|
+
changes.push({ field: "status", from: status, to: RUN_STATUS_ALIAS[status] });
|
|
153
|
+
header = next;
|
|
154
|
+
}
|
|
155
|
+
}
|
|
132
156
|
if (!hasField(header, "attempt") && hasField(header, "task")) {
|
|
133
157
|
const next = insertFieldAfter(header, "task", "attempt", "1");
|
|
134
158
|
if (next !== header) {
|
|
@@ -161,6 +185,16 @@ function analyze(scrumDir) {
|
|
|
161
185
|
const plan = planFile(file, "feature", ctx);
|
|
162
186
|
if (plan && plan.changes.length) entries.push(plan);
|
|
163
187
|
}
|
|
188
|
+
for (const file of listDir(path.join(scrumDir, "sprints"), SPRINT_FILE)) {
|
|
189
|
+
const plan = planFile(file, "sprint", ctx);
|
|
190
|
+
if (plan && plan.changes.length) entries.push(plan);
|
|
191
|
+
}
|
|
192
|
+
for (const subdir of ["memory", "memory/knowledge", "memory/decisions", "memory/insights", "memory/dossiers"]) {
|
|
193
|
+
for (const file of listDir(path.join(scrumDir, subdir), MEMORY_FILE)) {
|
|
194
|
+
const plan = planFile(file, "memory", ctx);
|
|
195
|
+
if (plan && plan.changes.length) entries.push(plan);
|
|
196
|
+
}
|
|
197
|
+
}
|
|
164
198
|
|
|
165
199
|
const totals = { files: entries.length, byField: {} };
|
|
166
200
|
for (const entry of entries) {
|