feat(auth): add pending action queue and api auth wrapper
This commit is contained in:
@@ -0,0 +1,24 @@
|
|||||||
|
import { useLoginDialogStore } from "@/store/login-dialog"
|
||||||
|
|
||||||
|
type RequestExecutor<T> = () => Promise<T>
|
||||||
|
|
||||||
|
interface RequestOptions {
|
||||||
|
onUnauthorized?: () => void
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function requestWithAuth<T>(executor: RequestExecutor<T>, options?: RequestOptions) {
|
||||||
|
try {
|
||||||
|
return await executor()
|
||||||
|
} catch (error) {
|
||||||
|
if (error instanceof Error && error.message === "UNAUTHORIZED") {
|
||||||
|
if (options?.onUnauthorized) {
|
||||||
|
useLoginDialogStore.getState().openLoginDialog(options.onUnauthorized)
|
||||||
|
} else {
|
||||||
|
useLoginDialogStore.getState().openLoginDialog()
|
||||||
|
}
|
||||||
|
return null
|
||||||
|
}
|
||||||
|
|
||||||
|
throw error
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,4 +1,5 @@
|
|||||||
export { getChatSessionById, listChatMessages, listChatSessions } from "./chat"
|
export { getChatSessionById, listChatMessages, listChatSessions } from "./chat"
|
||||||
|
export { requestWithAuth } from "./client"
|
||||||
export { listComments, listCommentsByPost } from "./comments"
|
export { listComments, listCommentsByPost } from "./comments"
|
||||||
export { getDisputeByOrderId, listDisputes } from "./disputes"
|
export { getDisputeByOrderId, listDisputes } from "./disputes"
|
||||||
export { isFavorited, listFavorites, listFavoritesByUser } from "./favorites"
|
export { isFavorited, listFavorites, listFavoritesByUser } from "./favorites"
|
||||||
|
|||||||
+13
-7
@@ -2,7 +2,7 @@ import { create } from "zustand"
|
|||||||
|
|
||||||
interface LoginDialogState {
|
interface LoginDialogState {
|
||||||
open: boolean
|
open: boolean
|
||||||
pendingAction: (() => void) | null
|
pendingActions: Array<() => void>
|
||||||
openLoginDialog: (action?: () => void) => void
|
openLoginDialog: (action?: () => void) => void
|
||||||
closeLoginDialog: () => void
|
closeLoginDialog: () => void
|
||||||
consumePendingAction: () => void
|
consumePendingAction: () => void
|
||||||
@@ -10,12 +10,18 @@ interface LoginDialogState {
|
|||||||
|
|
||||||
export const useLoginDialogStore = create<LoginDialogState>((set, get) => ({
|
export const useLoginDialogStore = create<LoginDialogState>((set, get) => ({
|
||||||
open: false,
|
open: false,
|
||||||
pendingAction: null,
|
pendingActions: [],
|
||||||
openLoginDialog: (action) => set({ open: true, pendingAction: action ?? null }),
|
openLoginDialog: (action) =>
|
||||||
closeLoginDialog: () => set({ open: false, pendingAction: null }),
|
set((state) => ({
|
||||||
|
open: true,
|
||||||
|
pendingActions: action ? [...state.pendingActions, action] : state.pendingActions,
|
||||||
|
})),
|
||||||
|
closeLoginDialog: () => set({ open: false, pendingActions: [] }),
|
||||||
consumePendingAction: () => {
|
consumePendingAction: () => {
|
||||||
const action = get().pendingAction
|
const actions = get().pendingActions
|
||||||
set({ pendingAction: null })
|
set({ pendingActions: [] })
|
||||||
action?.()
|
actions.forEach((action) => {
|
||||||
|
action()
|
||||||
|
})
|
||||||
},
|
},
|
||||||
}))
|
}))
|
||||||
|
|||||||
Reference in New Issue
Block a user