mirror of
https://github.com/Tria-plc/edr-platform.git
synced 2026-08-30 11:08:12 +00:00
Check payment before generating ticket
This commit is contained in:
@@ -68,7 +68,7 @@ export default function ConfirmationPage() {
|
|||||||
import("@/lib/generate-voucher");
|
import("@/lib/generate-voucher");
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
const { data: _booking } = useQuery<BookingWithTicket>({
|
const { data: _booking, refetch: refetchBooking } = useQuery<BookingWithTicket>({
|
||||||
queryKey: ["booking", bookingId],
|
queryKey: ["booking", bookingId],
|
||||||
queryFn: async (): Promise<BookingWithTicket> => {
|
queryFn: async (): Promise<BookingWithTicket> => {
|
||||||
try {
|
try {
|
||||||
@@ -88,6 +88,23 @@ export default function ConfirmationPage() {
|
|||||||
enabled: !!bookingId,
|
enabled: !!bookingId,
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// Poll the payment intent every 10 s while the booking is PENDING_PAYMENT.
|
||||||
|
// The backend auto-confirms (and generates tickets) when the payment-api reports
|
||||||
|
// SUCCEEDED, so detecting that here means the booking is now CONFIRMED — refetch
|
||||||
|
// to update the UI without requiring the user to refresh.
|
||||||
|
const { data: intentStatus } = useQuery<any>({
|
||||||
|
queryKey: ["payment-intent-status", bookingId],
|
||||||
|
queryFn: () => apiClient.get(`/payments/intents/${bookingId}`),
|
||||||
|
enabled: _booking?.status === "PENDING_PAYMENT" && !!bookingId,
|
||||||
|
refetchInterval: 10_000,
|
||||||
|
});
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
if (intentStatus?.status === "SUCCEEDED") {
|
||||||
|
refetchBooking();
|
||||||
|
}
|
||||||
|
}, [intentStatus?.status]);
|
||||||
|
|
||||||
// Only trust an actually-confirmed booking to show ticket numbers / a "CONFIRMED" badge —
|
// Only trust an actually-confirmed booking to show ticket numbers / a "CONFIRMED" badge —
|
||||||
// a gateway redirect back here does not mean payment succeeded (see payment return pages).
|
// a gateway redirect back here does not mean payment succeeded (see payment return pages).
|
||||||
// Ticket generation itself is never triggered from this page — the payment webhook
|
// Ticket generation itself is never triggered from this page — the payment webhook
|
||||||
|
|||||||
@@ -125,6 +125,22 @@ function BookingDetailContent() {
|
|||||||
booking?.status === "PENDING_PAYMENT" || booking?.status === "DRAFT",
|
booking?.status === "PENDING_PAYMENT" || booking?.status === "DRAFT",
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// When the booking is PENDING_PAYMENT, poll the payment intent endpoint every 10 s.
|
||||||
|
// The backend auto-confirms the booking when it finds a SUCCEEDED intent, so detecting
|
||||||
|
// SUCCEEDED here means the booking is now CONFIRMED — refetch to update the UI.
|
||||||
|
const { data: intentStatus } = useQuery<any>({
|
||||||
|
queryKey: ["payment-intent-status", booking?.id],
|
||||||
|
queryFn: () => apiClient.get(`/payments/intents/${booking!.id}`),
|
||||||
|
enabled: booking?.status === "PENDING_PAYMENT" && !!booking?.id,
|
||||||
|
refetchInterval: 10_000,
|
||||||
|
});
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
if (intentStatus?.status === "SUCCEEDED") {
|
||||||
|
refetch();
|
||||||
|
}
|
||||||
|
}, [intentStatus?.status]);
|
||||||
|
|
||||||
const selectedPaymentMethod =
|
const selectedPaymentMethod =
|
||||||
(paymentMethods || []).find((m: any) => m.type === selectedMethod) || null;
|
(paymentMethods || []).find((m: any) => m.type === selectedMethod) || null;
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user