diff --git a/lib/api/account.ts b/lib/api/account.ts index 81df02f..0cfdfb5 100644 --- a/lib/api/account.ts +++ b/lib/api/account.ts @@ -1,5 +1,5 @@ -import { makeRequest } from "."; -import { UserAccount, UserName } from ".."; +import { UserAccount, UserName } from "../model/account"; +import { makeRequest } from "./makeRequest"; const apiUrl = process.env.NODE_ENV === "production" ? "/customer" : "https://hub.pena.digital/customer"; diff --git a/lib/hooks/index.ts b/lib/hooks/index.ts index 97a344c..0fbd7bb 100644 --- a/lib/hooks/index.ts +++ b/lib/hooks/index.ts @@ -7,3 +7,5 @@ export * from "./useThrottle"; export * from "./useTicketMessages"; export * from "./useTickets"; export * from "./useToken"; +export * from "./useUserFetcher"; +export * from "./useUserAccountFetcher"; diff --git a/lib/hooks/useUserAccountFetcher.ts b/lib/hooks/useUserAccountFetcher.ts new file mode 100644 index 0000000..5212b35 --- /dev/null +++ b/lib/hooks/useUserAccountFetcher.ts @@ -0,0 +1,54 @@ +import { isAxiosError } from "axios"; +import { useEffect, useLayoutEffect, useRef } from "react"; +import { UserAccount } from "../model/account"; +import { makeRequest } from "../api/makeRequest"; +import { devlog } from "../utils/devlog"; +import { createUserAccount } from "../api/account"; + + +export function useUserAccountFetcher({ onError, onNewUserAccount, url, userId }: { + url: string; + userId: string | null; + onNewUserAccount: (response: UserAccount) => void; + onError?: (error: any) => void; +}) { + const onNewUserAccountRef = useRef(onNewUserAccount); + const onErrorRef = useRef(onError); + + useLayoutEffect(() => { + onNewUserAccountRef.current = onNewUserAccount; + onErrorRef.current = onError; + }, [onError, onNewUserAccount]); + + useEffect(() => { + if (!userId) return; + + const controller = new AbortController(); + makeRequest({ + url, + contentType: true, + method: "GET", + useToken: true, + withCredentials: false, + signal: controller.signal, + }).then(result => { + devlog("User account", result); + onNewUserAccountRef.current(result); + }).catch(error => { + devlog("Error fetching user account", error); + if (isAxiosError(error) && error.response?.status === 404) { + createUserAccount(controller.signal).then(result => { + devlog("Created user account", result); + onNewUserAccountRef.current(result); + }).catch(error => { + devlog("Error creating user account", error); + onErrorRef.current?.(error); + }); + } else { + onErrorRef.current?.(error); + } + }); + + return () => controller.abort(); + }, [url, userId]); +} diff --git a/lib/hooks/useUserFetcher.ts b/lib/hooks/useUserFetcher.ts new file mode 100644 index 0000000..a2bffb8 --- /dev/null +++ b/lib/hooks/useUserFetcher.ts @@ -0,0 +1,43 @@ +import { useEffect, useLayoutEffect, useRef } from "react"; +import { User } from "../model/user"; +import { devlog } from "../utils/devlog"; +import { makeRequest } from "../api/makeRequest"; + + +export function useUserFetcher({ onError, onNewUser, url, userId }: { + url: string; + userId: string | null; + onNewUser: (response: User) => void; + onError?: (error: any) => void; +}) { + const onNewUserRef = useRef(onNewUser); + const onErrorRef = useRef(onError); + + useLayoutEffect(() => { + onNewUserRef.current = onNewUser; + onErrorRef.current = onError; + }, [onError, onNewUser]); + + useEffect(() => { + if (!userId) return; + + const controller = new AbortController(); + + makeRequest({ + url, + contentType: true, + method: "GET", + useToken: true, + withCredentials: false, + signal: controller.signal, + }).then(result => { + devlog("User", result); + onNewUserRef.current(result); + }).catch(error => { + devlog("Error fetching user", error); + onErrorRef.current?.(error); + }); + + return () => controller.abort(); + }, [url, userId]); +}