import {
  log
} from "./chunk-2ODBA7MQ.js";

// src/extraction-judge-training.ts
import path from "path";
import { homedir } from "os";
import { appendFile, mkdir, readFile, readdir } from "fs/promises";
function expandTilde(p) {
  const home = homedir();
  if (p === "~" || p.startsWith("~/") || p.startsWith("~\\")) {
    return home + p.slice(1);
  }
  if (p === "$HOME" || p.startsWith("$HOME/") || p.startsWith("$HOME\\")) {
    return home + p.slice(5);
  }
  if (p === "${HOME}" || p.startsWith("${HOME}/") || p.startsWith("${HOME}\\")) {
    return home + p.slice(7);
  }
  return p;
}
function resolveTrainingDir(options) {
  if (options.directory && options.directory.length > 0) {
    return expandTilde(options.directory);
  }
  return path.join(homedir(), ".remnic", "judge-training");
}
function dateStamp(iso) {
  const ms = Date.parse(iso);
  const d = Number.isFinite(ms) ? new Date(ms) : /* @__PURE__ */ new Date();
  const yyyy = d.getUTCFullYear().toString().padStart(4, "0");
  const mm = (d.getUTCMonth() + 1).toString().padStart(2, "0");
  const dd = d.getUTCDate().toString().padStart(2, "0");
  return `${yyyy}-${mm}-${dd}`;
}
function trainingFilePathFor(directory, iso) {
  return path.join(directory, `${dateStamp(iso)}.jsonl`);
}
async function recordJudgeTrainingPair(row, options) {
  if (!options.enabled) return;
  const dir = resolveTrainingDir(options);
  const filePath = trainingFilePathFor(dir, row.ts);
  try {
    await mkdir(dir, { recursive: true });
    await appendFile(filePath, `${JSON.stringify(row)}
`, "utf-8");
  } catch (err) {
    log.debug(
      `extraction-judge-training: append failed (non-fatal): ${err instanceof Error ? err.message : String(err)}`
    );
  }
}
async function readJudgeTrainingPairs(options) {
  const dir = resolveTrainingDir({ enabled: true, ...options });
  let entries;
  try {
    entries = await readdir(dir);
  } catch (err) {
    const code = err.code;
    if (code === "ENOENT") return { rows: [], malformed: 0 };
    throw err;
  }
  const rows = [];
  let malformed = 0;
  entries.sort();
  for (const name of entries) {
    if (!name.endsWith(".jsonl")) continue;
    const raw = await readFile(path.join(dir, name), "utf-8");
    for (const line of raw.split("\n")) {
      if (!line.trim()) continue;
      let parsed;
      try {
        parsed = JSON.parse(line);
      } catch {
        malformed += 1;
        continue;
      }
      if (!isValidTrainingPair(parsed)) {
        malformed += 1;
        continue;
      }
      rows.push(parsed);
    }
  }
  return { rows, malformed };
}
function isValidTrainingPair(value) {
  if (typeof value !== "object" || value === null || Array.isArray(value)) {
    return false;
  }
  const p = value;
  if (p.version !== 1) return false;
  if (typeof p.ts !== "string") return false;
  if (typeof p.candidateText !== "string") return false;
  if (typeof p.candidateCategory !== "string") return false;
  if (p.verdictKind !== "accept" && p.verdictKind !== "reject" && p.verdictKind !== "defer") {
    return false;
  }
  if (typeof p.reason !== "string") return false;
  if (p.candidateConfidence !== void 0 && typeof p.candidateConfidence !== "number") {
    return false;
  }
  if (p.priorDeferrals !== void 0 && typeof p.priorDeferrals !== "number") {
    return false;
  }
  if (p.groundTruthLabel !== void 0 && p.groundTruthLabel !== "accept" && p.groundTruthLabel !== "reject" && p.groundTruthLabel !== "defer") {
    return false;
  }
  return true;
}

export {
  resolveTrainingDir,
  trainingFilePathFor,
  recordJudgeTrainingPair,
  readJudgeTrainingPairs,
  isValidTrainingPair
};
//# sourceMappingURL=chunk-DF3RVK3X.js.map