import { useState, useEffect, useContext, createContext } from 'react';
import ApiService from '../services/api';

// Create Auth Context
const AuthContext = createContext();

// Auth Provider Component
export const AuthProvider = ({ children }) => {
  const [user, setUser] = useState(null);
  const [loading, setLoading] = useState(true);
  const [error, setError] = useState(null);

  // Check for existing authentication on mount
  useEffect(() => {
    checkAuthStatus();
  }, []);

  const checkAuthStatus = async () => {
    try {
      setLoading(true);
      setError(null);
      
      // Check if we have stored auth data
      if (ApiService.isAuthenticated()) {
        const userData = ApiService.getCurrentUserData();
        
        // Verify token is still valid by making a request
        try {
          const currentUser = await ApiService.getCurrentUser();
          setUser(currentUser);
          
          // Trigger role-based preloading
          if (typeof window !== 'undefined' && window.roleBasedPreload) {
            window.roleBasedPreload(currentUser.rol);
          }
        } catch (error) {
          // Token is invalid, clear stored data
          console.error('Token validation failed:', error);
          await logout();
        }
      }
    } catch (error) {
      console.error('Auth status check failed:', error);
      setError('Error al verificar el estado de autenticación');
    } finally {
      setLoading(false);
    }
  };

  const login = async (credentials) => {
    try {
      setLoading(true);
      setError(null);
      
      const response = await ApiService.login(credentials);
      
      if (response.user) {
        setUser(response.user);
        
        // Trigger role-based preloading after successful login
        if (typeof window !== 'undefined' && window.roleBasedPreload) {
          window.roleBasedPreload(response.user.rol);
        }
        
        return { success: true, user: response.user };
      } else {
        throw new Error('Respuesta de login inválida');
      }
    } catch (error) {
      console.error('Login failed:', error);
      setError(error.message || 'Error al iniciar sesión');
      return { success: false, error: error.message };
    } finally {
      setLoading(false);
    }
  };

  const logout = async () => {
    try {
      setLoading(true);
      await ApiService.logout();
    } catch (error) {
      console.error('Logout error:', error);
    } finally {
      setUser(null);
      setError(null);
      setLoading(false);
    }
  };

  const refreshToken = async () => {
    try {
      const response = await ApiService.refreshToken();
      if (response.token) {
        // Token refreshed successfully
        return true;
      }
      return false;
    } catch (error) {
      console.error('Token refresh failed:', error);
      await logout();
      return false;
    }
  };

  // Check if user has specific role
  const hasRole = (role) => {
    return user?.rol === role;
  };

  // Check if user has any of the specified roles
  const hasAnyRole = (roles) => {
    return roles.includes(user?.rol);
  };

  // Check if user can access admin features
  const isAdmin = () => {
    return hasRole('Administrador');
  };

  // Check if user can manage projects
  const canManageProjects = () => {
    return hasAnyRole(['Administrador', 'Regente']);
  };

  // Check if user can use field app
  const canUseFieldApp = () => {
    return hasAnyRole(['Administrador', 'Regente', 'Técnico de Campo']);
  };

  const value = {
    user,
    loading,
    error,
    login,
    logout,
    refreshToken,
    checkAuthStatus,
    hasRole,
    hasAnyRole,
    isAdmin,
    canManageProjects,
    canUseFieldApp,
    isAuthenticated: !!user,
  };

  return (
    <AuthContext.Provider value={value}>
      {children}
    </AuthContext.Provider>
  );
};

// Custom hook to use auth context
export const useAuth = () => {
  const context = useContext(AuthContext);
  
  if (!context) {
    throw new Error('useAuth must be used within an AuthProvider');
  }
  
  return context;
};

export default useAuth;