import { test } from 'node:test'
import assert from 'node:assert/strict'
import path from 'node:path'
import { promises as fs } from 'node:fs'
import { determineNextState } from '../../src/state-machine/index.js'
import { stageChapter, rejectFrom } from '../../src/staging/index.js'
import { createGit } from '../../src/finalize/git.js'
import { gitBookCtx } from '../commands/_helper.js'

// 开关矩阵（PRD #14）：自动确认细纲 × 连写。全关=既有回归（router.test.js 全量）；
// 本文件测：单开细纲自动确认的序 6 标志、批次进行中的序 3 明细。全开端到端见 finalize-batch.test.js AC1。

async function reachOutline(ctx) {
  // sample-book 工作区自带细纲 → 会命中序 3，清掉以到达序 6
  await fs.rm(path.join(ctx.repoPath, '工作区', '细纲.md'), { force: true })
}

async function setBookYaml(ctx, key, value) {
  const p = path.join(ctx.repoPath, 'book.yaml')
  const src = await fs.readFile(p, 'utf8')
  const line = `${key}: ${value}`
  const re = new RegExp(`^${key}:.*$`, 'm')
  await fs.writeFile(p, re.test(src) ? src.replace(re, line) : `${src}${line}\n`, 'utf8')
  // book.yaml 在跟踪面内（决策 D6），不补登会被序 2 拦——模拟 relink 已完成
  const git = createGit(ctx.repoPath)
  await git.ensureIdentity()
  await git.add(['book.yaml'])
  await git.commit(`fix(手改): 配置 ${key}`)
}

async function stage3(ctx) {
  await fs.mkdir(path.join(ctx.repoPath, '工作区'), { recursive: true })
  await fs.writeFile(
    path.join(ctx.repoPath, '工作区', '审稿.md'),
    '# 第 3 章审稿单\n\n> 完整两审模式。\n> 共 0 个问题：0 阻断。\n',
    'utf8'
  )
  const r = await stageChapter(ctx, {
    chapterNum: 3,
    payload: {
      frontMatter: {
        章号: 3,
        标题: '连写3',
        卷: 1,
        书内时间: '夏月初三',
        字数: 100,
        章定位: '推进',
        钩子: '危机钩-强',
        情绪定位: '铺垫',
        伏笔: ['推进 伏笔-001'],
      },
      body: '第3章正文。',
      workspaceFiles: [],
    },
  })
  assert.equal(r.ok, true, r.error)
}

test('开关矩阵：全关 → 序 6 dto.自动确认细纲=false，行为与既有一致', async () => {
  const { ctx, cleanup } = await gitBookCtx()
  try {
    await reachOutline(ctx)
    const r = await determineNextState(ctx)
    assert.equal(r.序, 6, JSON.stringify(r))
    assert.equal(r.dto.自动确认细纲, false)
    assert.match(r.dto.期望产物, /作者确认/)
  } finally {
    await cleanup()
  }
})

test('开关矩阵：自动确认细纲开 → 序 6 dto 标志与提案直接生效指引', async () => {
  const { ctx, cleanup } = await gitBookCtx()
  try {
    await reachOutline(ctx)
    await setBookYaml(ctx, '自动确认细纲', 'true')
    const r = await determineNextState(ctx)
    assert.equal(r.序, 6, JSON.stringify(r))
    assert.equal(r.dto.自动确认细纲, true)
    assert.match(r.dto.期望产物, /不再问作者/)
  } finally {
    await cleanup()
  }
})

test('批次进行中：序 3 dto.批次 带章清单与「继续下一章」建议；打回后建议重写', async () => {
  const { ctx, cleanup } = await gitBookCtx()
  try {
    await reachOutline(ctx)
    await stage3(ctx)
    const r = await determineNextState(ctx)
    assert.equal(r.序, 3, JSON.stringify(r))
    assert.equal(r.state, 'resume')
    assert.equal(r.dto.从哪继续, '待定稿批次续跑')
    assert.equal(r.dto.批次.章数, 1)
    assert.deepEqual(r.dto.批次.章, [{ 章号: 3, 标题: '连写3', 状态: '待审收' }])
    assert.match(r.dto.批次.建议, /继续批内下一章（第 4 章）/)

    const rej = await rejectFrom(ctx.repoPath, 3)
    assert.equal(rej.ok, true, rej.error)
    const r2 = await determineNextState(ctx)
    assert.equal(r2.序, 3)
    assert.match(r2.dto.批次.建议, /重写打回章（第 3 章）/)
  } finally {
    await cleanup()
  }
})

test('批次进行中：停止命中（写满）→ 序 3 建议批量过稿', async () => {
  const { ctx, cleanup } = await gitBookCtx()
  try {
    await reachOutline(ctx)
    await setBookYaml(ctx, '连写批次大小', '1')
    await stage3(ctx)
    const r = await determineNextState(ctx)
    assert.equal(r.序, 3, JSON.stringify(r))
    assert.equal(r.dto.批次.停止.stop, true)
    assert.match(r.dto.批次.建议, /批量过稿/)
  } finally {
    await cleanup()
  }
})
