import {
  buildAuditPayload,
  buildComputedSnapshotPayload,
  computePayloadHash,
  createSqlClient,
  summarizeIssues,
  writeAuditArtifact
} from './pdf-audit-utils.ts';

function pickComparablePayload(payload: Record<string, unknown>) {
  return {
    templateInput: payload.templateInput,
    topicInputKeys:
      payload.topicInputs && typeof payload.topicInputs === 'object'
        ? Object.keys(payload.topicInputs as Record<string, unknown>).sort()
        : []
  };
}

async function main() {
  const sql = createSqlClient();

  try {
    const payload = await buildAuditPayload(sql);
    const previewPayload = pickComparablePayload({
      templateInput: payload.templateInput,
      topicInputs: payload.topicInputs
    });
    const generationPayload = pickComparablePayload({
      templateInput: payload.templateInput,
      topicInputs: payload.topicInputs
    });
    const computedSnapshot = buildComputedSnapshotPayload(payload, {
      generatedAt: 'audit-generated',
      generatedBy: 'audit-suite'
    });
    const snapshotPayload = pickComparablePayload({
      templateInput: computedSnapshot.templateInput,
      topicInputs: payload.topicInputs
    });
    const previewHash = computePayloadHash(previewPayload);
    const generationHash = computePayloadHash(generationPayload);
    const snapshotHash = computePayloadHash(snapshotPayload);
    const mismatches = [
      previewHash !== generationHash ? 'preview:generation' : null,
      generationHash !== snapshotHash ? 'generation:snapshot' : null,
      previewHash !== snapshotHash ? 'preview:snapshot' : null
    ].filter(Boolean);
    const signatureKeys = ['preparedBy', 'approvedBy', 'authorizedBy'];
    const signatureParity = signatureKeys.every((key) => {
      const signatures = payload.documentData.signatures as Record<string, unknown>;
      return key in signatures;
    });
    const priceTable = payload.templateInput.quotation_price_data;
    const firstPriceRow = Array.isArray(priceTable) && Array.isArray(priceTable[0]) ? priceTable[0] : null;
    const priceTableParity =
      Array.isArray(priceTable) &&
      Array.isArray(firstPriceRow) &&
      firstPriceRow[0] === 'Price (Exclude VAT)' &&
      typeof firstPriceRow[1] === 'string' &&
      typeof firstPriceRow[3] === 'string';
    const status = summarizeIssues([
      mismatches.length ? 'FAIL' : 'PASS',
      signatureParity ? 'PASS' : 'FAIL',
      priceTableParity ? 'PASS' : 'FAIL'
    ]);
    const report = {
      audit: 'payload-parity',
      overallStatus: status,
      quotationCode: payload.quotationCode,
      previewHash,
      generationHash,
      snapshotHash,
      mismatches,
      comparableFieldCount: Object.keys(payload.templateInput).length,
      topicInputKeyCount: Object.keys(payload.topicInputs).length,
      signatureParity,
      priceTableParity,
      priceTableRowCount: Array.isArray(priceTable) ? priceTable.length : 0,
      priceTableCurrency: Array.isArray(firstPriceRow) ? firstPriceRow[3] ?? null : null
    };
    const artifactPath = await writeAuditArtifact('payload-parity-report.json', report);

    console.log(JSON.stringify({ ...report, artifactPath }, null, 2));
  } finally {
    await sql.end({ timeout: 5 });
  }
}

main().catch((error) => {
  console.error(`[audit-payload-parity] ${error.message}`);
  process.exit(1);
});
