diff --git a/client/src/shared/auth/AuthProvider.tsx b/client/src/shared/auth/AuthProvider.tsx index 07c1343..71274da 100644 --- a/client/src/shared/auth/AuthProvider.tsx +++ b/client/src/shared/auth/AuthProvider.tsx @@ -6,6 +6,10 @@ import { getStoredToken, clearStoredToken } from "./token-storage.ts"; export type AuthUser = ApiCurrentUserDto; +const isAbortError = (e: unknown): boolean => { + return e instanceof DOMException && e.name === "AbortError"; +}; + const AuthContext = createContext< | { user: AuthUser | null; @@ -33,8 +37,12 @@ export const AuthProvider: React.FC<{ children: ReactNode }> = ({ children }) => setUser(current); if (!current) clearStoredToken(); }) - .catch(() => setUser(null)) - .finally(() => setLoading(false)); + .catch((e) => { + if (!isAbortError(e)) setUser(null); + }) + .finally(() => { + if (!abortController.signal.aborted) setLoading(false); + }); return () => abortController.abort(); }, []); diff --git a/client/src/shared/auth/__tests__/AuthProvider.test.tsx b/client/src/shared/auth/__tests__/AuthProvider.test.tsx new file mode 100644 index 0000000..be227ec --- /dev/null +++ b/client/src/shared/auth/__tests__/AuthProvider.test.tsx @@ -0,0 +1,73 @@ +/** @jest-environment jsdom */ + +const getCurrentUserMock = jest.fn(); + +jest.mock("@features/auth/apis", () => ({ + getCurrentUser: (...args: unknown[]) => getCurrentUserMock(...args), +})); + +import { StrictMode } from "react"; +import { render, screen, waitFor } from "@testing-library/react"; +import { AuthProvider } from "../AuthProvider"; +import { useAuth } from "../AuthHooks"; +import type { ApiCurrentUserDto } from "@features/auth/apis/auth-api.ts"; + +const user: ApiCurrentUserDto = { + id: 1, + first_name: "Taro", + last_name: "Yamada", + email: "taro@example.com", +}; + +type LogEntry = { isLoading: boolean; user: unknown }; + +function Probe({ log }: { log: LogEntry[] }) { + const { isLoading, user } = useAuth(); + log.push({ isLoading, user }); + return