import { useState, useEffect, useCallback } from 'react';
import { RoleDTO, PageResponse, PageRequest } from '@/types/backend';
import { api } from '@/services/api';

interface UseRolesOptions extends PageRequest {
  autoFetch?: boolean;
}

interface UseRolesReturn {
  roles: RoleDTO[];
  loading: boolean;
  error: string | null;
  page: number;
  totalPages: number;
  totalElements: number;
  refetch: () => Promise<void>;
  setPage: (page: number) => void;
  createRole: (role: Omit<RoleDTO, 'id'>) => Promise<RoleDTO>;
  updateRole: (id: string, role: Partial<RoleDTO>) => Promise<RoleDTO>;
  getRoleById: (id: string) => Promise<RoleDTO>;
  deleteRole: (id: string) => Promise<void>;
}

export function useRoles(options: UseRolesOptions = {}): UseRolesReturn {
  const {
    page: initialPage = 0,
    size = 20,
    sortBy,
    sortDirection = 'ASC',
    autoFetch = true,
  } = options;

  const [roles, setRoles] = useState<RoleDTO[]>([]);
  const [loading, setLoading] = useState(true);
  const [error, setError] = useState<string | null>(null);
  const [page, setPage] = useState(initialPage);
  const [totalPages, setTotalPages] = useState(0);
  const [totalElements, setTotalElements] = useState(0);

  const fetchRoles = useCallback(async () => {
    try {
      setLoading(true);
      setError(null);
      const response: PageResponse<RoleDTO> = await api.getPage<RoleDTO>(
        '/admin/roles',
        {
          page,
          size,
          sortBy,
          sortDirection,
        }
      );
      setRoles(response.content);
      setTotalPages(response.totalPages);
      setTotalElements(response.totalElements);
    } catch (err: any) {
      const errorMessage =
        err.response?.data?.message ||
        err.message ||
        'Erro ao carregar perfis';
      setError(errorMessage);
      console.error('Erro ao buscar perfis:', err);
    } finally {
      setLoading(false);
    }
  }, [page, size, sortBy, sortDirection]);

  useEffect(() => {
    if (autoFetch) {
      fetchRoles();
    }
  }, [fetchRoles, autoFetch]);

  const createRole = async (role: Omit<RoleDTO, 'id'>): Promise<RoleDTO> => {
    try {
      setError(null);
      const newRole = await api.post<RoleDTO>('/admin/roles', role);
      await fetchRoles();
      return newRole;
    } catch (err: any) {
      const errorMessage =
        err.response?.data?.message ||
        err.message ||
        'Erro ao criar perfil';
      setError(errorMessage);
      throw new Error(errorMessage);
    }
  };

  const updateRole = async (id: string, role: Partial<RoleDTO>): Promise<RoleDTO> => {
    try {
      setError(null);
      const updated = await api.put<RoleDTO>(`/admin/roles/${id}`, role);
      await fetchRoles();
      return updated;
    } catch (err: any) {
      const errorMessage =
        err.response?.data?.message ||
        err.message ||
        'Erro ao atualizar perfil';
      setError(errorMessage);
      throw new Error(errorMessage);
    }
  };

  const getRoleById = async (id: string): Promise<RoleDTO> => {
    try {
      setError(null);
      const role = await api.get<RoleDTO>(`/admin/roles/${id}`);
      return role;
    } catch (err: any) {
      const errorMessage =
        err.response?.data?.message ||
        err.message ||
        'Erro ao buscar perfil';
      setError(errorMessage);
      throw new Error(errorMessage);
    }
  };

  const deleteRole = async (id: string): Promise<void> => {
    try {
      setError(null);
      await api.delete(`/admin/roles/${id}`);
      await fetchRoles();
    } catch (err: any) {
      const errorMessage =
        err.response?.data?.message ||
        err.message ||
        'Erro ao excluir perfil';
      setError(errorMessage);
      throw new Error(errorMessage);
    }
  };

  return {
    roles,
    loading,
    error,
    page,
    totalPages,
    totalElements,
    refetch: fetchRoles,
    setPage,
    createRole,
    updateRole,
    getRoleById,
    deleteRole,
  };
}

export function useRole(id: string) {
  const [role, setRole] = useState<RoleDTO | null>(null);
  const [loading, setLoading] = useState(true);
  const [error, setError] = useState<string | null>(null);

  useEffect(() => {
    const fetchRole = async () => {
      if (!id) return;
      
      setLoading(true);
      setError(null);
      
      try {
        const data = await api.get<RoleDTO>(`/admin/roles/${id}`);
        setRole(data);
      } catch (err: any) {
        const errorMessage =
          err.response?.data?.message ||
          err.message ||
          'Erro ao buscar perfil';
        setError(errorMessage);
      } finally {
        setLoading(false);
      }
    };

    fetchRole();
  }, [id]);

  return { role, loading, error };
}

