| 1 |
import { useQuery, useMutation, useQueryClient } from "@tanstack/react-query"; |
| 2 |
import { apiClient } from "../lib/api-client"; |
| 3 |
|
| 4 |
/** |
| 5 |
* "New since you last looked" counts for the admin sidebar badges. |
| 6 |
* |
| 7 |
* Backed by GET /yatra/v1/admin/new-counts (markers live in wp_options; |
| 8 |
* see NotificationCountsController). Shared via a single react-query cache key |
| 9 |
* so the sidebar badges and the mark-seen effect stay in sync automatically. |
| 10 |
*/ |
| 11 |
export type NewCounts = { |
| 12 |
bookings?: number; |
| 13 |
payments?: number; |
| 14 |
enquiries?: number; |
| 15 |
reviews?: number; |
| 16 |
abandoned?: number; |
| 17 |
[section: string]: number | undefined; |
| 18 |
}; |
| 19 |
|
| 20 |
/** Sidebar subpages that carry a badge → the count key they map to. */ |
| 21 |
export const SUBPAGE_TO_SECTION: Record<string, string> = { |
| 22 |
bookings: "bookings", |
| 23 |
payments: "payments", |
| 24 |
enquiries: "enquiries", |
| 25 |
reviews: "reviews", |
| 26 |
"abandoned-recovery": "abandoned", |
| 27 |
}; |
| 28 |
|
| 29 |
export const NEW_COUNTS_QUERY_KEY = ["yatra", "admin", "new-counts"] as const; |
| 30 |
|
| 31 |
export function useNotificationCounts() { |
| 32 |
return useQuery<NewCounts>({ |
| 33 |
queryKey: NEW_COUNTS_QUERY_KEY, |
| 34 |
queryFn: async () => { |
| 35 |
const res = await apiClient.get("/admin/new-counts"); |
| 36 |
return (res?.counts ?? {}) as NewCounts; |
| 37 |
}, |
| 38 |
// Pick up new orders/payments while the admin sits on another page, |
| 39 |
// without hammering the server. |
| 40 |
staleTime: 30_000, |
| 41 |
refetchInterval: 60_000, |
| 42 |
refetchOnWindowFocus: true, |
| 43 |
// A failed counts call must never break the admin UI — just render no badge. |
| 44 |
retry: 1, |
| 45 |
}); |
| 46 |
} |
| 47 |
|
| 48 |
/** |
| 49 |
* Mark a section seen (bumps its marker to MAX(id) server-side), then refresh |
| 50 |
* the shared counts so the badge clears immediately. |
| 51 |
*/ |
| 52 |
export function useMarkSectionSeen() { |
| 53 |
const queryClient = useQueryClient(); |
| 54 |
|
| 55 |
return useMutation({ |
| 56 |
mutationFn: async (section: string) => { |
| 57 |
return apiClient.post("/admin/mark-seen", { section }); |
| 58 |
}, |
| 59 |
onSuccess: () => { |
| 60 |
queryClient.invalidateQueries({ queryKey: NEW_COUNTS_QUERY_KEY }); |
| 61 |
}, |
| 62 |
}); |
| 63 |
} |
| 64 |
|