From bec3342e41d80a93e6eb5fca4883d97dd7dc64c2 Mon Sep 17 00:00:00 2001 From: ignaciosantise <25931366+ignaciosantise@users.noreply.github.com> Date: Mon, 27 Jan 2025 12:29:59 -0300 Subject: [PATCH 1/5] fix: check for a connector when setting initial modal loader, added checks before resetting account --- .changeset/proud-badgers-provide.md | 18 ++++++++++++++++++ packages/wagmi/src/client.ts | 8 ++++---- 2 files changed, 22 insertions(+), 4 deletions(-) create mode 100644 .changeset/proud-badgers-provide.md diff --git a/.changeset/proud-badgers-provide.md b/.changeset/proud-badgers-provide.md new file mode 100644 index 000000000..b6d2b3159 --- /dev/null +++ b/.changeset/proud-badgers-provide.md @@ -0,0 +1,18 @@ +--- +'@reown/appkit-wagmi-react-native': patch +'@reown/appkit-auth-ethers-react-native': patch +'@reown/appkit-auth-wagmi-react-native': patch +'@reown/appkit-coinbase-ethers-react-native': patch +'@reown/appkit-coinbase-wagmi-react-native': patch +'@reown/appkit-common-react-native': patch +'@reown/appkit-core-react-native': patch +'@reown/appkit-ethers-react-native': patch +'@reown/appkit-ethers5-react-native': patch +'@reown/appkit-scaffold-react-native': patch +'@reown/appkit-scaffold-utils-react-native': patch +'@reown/appkit-siwe-react-native': patch +'@reown/appkit-ui-react-native': patch +'@reown/appkit-wallet-react-native': patch +--- + +fix: changed condition for initial modal loading diff --git a/packages/wagmi/src/client.ts b/packages/wagmi/src/client.ts index 828f04715..4ccc19be5 100644 --- a/packages/wagmi/src/client.ts +++ b/packages/wagmi/src/client.ts @@ -431,7 +431,7 @@ export class AppKit extends AppKitScaffold { 'address' | 'isConnected' | 'chainId' | 'connector' | 'isConnecting' | 'isReconnecting' >) { this.syncNetwork(address, chainId, isConnected); - this.setLoading(isConnecting || isReconnecting); + this.setLoading(!!connector && (isConnecting || isReconnecting)); if (isConnected && address && chainId) { const caipAddress: CaipAddress = `${ConstantsUtil.EIP155}:${chainId}:${address}`; @@ -444,8 +444,7 @@ export class AppKit extends AppKitScaffold { this.getApprovedCaipNetworksData() ]); this.hasSyncedConnectedAccount = true; - } else if (!isConnected && this.hasSyncedConnectedAccount) { - this.close(); + } else if (!isConnected && !isConnecting && !isReconnecting && this.hasSyncedConnectedAccount) { this.resetAccount(); this.resetWcConnection(); this.resetNetwork(); @@ -619,7 +618,8 @@ export class AppKit extends AppKitScaffold { provider.onSetPreferredAccount(async () => { await reconnect(this.wagmiConfig, { connectors: [connector] }); - this.setLoading(false); + // this.setLoading(false); + // console.log('setLoading', false); }); provider.setOnTimeout(async () => { From 35999c78ba6ee69aaad3586f1d2ba43172ef4a0d Mon Sep 17 00:00:00 2001 From: ignaciosantise <25931366+ignaciosantise@users.noreply.github.com> Date: Mon, 27 Jan 2025 15:19:23 -0300 Subject: [PATCH 2/5] fix: close wagmi modal on disconnect --- packages/wagmi/src/client.ts | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/packages/wagmi/src/client.ts b/packages/wagmi/src/client.ts index 4ccc19be5..07cb98c8c 100644 --- a/packages/wagmi/src/client.ts +++ b/packages/wagmi/src/client.ts @@ -377,8 +377,12 @@ export class AppKit extends AppKitScaffold { }); watchAccount(wagmiConfig, { - onChange: accountData => { + onChange: (accountData, prevAccountData) => { this.syncAccount({ ...accountData }); + + if (accountData.status === 'disconnected' && prevAccountData.status === 'connected') { + this.close(); + } } }); } From 3192787e4eaa55401d45ecdf0a76266fd8477c67 Mon Sep 17 00:00:00 2001 From: ignaciosantise <25931366+ignaciosantise@users.noreply.github.com> Date: Mon, 27 Jan 2025 15:27:01 -0300 Subject: [PATCH 3/5] chore: remove commented code --- packages/wagmi/src/client.ts | 2 -- 1 file changed, 2 deletions(-) diff --git a/packages/wagmi/src/client.ts b/packages/wagmi/src/client.ts index 07cb98c8c..15e2b5c68 100644 --- a/packages/wagmi/src/client.ts +++ b/packages/wagmi/src/client.ts @@ -622,8 +622,6 @@ export class AppKit extends AppKitScaffold { provider.onSetPreferredAccount(async () => { await reconnect(this.wagmiConfig, { connectors: [connector] }); - // this.setLoading(false); - // console.log('setLoading', false); }); provider.setOnTimeout(async () => { From cdc1af3878a9193b34c530d2a867397941ed0bbf Mon Sep 17 00:00:00 2001 From: ignaciosantise <25931366+ignaciosantise@users.noreply.github.com> Date: Mon, 27 Jan 2025 16:12:45 -0300 Subject: [PATCH 4/5] chore: export event subscription hook --- .changeset/five-pumas-wash.md | 18 ++++++++ .../core/src/controllers/EventsController.ts | 10 ++++- packages/core/src/utils/TypeUtil.ts | 45 +++++++++++++++++++ packages/ethers/src/index.tsx | 17 +++++++ packages/ethers5/src/index.tsx | 17 +++++++ packages/scaffold/src/client.ts | 7 ++- packages/wagmi/src/index.tsx | 17 +++++++ 7 files changed, 129 insertions(+), 2 deletions(-) create mode 100644 .changeset/five-pumas-wash.md diff --git a/.changeset/five-pumas-wash.md b/.changeset/five-pumas-wash.md new file mode 100644 index 000000000..53d402a0c --- /dev/null +++ b/.changeset/five-pumas-wash.md @@ -0,0 +1,18 @@ +--- +'@reown/appkit-scaffold-react-native': patch +'@reown/appkit-ethers5-react-native': patch +'@reown/appkit-ethers-react-native': patch +'@reown/appkit-wagmi-react-native': patch +'@reown/appkit-core-react-native': patch +'@reown/appkit-auth-ethers-react-native': patch +'@reown/appkit-auth-wagmi-react-native': patch +'@reown/appkit-coinbase-ethers-react-native': patch +'@reown/appkit-coinbase-wagmi-react-native': patch +'@reown/appkit-common-react-native': patch +'@reown/appkit-scaffold-utils-react-native': patch +'@reown/appkit-siwe-react-native': patch +'@reown/appkit-ui-react-native': patch +'@reown/appkit-wallet-react-native': patch +--- + +chore: added event subscription hook diff --git a/packages/core/src/controllers/EventsController.ts b/packages/core/src/controllers/EventsController.ts index 48e45cb1c..339229ec9 100644 --- a/packages/core/src/controllers/EventsController.ts +++ b/packages/core/src/controllers/EventsController.ts @@ -3,7 +3,7 @@ import { ApiController } from './ApiController'; import { OptionsController } from './OptionsController'; import { CoreHelperUtil } from '../utils/CoreHelperUtil'; import { FetchUtil } from '../utils/FetchUtil'; -import type { Event } from '../utils/TypeUtil'; +import type { Event, EventName } from '../utils/TypeUtil'; // -- Helpers ------------------------------------------- // const baseUrl = CoreHelperUtil.getAnalyticsUrl(); @@ -33,6 +33,14 @@ export const EventsController = { return sub(state, () => callback(state)); }, + subscribeEvent(event: EventName, callback: (newEvent: EventsControllerState) => void) { + return sub(state, () => { + if (state.data.event === event) { + callback(state); + } + }); + }, + async _sendAnalyticsEvent(data: EventsControllerState['data'], timestamp: number) { if (excluded.includes(data.event)) { return; diff --git a/packages/core/src/utils/TypeUtil.ts b/packages/core/src/utils/TypeUtil.ts index 41c6e6261..498a18106 100644 --- a/packages/core/src/utils/TypeUtil.ts +++ b/packages/core/src/utils/TypeUtil.ts @@ -343,6 +343,51 @@ export type CustomWallet = Pick< >; // -- EventsController Types ---------------------------------------------------- +export type EventName = + | 'MODAL_LOADED' + | 'MODAL_OPEN' + | 'MODAL_CLOSE' + | 'CLICK_ALL_WALLETS' + | 'CLICK_NETWORKS' + | 'SWITCH_NETWORK' + | 'SELECT_WALLET' + | 'CONNECT_SUCCESS' + | 'CONNECT_ERROR' + | 'DISCONNECT_SUCCESS' + | 'DISCONNECT_ERROR' + | 'CLICK_WALLET_HELP' + | 'CLICK_NETWORK_HELP' + | 'CLICK_GET_WALLET' + | 'EMAIL_LOGIN_SELECTED' + | 'EMAIL_SUBMITTED' + | 'DEVICE_REGISTERED_FOR_EMAIL' + | 'EMAIL_VERIFICATION_CODE_SENT' + | 'EMAIL_VERIFICATION_CODE_PASS' + | 'EMAIL_VERIFICATION_CODE_FAIL' + | 'EMAIL_EDIT' + | 'EMAIL_EDIT_COMPLETE' + | 'EMAIL_UPGRADE_FROM_MODAL' + | 'CLICK_SIGN_SIWE_MESSAGE' + | 'CLICK_CANCEL_SIWE' + | 'SIWE_AUTH_SUCCESS' + | 'SIWE_AUTH_ERROR' + | 'CLICK_TRANSACTIONS' + | 'ERROR_FETCH_TRANSACTIONS' + | 'LOAD_MORE_TRANSACTIONS' + | 'OPEN_SEND' + | 'OPEN_SWAP' + | 'INITIATE_SWAP' + | 'SWAP_SUCCESS' + | 'SWAP_ERROR' + | 'SEND_INITIATED' + | 'SEND_SUCCESS' + | 'SEND_ERROR' + | 'SOCIAL_LOGIN_STARTED' + | 'SOCIAL_LOGIN_SUCCESS' + | 'SOCIAL_LOGIN_REQUEST_USER_DATA' + | 'SOCIAL_LOGIN_CANCELED' + | 'SOCIAL_LOGIN_ERROR' + | 'SET_PREFERRED_ACCOUNT_TYPE'; export type Event = | { diff --git a/packages/ethers/src/index.tsx b/packages/ethers/src/index.tsx index 19a6dcbf3..80ed569fb 100644 --- a/packages/ethers/src/index.tsx +++ b/packages/ethers/src/index.tsx @@ -13,6 +13,7 @@ export { NetworkButton, AppKit } from '@reown/appkit-scaffold-react-native'; +import type { EventName } from '@reown/appkit-scaffold-react-native'; export { defaultConfig } from './utils/defaultConfig'; @@ -148,3 +149,19 @@ export function useAppKitEvents() { return event; } + +export function useAppKitEventSubscription(event: EventName, callback: () => void) { + if (!modal) { + throw new Error('Please call "createAppKit" before using "useAppKitEventSubscription" hook'); + } + + useEffect(() => { + const unsubscribe = modal?.subscribeEvent(event, callback); + + return () => { + unsubscribe?.(); + }; + }, [callback, event]); + + return event; +} diff --git a/packages/ethers5/src/index.tsx b/packages/ethers5/src/index.tsx index c213a7481..2bde979ec 100644 --- a/packages/ethers5/src/index.tsx +++ b/packages/ethers5/src/index.tsx @@ -6,6 +6,7 @@ export { NetworkButton, AppKit } from '@reown/appkit-scaffold-react-native'; +import type { EventName } from '@reown/appkit-scaffold-react-native'; import { ConstantsUtil, EthersStoreUtil, @@ -145,3 +146,19 @@ export function useAppKitEvents() { return event; } + +export function useAppKitEventSubscription(event: EventName, callback: () => void) { + if (!modal) { + throw new Error('Please call "createAppKit" before using "useAppKitEventSubscription" hook'); + } + + useEffect(() => { + const unsubscribe = modal?.subscribeEvent(event, callback); + + return () => { + unsubscribe?.(); + }; + }, [callback, event]); + + return event; +} diff --git a/packages/scaffold/src/client.ts b/packages/scaffold/src/client.ts index a5a3fc9e4..60daf796d 100644 --- a/packages/scaffold/src/client.ts +++ b/packages/scaffold/src/client.ts @@ -12,7 +12,8 @@ import type { ThemeControllerState, Connector, ConnectedWalletInfo, - Features + Features, + EventName } from '@reown/appkit-core-react-native'; import { SIWEController, type SIWEControllerClient } from '@reown/appkit-siwe-react-native'; import { @@ -145,6 +146,10 @@ export class AppKitScaffold { return EventsController.subscribe(callback); } + public subscribeEvent(event: EventName, callback: (newEvent: EventsControllerState) => void) { + return EventsController.subscribeEvent(event, callback); + } + public resolveReownName = async (name: string) => { const wcNameAddress = await EnsController.resolveName(name); const networkNameAddresses = wcNameAddress?.addresses diff --git a/packages/wagmi/src/index.tsx b/packages/wagmi/src/index.tsx index da1d90ad1..8d5403f26 100644 --- a/packages/wagmi/src/index.tsx +++ b/packages/wagmi/src/index.tsx @@ -6,6 +6,7 @@ export { NetworkButton, AppKit } from '@reown/appkit-scaffold-react-native'; +import type { EventName } from '@reown/appkit-scaffold-react-native'; import { ConstantsUtil } from '@reown/appkit-scaffold-utils-react-native'; export { defaultWagmiConfig } from './utils/defaultWagmiConfig'; import { useEffect, useState, useSyncExternalStore } from 'react'; @@ -101,3 +102,19 @@ export function useAppKitEvents() { return event; } + +export function useAppKitEventSubscription(event: EventName, callback: () => void) { + if (!modal) { + throw new Error('Please call "createAppKit" before using "useAppKitEventSubscription" hook'); + } + + useEffect(() => { + const unsubscribe = modal?.subscribeEvent(event, callback); + + return () => { + unsubscribe?.(); + }; + }, [callback, event]); + + return event; +} From c93188e3b4be31c39feb7955527bde427d96f920 Mon Sep 17 00:00:00 2001 From: ignaciosantise <25931366+ignaciosantise@users.noreply.github.com> Date: Mon, 27 Jan 2025 16:21:37 -0300 Subject: [PATCH 5/5] chore: typed event hook callback, added optional callback to useAppKitEvents --- packages/ethers/src/index.tsx | 14 ++++++++------ packages/ethers5/src/index.tsx | 14 ++++++++------ packages/wagmi/src/index.tsx | 14 ++++++++------ 3 files changed, 24 insertions(+), 18 deletions(-) diff --git a/packages/ethers/src/index.tsx b/packages/ethers/src/index.tsx index 80ed569fb..ccdeddbf9 100644 --- a/packages/ethers/src/index.tsx +++ b/packages/ethers/src/index.tsx @@ -13,7 +13,7 @@ export { NetworkButton, AppKit } from '@reown/appkit-scaffold-react-native'; -import type { EventName } from '@reown/appkit-scaffold-react-native'; +import type { EventName, EventsControllerState } from '@reown/appkit-scaffold-react-native'; export { defaultConfig } from './utils/defaultConfig'; @@ -130,7 +130,7 @@ export function useAppKitError() { }; } -export function useAppKitEvents() { +export function useAppKitEvents(callback?: (newEvent: EventsControllerState) => void) { if (!modal) { throw new Error('Please call "createAppKit" before using "useAppKitEvents" hook'); } @@ -140,17 +140,21 @@ export function useAppKitEvents() { useEffect(() => { const unsubscribe = modal?.subscribeEvents(newEvent => { setEvents({ ...newEvent }); + callback?.(newEvent); }); return () => { unsubscribe?.(); }; - }, []); + }, [callback]); return event; } -export function useAppKitEventSubscription(event: EventName, callback: () => void) { +export function useAppKitEventSubscription( + event: EventName, + callback: (newEvent: EventsControllerState) => void +) { if (!modal) { throw new Error('Please call "createAppKit" before using "useAppKitEventSubscription" hook'); } @@ -162,6 +166,4 @@ export function useAppKitEventSubscription(event: EventName, callback: () => voi unsubscribe?.(); }; }, [callback, event]); - - return event; } diff --git a/packages/ethers5/src/index.tsx b/packages/ethers5/src/index.tsx index 2bde979ec..72e55c58a 100644 --- a/packages/ethers5/src/index.tsx +++ b/packages/ethers5/src/index.tsx @@ -6,7 +6,7 @@ export { NetworkButton, AppKit } from '@reown/appkit-scaffold-react-native'; -import type { EventName } from '@reown/appkit-scaffold-react-native'; +import type { EventName, EventsControllerState } from '@reown/appkit-scaffold-react-native'; import { ConstantsUtil, EthersStoreUtil, @@ -127,7 +127,7 @@ export function useAppKitError() { }; } -export function useAppKitEvents() { +export function useAppKitEvents(callback?: (newEvent: EventsControllerState) => void) { if (!modal) { throw new Error('Please call "createAppKit" before using "useAppKitEvents" hook'); } @@ -137,17 +137,21 @@ export function useAppKitEvents() { useEffect(() => { const unsubscribe = modal?.subscribeEvents(newEvent => { setEvents({ ...newEvent }); + callback?.(newEvent); }); return () => { unsubscribe?.(); }; - }, []); + }, [callback]); return event; } -export function useAppKitEventSubscription(event: EventName, callback: () => void) { +export function useAppKitEventSubscription( + event: EventName, + callback: (newEvent: EventsControllerState) => void +) { if (!modal) { throw new Error('Please call "createAppKit" before using "useAppKitEventSubscription" hook'); } @@ -159,6 +163,4 @@ export function useAppKitEventSubscription(event: EventName, callback: () => voi unsubscribe?.(); }; }, [callback, event]); - - return event; } diff --git a/packages/wagmi/src/index.tsx b/packages/wagmi/src/index.tsx index 8d5403f26..642fe8e49 100644 --- a/packages/wagmi/src/index.tsx +++ b/packages/wagmi/src/index.tsx @@ -6,7 +6,7 @@ export { NetworkButton, AppKit } from '@reown/appkit-scaffold-react-native'; -import type { EventName } from '@reown/appkit-scaffold-react-native'; +import type { EventName, EventsControllerState } from '@reown/appkit-scaffold-react-native'; import { ConstantsUtil } from '@reown/appkit-scaffold-utils-react-native'; export { defaultWagmiConfig } from './utils/defaultWagmiConfig'; import { useEffect, useState, useSyncExternalStore } from 'react'; @@ -83,7 +83,7 @@ export function useWalletInfo() { return { walletInfo }; } -export function useAppKitEvents() { +export function useAppKitEvents(callback?: (newEvent: EventsControllerState) => void) { if (!modal) { throw new Error('Please call "createAppKit" before using "useAppKitEvents" hook'); } @@ -93,17 +93,21 @@ export function useAppKitEvents() { useEffect(() => { const unsubscribe = modal?.subscribeEvents(newEvent => { setEvents({ ...newEvent }); + callback?.(newEvent); }); return () => { unsubscribe?.(); }; - }, []); + }, [callback]); return event; } -export function useAppKitEventSubscription(event: EventName, callback: () => void) { +export function useAppKitEventSubscription( + event: EventName, + callback: (newEvent: EventsControllerState) => void +) { if (!modal) { throw new Error('Please call "createAppKit" before using "useAppKitEventSubscription" hook'); } @@ -115,6 +119,4 @@ export function useAppKitEventSubscription(event: EventName, callback: () => voi unsubscribe?.(); }; }, [callback, event]); - - return event; }