import { useModalsManagerContext } from "@/contexts/ModalsManagerContext"; import type { IpaymentStackNavigator } from "@/navigations/Types"; import { type IwavePaymentStarter, getTransactionStatus, initTransaction, } from "@/utils/requests/wavePayment"; import ErrorModal from "@components/modals/ErrorModal"; import LoadingModal from "@components/modals/LoadingModal"; import { LOG } from "@logger"; import type { NativeStackNavigationProp } from "@react-navigation/native-stack"; import { useMutation, useQueryClient } from "@tanstack/react-query"; import * as WebBrowser from "expo-web-browser"; import { useState } from "react"; const log = LOG.extend("useWave"); const paymentObjectDefault: IwavePaymentStarter = { // biome-ignore lint/style/useNamingConvention: type_paiement: 2, marchand: "1", service: "2", montant: 0, }; const useWave = ( navigation?: NativeStackNavigationProp< IpaymentStackNavigator, "paymentAmountInputScreen", "IpaymentStackNavigator" >, ) => { const { showModal, closeModal } = useModalsManagerContext(); const [isBrowserOpen, setIsBrowserOpen] = useState(false); const queryClient = useQueryClient(); // Mutations const waveTransactionInitializerMutation = useMutation({ mutationFn: (amount: number) => initTransaction({ ...paymentObjectDefault, montant: amount, }), onSuccess: (data) => {}, onError: (err) => { log.error("waveTransactionInitializerMutation |", err); }, }); const waveTransactionStatusMutation = useMutation({ mutationFn: (orderId: string) => getTransactionStatus(orderId), onSuccess: (data) => { log.debug("waveTransactionStatusMutation request success"); }, onError: (err) => { log.error("waveTransactionStatusMutation |", err); }, }); // Browser stuff const handlePaymentUsingBrowser = async (url: string) => { log.debug("handlePaymentUsingBrowser | Opening the browser at url :: ", url); setIsBrowserOpen(true); const result = await WebBrowser.openBrowserAsync(url); // setResult(result); log.debug("handlePaymentUsingBrowser | Result ::", result); setIsBrowserOpen(false); }; const openBrowserThenCheckStatus = async (paymentUrl: string, orderId: string) => { try { await handlePaymentUsingBrowser(paymentUrl); log.info("openBrowserThenCheckStatus | Verifying transaction status..."); showModal(); await waveTransactionStatusMutation.mutateAsync(orderId); closeModal(); // navigation?.getParent()?.navigate("paymentResultScreen"); } catch (error) { log.error("openBrowserThenCheckStatus |", error); // if (error instanceof Error) { // if (error.name === "ORANGE_PAYMENT_IN_PROGRESS") { // log.warn("openBrowserThenCheckStatus | ORANGE_PAYMENT_IN_PROGRESS"); // await showModal( // openBrowserThenCheckStatus(paymentUrl, orderId)} // />, // ); // } else if (error.name === "ORANGE_PAYMENT_FAILED") { // showModal(); // log.error("openBrowserThenCheckStatus | ORANGE_PAYMENT_FAILED"); // } // } else { // log.error("openBrowserThenCheckStatus |", error); // closeModal(); // throw error; // } } }; // Handlers const waveTransactionHandler = async (amount: number) => { try { showModal(); const response = await waveTransactionInitializerMutation.mutateAsync(amount); log.info("waveTransactionHandler payment url received :: ", response.wave_launch_url); // log.info("Opening browser for payment..."); log.info("Navigating to the qr code screen..."); closeModal(); navigation?.getParent()?.navigate("waveQrCodePaymentScreen", { data: response }); // await openBrowserThenCheckStatus(response.wave_launch_url, response.id); } catch (error) { log.error("waveTransactionHandler |", error); showModal(); throw error; } }; const handlePaymentVerification = async (id: string) => { log.info("handlePaymentVerification |", id); try { showModal(); const response = await waveTransactionStatusMutation.mutateAsync(id); closeModal(); } catch (error) { log.error("handlePaymentVerification |", error); // closeModal(); // showModal(); } finally { // TODO : remove this finally block once a proper implementation workflow is set. currently we close the modal after logging whatever response we get from the request closeModal(); } }; return { waveTransactionInitializerMutation, waveTransactionHandler, handlePaymentVerification, }; }; export default useWave;