import { NextRequest, NextResponse } from 'next/server';
import { ethers } from 'ethers';
import { resolveChain, SUPPORTED_CHAINS } from '../../_lib/resolve-chain';
import { withFailover } from '../../_lib/rpc-retry';

/**
 * GET /api/agent/disputes
 *
 * Query dispute data from the VaultfireDisputeResolution contract.
 *
 * Query params:
 *   ?id=<number>   — (optional) dispute ID to fetch a specific dispute
 *   ?chain=base    — chain to query (default: "base")
 *
 * Without `id`:  Returns aggregate dispute stats (filed, resolved, totalStake).
 * With    `id`:  Returns the individual dispute record for that ID.
 */

const CONTRACTS: Record<string, string> = {
  base:      '0x3a681b6eF98c6d35643Ca631eE50EF35edd6BcBD',
  avalanche: '0x98afd1440B2238D73c1394720277a6d031fCbbD0',
  arbitrum:  '0x152a0446958f48EB3F1f5126FAF418D663359e95',
  polygon:   '0x5F7680a9a720c03812532A735D1165D9f97c0Cd1',
};

const ABI = [
  {
    name: 'getDisputeStats',
    type: 'function',
    stateMutability: 'view',
    inputs: [],
    outputs: [
      { name: 'filed',      type: 'uint256' },
      { name: 'resolved',   type: 'uint256' },
      { name: 'totalStake', type: 'uint256' },
    ],
  },
  {
    name: 'getDispute',
    type: 'function',
    stateMutability: 'view',
    inputs: [{ name: 'id', type: 'uint256' }],
    outputs: [
      { name: 'id',          type: 'uint256' },
      { name: 'plaintiff',   type: 'address' },
      { name: 'defendant',   type: 'address' },
      { name: 'stake',       type: 'uint256' },
      { name: 'status',      type: 'uint8'   },
      { name: 'resolution',  type: 'uint8'   },
      { name: 'createdAt',   type: 'uint256' },
      { name: 'resolvedAt',  type: 'uint256' },
    ],
  },
];

export async function GET(req: NextRequest) {
  try {
    const { searchParams } = new URL(req.url);
    const chain = resolveChain(searchParams.get('chain'));
    const idParam = searchParams.get('id');

    if (!chain) {
      return NextResponse.json(
        { error: `Unsupported chain. Use one of: ${SUPPORTED_CHAINS.join(', ')} (or chain IDs: 8453, 43114, 42161, 137)` },
        { status: 400 },
      );
    }
    const contractAddress = CONTRACTS[chain];

    // Specific dispute lookup
    if (idParam !== null) {
      const id = Number(idParam);
      if (!Number.isInteger(id) || id < 0) {
        return NextResponse.json({ error: 'Invalid dispute id — must be a non-negative integer' }, { status: 400 });
      }

      const d = await withFailover(chain, async (provider) => {
        const contract = new ethers.Contract(contractAddress, ABI, provider);
        return contract.getDispute(BigInt(id));
      });

      return NextResponse.json({
        chain,
        contract: contractAddress,
        dispute: {
          id:         d.id.toString(),
          plaintiff:  d.plaintiff,
          defendant:  d.defendant,
          stake:      d.stake.toString(),
          status:     Number(d.status),
          resolution: Number(d.resolution),
          createdAt:  d.createdAt.toString(),
          resolvedAt: d.resolvedAt.toString(),
        },
      });
    }

    // Aggregate stats
    const stats = await withFailover(chain, async (provider) => {
      const contract = new ethers.Contract(contractAddress, ABI, provider);
      return contract.getDisputeStats();
    });

    return NextResponse.json({
      chain,
      contract: contractAddress,
      disputeStats: {
        filed:      stats.filed.toString(),
        resolved:   stats.resolved.toString(),
        totalStake: stats.totalStake.toString(),
      },
    });
  } catch (error: unknown) {
    // VF-N05/VF-14: Never leak raw error messages to clients — log server-side only
    console.error('[disputes] Unhandled error:', error);
    return NextResponse.json({ error: 'Internal server error' }, { status: 500 });
  }
}
