// allow-test-rule: source-text-is-the-product — workflow markdown is the runtime contract. 'use strict'; const { describe, test } = require('node:test'); const assert = require('node:assert/strict'); const fs = require('node:fs'); const path = require('node:path'); const root = path.join(__dirname, '..'); const workflow = fs.readFileSync(path.join(root, 'msd-core/workflows/plan-phase.md'), 'utf8'); const recovery = fs.readFileSync(path.join(root, 'msd-core/workflows/plan-phase/steps/agent-recovery-and-timing.md'), 'utf8'); describe('plan-phase agent recovery and timing', () => { test('classifies quota failures and forbids immediate retry', () => { assert.match(recovery, /agent\.classify-failure/); assert.match(recovery, /class is `quota-exceeded`/); assert.match(recovery, /Never offer or perform an immediate retry/); }); test('stops stale planning after execution starts', () => { assert.match(recovery, /PLAN_PHASE_BASELINE_SUMMARIES/); assert.match(recovery, /summary_count/); assert.match(recovery, /find-phase "\$\{phase_number\}"/); assert.match(recovery, /stop this stale planning run immediately/); }); test('times all three agent stages and quota exits', () => { for (const stage of ['planner', 'checker', 'revision']) assert.match(workflow, new RegExp(`msd_plan_stage_start ${stage}`)); assert.match(recovery, /msd_plan_stage_end quota-exceeded/); assert.match(recovery, /plan-phase total/); }); test('existing plans resume directly at verification', () => { assert.match(workflow, /Verify existing plans[\s\S]{0,160}proceed to step 10/); assert.doesNotMatch(workflow, /find-phase "\$\{PHASE_NUMBER\}"/); }); });