import assert from 'node:assert/strict';
import { readFileSync } from 'node:fs';
import path from 'node:path';
import test from 'node:test';
import { fileURLToPath } from 'node:url';

const root = path.resolve(path.dirname(fileURLToPath(import.meta.url)), '..');
const read = (relative) => readFileSync(path.join(root, relative), 'utf8');

test('direct payment endpoints close before parsing caller payloads', () => {
  for (const route of [
    'app/api/x402/verify/route.ts',
    'app/api/x402/settle/route.ts',
    'app/api/x402/submit-signed/route.ts',
    'app/app/api/x402/verify/route.ts',
    'app/app/api/x402/settle/route.ts',
  ]) {
    const source = read(route);
    assert.match(source, /x402ReleaseGateClosed/);
    assert.ok(source.indexOf('return x402ReleaseGateClosed();') < source.indexOf('await req.json()'), route);
  }
});

test('Vercel middleware disables V2 and V3 payment APIs and self-payment controls', () => {
  const source = read('middleware.ts');
  for (const matcher of [
    '/api/x402/:path*',
    '/api/v3/x402/:path*',
    '/sign/x402-test',
    '/sign/x402-pay',
    '/sign/x402-register',
  ]) {
    assert.ok(source.includes(matcher), matcher);
  }
  assert.match(source, /x402_release_gate_closed/);
  assert.match(source, /status: 503/);
  assert.match(source, /'Cache-Control': 'no-store'/);
});

test('payment helper has no fabricated Solana recipient and remains closed before header processing', () => {
  const source = read('app/api/x402/trust/_lib/verify-payment.ts');
  assert.match(source, /process\.env\.PAY_TO_ADDRESS\?\.trim\(\) \?\? ''/);
  assert.ok(!source.includes('PAY_TO_SOL ||'));
  assert.ok(!source.includes('6KpXaFmaR8WPWr79qzsMBvwDbDzYFErwNoWxfwqDr8JU'));
  assert.ok(source.indexOf('return { valid: false, response: x402ReleaseGateClosed() };') < source.indexOf('const paymentHeader'));
  assert.match(source, /paymentPayload\.network !== 'base' \|\| resource !== req\.nextUrl\.toString\(\)/);
  assert.match(source, /Number\(auth\.validAfter\) > now \|\| Number\(auth\.validBefore\) < now/);
  assert.match(source, /waitForTransactionReceipt/);
});

test('public discovery and agent cards truthfully label the release-closed x402 surface', () => {
  const discovery = JSON.parse(read('public/.well-known/x402.json'));
  assert.equal(discovery.releaseStatus, 'disabled_pending_readiness_evidence');
  assert.deepEqual(discovery.networks, []);
  assert.deepEqual(discovery.accepts, []);
  assert.deepEqual(discovery.endpoints, []);
  assert.equal(discovery.payTo, undefined);
  assert.equal(discovery.payToSolana, undefined);

  const skill = read('public/SKILL.md');
  const llms = read('public/llms.txt');
  const agents = read('public/agents.txt');
  const plugin = JSON.parse(read('public/.well-known/ai-plugin.json'));
  const agentManifest = JSON.parse(read('public/.well-known/agent.json'));
  const genesis = JSON.parse(read('public/nft/vaultfire-genesis.json'));
  const agentCard = read('app/api/.well-known/agent-card.json/route.ts');
  const nestedAgentCard = read('app/app/api/.well-known/agent-card.json/route.ts');
  const openapi = read('app/api/openapi.json/route.ts');
  assert.ok(!skill.includes('## Live x402 Customers'));
  assert.ok(!skill.includes('Vaultfire x402 Surface (live'));
  assert.ok(!skill.includes('"x402Support": true'));
  assert.match(skill, /x402 is \*\*disabled pending release-readiness evidence\*\*/);
  assert.match(llms, /x402 payment processing is release-gated and accepts no payment requests/);
  assert.match(llms, /\/api\/v3\/x402\/\*/);
  assert.ok(!llms.includes('POST https://theloopbreaker.com/api/x402/verify'));
  assert.ok(!llms.includes('POST https://theloopbreaker.com/api/x402/settle'));
  assert.ok(!agents.includes('POST /api/x402/verify'));
  assert.ok(!agents.includes('POST /api/x402/settle'));
  assert.match(agents, /Payments: disabled pending release-readiness evidence/);
  assert.match(agents, /\/api\/v3\/x402\/\*/);
  assert.match(plugin.description_for_model, /x402 payment endpoints are disabled pending release-readiness evidence/);
  assert.ok(!plugin.description_for_model.includes('settle payments via x402'));
  assert.ok(!agentManifest.capabilities.includes('x402-usdc-payments'));
  assert.equal(agentManifest.x402.releaseStatus, 'disabled_pending_readiness_evidence');
  assert.deepEqual(agentManifest.x402.networks, []);
  assert.deepEqual(agentManifest.x402.accepts, []);
  assert.deepEqual(agentManifest.x402.endpoints, []);
  assert.equal(agentManifest.x402.payTo, undefined);
  assert.equal(agentManifest.x402.network, undefined);
  assert.equal(agentManifest.endpoints.write.x402_verify, undefined);
  assert.equal(agentManifest.endpoints.write.x402_settle, undefined);
  assert.match(genesis.description, /x402 payment routes are release-gated and not live/);
  for (const card of [agentCard, nestedAgentCard]) {
    assert.ok(!card.includes("id: 'payments'"));
    assert.match(card, /x402: 'disabled_pending_readiness_evidence'/);
  }
  assert.ok(!agentCard.includes("id: 'x402-email'"));
  assert.ok(!agentCard.includes('verifierPaid:'));
  assert.ok(!openapi.includes("'/x402/verify'"));
  assert.ok(!openapi.includes("'/x402/settle'"));
});

test('email discovery, documentation, and activity board make no settlement claim', () => {
  const email = read('app/api/.well-known/x402-email.json/route.ts');
  const emailPage = read('app/x402-email/page.tsx');
  const live = read('app/live/page.tsx');
  assert.match(email, /releaseStatus: 'disabled_pending_readiness_evidence'/);
  assert.match(email, /verifier: null/);
  assert.match(email, /status: 503/);
  assert.match(live, /x402 settlement activity is unavailable/);
  assert.ok(!live.includes('Real x402 settlements'));
  assert.match(emailPage, /x402 payment and verifier routes are disabled pending release-readiness/);
  assert.match(emailPage, /x402-email verifier and payment\s+workflow are release-gated/);
  assert.ok(!emailPage.includes('Live on Base mainnet'));
  assert.ok(!emailPage.includes('(live)'));
  assert.ok(!emailPage.includes('The verifier endpoint is live'));
  assert.ok(!emailPage.includes('Bonds and payments are settled'));
});

test('generated registry preserves both executable contract-call methods as metadata candidates', () => {
  const repositoryRoot = path.resolve(root, '..', '..');
  const registry = JSON.parse(readFileSync(path.join(repositoryRoot, 'pr7/generated/route-registry.json'), 'utf8'));
  const openapi = JSON.parse(readFileSync(path.join(repositoryRoot, 'pr7/generated/openapi.json'), 'utf8'));
  const methods = registry.routes
    .filter((route) => route.path === '/api/x402/contract-call')
    .map((route) => route.method)
    .sort();

  assert.deepEqual(methods, ['GET', 'POST']);
  assert.ok(openapi.paths['/api/x402/contract-call'].get);
  assert.ok(openapi.paths['/api/x402/contract-call'].post);
  assert.ok(
    registry.routes
      .filter((route) => route.path === '/api/x402/contract-call')
      .every((route) => route.free === false && route.evidenceKind === 'x402-manifest'),
  );
});

test('verification script reads scanner credentials from the environment', () => {
  const script = read('scripts/verify-all.sh');
  assert.match(script, /ETHERSCAN_API_KEY/);
  assert.match(script, /BASESCAN_API_KEY/);
  assert.match(script, /Set ETHERSCAN_API_KEY or BASESCAN_API_KEY before running verification/);
  assert.doesNotMatch(script, /(?:BASESCAN|ETHERSCAN)_API_KEY="[^"$][^"]*"/);
});

test('webhook and heartbeat writes fail closed without configured authorization', () => {
  for (const route of ['app/api/agent/webhooks/route.ts', 'app/app/api/agent/webhooks/route.ts']) {
    const source = read(route);
    assert.match(source, /WEBHOOK_ADMIN_TOKEN/);
    assert.match(source, /webhook_auth_unconfigured/);
    assert.equal((source.match(/requireWebhookWriteAuthorization\(req\)/g) || []).length, 3);
    assert.ok(!source.includes('agentAddress is required'));
  }
  const cron = read('app/api/cron/heartbeat/route.ts');
  assert.match(cron, /if \(!cronSecret\)/);
  assert.match(cron, /heartbeat persistence write\/read failed/);
});
