import { createServerFn } from "@tanstack/react-start";
import { requireSupabaseAuth } from "@/integrations/supabase/auth-middleware";
import { z } from "zod";
import { PLAN_LIMITS, type PlanId } from "@/lib/plans";

function monthStartISO() {
  const d = new Date();
  return new Date(Date.UTC(d.getUTCFullYear(), d.getUTCMonth(), 1)).toISOString();
}

/** Server-side source of truth for what the signed-in user may do this month. */
export const getEntitlements = createServerFn({ method: "GET" })
  .middleware([requireSupabaseAuth])
  .handler(async ({ context }) => {
    const { supabase, userId } = context;
    const since = monthStartISO();

    const [{ data: sub }, decisions, simulations] = await Promise.all([
      supabase.from("subscriptions").select("*").eq("user_id", userId).maybeSingle(),
      supabase.from("decisions").select("id", { count: "exact", head: true }).eq("user_id", userId).gte("created_at", since),
      supabase.from("simulations").select("id", { count: "exact", head: true }).eq("user_id", userId).gte("created_at", since),
    ]);

    const now = Date.now();
    const periodEnd = sub?.current_period_end ? new Date(sub.current_period_end).getTime() : null;
    const statusOk = sub ? ["active", "trialing", "past_due"].includes(sub.status) : false;
    const notExpired = periodEnd == null || periodEnd > now;
    const plan: PlanId = (statusOk && notExpired ? (sub?.plan as PlanId) : "free") ?? "free";
    const limits = PLAN_LIMITS[plan] ?? PLAN_LIMITS.free;

    return {
      plan,
      status: sub?.status ?? "active",
      billingInterval: (sub?.billing_interval ?? null) as "monthly" | "annual" | null,
      currentPeriodEnd: sub?.current_period_end ?? null,
      cancelAtPeriodEnd: !!sub?.cancel_at_period_end,
      provider: sub?.provider ?? null,
      lastPaymentStatus: sub?.last_payment_status ?? null,
      limits,
      usage: {
        decisions: decisions.count ?? 0,
        simulations: simulations.count ?? 0,
      },
      remaining: {
        decisions: limits.decisions == null ? null : Math.max(0, limits.decisions - (decisions.count ?? 0)),
        simulations: limits.simulations == null ? null : Math.max(0, limits.simulations - (simulations.count ?? 0)),
      },
      showsAds: limits.ads,
    };
  });

/** Records the plan the user picked on the intro screen (choice only — never grants access). */
export const recordPlanIntent = createServerFn({ method: "POST" })
  .middleware([requireSupabaseAuth])
  .inputValidator((v: unknown) =>
    z.object({ plan: z.enum(["free", "pro", "elite"]), interval: z.enum(["monthly", "annual"]).optional() }).parse(v),
  )
  .handler(async ({ context, data }) => {
    const { supabase, userId } = context;
    const { data: profile } = await supabase.from("profiles").select("preferences").eq("id", userId).maybeSingle();
    const preferences = {
      ...((profile?.preferences as Record<string, unknown>) ?? {}),
      plan_intent: data.plan,
      plan_intent_interval: data.interval ?? "monthly",
      plan_intro_seen_at: new Date().toISOString(),
    };
    const { error } = await supabase.from("profiles").update({ preferences }).eq("id", userId);
    if (error) throw new Error(error.message);
    return { ok: true, plan: data.plan };
  });
