diff --git a/client/src/contexts/AuthContext.jsx b/client/src/contexts/AuthContext.jsx index 49059ce..707a876 100644 --- a/client/src/contexts/AuthContext.jsx +++ b/client/src/contexts/AuthContext.jsx @@ -66,6 +66,16 @@ export const AuthProvider = ({ children }) => { } }, []); + // Listen for auth logout events from API interceptor + useEffect(() => { + const handleAuthLogout = () => { + dispatch({ type: 'LOGOUT' }); + }; + + window.addEventListener('auth-logout', handleAuthLogout); + return () => window.removeEventListener('auth-logout', handleAuthLogout); + }, []); + const checkAuthStatus = async () => { try { dispatch({ type: 'SET_LOADING', payload: true }); diff --git a/client/src/services/api.js b/client/src/services/api.js index 5944d7c..574134c 100644 --- a/client/src/services/api.js +++ b/client/src/services/api.js @@ -46,12 +46,10 @@ api.interceptors.response.use( (response) => response, (error) => { if (error.response?.status === 401) { - // Token expired or invalid - let AuthContext handle this + // Token expired or invalid - remove token and let ProtectedRoute handle navigation localStorage.removeItem('token'); - // Only redirect if not already on login page - if (window.location.pathname !== '/login') { - window.location.href = '/login'; - } + // Force a state update by dispatching a custom event + window.dispatchEvent(new CustomEvent('auth-logout')); } return Promise.reject(error); }