import { captureException } from "@sentry/nextjs";
import { eq } from "drizzle-orm";
import { redirect } from "next/navigation";
import { db, teams } from "@/db";
import { getCurrentUser } from "@/lib/get-current-user";
import { getGiselleSession, updateGiselleSession } from "@/lib/giselle-session";
import { stripe } from "@/services/external/stripe";
import { getLatestSubscriptionV2 } from "@/services/subscriptions/get-latest-subscription-v2";
import { isMemberOfTeam } from "@/services/teams";

export async function GET(_request: Request) {
	const session = await getGiselleSession();
	const checkoutSessionId = session?.checkoutSessionId;
	if (checkoutSessionId == null) {
		// no checkout session id, redirect to /settings/team
		redirect("/settings/team");
	}

	try {
		const checkoutSession = await stripe.checkout.sessions.retrieve(
			checkoutSessionId,
			{
				apiVersion: "2025-12-15.preview;checkout_product_catalog_preview=v1",
			},
		);
		const checkoutItem = checkoutSession.checkout_items?.[0];
		if (checkoutItem?.type !== "pricing_plan_subscription_item") {
			throw new Error(
				`Expected checkout item type 'pricing_plan_subscription_item', but got '${checkoutItem?.type}'`,
			);
		}

		const subscriptionId =
			checkoutItem.pricing_plan_subscription_item?.pricing_plan_subscription;
		if (subscriptionId === undefined) {
			throw new Error("Subscription ID not found in checkout session");
		}

		const [currentUser, team] = await Promise.all([
			getCurrentUser(),
			getTeamFromSubscription(subscriptionId),
		]);
		const isCurrentUserMember = await isMemberOfTeam(
			currentUser.dbId,
			team.teamDbId,
		);
		await updateGiselleSession({
			checkoutSessionId: undefined,
			...(isCurrentUserMember ? { teamId: team.teamId } : {}),
		});
	} catch (error) {
		// fallback
		captureException(error);
		await updateGiselleSession({ checkoutSessionId: undefined });
	}

	redirect("/settings/team");
}

async function getTeamFromSubscription(subscriptionId: string) {
	const result = await getLatestSubscriptionV2(subscriptionId);
	if (!result) {
		throw new Error("Subscription not found");
	}
	if (result.subscription.servicingStatus !== "active") {
		throw new Error("Subscription is not active");
	}
	const [team] = await db
		.select({
			teamId: teams.id,
		})
		.from(teams)
		.where(eq(teams.dbId, result.subscription.teamDbId));
	if (!team) {
		throw new Error("Team not found");
	}
	return {
		teamId: team.teamId,
		teamDbId: result.subscription.teamDbId,
	};
}
