@magnusekdahl/parallix 1.2.1 → 1.3.1
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/index.js +190 -185
- package/lib/agents/agents.js +34 -4
- package/lib/agents/agents.ts +40 -5
- package/lib/commands/active.js +502 -579
- package/lib/commands/active.ts +665 -0
- package/lib/commands/checkpoint.js +98 -74
- package/lib/commands/checkpoint.ts +79 -0
- package/lib/commands/config.js +61 -31
- package/lib/commands/config.ts +47 -0
- package/lib/commands/coverage-gate.js +271 -246
- package/lib/commands/coverage-gate.ts +362 -0
- package/lib/commands/diff.js +140 -119
- package/lib/commands/diff.ts +125 -0
- package/lib/commands/draft.js +770 -923
- package/lib/commands/draft.ts +1021 -0
- package/lib/commands/handoff.js +588 -608
- package/lib/commands/handoff.ts +694 -0
- package/lib/commands/integrate.js +1331 -1468
- package/lib/commands/integrate.ts +1688 -0
- package/lib/commands/mission-start.js +279 -237
- package/lib/commands/mission-start.ts +263 -0
- package/lib/commands/rebase.js +606 -582
- package/lib/commands/rebase.ts +635 -0
- package/lib/commands/repair-handoff.js +181 -179
- package/lib/commands/repair-handoff.ts +228 -0
- package/lib/commands/resolve-conflict.js +121 -102
- package/lib/commands/resolve-conflict.ts +112 -0
- package/lib/commands/review.js +3 -4
- package/lib/commands/review.ts +14 -0
- package/lib/commands/setup-review.js +4 -5
- package/lib/commands/setup-review.ts +14 -0
- package/lib/commands/setup.js +3 -3
- package/lib/commands/setup.ts +2 -0
- package/lib/commands/stats-backfill.js +394 -359
- package/lib/commands/stats-backfill.ts +418 -0
- package/lib/commands/stats.js +1424 -1665
- package/lib/commands/stats.ts +2186 -0
- package/lib/commands/status.js +219 -200
- package/lib/commands/status.ts +219 -0
- package/lib/commands/verify.js +3 -1
- package/lib/commands/verify.ts +2 -0
- package/lib/core/nels.js +112 -127
- package/lib/core/nels.ts +189 -0
- package/lib/core/subagent-limit.js +15 -16
- package/lib/core/subagent-limit.ts +25 -0
- package/lib/index.js +142 -59
- package/lib/index.ts +134 -0
- package/lib/review/rebase.js +142 -145
- package/lib/review/rebase.ts +188 -0
- package/lib/review/review-adapter.js +99 -87
- package/lib/review/review-adapter.ts +198 -0
- package/lib/review/review-artifacts.js +486 -629
- package/lib/review/review-artifacts.ts +622 -0
- package/lib/review/review-commands.js +1220 -1373
- package/lib/review/review-commands.ts +1579 -0
- package/lib/review/review-events.js +544 -886
- package/lib/review/review-events.ts +954 -0
- package/lib/review/review-loop.js +945 -1020
- package/lib/review/review-loop.ts +1174 -0
- package/lib/review/review-polling.js +86 -115
- package/lib/review/review-polling.ts +194 -0
- package/lib/review/review-prompts.js +154 -189
- package/lib/review/review-prompts.ts +182 -0
- package/lib/review/review-state.js +246 -225
- package/lib/review/review-state.ts +353 -0
- package/lib/review/review.js +63 -84
- package/lib/review/review.ts +138 -0
- package/lib/tools/backlog.js +694 -680
- package/lib/tools/backlog.ts +835 -0
- package/lib/tools/forgejo.js +1270 -1405
- package/lib/tools/forgejo.ts +1793 -0
- package/lib/tools/gatekeeper.js +106 -96
- package/lib/tools/gatekeeper.ts +124 -0
- package/lib/tools/redgreen.js +200 -181
- package/lib/tools/redgreen.ts +221 -0
- package/lib/tools/sessions.js +58 -52
- package/lib/tools/sessions.ts +81 -0
- package/lib/tools/setup-review.js +902 -975
- package/lib/tools/setup-review.ts +1152 -0
- package/package.json +4 -4
- package/px.js +226 -208
|
@@ -0,0 +1,353 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Reviewer-family persistence for the autonomous review loop.
|
|
3
|
+
*
|
|
4
|
+
* State is stored under the adapter-resolved mission directory on the mission branch.
|
|
5
|
+
* Writing and committing state before each round ensures session-restart safety.
|
|
6
|
+
*
|
|
7
|
+
* Owned by the Node workflow harness (ADR 0037 / task-089).
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
import * as fs from 'fs';
|
|
11
|
+
import * as path from 'path';
|
|
12
|
+
import { git } from '../core/git.js';
|
|
13
|
+
import { findMissionDir, resolveWorktree } from '../core/mission-utils.js';
|
|
14
|
+
import { log } from '../core/fmt.js';
|
|
15
|
+
|
|
16
|
+
/**
|
|
17
|
+
* Return the path to the review-state file for a given slug.
|
|
18
|
+
* Resolves using the same mission-dir discovery as other workflow commands.
|
|
19
|
+
*
|
|
20
|
+
* @param {string} slug
|
|
21
|
+
* @param {string} [rootDir]
|
|
22
|
+
* @returns {string|null} Absolute path, or null if mission dir not found
|
|
23
|
+
*/
|
|
24
|
+
export function reviewStateFile(slug: string, rootDir = process.cwd()): string | null {
|
|
25
|
+
const missionDir = findMissionDir(slug, rootDir);
|
|
26
|
+
if (!missionDir) { return null; }
|
|
27
|
+
return path.join(missionDir, 'review-state.json');
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
/**
|
|
31
|
+
* Read the persisted review state for a mission.
|
|
32
|
+
*
|
|
33
|
+
* @param {string} slug
|
|
34
|
+
* @param {string} [rootDir] Directory to resolve the mission from (defaults to process.cwd())
|
|
35
|
+
* @returns {ReviewState|null}
|
|
36
|
+
*/
|
|
37
|
+
export function readReviewState(slug: string, rootDir = process.cwd()): ReviewState | null {
|
|
38
|
+
const statePath = reviewStateFile(slug, rootDir);
|
|
39
|
+
if (!statePath || !fs.existsSync(statePath)) { return null; }
|
|
40
|
+
|
|
41
|
+
try {
|
|
42
|
+
const raw = fs.readFileSync(statePath, 'utf8');
|
|
43
|
+
const parsed = JSON.parse(raw);
|
|
44
|
+
if (parsed && parsed.reviewer && parsed.implementer) {
|
|
45
|
+
return new ReviewState(slug, parsed);
|
|
46
|
+
}
|
|
47
|
+
return null;
|
|
48
|
+
} catch {
|
|
49
|
+
return null;
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
/**
|
|
54
|
+
* Resolve the review-provider identity for a review workflow path.
|
|
55
|
+
*
|
|
56
|
+
* The normal contract is review-state-backed so standard review/handoff/rebase
|
|
57
|
+
* paths do not require a provider identity env var to be exported.
|
|
58
|
+
*
|
|
59
|
+
* @param {string} slug
|
|
60
|
+
* @param {string} [rootDir]
|
|
61
|
+
* @param {{readReviewStateFn?: Function}} [options]
|
|
62
|
+
* @returns {{ identityUser: string|null, commentIdentityUser: string|null, forgejoUser: string|null, commentForgejoUser: string|null, reviewState: ReviewState|null, source: 'review-state'|null }}
|
|
63
|
+
*/
|
|
64
|
+
export function resolveReviewIdentity(
|
|
65
|
+
slug: string,
|
|
66
|
+
rootDir = process.cwd(),
|
|
67
|
+
options: { readReviewStateFn?: (s: string, r: string) => ReviewState | null } = {}
|
|
68
|
+
): {
|
|
69
|
+
identityUser: string | null;
|
|
70
|
+
commentIdentityUser: string | null;
|
|
71
|
+
forgejoUser: string | null;
|
|
72
|
+
commentForgejoUser: string | null;
|
|
73
|
+
reviewState: ReviewState | null;
|
|
74
|
+
source: 'review-state' | null;
|
|
75
|
+
} {
|
|
76
|
+
const readReviewStateFn = options.readReviewStateFn || readReviewState;
|
|
77
|
+
const reviewState = readReviewStateFn(slug, rootDir);
|
|
78
|
+
const reviewerUser = reviewState ? (reviewState.reviewer || reviewState.implementer || null) : null;
|
|
79
|
+
const implementerUser = reviewState ? (reviewState.implementer || reviewState.reviewer || null) : null;
|
|
80
|
+
|
|
81
|
+
return {
|
|
82
|
+
identityUser: reviewerUser || null,
|
|
83
|
+
commentIdentityUser: implementerUser || null,
|
|
84
|
+
forgejoUser: reviewerUser || null,
|
|
85
|
+
commentForgejoUser: implementerUser || null,
|
|
86
|
+
reviewState,
|
|
87
|
+
source: reviewerUser ? 'review-state' : null
|
|
88
|
+
};
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
/**
|
|
92
|
+
* Manager class for mission review state.
|
|
93
|
+
* Expanded to include phase, disposition, and metadata for canonical state ownership.
|
|
94
|
+
*/
|
|
95
|
+
export const VALID_PHASES = ['reviewing', 'fixing', 'pending-approval', 'approved'] as const;
|
|
96
|
+
const PHASE_ALIASES = new Map<string, string>([
|
|
97
|
+
['review', 'reviewing'],
|
|
98
|
+
['rewiewing', 'reviewing'],
|
|
99
|
+
['fix', 'fixing'],
|
|
100
|
+
['pending_approval', 'pending-approval'],
|
|
101
|
+
['pending approval', 'pending-approval']
|
|
102
|
+
]);
|
|
103
|
+
|
|
104
|
+
const PHASE_TRANSITIONS: Record<string, string[]> = {
|
|
105
|
+
'reviewing': ['fixing', 'approved'],
|
|
106
|
+
'fixing': ['reviewing', 'pending-approval'],
|
|
107
|
+
'pending-approval': ['reviewing'],
|
|
108
|
+
'approved': []
|
|
109
|
+
};
|
|
110
|
+
|
|
111
|
+
/** @param {string} disposition */
|
|
112
|
+
function inferPhaseFromDisposition(disposition: string): string {
|
|
113
|
+
switch (String(disposition || '').trim().toUpperCase()) {
|
|
114
|
+
case 'APPROVED':
|
|
115
|
+
return 'approved';
|
|
116
|
+
case 'REQUEST_CHANGES':
|
|
117
|
+
case 'COMMENT':
|
|
118
|
+
case 'PUSHBACK_ALL':
|
|
119
|
+
case 'BLOCKED':
|
|
120
|
+
case 'PARKED':
|
|
121
|
+
return 'fixing';
|
|
122
|
+
case 'CHANGES_MADE':
|
|
123
|
+
return 'reviewing';
|
|
124
|
+
default:
|
|
125
|
+
return 'reviewing';
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
/** @param {string} phase @param {string} disposition */
|
|
130
|
+
export function normalizeReviewPhase(phase: string, disposition: string): { phase: string; original: string | null; normalized: boolean } {
|
|
131
|
+
if (!phase) {
|
|
132
|
+
return { phase: 'reviewing', original: null, normalized: false };
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
const raw = String(phase).trim();
|
|
136
|
+
const canonical = raw.toLowerCase().replace(/[_\s]+/g, '-');
|
|
137
|
+
if ((VALID_PHASES as readonly string[]).includes(canonical)) {
|
|
138
|
+
return { phase: canonical, original: raw, normalized: canonical !== raw };
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
const alias = PHASE_ALIASES.get(raw.toLowerCase()) || PHASE_ALIASES.get(canonical);
|
|
142
|
+
if (alias) {
|
|
143
|
+
return { phase: alias, original: raw, normalized: true };
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
return {
|
|
147
|
+
phase: inferPhaseFromDisposition(disposition),
|
|
148
|
+
original: raw,
|
|
149
|
+
normalized: true
|
|
150
|
+
};
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
/** @typedef {{reviewer?: string, implementer?: string, round?: number, startedAt?: string, phase?: string, disposition?: string | null, reviewerRetryCount?: number, implementerRetryCount?: number, metadata?: {[key: string]: unknown}}} ReviewStateData */
|
|
154
|
+
export interface ReviewStateData {
|
|
155
|
+
reviewer?: string;
|
|
156
|
+
implementer?: string;
|
|
157
|
+
round?: number;
|
|
158
|
+
startedAt?: string;
|
|
159
|
+
phase?: string;
|
|
160
|
+
disposition?: string | null;
|
|
161
|
+
reviewerRetryCount?: number;
|
|
162
|
+
implementerRetryCount?: number;
|
|
163
|
+
metadata?: Record<string, unknown>;
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
export class ReviewState {
|
|
167
|
+
slug: string;
|
|
168
|
+
reviewer?: string;
|
|
169
|
+
implementer?: string;
|
|
170
|
+
round: number;
|
|
171
|
+
startedAt: string;
|
|
172
|
+
phase: string;
|
|
173
|
+
disposition: string | null;
|
|
174
|
+
reviewerRetryCount: number;
|
|
175
|
+
implementerRetryCount: number;
|
|
176
|
+
metadata: Record<string, unknown>;
|
|
177
|
+
phaseOriginal: string | null;
|
|
178
|
+
|
|
179
|
+
/**
|
|
180
|
+
* @param {string} slug
|
|
181
|
+
* @param {ReviewStateData} [data]
|
|
182
|
+
*/
|
|
183
|
+
constructor(slug: string, data: ReviewStateData = {}) {
|
|
184
|
+
const phaseInfo = normalizeReviewPhase(data.phase || '', data.disposition || '');
|
|
185
|
+
this.slug = slug;
|
|
186
|
+
this.reviewer = data.reviewer;
|
|
187
|
+
this.implementer = data.implementer;
|
|
188
|
+
this.round = data.round || 1;
|
|
189
|
+
this.startedAt = data.startedAt || new Date().toISOString();
|
|
190
|
+
this.phase = phaseInfo.phase;
|
|
191
|
+
this.disposition = data.disposition || null;
|
|
192
|
+
this.reviewerRetryCount = data.reviewerRetryCount || 0;
|
|
193
|
+
this.implementerRetryCount = data.implementerRetryCount || 0;
|
|
194
|
+
this.metadata = data.metadata || {};
|
|
195
|
+
this.phaseOriginal = phaseInfo.normalized ? phaseInfo.original : null;
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
/**
|
|
199
|
+
* @param {string} slug
|
|
200
|
+
* @param {ReviewState|ReviewStateData} dataOrInstance
|
|
201
|
+
* @returns {ReviewState}
|
|
202
|
+
*/
|
|
203
|
+
static from(slug: string, dataOrInstance: ReviewState | ReviewStateData): ReviewState {
|
|
204
|
+
if (dataOrInstance instanceof ReviewState) {
|
|
205
|
+
if (dataOrInstance.slug !== slug) {
|
|
206
|
+
throw new Error(`ReviewState slug mismatch: expected "${slug}", got "${dataOrInstance.slug}"`);
|
|
207
|
+
}
|
|
208
|
+
return dataOrInstance;
|
|
209
|
+
}
|
|
210
|
+
return new ReviewState(slug, dataOrInstance || {});
|
|
211
|
+
}
|
|
212
|
+
|
|
213
|
+
/**
|
|
214
|
+
* @param {string} nextPhase
|
|
215
|
+
* @returns {ReviewState}
|
|
216
|
+
*/
|
|
217
|
+
transitionTo(nextPhase: string): ReviewState {
|
|
218
|
+
if (!(VALID_PHASES as readonly string[]).includes(nextPhase)) {
|
|
219
|
+
throw new Error(`Invalid phase: "${nextPhase}". Valid: ${(VALID_PHASES as readonly string[]).join(', ')}`);
|
|
220
|
+
}
|
|
221
|
+
const allowedArr = PHASE_TRANSITIONS[this.phase];
|
|
222
|
+
if (!allowedArr || !allowedArr.includes(nextPhase)) {
|
|
223
|
+
throw new Error(`Cannot transition from "${this.phase}" to "${nextPhase}". Allowed: ${(allowedArr || []).join(', ') || 'none'}`);
|
|
224
|
+
}
|
|
225
|
+
this.phase = nextPhase;
|
|
226
|
+
return this;
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
advanceRound(): ReviewState {
|
|
230
|
+
this.round += 1;
|
|
231
|
+
this.phase = 'reviewing';
|
|
232
|
+
this.disposition = null;
|
|
233
|
+
this.reviewerRetryCount = 0;
|
|
234
|
+
this.implementerRetryCount = 0;
|
|
235
|
+
this.startedAt = new Date().toISOString();
|
|
236
|
+
return this;
|
|
237
|
+
}
|
|
238
|
+
|
|
239
|
+
/**
|
|
240
|
+
* @returns {{reviewer?: string, implementer?: string, round?: number, startedAt?: string, phase?: string, disposition?: string, reviewerRetryCount?: number, implementerRetryCount?: number, metadata?: {[key: string]: unknown}}}
|
|
241
|
+
*/
|
|
242
|
+
toJSON(): {
|
|
243
|
+
reviewer?: string;
|
|
244
|
+
implementer?: string;
|
|
245
|
+
round?: number;
|
|
246
|
+
startedAt?: string;
|
|
247
|
+
phase?: string;
|
|
248
|
+
disposition?: string;
|
|
249
|
+
reviewerRetryCount?: number;
|
|
250
|
+
implementerRetryCount?: number;
|
|
251
|
+
metadata?: Record<string, unknown>;
|
|
252
|
+
} {
|
|
253
|
+
const payload: {
|
|
254
|
+
reviewer?: string;
|
|
255
|
+
implementer?: string;
|
|
256
|
+
round?: number;
|
|
257
|
+
startedAt?: string;
|
|
258
|
+
phase?: string;
|
|
259
|
+
disposition?: string;
|
|
260
|
+
reviewerRetryCount?: number;
|
|
261
|
+
implementerRetryCount?: number;
|
|
262
|
+
metadata?: Record<string, unknown>;
|
|
263
|
+
} = {
|
|
264
|
+
reviewer: this.reviewer,
|
|
265
|
+
implementer: this.implementer,
|
|
266
|
+
round: this.round,
|
|
267
|
+
startedAt: this.startedAt,
|
|
268
|
+
phase: this.phase,
|
|
269
|
+
disposition: this.disposition || undefined
|
|
270
|
+
};
|
|
271
|
+
|
|
272
|
+
if (this.reviewerRetryCount > 0) { payload.reviewerRetryCount = this.reviewerRetryCount; }
|
|
273
|
+
if (this.implementerRetryCount > 0) { payload.implementerRetryCount = this.implementerRetryCount; }
|
|
274
|
+
if (Object.keys(this.metadata || {}).length > 0) { payload.metadata = this.metadata; }
|
|
275
|
+
|
|
276
|
+
return payload;
|
|
277
|
+
}
|
|
278
|
+
|
|
279
|
+
save(
|
|
280
|
+
worktree = resolveWorktree(this.slug) || process.cwd(),
|
|
281
|
+
gitFn = git
|
|
282
|
+
): boolean {
|
|
283
|
+
const statePath = reviewStateFile(this.slug, worktree);
|
|
284
|
+
if (!statePath) { return false; }
|
|
285
|
+
|
|
286
|
+
const payload = this.toJSON();
|
|
287
|
+
fs.writeFileSync(statePath, JSON.stringify(payload, null, 2) + '\n', 'utf8');
|
|
288
|
+
|
|
289
|
+
const relPath = path.relative(worktree, statePath);
|
|
290
|
+
const result = gitFn(['-C', worktree, 'add', relPath]);
|
|
291
|
+
const msg = `review-state(${this.slug}): round ${this.round} (${this.phase}) [${this.reviewer} -> ${this.implementer}]${this.disposition ? ` disposition=${this.disposition}` : ''}`;
|
|
292
|
+
const commitResult = gitFn(['-C', worktree, 'commit', '-m', msg]);
|
|
293
|
+
|
|
294
|
+
if (commitResult.status !== 0) {
|
|
295
|
+
const statusResult = gitFn(['-C', worktree, 'status', '--porcelain', relPath]);
|
|
296
|
+
if (statusResult.stdout.trim() === '') {
|
|
297
|
+
return true;
|
|
298
|
+
}
|
|
299
|
+
log.warn(`Failed to commit review state update: ${commitResult.stderr}`);
|
|
300
|
+
}
|
|
301
|
+
|
|
302
|
+
return true;
|
|
303
|
+
}
|
|
304
|
+
}
|
|
305
|
+
|
|
306
|
+
/**
|
|
307
|
+
* Write and commit the review state for a mission.
|
|
308
|
+
* Commits to the current branch so the state is visible after session restarts.
|
|
309
|
+
*
|
|
310
|
+
* @param {string} slug
|
|
311
|
+
* @param {ReviewState|object} state
|
|
312
|
+
* @returns {boolean} true if written successfully
|
|
313
|
+
*/
|
|
314
|
+
export function writeReviewState(
|
|
315
|
+
slug: string,
|
|
316
|
+
state: ReviewState | Record<string, unknown>,
|
|
317
|
+
worktree = resolveWorktree(slug) || process.cwd(),
|
|
318
|
+
gitFn = git
|
|
319
|
+
): boolean {
|
|
320
|
+
const instance = state instanceof ReviewState ? state : new ReviewState(slug, state as ReviewStateData);
|
|
321
|
+
return instance.save(worktree, gitFn);
|
|
322
|
+
}
|
|
323
|
+
|
|
324
|
+
/**
|
|
325
|
+
* Delete the review state file for a mission (used by --reset).
|
|
326
|
+
* Commits the deletion if the file was tracked.
|
|
327
|
+
*
|
|
328
|
+
* @param {string} slug
|
|
329
|
+
* @returns {boolean} true if a file was deleted
|
|
330
|
+
*/
|
|
331
|
+
export function resetReviewState(
|
|
332
|
+
slug: string,
|
|
333
|
+
worktree = resolveWorktree(slug) || process.cwd(),
|
|
334
|
+
gitFn = git
|
|
335
|
+
): boolean {
|
|
336
|
+
const statePath = reviewStateFile(slug, worktree);
|
|
337
|
+
if (!statePath || !fs.existsSync(statePath)) { return false; }
|
|
338
|
+
|
|
339
|
+
fs.unlinkSync(statePath);
|
|
340
|
+
|
|
341
|
+
const relPath = path.relative(worktree, statePath);
|
|
342
|
+
try {
|
|
343
|
+
gitFn(['-C', worktree, 'rm', '--cached', relPath]);
|
|
344
|
+
const result = gitFn(['-C', worktree, 'commit', '-m', `review-state(${slug}): reset (--reset flag)`]);
|
|
345
|
+
if (result.status !== 0) {
|
|
346
|
+
log.warn(`Failed to commit review state reset: ${result.stderr}`);
|
|
347
|
+
}
|
|
348
|
+
} catch {
|
|
349
|
+
// file may not have been tracked yet
|
|
350
|
+
}
|
|
351
|
+
|
|
352
|
+
return true;
|
|
353
|
+
}
|
package/lib/review/review.js
CHANGED
|
@@ -1,97 +1,76 @@
|
|
|
1
|
+
"use strict";
|
|
1
2
|
/**
|
|
2
3
|
* Review Module - Main Entry Point
|
|
3
4
|
* Refactored for task-1201: complexity reduction via service extraction
|
|
4
|
-
*
|
|
5
|
+
*
|
|
5
6
|
* This file now serves as a re-export hub for the extracted sub-modules:
|
|
6
|
-
* - review-commands.
|
|
7
|
-
* - review-loop.
|
|
8
|
-
* - review-artifacts.
|
|
9
|
-
* - review-polling.
|
|
7
|
+
* - review-commands.ts (command dispatcher and CLI handlers)
|
|
8
|
+
* - review-loop.ts (autonomous review loop orchestration)
|
|
9
|
+
* - review-artifacts.ts (artifact handling and posting)
|
|
10
|
+
* - review-polling.ts (polling utilities)
|
|
10
11
|
*/
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
//
|
|
16
|
-
const
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
// Re-export from review-commands module
|
|
22
|
-
const {
|
|
23
|
-
flagValue,
|
|
24
|
-
readTextFlag,
|
|
25
|
-
formatStaticReviewFindings,
|
|
26
|
-
formatStaticReviewSuccess,
|
|
27
|
-
postStaticReviewComment,
|
|
28
|
-
performStaticReview,
|
|
29
|
-
verifyReview,
|
|
30
|
-
submitForReview,
|
|
31
|
-
readComments,
|
|
32
|
-
pushRound,
|
|
33
|
-
showReviewStatus,
|
|
34
|
-
commentRound,
|
|
35
|
-
submitReviewRound,
|
|
36
|
-
closeMissionPr,
|
|
37
|
-
createEventHandler,
|
|
38
|
-
importLegacyHandler,
|
|
39
|
-
review
|
|
40
|
-
} = require('./review-commands');
|
|
41
|
-
|
|
12
|
+
// Import from review-polling module
|
|
13
|
+
const review_polling_js_1 = require("./review-polling.js");
|
|
14
|
+
// Import from review-artifacts module
|
|
15
|
+
const review_artifacts_js_1 = require("./review-artifacts.js");
|
|
16
|
+
// Import from review-loop module
|
|
17
|
+
const review_loop_js_1 = require("./review-loop.js");
|
|
18
|
+
// Import from review-commands module
|
|
19
|
+
const review_commands_js_1 = require("./review-commands.js");
|
|
20
|
+
// Import from review-state module
|
|
21
|
+
const review_state_js_1 = require("./review-state.js");
|
|
42
22
|
// ============================================================================
|
|
43
23
|
// Module Exports
|
|
44
24
|
// ============================================================================
|
|
45
|
-
// Set module
|
|
25
|
+
// Set the module exports to the main review function (for backward compatibility)
|
|
46
26
|
// then add all other exports as properties
|
|
47
|
-
|
|
48
|
-
module.exports = review;
|
|
49
|
-
|
|
27
|
+
const _review = review_commands_js_1.review;
|
|
50
28
|
// From review-polling
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
29
|
+
_review.POLL_TIMEOUT = review_polling_js_1.POLL_TIMEOUT;
|
|
30
|
+
_review.delay = review_polling_js_1.delay;
|
|
31
|
+
_review.resolvePollIntervalMs = review_polling_js_1.resolvePollIntervalMs;
|
|
32
|
+
_review.resolvePollTimeoutMs = review_polling_js_1.resolvePollTimeoutMs;
|
|
33
|
+
_review.formatElapsed = review_polling_js_1.formatElapsed;
|
|
34
|
+
_review.isPollTimeout = review_polling_js_1.isPollTimeout;
|
|
35
|
+
_review.pollForReview = review_polling_js_1.pollForReview;
|
|
36
|
+
_review.pollForDisposition = review_polling_js_1.pollForDisposition;
|
|
60
37
|
// From review-artifacts
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
38
|
+
_review.buildMetadataFooter = review_artifacts_js_1.buildMetadataFooter;
|
|
39
|
+
_review.reviewArtifactPath = review_artifacts_js_1.reviewArtifactPath;
|
|
40
|
+
_review.readArtifactFile = review_artifacts_js_1.readArtifactFile;
|
|
41
|
+
_review.deleteArtifactFile = review_artifacts_js_1.deleteArtifactFile;
|
|
42
|
+
_review.normalizeReviewVerdict = review_artifacts_js_1.normalizeReviewVerdict;
|
|
43
|
+
_review.normalizeDisposition = review_artifacts_js_1.normalizeDisposition;
|
|
44
|
+
_review.postWorkflowComment = review_artifacts_js_1.postWorkflowComment;
|
|
45
|
+
_review.postWorkflowReview = review_artifacts_js_1.postWorkflowReview;
|
|
46
|
+
_review.consumeReviewerArtifacts = review_artifacts_js_1.consumeReviewerArtifacts;
|
|
47
|
+
_review.consumeImplementerArtifacts = review_artifacts_js_1.consumeImplementerArtifacts;
|
|
72
48
|
// From review-loop
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
49
|
+
_review.recordStageStatsSafe = review_loop_js_1.recordStageStatsSafe;
|
|
50
|
+
_review.maybeUpdateGraphifyBeforeReview = review_loop_js_1.maybeUpdateGraphifyBeforeReview;
|
|
51
|
+
_review.commitSafeMissionArtifacts = review_loop_js_1.commitSafeMissionArtifacts;
|
|
52
|
+
_review.rebaseBeforeReviewRound = review_loop_js_1.rebaseBeforeReviewRound;
|
|
53
|
+
_review.applyAgentFallback = review_loop_js_1.applyAgentFallback;
|
|
54
|
+
_review.persistNormalizedPhaseRepair = review_loop_js_1.persistNormalizedPhaseRepair;
|
|
55
|
+
_review.startReviewLoop = review_loop_js_1.startReviewLoop;
|
|
81
56
|
// From review-commands
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
57
|
+
_review.flagValue = review_commands_js_1.flagValue;
|
|
58
|
+
_review.readTextFlag = review_commands_js_1.readTextFlag;
|
|
59
|
+
_review.formatStaticReviewFindings = review_commands_js_1.formatStaticReviewFindings;
|
|
60
|
+
_review.formatStaticReviewSuccess = review_commands_js_1.formatStaticReviewSuccess;
|
|
61
|
+
_review.postStaticReviewComment = review_commands_js_1.postStaticReviewComment;
|
|
62
|
+
_review.performStaticReview = review_commands_js_1.performStaticReview;
|
|
63
|
+
_review.verifyReview = review_commands_js_1.verifyReview;
|
|
64
|
+
_review.submitForReview = review_commands_js_1.submitForReview;
|
|
65
|
+
_review.readComments = review_commands_js_1.readComments;
|
|
66
|
+
_review.pushRound = review_commands_js_1.pushRound;
|
|
67
|
+
_review.showReviewStatus = review_commands_js_1.showReviewStatus;
|
|
68
|
+
_review.commentRound = review_commands_js_1.commentRound;
|
|
69
|
+
_review.submitReviewRound = review_commands_js_1.submitReviewRound;
|
|
70
|
+
_review.closeMissionPr = review_commands_js_1.closeMissionPr;
|
|
71
|
+
_review.createEventHandler = review_commands_js_1.createEventHandler;
|
|
72
|
+
_review.importLegacyHandler = review_commands_js_1.importLegacyHandler;
|
|
73
|
+
// From review-state
|
|
74
|
+
_review.reviewStateFile = review_state_js_1.reviewStateFile;
|
|
75
|
+
_review.ReviewState = review_state_js_1.ReviewState;
|
|
76
|
+
module.exports = _review;
|
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Review Module - Main Entry Point
|
|
3
|
+
* Refactored for task-1201: complexity reduction via service extraction
|
|
4
|
+
*
|
|
5
|
+
* This file now serves as a re-export hub for the extracted sub-modules:
|
|
6
|
+
* - review-commands.ts (command dispatcher and CLI handlers)
|
|
7
|
+
* - review-loop.ts (autonomous review loop orchestration)
|
|
8
|
+
* - review-artifacts.ts (artifact handling and posting)
|
|
9
|
+
* - review-polling.ts (polling utilities)
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
// Import from review-polling module
|
|
13
|
+
import {
|
|
14
|
+
POLL_TIMEOUT,
|
|
15
|
+
delay,
|
|
16
|
+
resolvePollIntervalMs,
|
|
17
|
+
resolvePollTimeoutMs,
|
|
18
|
+
formatElapsed,
|
|
19
|
+
isPollTimeout,
|
|
20
|
+
pollForReview,
|
|
21
|
+
pollForDisposition
|
|
22
|
+
} from './review-polling.js';
|
|
23
|
+
|
|
24
|
+
// Import from review-artifacts module
|
|
25
|
+
import {
|
|
26
|
+
buildMetadataFooter,
|
|
27
|
+
reviewArtifactPath,
|
|
28
|
+
readArtifactFile,
|
|
29
|
+
deleteArtifactFile,
|
|
30
|
+
normalizeReviewVerdict,
|
|
31
|
+
normalizeDisposition,
|
|
32
|
+
postWorkflowComment,
|
|
33
|
+
postWorkflowReview,
|
|
34
|
+
consumeReviewerArtifacts,
|
|
35
|
+
consumeImplementerArtifacts
|
|
36
|
+
} from './review-artifacts.js';
|
|
37
|
+
|
|
38
|
+
// Import from review-loop module
|
|
39
|
+
import {
|
|
40
|
+
maybeUpdateGraphifyBeforeReview,
|
|
41
|
+
commitSafeMissionArtifacts,
|
|
42
|
+
rebaseBeforeReviewRound,
|
|
43
|
+
applyAgentFallback,
|
|
44
|
+
persistNormalizedPhaseRepair,
|
|
45
|
+
startReviewLoop,
|
|
46
|
+
recordStageStatsSafe
|
|
47
|
+
} from './review-loop.js';
|
|
48
|
+
|
|
49
|
+
// Import from review-commands module
|
|
50
|
+
import {
|
|
51
|
+
flagValue,
|
|
52
|
+
readTextFlag,
|
|
53
|
+
formatStaticReviewFindings,
|
|
54
|
+
formatStaticReviewSuccess,
|
|
55
|
+
postStaticReviewComment,
|
|
56
|
+
performStaticReview,
|
|
57
|
+
verifyReview,
|
|
58
|
+
submitForReview,
|
|
59
|
+
readComments,
|
|
60
|
+
pushRound,
|
|
61
|
+
showReviewStatus,
|
|
62
|
+
commentRound,
|
|
63
|
+
submitReviewRound,
|
|
64
|
+
closeMissionPr,
|
|
65
|
+
createEventHandler,
|
|
66
|
+
importLegacyHandler,
|
|
67
|
+
review
|
|
68
|
+
} from './review-commands.js';
|
|
69
|
+
|
|
70
|
+
// Import from review-state module
|
|
71
|
+
import {
|
|
72
|
+
reviewStateFile,
|
|
73
|
+
ReviewState
|
|
74
|
+
} from './review-state.js';
|
|
75
|
+
|
|
76
|
+
// ============================================================================
|
|
77
|
+
// Module Exports
|
|
78
|
+
// ============================================================================
|
|
79
|
+
// Set the module exports to the main review function (for backward compatibility)
|
|
80
|
+
// then add all other exports as properties
|
|
81
|
+
|
|
82
|
+
const _review = review as any;
|
|
83
|
+
|
|
84
|
+
// From review-polling
|
|
85
|
+
_review.POLL_TIMEOUT = POLL_TIMEOUT;
|
|
86
|
+
_review.delay = delay;
|
|
87
|
+
_review.resolvePollIntervalMs = resolvePollIntervalMs;
|
|
88
|
+
_review.resolvePollTimeoutMs = resolvePollTimeoutMs;
|
|
89
|
+
_review.formatElapsed = formatElapsed;
|
|
90
|
+
_review.isPollTimeout = isPollTimeout;
|
|
91
|
+
_review.pollForReview = pollForReview;
|
|
92
|
+
_review.pollForDisposition = pollForDisposition;
|
|
93
|
+
|
|
94
|
+
// From review-artifacts
|
|
95
|
+
_review.buildMetadataFooter = buildMetadataFooter;
|
|
96
|
+
_review.reviewArtifactPath = reviewArtifactPath;
|
|
97
|
+
_review.readArtifactFile = readArtifactFile;
|
|
98
|
+
_review.deleteArtifactFile = deleteArtifactFile;
|
|
99
|
+
_review.normalizeReviewVerdict = normalizeReviewVerdict;
|
|
100
|
+
_review.normalizeDisposition = normalizeDisposition;
|
|
101
|
+
_review.postWorkflowComment = postWorkflowComment;
|
|
102
|
+
_review.postWorkflowReview = postWorkflowReview;
|
|
103
|
+
_review.consumeReviewerArtifacts = consumeReviewerArtifacts;
|
|
104
|
+
_review.consumeImplementerArtifacts = consumeImplementerArtifacts;
|
|
105
|
+
|
|
106
|
+
// From review-loop
|
|
107
|
+
_review.recordStageStatsSafe = recordStageStatsSafe;
|
|
108
|
+
_review.maybeUpdateGraphifyBeforeReview = maybeUpdateGraphifyBeforeReview;
|
|
109
|
+
_review.commitSafeMissionArtifacts = commitSafeMissionArtifacts;
|
|
110
|
+
_review.rebaseBeforeReviewRound = rebaseBeforeReviewRound;
|
|
111
|
+
_review.applyAgentFallback = applyAgentFallback;
|
|
112
|
+
_review.persistNormalizedPhaseRepair = persistNormalizedPhaseRepair;
|
|
113
|
+
_review.startReviewLoop = startReviewLoop;
|
|
114
|
+
|
|
115
|
+
// From review-commands
|
|
116
|
+
_review.flagValue = flagValue;
|
|
117
|
+
_review.readTextFlag = readTextFlag;
|
|
118
|
+
_review.formatStaticReviewFindings = formatStaticReviewFindings;
|
|
119
|
+
_review.formatStaticReviewSuccess = formatStaticReviewSuccess;
|
|
120
|
+
_review.postStaticReviewComment = postStaticReviewComment;
|
|
121
|
+
_review.performStaticReview = performStaticReview;
|
|
122
|
+
_review.verifyReview = verifyReview;
|
|
123
|
+
_review.submitForReview = submitForReview;
|
|
124
|
+
_review.readComments = readComments;
|
|
125
|
+
_review.pushRound = pushRound;
|
|
126
|
+
_review.showReviewStatus = showReviewStatus;
|
|
127
|
+
_review.commentRound = commentRound;
|
|
128
|
+
_review.submitReviewRound = submitReviewRound;
|
|
129
|
+
_review.closeMissionPr = closeMissionPr;
|
|
130
|
+
_review.createEventHandler = createEventHandler;
|
|
131
|
+
_review.importLegacyHandler = importLegacyHandler;
|
|
132
|
+
|
|
133
|
+
// From review-state
|
|
134
|
+
_review.reviewStateFile = reviewStateFile;
|
|
135
|
+
_review.ReviewState = ReviewState;
|
|
136
|
+
|
|
137
|
+
// Export the review function as the module exports (CJS-compatible)
|
|
138
|
+
export = _review;
|