Something went wrong. Try again.
An agent harness for parametric learning.
Something went wrong. Try again.
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384import type { CandidateRecord, PreferenceRecord, SerializedMessage } from "./types.js";
export interface TrainingMessage { role: "system" | "user" | "assistant"; content: string;}
export interface SftExample { schema: "branch-sft/v1"; sourceRecordId: string; messages: TrainingMessage[]; metadata: Record<string, unknown>;}
export interface DpoExample { schema: "branch-dpo/v1"; sourceRecordId: string; prompt: TrainingMessage[]; chosen: string; rejected: string; metadata: Record<string, unknown>;}
export function exportRecord(record: PreferenceRecord): { sft: SftExample; dpo: DpoExample[] } { const preferred = candidateById(record, record.preferredCandidateId); const rejected = record.rejectedCandidateIds.map((id) => candidateById(record, id)); const prompt: TrainingMessage[] = [ { role: "system", content: record.systemPrompt }, ...normalizeHistory(record.parentHistory), { role: "user", content: record.prompt }, ]; const metadata = { selection: record.selection, systemPromptHash: record.systemPromptHash, parentHistoryHash: record.parentHistoryHash, preferredModel: preferred.model, ...(record.correction ? { correctionFeedback: record.correction.feedback } : {}), };
return { sft: { schema: "branch-sft/v1", sourceRecordId: record.id, messages: [...prompt, { role: "assistant", content: preferred.response }], metadata, }, dpo: rejected.map((candidate) => ({ schema: "branch-dpo/v1", sourceRecordId: record.id, prompt, chosen: preferred.response, rejected: candidate.response, metadata: { ...metadata, rejectedCandidateId: candidate.id, rejectedModel: candidate.model }, })), };}
function candidateById(record: PreferenceRecord, id: string): CandidateRecord { const candidate = record.candidates.find((item) => item.id === id); if (!candidate) throw new Error(`Preference record ${record.id} references missing candidate ${id}.`); if (!candidate.response.trim()) throw new Error(`Candidate ${id} has no text response and cannot be exported.`); return candidate;}
function normalizeHistory(history: SerializedMessage[]): TrainingMessage[] { return history.flatMap((message): TrainingMessage[] => { if (message.role !== "user" && message.role !== "assistant") return []; const content = contentText(message.content); return content ? [{ role: message.role, content }] : []; });}
function contentText(content: unknown): string { if (typeof content === "string") return content; if (!Array.isArray(content)) return ""; return content .flatMap((part): string[] => { if (!part || typeof part !== "object") return []; if (part.type === "text" && typeof part.text === "string") return [part.text]; return []; }) .join("");}