/** biome-ignore-all lint/nursery/useUniqueElementIds: "id" is not a html attribute here - TODO: stop using 'id' as a prop on JSX elements */ "use client"; import { ReloadIcon } from "@radix-ui/react-icons"; import { useMutation, useQuery, useQueryClient } from "@tanstack/react-query"; import { useState } from "react"; import type { Chain } from "../../../../../chains/types.js"; import type { ThirdwebClient } from "../../../../../client/client.js"; import { createWalletConnectClient, createWalletConnectSession, disconnectWalletConnectSession, getActiveWalletConnectSessions, } from "../../../../../wallets/wallet-connect/receiver/index.js"; import { iconSize, spacing } from "../../../../core/design-system/index.js"; import { useActiveWallet } from "../../../../core/hooks/wallets/useActiveWallet.js"; import { InputSelectionUI } from "../../../wallets/in-app/InputSelectionUI.js"; import { Container, Line, ModalHeader } from "../../components/basic.js"; import { Button } from "../../components/buttons.js"; import { Spacer } from "../../components/Spacer.js"; import { Text } from "../../components/text.js"; import { WalletConnectDisconnectScreen } from "./WalletConnectDisconnectScreen.js"; import { WalletLogoSpinner } from "./WalletLogoSpinner.js"; /** * @internal */ export function WalletConnectReceiverScreen(props: { onBack: () => void; client: ThirdwebClient; chains?: Chain[]; }) { const activeWallet = useActiveWallet(); const [loading, setLoading] = useState(false); const [errorConnecting, setErrorConnecting] = useState(false); const queryClient = useQueryClient(); const { data: walletConnectClient } = useQuery({ enabled: !!activeWallet, queryFn: async () => { if (!activeWallet) return; try { const client = await createWalletConnectClient({ chains: props.chains, client: props.client, onConnect: () => { setLoading(false); queryClient.invalidateQueries({ queryKey: ["walletConnectSession"], }); }, onDisconnect: () => { setLoading(false); queryClient.invalidateQueries({ queryKey: ["walletConnectSession"], }); }, onError: (error) => { setErrorConnecting(error.message); setLoading(false); }, wallet: activeWallet, }); return client; } catch { setErrorConnecting("Failed to establish WalletConnect connection"); return; } }, queryKey: ["walletConnectClient"], retry: false, }); const { data: session, refetch: refetchSession } = useQuery({ enabled: !!walletConnectClient, queryFn: async () => { if (!walletConnectClient) return null; const sessions = await getActiveWalletConnectSessions(); return sessions[0] || null; }, queryKey: ["walletConnectSession"], }); const { mutateAsync: disconnect } = useMutation({ mutationFn: async () => { if (!walletConnectClient || !session) throw new Error("No session"); await disconnectWalletConnectSession({ session: session, walletConnectClient: walletConnectClient, }); }, onError: (error) => { console.error(error); setErrorConnecting(error.message); }, onSuccess: () => { setErrorConnecting(false); queryClient.invalidateQueries({ queryKey: ["walletConnectSession"], }); refetchSession(); }, }); if (session) { return ( ); } return ( {!errorConnecting ? ( <> Copy your connection URI from the external app. { setLoading(true); if (!walletConnectClient) { setErrorConnecting("No WalletConnect client found"); } else { try { createWalletConnectSession({ uri: value, walletConnectClient, }); } catch { setErrorConnecting( "Error creating WalletConnect session", ); } } }} placeholder="WalletConnect URI" submitButtonText="Connect" type="text" /> ) : ( <> {errorConnecting} )} ); }