// 裁决纯逻辑：完整性判定（未决禁验收）、accept 请求体组装、缺判高亮映射。
// 对齐 C3 accept 契约 + R5 冲突 gate（裁决 conflict_index 须覆盖 range(len(conflicts))）。

import type { AcceptRequest, ConflictDecision } from "@/lib/api/types";

export type Verdict = "accept" | "ignore" | "manual";

// 单个冲突的本地裁决草稿（按下标定位）。
export interface DecisionDraft {
  verdict: Verdict | null;
  note: string;
}

// 初始化 N 个冲突的裁决草稿（全部未决）。
export function emptyDecisions(conflictCount: number): DecisionDraft[] {
  return Array.from({ length: conflictCount }, () => ({
    verdict: null,
    note: "",
  }));
}

// 不可变更新：设置某个冲突的 verdict。
export function setVerdict(
  drafts: readonly DecisionDraft[],
  index: number,
  verdict: Verdict,
): DecisionDraft[] {
  return drafts.map((d, i) => (i === index ? { ...d, verdict } : d));
}

// 不可变更新：设置某个冲突的 note。
export function setNote(
  drafts: readonly DecisionDraft[],
  index: number,
  note: string,
): DecisionDraft[] {
  return drafts.map((d, i) => (i === index ? { ...d, note } : d));
}

// 是否全部已决：每个冲突都有 verdict（覆盖 range(len(conflicts))）。零冲突 → 直通。
export function allResolved(drafts: readonly DecisionDraft[]): boolean {
  return drafts.every((d) => d.verdict !== null);
}

// 本地仍未决的冲突下标（用于禁用态提示）。
export function unresolvedIndices(drafts: readonly DecisionDraft[]): number[] {
  return drafts.flatMap((d, i) => (d.verdict === null ? [i] : []));
}

// 组装 accept 请求体（仅含已决项；note 去空白后非空才带）。
export function buildAcceptRequest(
  finalText: string,
  drafts: readonly DecisionDraft[],
): AcceptRequest {
  const decisions: ConflictDecision[] = drafts.flatMap((d, i) => {
    if (d.verdict === null) return [];
    const trimmed = d.note.trim();
    const decision: ConflictDecision = {
      conflict_index: i,
      verdict: d.verdict,
    };
    return [trimmed ? { ...decision, note: trimmed } : decision];
  });
  return { final_text: finalText, decisions };
}

// 从 409 CONFLICT_UNRESOLVED 的 details 提取缺判下标集合（用于报告卡高亮）。
export function missingConflictIndices(details: unknown): Set<number> {
  if (typeof details !== "object" || details === null) return new Set();
  const raw = (details as { missing_conflict_indices?: unknown })
    .missing_conflict_indices;
  if (!Array.isArray(raw)) return new Set();
  return new Set(raw.filter((n): n is number => typeof n === "number"));
}
