#!/usr/bin/env node import { createHash } from 'node:crypto' import { readFile, rename, writeFile } from 'node:fs/promises' import { dirname, extname, resolve, sep } from 'node:path' import { spawnSync } from 'node:child_process' const [runtime, compiler, source, girOutput, receiptOutput, allowedRoot] = process.argv.slice(2) if (![runtime, compiler, source, girOutput, receiptOutput, allowedRoot].every(Boolean)) { throw new Error('usage: tcs-agent-driver ') } if (extname(source) !== '.tcs') throw new Error('TCS_SOURCE_ONLY') const root = resolve(allowedRoot) const inside = (value) => { const target = resolve(value) if (target !== root && !target.startsWith(`${root}${sep}`)) throw new Error('TARGET_OUTSIDE_ALLOWED_ROOT') return target } const girPath = inside(girOutput) const receiptPath = inside(receiptOutput) const compile = spawnSync(runtime, ['compile-with', compiler, source, girPath], { encoding: 'utf8', timeout: 30000 }) if (compile.status !== 0) throw new Error(`TCS_COMPILE_FAILED:${(compile.stderr || '').trim().slice(0, 240)}`) const gir = JSON.parse(await readFile(girPath, 'utf8')) if (resolve(root, gir.exact_target?.exact_path || '') !== receiptPath || resolve(root, gir.receipt_plan?.machine_path || '') !== receiptPath) throw new Error('TCS_RECEIPT_TARGET_MISMATCH') const actions = Object.values(gir.deterministic_action_graph || {}) if (actions.length !== 1 || actions[0].operation !== 'CORE.AGENT_TRANSLATION_CANDIDATE') throw new Error('TCS_AGENT_OPERATION_REQUIRED') const value = (name) => gir.inputs?.[name]?.value const exact = { MODULE_ID: 'ZY-PM-0002', EXECUTION_LIMB: 'ZY-JD-LIMB-001', CONTROLLER: 'ZHUYUAN', MODEL_ROLE: 'THIRD_GENERATION_STATELESS_REASONING_TOOL', INPUT_POLICY: 'TCS_SOURCE_AND_SELFHOSTED_GIR_ONLY', OUTPUT_POLICY: 'CANDIDATE_ONLY_NO_SEMANTIC_OR_REALITY_AUTHORITY', } for (const [name, expected] of Object.entries(exact)) if (value(name) !== expected) throw new Error(`TCS_CONTRACT_MISMATCH:${name}`) if (gir.native_self_hosted !== true || gir.compiled_from?.compiler_state !== 'TCS_COMPILER_GIR_EXECUTED') throw new Error('SELFHOSTED_GIR_REQUIRED') const apiKey = process.env.DEEPSEEK_API_KEY const base = String(process.env.DEEPSEEK_API_URL || 'https://api.deepseek.com/v1').replace(/\/$/, '') const endpoint = base.endsWith('/chat/completions') ? base : `${base}/chat/completions` const model = process.env.DEEPSEEK_MODEL || 'deepseek-chat' if (!apiKey) throw new Error('DEEPSEEK_API_KEY_MISSING') const tcsSource = await readFile(source, 'utf8') const response = await fetch(endpoint, { method: 'POST', signal: AbortSignal.timeout(90000), headers: { authorization: `Bearer ${apiKey}`, 'content-type': 'application/json' }, body: JSON.stringify({ model, temperature: 0, response_format: { type: 'json_object' }, messages: [ { role: 'system', content: 'You are a stateless third-generation reasoning tool. TCS and its self-hosted GIR are the only task semantics. Return one closed JSON object with exactly summary:string, verified_constraints:string[], unknowns:string[], acceptance_candidate:0|100. You have no semantic authority and no reality-action authority.' }, { role: 'user', content: JSON.stringify({ tcs_source: tcsSource, self_hosted_gir: gir }) }, ], }), }) if (!response.ok) throw new Error(`MODEL_HTTP_${response.status}`) const envelope = await response.json() const raw = envelope?.choices?.[0]?.message?.content const candidate = JSON.parse(raw) const keys = Object.keys(candidate).sort().join(',') if (keys !== 'acceptance_candidate,summary,unknowns,verified_constraints' || typeof candidate.summary !== 'string' || !Array.isArray(candidate.verified_constraints) || !candidate.verified_constraints.every((item) => typeof item === 'string') || !Array.isArray(candidate.unknowns) || !candidate.unknowns.every((item) => typeof item === 'string') || ![0, 100].includes(candidate.acceptance_candidate)) throw new Error('MODEL_OUTPUT_INVALID') const receipt = { schema: 'tcs.agent-translation-candidate-receipt/v1', state: 'CANDIDATE_TARGET_READBACK_VERIFIED', module_id: value('MODULE_ID'), execution_limb: value('EXECUTION_LIMB'), controller: value('CONTROLLER'), model_role: value('MODEL_ROLE'), model_provider: 'DEEPSEEK_REPLACEABLE_TOOL', model, source_language: 'TCS/0.1', source_sha256: gir.compiled_from.source_sha256, semantic_authority: false, reality_action_authority: false, ...candidate, } const encoded = `${JSON.stringify(receipt, null, 2)}\n` const pending = `${receiptPath}.pending` await writeFile(pending, encoded, { mode: 0o600 }) await rename(pending, receiptPath) if (await readFile(receiptPath, 'utf8') !== encoded) throw new Error('RECEIPT_READBACK_MISMATCH') process.stdout.write(`${JSON.stringify({ state: receipt.state, module_id: receipt.module_id, acceptance_candidate: receipt.acceptance_candidate, receipt_sha256: createHash('sha256').update(encoded).digest('hex') })}\n`)