import { FastifyInstance } from 'fastify';
import { withTenant } from '../data/db.js';

export async function registerApiRoutes(app: FastifyInstance) {
  // List stacks
  app.get('/api/v1/stacks', async (request, reply) => {
    const tenantId = (request as any).tenantId;
    const pool = (app as any).pool;

    const result = await withTenant(pool, tenantId, async (client) => {
      const { rows } = await client.query(
        `SELECT DISTINCT ON (stack_name)
           stack_name, stack_fingerprint, drift_score, total_resources, scanned_at, state_serial
         FROM drift_reports
         WHERE tenant_id = $1
         ORDER BY stack_name, scanned_at DESC`,
        [tenantId]
      );
      return rows;
    });

    return reply.send(result);
  });

  // Get stack drift history
  app.get('/api/v1/stacks/:stackName/history', async (request, reply) => {
    const tenantId = (request as any).tenantId;
    const { stackName } = request.params as { stackName: string };
    const pool = (app as any).pool;

    const result = await withTenant(pool, tenantId, async (client) => {
      const { rows } = await client.query(
        `SELECT id, drift_score, total_resources, scanned_at, state_serial,
                (raw_report->'drifted_resources') as drifted_resources
         FROM drift_reports
         WHERE tenant_id = $1 AND stack_name = $2
         ORDER BY scanned_at DESC
         LIMIT 50`,
        [tenantId, stackName]
      );
      return rows;
    });

    return reply.send(result);
  });

  // Get single drift report
  app.get('/api/v1/reports/:reportId', async (request, reply) => {
    const tenantId = (request as any).tenantId;
    const { reportId } = request.params as { reportId: string };
    const pool = (app as any).pool;

    const result = await withTenant(pool, tenantId, async (client) => {
      const { rows } = await client.query(
        `SELECT * FROM drift_reports WHERE tenant_id = $1 AND id = $2`,
        [tenantId, reportId]
      );
      return rows[0] ?? null;
    });

    if (!result) {
      return reply.status(404).send({ error: 'Not found' });
    }

    return reply.send(result);
  });

  // Dashboard summary
  app.get('/api/v1/dashboard', async (request, reply) => {
    const tenantId = (request as any).tenantId;
    const pool = (app as any).pool;

    const result = await withTenant(pool, tenantId, async (client) => {
      const stacks = await client.query(
        `SELECT COUNT(DISTINCT stack_name) as stack_count FROM drift_reports WHERE tenant_id = $1`,
        [tenantId]
      );
      const drifted = await client.query(
        `SELECT COUNT(DISTINCT stack_name) as drifted_count
         FROM drift_reports
         WHERE tenant_id = $1 AND drift_score > 0
           AND scanned_at = (SELECT MAX(scanned_at) FROM drift_reports r2 WHERE r2.stack_name = drift_reports.stack_name AND r2.tenant_id = $1)`,
        [tenantId]
      );
      const critical = await client.query(
        `SELECT COUNT(*) as critical_count
         FROM drift_reports
         WHERE tenant_id = $1 AND drift_score >= 80
           AND scanned_at >= NOW() - INTERVAL '24 hours'`,
        [tenantId]
      );

      return {
        total_stacks: parseInt(stacks.rows[0]?.stack_count ?? '0'),
        drifted_stacks: parseInt(drifted.rows[0]?.drifted_count ?? '0'),
        critical_last_24h: parseInt(critical.rows[0]?.critical_count ?? '0'),
      };
    });

    return reply.send(result);
  });
}
