mirror of
https://github.com/Tria-plc/edr-platform.git
synced 2026-09-09 01:18:18 +00:00
168 lines
5.0 KiB
TypeScript
168 lines
5.0 KiB
TypeScript
import { useMutation, useQuery, useQueryClient } from "@tanstack/react-query";
|
|
import toast from "react-hot-toast";
|
|
|
|
import { QUERY_KEYS } from "@/constants/QUERY_KEYS";
|
|
import { api } from "@/services/api";
|
|
import {
|
|
bookingsService,
|
|
type BookingListFilter,
|
|
} from "@/services/bookings.service";
|
|
import { invalidateBookingDetail } from "@/utils/queryInvalidation";
|
|
|
|
export function useBookingList(filter?: BookingListFilter, enabled = true) {
|
|
return useQuery({
|
|
queryKey: QUERY_KEYS.BOOKINGS.list(filter),
|
|
queryFn: () => bookingsService.list(filter),
|
|
enabled,
|
|
});
|
|
}
|
|
|
|
export function useBookingListSummary(filter?: BookingListFilter, enabled = true) {
|
|
return useQuery({
|
|
queryKey: QUERY_KEYS.BOOKINGS.listSummary(filter),
|
|
queryFn: () => bookingsService.getListSummary(filter),
|
|
enabled,
|
|
});
|
|
}
|
|
|
|
export function useBookingDetail(id: string | undefined) {
|
|
return useQuery({
|
|
queryKey: QUERY_KEYS.BOOKINGS.byId(id ?? ""),
|
|
queryFn: () => bookingsService.getById(id!),
|
|
enabled: Boolean(id),
|
|
});
|
|
}
|
|
|
|
export function useBookingMutations(bookingId: string) {
|
|
const qc = useQueryClient();
|
|
const onSuccess = (data: { id: string }, message: string) => {
|
|
toast.success(message);
|
|
void invalidateBookingDetail(qc, data.id);
|
|
};
|
|
|
|
const staffAccept = useMutation({
|
|
mutationFn: () => api.bookings.staffAccept.call({ id: bookingId }),
|
|
onSuccess: (data) => onSuccess(data, "Booking accepted for approval"),
|
|
onError: () => toast.error("Failed to accept booking"),
|
|
});
|
|
|
|
const requestChanges = useMutation({
|
|
mutationFn: (note: string) =>
|
|
api.bookings.requestChanges.call({ id: bookingId, note }),
|
|
onSuccess: (data) => onSuccess(data, "Changes requested from customer"),
|
|
onError: () => toast.error("Failed to request changes"),
|
|
});
|
|
|
|
const staffReject = useMutation({
|
|
mutationFn: (reason: string) =>
|
|
api.bookings.staffReject.call({ id: bookingId, reason }),
|
|
onSuccess: (data) => onSuccess(data, "Booking rejected"),
|
|
onError: () => toast.error("Failed to reject booking"),
|
|
});
|
|
|
|
const approveStep = useMutation({
|
|
mutationFn: ({
|
|
stepId,
|
|
requiredRole,
|
|
}: {
|
|
stepId: string;
|
|
requiredRole: string;
|
|
}) =>
|
|
api.bookings.approveStep.call({
|
|
id: bookingId,
|
|
stepId,
|
|
requiredRole,
|
|
}),
|
|
onSuccess: (data) => onSuccess(data, "Approval step completed"),
|
|
onError: () => toast.error("Failed to approve step"),
|
|
});
|
|
|
|
const rejectStep = useMutation({
|
|
mutationFn: ({
|
|
stepId,
|
|
reason,
|
|
}: {
|
|
stepId: string;
|
|
reason: string;
|
|
}) =>
|
|
api.bookings.rejectStep.call({
|
|
id: bookingId,
|
|
stepId,
|
|
reason,
|
|
}),
|
|
onSuccess: (data) => onSuccess(data, "Booking rejected at approval step"),
|
|
onError: () => toast.error("Failed to reject step"),
|
|
});
|
|
|
|
const generateContract = useMutation({
|
|
mutationFn: () => api.bookings.generateContract.call({ id: bookingId }),
|
|
onSuccess: (data) => onSuccess(data, "Contract generated"),
|
|
onError: () => toast.error("Failed to generate contract"),
|
|
});
|
|
|
|
const signContract = useMutation({
|
|
mutationFn: (payload: {
|
|
role: "CUSTOMER" | "STAFF";
|
|
signatureImageBase64: string;
|
|
signerDisplayName: string;
|
|
consentText?: string;
|
|
}) => bookingsService.signContract(bookingId, payload),
|
|
onSuccess: (data) => onSuccess(data, "Contract signed"),
|
|
onError: () => toast.error("Failed to sign contract"),
|
|
});
|
|
|
|
const payBooking = useMutation({
|
|
mutationFn: () => api.bookings.payBooking.call({ id: bookingId }),
|
|
onSuccess: (data) => onSuccess(data, "Payment completed"),
|
|
onError: () => toast.error("Failed to complete payment"),
|
|
});
|
|
|
|
const startTransit = useMutation({
|
|
mutationFn: () => api.bookings.startTransit.call({ id: bookingId }),
|
|
onSuccess: (data) => onSuccess(data, "Marked in transit"),
|
|
onError: () => toast.error("Failed to start transit"),
|
|
});
|
|
|
|
const complete = useMutation({
|
|
mutationFn: () => api.bookings.complete.call({ id: bookingId }),
|
|
onSuccess: (data) => onSuccess(data, "Booking completed"),
|
|
onError: () => toast.error("Failed to complete booking"),
|
|
});
|
|
|
|
const cancel = useMutation({
|
|
mutationFn: (reason: string) =>
|
|
api.bookings.cancel.call({ id: bookingId, reason }),
|
|
onSuccess: (data) => onSuccess(data, "Booking cancelled"),
|
|
onError: () => toast.error("Failed to cancel booking"),
|
|
});
|
|
|
|
const isPending =
|
|
staffAccept.isPending ||
|
|
requestChanges.isPending ||
|
|
staffReject.isPending ||
|
|
approveStep.isPending ||
|
|
rejectStep.isPending ||
|
|
generateContract.isPending ||
|
|
signContract.isPending ||
|
|
payBooking.isPending ||
|
|
startTransit.isPending ||
|
|
complete.isPending ||
|
|
cancel.isPending;
|
|
|
|
return {
|
|
staffAccept,
|
|
requestChanges,
|
|
staffReject,
|
|
approveStep,
|
|
rejectStep,
|
|
generateContract,
|
|
signContract,
|
|
payBooking,
|
|
startTransit,
|
|
complete,
|
|
cancel,
|
|
isPending,
|
|
downloadContract: () => bookingsService.downloadContract(bookingId),
|
|
};
|
|
}
|