import { projectInviteUser, projectMembers, projectRemoveMember } from "@/client";
import type { MemberInfo } from "@/client";
import { Button } from "@/components/ui/button";
import { Input } from "@/components/ui/input";
import { Label } from "@/components/ui/label";
import { useMutation, useQuery, useQueryClient } from "@tanstack/react-query";
import {
  Loader2,
  Plus,
  Trash2,
} from "lucide-react";
import { useState } from "react";
import { useParams } from "react-router-dom";
import { toast } from "sonner";
import {getApiErrorMessage} from '@/lib/api-error';

export function RepoSettingsMembers() {
  const queryClient = useQueryClient();
  const { namespace } = useParams<{ namespace: string; repoName: string }>();
  const ns = namespace!;
  const [isInviting, setIsInviting] = useState(false);
  const [inviteEmail, setInviteEmail] = useState("");
  const [inviteRole, setInviteRole] = useState<"Member" | "Admin">("Member");

  const { data: membersData, isLoading } = useQuery({
    queryKey: ["project-members", ns],
    queryFn: async () => {
      const resp = await projectMembers({ path: { project_name: ns } });
      return resp.data?.data ?? null;
    },
    enabled: !!namespace,
    staleTime: 30 * 1000,
  });

  const inviteMutation = useMutation({
    mutationFn: async () => {
      if (!inviteEmail.trim()) throw new Error("Email is required");
      await projectInviteUser({
        path: { project_name: ns },
        body: { email: inviteEmail.trim(), scope: inviteRole },
      });
    },
    onSuccess: () => {
      toast.success(`Invitation sent to ${inviteEmail}`);
      queryClient.invalidateQueries({ queryKey: ["project-members", ns] });
      setInviteEmail("");
      setIsInviting(false);
    },
    onError: (err: unknown) => {
      toast.error(getApiErrorMessage(err, "Failed to send invitation"));
    },
  });

  const removeMutation = useMutation({
    mutationFn: async (userId: string) => {
      await projectRemoveMember({ path: { project_name: ns, user_id: userId } });
    },
    onSuccess: () => {
      toast.success("Member removed");
      queryClient.invalidateQueries({ queryKey: ["project-members", ns] });
    },
    onError: (err: unknown) => {
      toast.error(getApiErrorMessage(err, "Failed to remove member"));
    },
  });

  const members: MemberInfo[] = membersData?.members ?? [];

  const roleBadgeColor = (scope: string) => {
    if (scope === "Owner") return "bg-purple-500/10 text-purple-600 border-purple-500/20";
    if (scope === "Admin") return "bg-red-500/10 text-red-600 border-red-500/20";
    return "bg-blue-500/10 text-blue-600 border-blue-500/20";
  };

  return (
    <div className="space-y-4">
      <div className="border rounded-lg bg-card">
        <div className="p-4 border-b flex items-center justify-between">
          <div>
            <h2 className="text-sm font-semibold">Members</h2>
            <p className="text-xs text-muted-foreground mt-0.5">{members.length} member{members.length !== 1 ? "s" : ""}</p>
          </div>
          {!isInviting && (
            <Button onClick={() => setIsInviting(true)} size="sm">
              <Plus className="h-3.5 w-3.5 mr-1" />
              Invite
            </Button>
          )}
        </div>
        {isLoading ? (
          <div className="p-8 flex justify-center">
            <Loader2 className="h-5 w-5 animate-spin text-muted-foreground" />
          </div>
        ) : members.length === 0 && !isInviting ? (
          <div className="p-8 text-center text-muted-foreground text-sm">No members found</div>
        ) : (
          <div className="divide-y">
            {members.map((member) => (
              <div key={member.user_id} className="flex items-center gap-3 px-4 py-3 hover:bg-muted/50">
                <div className="h-8 w-8 rounded-full bg-muted flex items-center justify-center flex-shrink-0 overflow-hidden">
                  {member.avatar_url ? (
                    <img src={member.avatar_url} alt={member.display_name ?? member.username} className="h-full w-full object-cover" />
                  ) : (
                    <span className="text-xs font-semibold text-muted-foreground">
                      {(member.display_name ?? member.username).charAt(0).toUpperCase()}
                    </span>
                  )}
                </div>
                <div className="flex-1 min-w-0">
                  <p className="text-sm font-medium truncate">
                    {member.display_name || member.username}
                    {member.display_name && <span className="text-muted-foreground ml-1">@{member.username}</span>}
                  </p>
                  <p className="text-xs text-muted-foreground">Joined {new Date(member.joined_at).toLocaleDateString()}</p>
                </div>
                <span className={`flex-shrink-0 text-xs px-2 py-0.5 rounded border ${roleBadgeColor(member.scope)}`}>
                  {member.scope}
                </span>
                {member.scope !== "Owner" && (
                  <Button
                    size="sm"
                    variant="ghost"
                    className="text-destructive hover:text-destructive flex-shrink-0"
                    onClick={() => removeMutation.mutate(member.user_id)}
                    disabled={removeMutation.isPending}
                  >
                    <Trash2 className="h-3.5 w-3.5" />
                  </Button>
                )}
              </div>
            ))}
          </div>
        )}
      </div>

      {isInviting && (
        <div className="border rounded-lg bg-card">
          <div className="p-4 border-b">
            <h2 className="text-sm font-semibold">Invite Member</h2>
          </div>
          <div className="p-4 space-y-3">
            <div>
              <Label className="text-xs">Email Address</Label>
              <Input
                type="email"
                value={inviteEmail}
                onChange={(e) => setInviteEmail(e.target.value)}
                placeholder="user@example.com"
                className="mt-1"
              />
            </div>
            <div>
              <Label className="text-xs">Role</Label>
              <div className="flex gap-2 mt-1">
                {(["Member", "Admin"] as const).map((role) => (
                  <button
                    key={role}
                    onClick={() => setInviteRole(role)}
                    className={`px-3 py-1.5 text-sm rounded-md border transition-colors ${
                      inviteRole === role
                        ? "bg-primary text-primary-foreground"
                        : "border-border hover:bg-muted"
                    }`}
                  >
                    {role}
                  </button>
                ))}
              </div>
            </div>
            <div className="flex gap-2">
              <Button
                size="sm"
                onClick={() => inviteMutation.mutate()}
                disabled={inviteMutation.isPending || !inviteEmail.trim()}
              >
                {inviteMutation.isPending && <Loader2 className="h-3.5 w-3.5 mr-1 animate-spin" />}
                Send Invitation
              </Button>
              <Button size="sm" variant="outline" onClick={() => setIsInviting(false)}>
                Cancel
              </Button>
            </div>
          </div>
        </div>
      )}
    </div>
  );
}
