import { Form, redirect, useNavigate } from "react-router";
import { auth } from "~/lib/auth.server";
import type { Route } from "./+types/$teamId.settings";

import {
  findTeamById,
  findTeamByNameInSeason,
  updateTeam,
  removeTeamOwner,
} from "~/models/team";
import { findSeasonById } from "~/models/season";
import { findUserById } from "~/models/user";
import { resolveUserAvatarData } from "~/lib/avatar-data";
import { Button } from "~/components/ui/button";
import { TeamAvatar } from "~/components/TeamAvatar";
import {
  Card,
  CardContent,
  CardDescription,
  CardHeader,
  CardTitle,
} from "~/components/ui/card";
import { Input } from "~/components/ui/input";
import { Label } from "~/components/ui/label";
import { AvatarEditor } from "~/components/ui/AvatarEditor";
import { parseFlagConfig } from "~/lib/flag-types";
import { deleteCloudinaryImageByUrl } from "~/lib/cloudinary.server";
import { logger } from "~/lib/logger";
import {
  AlertDialog,
  AlertDialogAction,
  AlertDialogCancel,
  AlertDialogContent,
  AlertDialogDescription,
  AlertDialogFooter,
  AlertDialogHeader,
  AlertDialogTitle,
  AlertDialogTrigger,
} from "~/components/ui/alert-dialog";
import { syncPrivateBracktParticipants } from "~/services/brackt.server";

export function meta({ data }: Route.MetaArgs): Route.MetaDescriptors {
  return [{ title: `Team Settings — ${data?.team?.name ?? "Team"} - Brackt` }];
}

export async function loader(args: Route.LoaderArgs) {
  const { params } = args;
  const { teamId } = params;
  const session = await auth.api.getSession({ headers: args.request.headers });
  const userId = session?.user.id ?? null;

  if (!userId) {
    throw new Response("You must be logged in", { status: 401 });
  }

  const team = await findTeamById(teamId);

  if (!team) {
    throw new Response("Team not found", { status: 404 });
  }

  // Only the team owner can access settings
  if (team.ownerId !== userId) {
    throw new Response("You do not have access to this team", { status: 403 });
  }

  const season = await findSeasonById(team.seasonId);

  if (!season) {
    throw new Response("Season not found", { status: 404 });
  }

  const owner = await findUserById(userId);
  const ownerAvatarData = owner ? resolveUserAvatarData(owner) : null;

  return { team, season, ownerAvatarData };
}

export async function action(args: Route.ActionArgs) {
  const { params, request } = args;
  const { teamId } = params;
  const session = await auth.api.getSession({ headers: args.request.headers });
  const userId = session?.user.id ?? null;

  if (!userId) {
    throw new Response("You must be logged in", { status: 401 });
  }

  const team = await findTeamById(teamId);

  if (!team) {
    throw new Response("Team not found", { status: 404 });
  }

  // Only the team owner can modify settings
  if (team.ownerId !== userId) {
    throw new Response("You do not have access to this team", { status: 403 });
  }

  const formData = await request.formData();
  const intent = formData.get("intent");

  if (intent === "update-avatar-flag") {
    const rawConfig = formData.get("flagConfig");
    if (typeof rawConfig !== "string") {
      return { error: "Flag config is required" };
    }

    let parsedConfig: unknown;
    try {
      parsedConfig = JSON.parse(rawConfig);
    } catch {
      return { error: "Invalid flag config" };
    }

    const flagConfig = parseFlagConfig(parsedConfig);
    if (!flagConfig) {
      return { error: "Invalid flag config" };
    }

    await updateTeam(teamId, {
      flagConfig,
      avatarType: "flag",
    });

    return { success: true };
  }

  if (intent === "remove-avatar-photo") {
    await updateTeam(teamId, {
      logoUrl: null,
      avatarType: "owner",
    });
    if (team.logoUrl) {
      deleteCloudinaryImageByUrl(team.logoUrl).catch((error) => {
        logger.error("Failed to delete team avatar from Cloudinary:", error);
      });
    }

    return { success: true };
  }

  if (intent === "use-owner-avatar") {
    await updateTeam(teamId, { avatarType: "owner", flagConfig: null });
    if (team.avatarType === "uploaded" && team.logoUrl) {
      deleteCloudinaryImageByUrl(team.logoUrl).catch((error) => {
        logger.error("Failed to delete replaced team avatar from Cloudinary:", error);
      });
    }
    return { success: true };
  }

  if (intent === "update") {
    const name = formData.get("name");

    if (!name || typeof name !== "string") {
      return { error: "Team name is required" };
    }

    const trimmedName = name.trim();
    if (!trimmedName) {
      return { error: "Team name is required" };
    }
    const conflict = await findTeamByNameInSeason(team.seasonId, trimmedName, teamId);
    if (conflict) {
      return { error: "A team with that name already exists in this season." };
    }

    await updateTeam(teamId, {
      name: trimmedName,
    });
    await syncPrivateBracktParticipants(team.seasonId);

    const season = await findSeasonById(team.seasonId);
    return redirect(`/leagues/${season?.leagueId}?updated=true`);
  }

  if (intent === "leave") {
    await removeTeamOwner(teamId);
    return redirect("/?left=true");
  }

  return { error: "Invalid action" };
}

export default function TeamSettings({ loaderData, actionData }: Route.ComponentProps) {
  const { team, season } = loaderData;
  const navigate = useNavigate();

  return (
    <div className="container mx-auto py-8 px-4">
      <div className="max-w-2xl mx-auto">
        <div className="mb-8">
          <div className="flex items-center justify-between mb-2">
            <h1 className="text-4xl font-bold">Team Settings</h1>
            <Button
              variant="outline"
              onClick={() => navigate(`/leagues/${season.leagueId}`)}
            >
              Back to League
            </Button>
          </div>
          <p className="text-muted-foreground">
            Manage your team settings and preferences
          </p>
        </div>

        <div className="space-y-6">
          {actionData && "success" in actionData && actionData.success && (
            <p className="text-sm text-[#adf661]">Team settings updated.</p>
          )}
          {actionData && "error" in actionData && actionData.error && (
            <p className="text-sm text-destructive">{actionData.error}</p>
          )}

          <Card>
            <CardHeader>
              <div className="flex items-center gap-3">
                <TeamAvatar
                  teamId={team.id}
                  teamName={team.name}
                  logoUrl={team.logoUrl}
                  flagConfig={team.flagConfig}
                  avatarType={team.avatarType}
                  ownerAvatarData={loaderData.ownerAvatarData}
                  size="lg"
                />
                <div>
                  <CardTitle>Team Avatar</CardTitle>
                  <CardDescription>
                    Update the flag or submit a photo for review
                  </CardDescription>
                </div>
              </div>
            </CardHeader>
            <CardContent>
              <AvatarEditor
                id={team.id}
                isTeam
                currentAvatarType={team.avatarType}
                flagConfig={team.flagConfig}
                uploadedPhotoUrl={team.avatarType === "uploaded" ? team.logoUrl : null}
                uploadUrl="/api/upload-team-logo"
                ownerAvatarData={loaderData.ownerAvatarData}
              />
            </CardContent>
          </Card>

          <Card>
            <CardHeader>
              <CardTitle>Team Information</CardTitle>
              <CardDescription>
                Update your team name
              </CardDescription>
            </CardHeader>
            <CardContent>
              <Form method="post" className="space-y-4">
                <input type="hidden" name="intent" value="update" />
                
                <div className="space-y-2">
                  <Label htmlFor="name">Team Name</Label>
                  <Input
                    id="name"
                    name="name"
                    type="text"
                    defaultValue={team.name}
                    required
                    maxLength={255}
                  />
                </div>

                <Button type="submit">Save Changes</Button>
              </Form>
            </CardContent>
          </Card>

          <Card className="border-destructive">
            <CardHeader>
              <CardTitle className="text-destructive">Danger Zone</CardTitle>
              <CardDescription>
                Irreversible actions for your team
              </CardDescription>
            </CardHeader>
            <CardContent>
              <AlertDialog>
                <AlertDialogTrigger asChild>
                  <Button variant="destructive">Leave League</Button>
                </AlertDialogTrigger>
                <AlertDialogContent>
                  <AlertDialogHeader>
                    <AlertDialogTitle>Are you sure?</AlertDialogTitle>
                    <AlertDialogDescription>
                      This will remove you as the owner of "{team.name}" and make the team
                      available for others to claim. This action cannot be undone.
                    </AlertDialogDescription>
                  </AlertDialogHeader>
                  <AlertDialogFooter>
                    <AlertDialogCancel>Cancel</AlertDialogCancel>
                    <Form method="post">
                      <input type="hidden" name="intent" value="leave" />
                      <AlertDialogAction type="submit" className="bg-destructive hover:bg-destructive/90">
                        Leave League
                      </AlertDialogAction>
                    </Form>
                  </AlertDialogFooter>
                </AlertDialogContent>
              </AlertDialog>
            </CardContent>
          </Card>
        </div>
      </div>
    </div>
  );
}
