import type { FastifyInstance } from "fastify";
import { z } from "zod";

import { AppError } from "../lib/errors.js";
import { supabaseAdmin } from "../lib/supabase.js";
import { unsubscribeContactByToken } from "../services/unsubscribe-service.js";

function renderUnsubscribePage(message: string) {
  return `<!doctype html>
<html lang="en">
  <head>
    <meta charset="utf-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1" />
    <title>Unsubscribed</title>
    <style>
      body { margin: 0; font-family: Arial, sans-serif; background: #f8fafc; color: #0f172a; }
      main { max-width: 560px; margin: 48px auto; background: #ffffff; border: 1px solid #e2e8f0; border-radius: 24px; padding: 32px; box-shadow: 0 18px 48px rgba(15, 23, 42, 0.08); }
      .eyebrow { font-size: 12px; font-weight: 700; letter-spacing: 0.18em; text-transform: uppercase; color: #ea580c; }
      h1 { margin: 12px 0 0; font-size: 32px; line-height: 1.1; }
      p { margin: 14px 0 0; font-size: 16px; line-height: 1.7; color: #475569; }
    </style>
  </head>
  <body>
    <main>
      <div class="eyebrow">Nextacom</div>
      <h1>Email preference updated</h1>
      <p>${message}</p>
    </main>
  </body>
</html>`;
}

export function registerPublicRoutes(app: FastifyInstance) {
  app.get("/api/public/unsubscribe/:token", async (request, reply) => {
    const params = z.object({ token: z.string().min(12) }).parse(request.params);
    await unsubscribeContactByToken({
      token: params.token,
      usedVia: "browser_get",
      requestMetadata: {
        ip: request.ip,
        userAgent: request.headers["user-agent"] ?? null,
      }
    });

    reply.type("text/html; charset=utf-8");
    return reply.send(renderUnsubscribePage("You have been unsubscribed from future live campaigns for this workspace."));
  });

  app.post("/api/public/unsubscribe/:token", async (request, reply) => {
    const params = z.object({ token: z.string().min(12) }).parse(request.params);
    await unsubscribeContactByToken({
      token: params.token,
      usedVia: "one_click_post",
      requestMetadata: {
        ip: request.ip,
        userAgent: request.headers["user-agent"] ?? null,
      }
    });

    reply.type("text/plain; charset=utf-8");
    return reply.send("Unsubscribed");
  });

  app.get("/api/public/bootstrap", async () => {
    const [{ data: plans }, { data: pages }, { data: settings }] = await Promise.all([
      supabaseAdmin
        .from("plan_definitions")
        .select("code, name, price_cents, contact_limit, monthly_email_limit, description")
        .eq("is_active", true)
        .order("price_cents", { ascending: true }),
      supabaseAdmin
        .from("admin_content_pages")
        .select("slug, title, body")
        .eq("published", true),
      supabaseAdmin.from("admin_settings").select("key, value")
    ]);

    const contentPages = pages ?? [];

    if (!contentPages.some((page) => page.slug === "landing")) {
      contentPages.unshift({
        slug: "landing",
        title: "Nextacom",
        body: {
          hero: {
            eyebrow: "Email orchestration",
            title: "Send precise campaigns with less operational drag.",
            subtitle: "A minimal, responsive email workspace for modern teams."
          }
        }
      });
    }

    return {
      plans: plans ?? [],
      pages: contentPages,
      settings: settings ?? []
    };
  });

  app.get("/api/plans", async () => {
    const { data, error } = await supabaseAdmin
      .from("plan_definitions")
      .select("code, name, price_cents, contact_limit, monthly_email_limit, description")
      .eq("is_active", true)
      .order("price_cents", { ascending: true });

    if (error) {
      throw new AppError(400, "PLAN_LOOKUP_FAILED", error.message);
    }

    return {
      plans: data ?? []
    };
  });

  app.get("/api/content/:slug", async (request) => {
    const params = z.object({ slug: z.string().min(1) }).parse(request.params);
    const { data, error } = await supabaseAdmin
      .from("admin_content_pages")
      .select("slug, title, body, published")
      .eq("slug", params.slug)
      .eq("published", true)
      .maybeSingle();

    if (error) {
      throw new AppError(400, "CONTENT_LOOKUP_FAILED", error.message);
    }

    return {
      page: data
    };
  });
}
