@sodax/wallet-sdk-react 2.0.0-rc.2 → 2.0.0-rc.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +12 -5
- package/dist/{chunk-BKJB527E.mjs → chunk-3QETHO6P.mjs} +1 -3
- package/dist/{chunk-PJLEJVAU.mjs → chunk-42LTUHMZ.mjs} +1 -3
- package/dist/{chunk-NY7U7OJW.mjs → chunk-7V7O3Q7Y.mjs} +0 -2
- package/dist/{chunk-BXJLBR4G.mjs → chunk-C6M34IVL.mjs} +2 -4
- package/dist/{chunk-XZ7CHO2S.mjs → chunk-FSOGMSJH.mjs} +2 -4
- package/dist/{chunk-X2MHIWXO.mjs → chunk-IFXZQW4C.mjs} +0 -2
- package/dist/{chunk-7ULB6DW4.mjs → chunk-JQ4H4GJ5.mjs} +3 -5
- package/dist/{chunk-N5A2TMF6.mjs → chunk-LKSSME2J.mjs} +2 -4
- package/dist/{chunk-PLCA4ZDJ.mjs → chunk-LUKR7YKV.mjs} +54 -30
- package/dist/{chunk-MXZVF5HR.mjs → chunk-NAKCAL2M.mjs} +0 -2
- package/dist/chunk-QMXBY3UI.mjs +1 -0
- package/dist/{chunk-MAQ47Q52.mjs → chunk-TACW7Z4D.mjs} +0 -2
- package/dist/{chunk-2BOUGCJ7.mjs → chunk-WPZOLGVB.mjs} +4 -6
- package/dist/{chunk-66BAUK56.mjs → chunk-X7BHR7WS.mjs} +2 -4
- package/dist/{chunk-E5IAZ7E6.mjs → chunk-Z5GXDHGL.mjs} +9 -5
- package/dist/{config-OlnzyEUE.d.ts → config-GVKK8IfY.d.ts} +6 -1
- package/dist/index.d.ts +4 -4
- package/dist/index.mjs +20 -31
- package/dist/xchains/bitcoin/index.mjs +14 -16
- package/dist/xchains/evm/index.d.ts +1 -1
- package/dist/xchains/evm/index.mjs +3 -5
- package/dist/xchains/icon/index.mjs +5 -7
- package/dist/xchains/injective/index.mjs +3 -5
- package/dist/xchains/near/index.mjs +4 -6
- package/dist/xchains/solana/index.mjs +5 -7
- package/dist/xchains/stacks/index.mjs +3 -5
- package/dist/xchains/stellar/index.mjs +4 -6
- package/dist/xchains/sui/index.mjs +5 -7
- package/docs/ADDING_A_NEW_CHAIN.md +1 -1
- package/docs/SUB_PATH_EXPORTS.md +14 -42
- package/package.json +32 -23
- package/ai-exported/AGENTS.md +0 -122
- package/ai-exported/integration/README.md +0 -102
- package/ai-exported/integration/ai-rules.md +0 -136
- package/ai-exported/integration/architecture.md +0 -181
- package/ai-exported/integration/examples/01-minimal-evm.tsx +0 -75
- package/ai-exported/integration/examples/02-multi-chain-modal.tsx +0 -169
- package/ai-exported/integration/examples/03-nextjs-app-router.tsx +0 -99
- package/ai-exported/integration/examples/04-walletconnect-setup.tsx +0 -89
- package/ai-exported/integration/examples/README.md +0 -29
- package/ai-exported/integration/recipes/batch-operations.md +0 -223
- package/ai-exported/integration/recipes/bridge-to-sdk.md +0 -164
- package/ai-exported/integration/recipes/chain-detection.md +0 -254
- package/ai-exported/integration/recipes/connect-button.md +0 -156
- package/ai-exported/integration/recipes/multi-chain-modal.md +0 -199
- package/ai-exported/integration/recipes/setup.md +0 -158
- package/ai-exported/integration/recipes/sign-message.md +0 -137
- package/ai-exported/integration/recipes/sub-path-imports.md +0 -95
- package/ai-exported/integration/recipes/switch-chain.md +0 -141
- package/ai-exported/integration/recipes/walletconnect-setup.md +0 -139
- package/ai-exported/integration/reference/api-surface.md +0 -175
- package/ai-exported/integration/reference/chain-support.md +0 -78
- package/ai-exported/integration/reference/connectors.md +0 -74
- package/ai-exported/integration/reference/hooks.md +0 -204
- package/ai-exported/integration/reference/wallet-brands.md +0 -106
- package/ai-exported/migration/README.md +0 -49
- package/ai-exported/migration/ai-rules.md +0 -144
- package/ai-exported/migration/breaking-changes.md +0 -305
- package/ai-exported/migration/checklist.md +0 -159
- package/ai-exported/migration/recipes/connect-button.md +0 -166
- package/ai-exported/migration/recipes/multi-chain-modal.md +0 -244
- package/ai-exported/migration/recipes/ssr-setup.md +0 -162
- package/ai-exported/migration/recipes/walletconnect-migration.md +0 -168
- package/ai-exported/migration/reference/components.md +0 -73
- package/ai-exported/migration/reference/config.md +0 -307
- package/ai-exported/migration/reference/hooks.md +0 -278
- package/ai-exported/migration/reference/imports.md +0 -157
- package/dist/chunk-2BOUGCJ7.mjs.map +0 -1
- package/dist/chunk-66BAUK56.mjs.map +0 -1
- package/dist/chunk-7ULB6DW4.mjs.map +0 -1
- package/dist/chunk-BKJB527E.mjs.map +0 -1
- package/dist/chunk-BXJLBR4G.mjs.map +0 -1
- package/dist/chunk-E5IAZ7E6.mjs.map +0 -1
- package/dist/chunk-MAQ47Q52.mjs.map +0 -1
- package/dist/chunk-MXZVF5HR.mjs.map +0 -1
- package/dist/chunk-N5A2TMF6.mjs.map +0 -1
- package/dist/chunk-NY7U7OJW.mjs.map +0 -1
- package/dist/chunk-PJLEJVAU.mjs.map +0 -1
- package/dist/chunk-PLCA4ZDJ.mjs.map +0 -1
- package/dist/chunk-TZMKDXFA.mjs +0 -3
- package/dist/chunk-TZMKDXFA.mjs.map +0 -1
- package/dist/chunk-X2MHIWXO.mjs.map +0 -1
- package/dist/chunk-XZ7CHO2S.mjs.map +0 -1
- package/dist/index.cjs +0 -3337
- package/dist/index.cjs.map +0 -1
- package/dist/index.mjs.map +0 -1
- package/dist/xchains/bitcoin/index.cjs +0 -1927
- package/dist/xchains/bitcoin/index.cjs.map +0 -1
- package/dist/xchains/bitcoin/index.mjs.map +0 -1
- package/dist/xchains/evm/index.cjs +0 -316
- package/dist/xchains/evm/index.cjs.map +0 -1
- package/dist/xchains/evm/index.mjs.map +0 -1
- package/dist/xchains/icon/index.cjs +0 -311
- package/dist/xchains/icon/index.cjs.map +0 -1
- package/dist/xchains/icon/index.mjs.map +0 -1
- package/dist/xchains/injective/index.cjs +0 -223
- package/dist/xchains/injective/index.cjs.map +0 -1
- package/dist/xchains/injective/index.mjs.map +0 -1
- package/dist/xchains/near/index.cjs +0 -190
- package/dist/xchains/near/index.cjs.map +0 -1
- package/dist/xchains/near/index.mjs.map +0 -1
- package/dist/xchains/solana/index.cjs +0 -186
- package/dist/xchains/solana/index.cjs.map +0 -1
- package/dist/xchains/solana/index.mjs.map +0 -1
- package/dist/xchains/stacks/index.cjs +0 -240
- package/dist/xchains/stacks/index.cjs.map +0 -1
- package/dist/xchains/stacks/index.mjs.map +0 -1
- package/dist/xchains/stellar/index.cjs +0 -322
- package/dist/xchains/stellar/index.cjs.map +0 -1
- package/dist/xchains/stellar/index.mjs.map +0 -1
- package/dist/xchains/sui/index.cjs +0 -248
- package/dist/xchains/sui/index.cjs.map +0 -1
- package/dist/xchains/sui/index.mjs.map +0 -1
- package/skills/SKILLS.md +0 -84
- package/skills/bridge-to-sdk.md +0 -148
- package/skills/connect-button.md +0 -116
- package/skills/evm-only-walletconnect.md +0 -111
- package/skills/multi-chain-modal.md +0 -178
- package/skills/setup.md +0 -107
|
@@ -1,74 +0,0 @@
|
|
|
1
|
-
# Reference: Connectors
|
|
2
|
-
|
|
3
|
-
A connector is the adapter between a specific wallet (Hana, MetaMask, Phantom, Xverse…) and the SODAX store. Every connector implements `IXConnector`, the public contract every hook in `wallet-sdk-react` consumes.
|
|
4
|
-
|
|
5
|
-
Concrete connector classes live behind sub-path imports — see [`api-surface.md`](./api-surface.md) § "Sub-path exports" for the per-chain map.
|
|
6
|
-
|
|
7
|
-
---
|
|
8
|
-
|
|
9
|
-
## `IXConnector` interface
|
|
10
|
-
|
|
11
|
-
```typescript
|
|
12
|
-
export interface IXConnector {
|
|
13
|
-
readonly xChainType: ChainType;
|
|
14
|
-
readonly name: string; // 'Hana', 'MetaMask', 'Xverse', …
|
|
15
|
-
readonly id: string; // unique connector id (e.g. 'io.metamask')
|
|
16
|
-
readonly icon: string | undefined;
|
|
17
|
-
readonly isInstalled: boolean; // wallet extension presence (read at getter call time)
|
|
18
|
-
readonly installUrl: string | undefined;
|
|
19
|
-
connect(): Promise<XAccount | undefined>;
|
|
20
|
-
disconnect(): Promise<void>;
|
|
21
|
-
}
|
|
22
|
-
```
|
|
23
|
-
|
|
24
|
-
Consumer code should depend on **`IXConnector`** (the interface), not the concrete `XConnector` class — keeps your code chain-implementation-agnostic and allows custom connectors to slot in without inheriting from the abstract base.
|
|
25
|
-
|
|
26
|
-
`isInstalled` reads `window.*` at getter-call time — no extra subscription is installed. Components get fresh values through normal React render triggers.
|
|
27
|
-
|
|
28
|
-
---
|
|
29
|
-
|
|
30
|
-
## Listing connectors at runtime
|
|
31
|
-
|
|
32
|
-
Don't import concrete classes to discover what's available — use the hook:
|
|
33
|
-
|
|
34
|
-
```ts
|
|
35
|
-
const connectors = useXConnectors({ xChainType: 'EVM' });
|
|
36
|
-
// IXConnector[] — already filtered to enabled chain
|
|
37
|
-
```
|
|
38
|
-
|
|
39
|
-
For the per-chain class names (only needed for `instanceof` or custom-connector-list use cases), see [`api-surface.md`](./api-surface.md) § "Sub-path exports" and the worked example in [`../recipes/sub-path-imports.md`](../recipes/sub-path-imports.md). Bitcoin's `BitcoinXConnector` is the only abstract base — its concrete subclasses (Unisat, Xverse, OKX) override per-wallet signing methods (see [`sign-message.md`](../recipes/sign-message.md)).
|
|
40
|
-
|
|
41
|
-
---
|
|
42
|
-
|
|
43
|
-
## `sortConnectors` — display ordering
|
|
44
|
-
|
|
45
|
-
Pure utility for ranking connectors in lists. Stable sort by:
|
|
46
|
-
|
|
47
|
-
1. Position in `preferred[]` (earlier wins)
|
|
48
|
-
2. `isInstalled === true`
|
|
49
|
-
3. Original index
|
|
50
|
-
|
|
51
|
-
```typescript
|
|
52
|
-
import { useXConnectors, sortConnectors } from '@sodax/wallet-sdk-react';
|
|
53
|
-
|
|
54
|
-
const PREFERRED = ['hana', 'metamask'];
|
|
55
|
-
|
|
56
|
-
function ConnectorList() {
|
|
57
|
-
const raw = useXConnectors({ xChainType: 'EVM' });
|
|
58
|
-
const sorted = sortConnectors(raw, { preferred: PREFERRED });
|
|
59
|
-
// Hana first if present, then MetaMask, then any other installed wallets, then uninstalled.
|
|
60
|
-
}
|
|
61
|
-
```
|
|
62
|
-
|
|
63
|
-
`preferred` matches by exact `connector.id`. For substring/case-insensitive matching across chains, use `useIsWalletInstalled` instead — see [`batch-operations.md`](../recipes/batch-operations.md).
|
|
64
|
-
|
|
65
|
-
---
|
|
66
|
-
|
|
67
|
-
## Custom connectors
|
|
68
|
-
|
|
69
|
-
Two ways to plug in a wallet the SDK doesn't ship:
|
|
70
|
-
|
|
71
|
-
1. **Extend `XConnector`** (abstract base, exported from the barrel) — implement `connect()` / `disconnect()` / `isInstalled` / `installUrl`. Pass via `SodaxWalletConfig.<CHAIN>.connectors` to replace the registry defaults for that chain.
|
|
72
|
-
2. **Implement `IXConnector` directly** — skip the abstract base. The SDK never does `instanceof XConnector` on user-supplied connectors; it only relies on the interface.
|
|
73
|
-
|
|
74
|
-
For a worked example with code, see [`../recipes/sub-path-imports.md`](../recipes/sub-path-imports.md) § "Custom connector list". For chains with extra signing methods (Bitcoin's `signBip322Message`, Injective specifics), implement the chain-specific extras — the SDK detects them via type guards at dispatch time.
|
|
@@ -1,204 +0,0 @@
|
|
|
1
|
-
# Reference: Hooks
|
|
2
|
-
|
|
3
|
-
Full hook surface of `@sodax/wallet-sdk-react` v2. All hooks accept an options object — never positional args. Pair this with [`connectors.md`](./connectors.md) for connector shape and [`chain-support.md`](./chain-support.md) for chain identifiers.
|
|
4
|
-
|
|
5
|
-
> **All hooks are client-only.** They depend on `<SodaxWalletProvider>` and `<QueryClientProvider>`, which only mount on the client. Next.js App Router consumers must mark every file calling these hooks with `'use client'`. Server Components cannot read connection state directly — pass it down from a client boundary.
|
|
6
|
-
|
|
7
|
-
---
|
|
8
|
-
|
|
9
|
-
## Behavior when the chain slot is not in `walletConfig`
|
|
10
|
-
|
|
11
|
-
Hooks do **not** throw when their chain isn't enabled — each picks its own no-op fallback. UI code can call them unconditionally and branch on the return value.
|
|
12
|
-
|
|
13
|
-
| Hook | Behavior when chain absent |
|
|
14
|
-
|---|---|
|
|
15
|
-
| `useXAccount`, `useXAccounts` | Returns shape with `address: undefined` |
|
|
16
|
-
| `useXConnection`, `useXConnections` | Returns `undefined` / empty record |
|
|
17
|
-
| `useXConnectors` | Returns `[]`. **One-time `console.warn`** per chain type to surface config mistakes. |
|
|
18
|
-
| `useXConnectorsByChain` | Returns empty record. No warning. |
|
|
19
|
-
| `useWalletProvider` | Returns `undefined` |
|
|
20
|
-
| `useXService`, `useXServices` | Returns `undefined` / empty record |
|
|
21
|
-
| `useEvmSwitchChain` | Returns `{ isWrongChain: false, handleSwitchChain: () => {} }` (no-op) |
|
|
22
|
-
| `useEnabledChains` | Returns the list of slots actually present (does not include the disabled one) |
|
|
23
|
-
| `useChainGroups`, `useConnectedChains` | Excludes the chain from output |
|
|
24
|
-
| `useXConnect`, `useXDisconnect`, `useXSignMessage` | Mutation rejects when invoked with an unsupported `xChainType` |
|
|
25
|
-
|
|
26
|
-
Rule of thumb: read-hooks degrade silently to "empty"; mutation-hooks reject. Both cases are safe to call unconditionally.
|
|
27
|
-
|
|
28
|
-
---
|
|
29
|
-
|
|
30
|
-
## Connect / disconnect
|
|
31
|
-
|
|
32
|
-
| Hook | Signature | Returns |
|
|
33
|
-
|---|---|---|
|
|
34
|
-
| `useXConnect` | `useXConnect(): UseMutationResult<XAccount \| undefined, Error, IXConnector>` | React Query mutation. **Resolves to `undefined` for provider-managed chains** (EVM/Solana/Sui) — read the connected account via `useXAccount` after the mutation lands. |
|
|
35
|
-
| `useXDisconnect` | `useXDisconnect(): (args: UseXDisconnectArgs) => Promise<void>` where `UseXDisconnectArgs = { xChainType: ChainType }` | Async function — never throws |
|
|
36
|
-
| `useConnectionFlow` | `useConnectionFlow(): { status, error, connect, retry, activeConnector }` | Status object |
|
|
37
|
-
| `useBatchConnect` | `useBatchConnect({ connectors, skipConnected?, onProgress? })` | `{ run, status, result, reset }` |
|
|
38
|
-
| `useBatchDisconnect` | `useBatchDisconnect({ connectors?, onProgress? })` | `{ run, status, result, reset }` |
|
|
39
|
-
|
|
40
|
-
```ts
|
|
41
|
-
const { mutateAsync: connect } = useXConnect();
|
|
42
|
-
await connect(connector);
|
|
43
|
-
|
|
44
|
-
const disconnect = useXDisconnect();
|
|
45
|
-
await disconnect({ xChainType: 'EVM' });
|
|
46
|
-
```
|
|
47
|
-
|
|
48
|
-
---
|
|
49
|
-
|
|
50
|
-
## Read account / connection state
|
|
51
|
-
|
|
52
|
-
| Hook | Signature | Returns |
|
|
53
|
-
|---|---|---|
|
|
54
|
-
| `useXAccount` | `useXAccount({ xChainType }) \| useXAccount({ xChainId })` | `XAccount` (always populated; `address` undefined when disconnected) |
|
|
55
|
-
| `useXAccounts` | `useXAccounts()` | `Partial<Record<ChainType, XAccount>>` (only enabled chains; entries are populated, `address` undefined when disconnected) |
|
|
56
|
-
| `useXConnection` | `useXConnection({ xChainType })` | `XConnection \| undefined` |
|
|
57
|
-
| `useXConnections` | `useXConnections()` | `Partial<Record<ChainType, XConnection>>` |
|
|
58
|
-
| `useConnectedChains` | `useConnectedChains({ order? })` | `{ status: 'loading' \| 'ready', chains: ConnectedChain[], total: number }` |
|
|
59
|
-
|
|
60
|
-
```ts
|
|
61
|
-
import { ChainKeys } from '@sodax/types';
|
|
62
|
-
|
|
63
|
-
const { address } = useXAccount({ xChainType: 'EVM' });
|
|
64
|
-
const { address } = useXAccount({ xChainId: ChainKeys.BSC_MAINNET });
|
|
65
|
-
```
|
|
66
|
-
|
|
67
|
-
---
|
|
68
|
-
|
|
69
|
-
## Connector discovery
|
|
70
|
-
|
|
71
|
-
| Hook | Signature | Returns |
|
|
72
|
-
|---|---|---|
|
|
73
|
-
| `useXConnectors` | `useXConnectors({ xChainType })` | `IXConnector[]` (returns `[]` and logs a one-time warning if `xChainType` isn't enabled in `walletConfig`) |
|
|
74
|
-
| `useXConnectorsByChain` | `useXConnectorsByChain()` | `Partial<Record<ChainType, IXConnector[]>>` (no per-chain warnings) |
|
|
75
|
-
| `useIsWalletInstalled` | `useIsWalletInstalled({ connectors?, chainType? })` | `boolean` (at least one of `connectors`/`chainType` required) |
|
|
76
|
-
| `sortConnectors` | `sortConnectors(list, { preferred }): IXConnector[]` | Pure utility — installed first |
|
|
77
|
-
|
|
78
|
-
```ts
|
|
79
|
-
const connectors = useXConnectors({ xChainType: 'EVM' });
|
|
80
|
-
const sorted = sortConnectors(connectors, { preferred: ['hana', 'metamask'] });
|
|
81
|
-
|
|
82
|
-
const isInstalled = useIsWalletInstalled({ connectors: ['hana'] });
|
|
83
|
-
```
|
|
84
|
-
|
|
85
|
-
---
|
|
86
|
-
|
|
87
|
-
## Wallet provider bridge (for `@sodax/sdk` calls)
|
|
88
|
-
|
|
89
|
-
| Hook | Signature | Returns |
|
|
90
|
-
|---|---|---|
|
|
91
|
-
| `useWalletProvider` | `useWalletProvider({ xChainId })` | Chain-narrowed `IXxxWalletProvider \| undefined` |
|
|
92
|
-
| `useWalletProvider` | `useWalletProvider({ xChainType })` | Family-level `IXxxWalletProvider \| undefined` |
|
|
93
|
-
| `useWalletProvider` | `useWalletProvider()` | `IWalletProvider \| undefined` |
|
|
94
|
-
|
|
95
|
-
```ts
|
|
96
|
-
import { ChainKeys } from '@sodax/types';
|
|
97
|
-
|
|
98
|
-
const evm = useWalletProvider({ xChainId: ChainKeys.BSC_MAINNET });
|
|
99
|
-
// evm: IEvmWalletProvider | undefined
|
|
100
|
-
```
|
|
101
|
-
|
|
102
|
-
See [`bridge-to-sdk.md`](../recipes/bridge-to-sdk.md) for usage with SDK calls.
|
|
103
|
-
|
|
104
|
-
---
|
|
105
|
-
|
|
106
|
-
## Modal / multi-chain UI
|
|
107
|
-
|
|
108
|
-
| Hook | Signature | Returns |
|
|
109
|
-
|---|---|---|
|
|
110
|
-
| `useWalletModal` | `useWalletModal({ onConnected? })` | `{ state, open, close, back, selectChain, selectWallet, retry }` |
|
|
111
|
-
| `useChainGroups` | `useChainGroups({ order? })` | `ChainGroup[]` (one per enabled chain family) |
|
|
112
|
-
|
|
113
|
-
State machine kinds: `closed`, `chainSelect`, `walletSelect`, `connecting`, `success`, `error`.
|
|
114
|
-
|
|
115
|
-
See [`multi-chain-modal.md`](../recipes/multi-chain-modal.md).
|
|
116
|
-
|
|
117
|
-
---
|
|
118
|
-
|
|
119
|
-
## Sign message
|
|
120
|
-
|
|
121
|
-
| Hook | Signature | Returns |
|
|
122
|
-
|---|---|---|
|
|
123
|
-
| `useXSignMessage` | `useXSignMessage()` | React Query mutation — `{ xChainType, message }` → `` `0x${string}` \| Uint8Array \| string \| undefined `` |
|
|
124
|
-
|
|
125
|
-
```ts
|
|
126
|
-
const sign = useXSignMessage();
|
|
127
|
-
const sig = await sign.mutateAsync({ xChainType: 'EVM', message: 'hello' });
|
|
128
|
-
```
|
|
129
|
-
|
|
130
|
-
See [`sign-message.md`](../recipes/sign-message.md) for per-chain matrix.
|
|
131
|
-
|
|
132
|
-
---
|
|
133
|
-
|
|
134
|
-
## EVM-specific
|
|
135
|
-
|
|
136
|
-
| Hook | Signature | Returns |
|
|
137
|
-
|---|---|---|
|
|
138
|
-
| `useEvmSwitchChain` | `useEvmSwitchChain({ xChainId }: { xChainId: SpokeChainKey })` | `{ isWrongChain: boolean, handleSwitchChain: () => void }`. Compares the connected EVM chain to `xChainId` and exposes wrong-network state. Also handles Injective + MetaMask (auto-switches to Ethereum mainnet). Returns no-op values when `EVM` is not in `walletConfig`. |
|
|
139
|
-
|
|
140
|
-
```ts
|
|
141
|
-
import { ChainKeys } from '@sodax/types';
|
|
142
|
-
|
|
143
|
-
const { isWrongChain, handleSwitchChain } = useEvmSwitchChain({
|
|
144
|
-
xChainId: ChainKeys.BSC_MAINNET,
|
|
145
|
-
});
|
|
146
|
-
|
|
147
|
-
if (isWrongChain) handleSwitchChain();
|
|
148
|
-
```
|
|
149
|
-
|
|
150
|
-
> **No top-level `useEthereumChainId` in v2.** The raw EVM chain ID is internal — read it via wagmi's `useAccount().chainId` instead. v2 folds the Injective+MetaMask "wrong network" UX into `useEvmSwitchChain` above.
|
|
151
|
-
|
|
152
|
-
---
|
|
153
|
-
|
|
154
|
-
## Service-level (advanced)
|
|
155
|
-
|
|
156
|
-
| Hook | Signature | Returns |
|
|
157
|
-
|---|---|---|
|
|
158
|
-
| `useXService` | `useXService({ xChainType })` | `IXService \| undefined` |
|
|
159
|
-
| `useXServices` | `useXServices()` | `Partial<Record<ChainType, IXService>>` |
|
|
160
|
-
| `useEnabledChains` | `useEnabledChains()` | `ChainType[]` |
|
|
161
|
-
| `useInitChainServices` | (internal — handled by `SodaxWalletProvider`) | — |
|
|
162
|
-
|
|
163
|
-
---
|
|
164
|
-
|
|
165
|
-
## Hook return-shape glossary
|
|
166
|
-
|
|
167
|
-
```ts
|
|
168
|
-
type XAccount = {
|
|
169
|
-
address: string | undefined;
|
|
170
|
-
xChainType: ChainType | undefined;
|
|
171
|
-
publicKey?: string;
|
|
172
|
-
};
|
|
173
|
-
|
|
174
|
-
type XConnection = {
|
|
175
|
-
xAccount: XAccount;
|
|
176
|
-
xConnectorId: string;
|
|
177
|
-
};
|
|
178
|
-
|
|
179
|
-
type IXConnector = {
|
|
180
|
-
readonly xChainType: ChainType;
|
|
181
|
-
readonly name: string;
|
|
182
|
-
readonly id: string;
|
|
183
|
-
readonly icon: string | undefined;
|
|
184
|
-
readonly isInstalled: boolean;
|
|
185
|
-
readonly installUrl: string | undefined;
|
|
186
|
-
connect(): Promise<XAccount | undefined>;
|
|
187
|
-
disconnect(): Promise<void>;
|
|
188
|
-
};
|
|
189
|
-
```
|
|
190
|
-
|
|
191
|
-
---
|
|
192
|
-
|
|
193
|
-
## "Exactly one of" rule for chain identifiers
|
|
194
|
-
|
|
195
|
-
Hooks that accept both `xChainId` and `xChainType` enforce **exactly one** — passing both, neither, or `undefined` for both throws at runtime (and is a type error):
|
|
196
|
-
|
|
197
|
-
```ts
|
|
198
|
-
useXAccount({ xChainType: 'EVM' }); // ✅
|
|
199
|
-
useXAccount({ xChainId: ChainKeys.BSC_MAINNET }); // ✅
|
|
200
|
-
useXAccount({ xChainType: 'EVM', xChainId: ChainKeys.BSC_MAINNET }); // ❌ throws
|
|
201
|
-
useXAccount({}); // ❌ throws
|
|
202
|
-
```
|
|
203
|
-
|
|
204
|
-
The chain-id form gives narrowest TypeScript inference (e.g. `xChainId: ChainKeys.BSC_MAINNET` → `IEvmWalletProvider`); the chain-type form is family-level.
|
|
@@ -1,106 +0,0 @@
|
|
|
1
|
-
# Reference: Wallet Brand Identifiers
|
|
2
|
-
|
|
3
|
-
`useBatchConnect`, `useBatchDisconnect`, and `useIsWalletInstalled` accept a `connectors: readonly string[]` of **wallet brand identifiers** — short strings that match by **case-insensitive substring** against `connector.id` and `connector.name` (see [`../recipes/batch-operations.md`](../recipes/batch-operations.md)).
|
|
4
|
-
|
|
5
|
-
The identifiers are **open**: any string works. The table below lists every brand the package ships connectors for so you can pick an identifier short enough to match across chain families. To target a specific connector (not a brand), bypass this API and use `useXConnectors({ xChainType }).find(c => c.id === '…')` directly — see [`../recipes/sub-path-imports.md`](../recipes/sub-path-imports.md).
|
|
6
|
-
|
|
7
|
-
---
|
|
8
|
-
|
|
9
|
-
## Known wallet brands
|
|
10
|
-
|
|
11
|
-
| Identifier | Chains it matches | Underlying connector id / name |
|
|
12
|
-
|---|---|---|
|
|
13
|
-
| `'hana'` | EVM, ICON, Sui, Stellar | EVM via EIP-6963 RDNS (e.g. `io.havah.hana`); ICON id `hana`; Sui/Stellar — connector names containing "Hana" |
|
|
14
|
-
| `'phantom'` | EVM, Solana | EVM RDNS `app.phantom`; Solana adapter name `Phantom` |
|
|
15
|
-
| `'metamask'` | EVM, Injective | EVM RDNS `io.metamask`; Injective `Wallet.Metamask` strategy |
|
|
16
|
-
| `'xverse'` | Bitcoin, Stacks | Bitcoin id `xverse`; Stacks id `XverseProviders.BitcoinProvider` |
|
|
17
|
-
| `'unisat'` | Bitcoin | id `unisat` |
|
|
18
|
-
| `'okx'` | Bitcoin | id `okx-bitcoin` |
|
|
19
|
-
| `'leather'` | Stacks | id `LeatherProvider` |
|
|
20
|
-
| `'asigna'` | Stacks | id `AsignaProvider` |
|
|
21
|
-
| `'fordefi'` | Stacks | id `FordefiProviders.UtxoProvider` |
|
|
22
|
-
| `'solflare'`, `'backpack'`, `'coinbase'`, `'trust'`, `'ledger'`, … | Solana | Adapter names from `@solana/wallet-adapter-wallets` |
|
|
23
|
-
| `'freighter'`, `'albedo'`, `'lobstr'`, `'xbull'`, … | Stellar | Names from `@creit.tech/stellar-wallets-kit` |
|
|
24
|
-
|
|
25
|
-
EVM (via EIP-6963), Solana, Sui, Stellar, and Injective surface connectors **dynamically** — the actual ids depend on what's installed in the user's browser. The table reflects names the upstream libraries ship by default.
|
|
26
|
-
|
|
27
|
-
---
|
|
28
|
-
|
|
29
|
-
## Picking a short identifier
|
|
30
|
-
|
|
31
|
-
Substring match is greedy. `'hana'` matches `Hana`, `io.havah.hana`, `hana-anything`. Trade-offs:
|
|
32
|
-
|
|
33
|
-
- **Shorter = broader.** `'hana'` matches everywhere Hana appears across chain families. Good for batch ops targeting a brand across many chains.
|
|
34
|
-
- **Longer = narrower.** `'io.metamask'` only matches the EIP-6963 RDNS — not Injective's MetaMask connector (which uses a different name string). Use when you specifically want one connector and nothing else.
|
|
35
|
-
- **`< 3 chars`** triggers a dev-mode warning — substring matching on 1–2 char identifiers (e.g. `'ok'`) hits unintended connectors. The package will keep working but logs once per identifier.
|
|
36
|
-
|
|
37
|
-
---
|
|
38
|
-
|
|
39
|
-
## Runtime discovery — list what's actually installed
|
|
40
|
-
|
|
41
|
-
The table above is a guide, not authoritative. Browser extensions evolve and RDNS strings change. To inspect the real environment:
|
|
42
|
-
|
|
43
|
-
```tsx
|
|
44
|
-
'use client';
|
|
45
|
-
|
|
46
|
-
import { useXConnectors } from '@sodax/wallet-sdk-react';
|
|
47
|
-
import type { ChainType } from '@sodax/types';
|
|
48
|
-
|
|
49
|
-
const CHAINS: ChainType[] = ['EVM', 'SOLANA', 'SUI', 'BITCOIN', 'STELLAR', 'ICON', 'INJECTIVE', 'NEAR', 'STACKS'];
|
|
50
|
-
|
|
51
|
-
export function DevConnectorLister() {
|
|
52
|
-
return (
|
|
53
|
-
<table>
|
|
54
|
-
<thead>
|
|
55
|
-
<tr><th>Chain</th><th>id</th><th>name</th><th>installed</th></tr>
|
|
56
|
-
</thead>
|
|
57
|
-
<tbody>
|
|
58
|
-
{CHAINS.flatMap((chainType) => (
|
|
59
|
-
<ChainRow key={chainType} chainType={chainType} />
|
|
60
|
-
))}
|
|
61
|
-
</tbody>
|
|
62
|
-
</table>
|
|
63
|
-
);
|
|
64
|
-
}
|
|
65
|
-
|
|
66
|
-
function ChainRow({ chainType }: { chainType: ChainType }) {
|
|
67
|
-
const connectors = useXConnectors({ xChainType: chainType });
|
|
68
|
-
return (
|
|
69
|
-
<>
|
|
70
|
-
{connectors.map((c) => (
|
|
71
|
-
<tr key={`${chainType}-${c.id}`}>
|
|
72
|
-
<td>{chainType}</td>
|
|
73
|
-
<td><code>{c.id}</code></td>
|
|
74
|
-
<td>{c.name}</td>
|
|
75
|
-
<td>{c.isInstalled ? '✓' : '—'}</td>
|
|
76
|
-
</tr>
|
|
77
|
-
))}
|
|
78
|
-
</>
|
|
79
|
-
);
|
|
80
|
-
}
|
|
81
|
-
```
|
|
82
|
-
|
|
83
|
-
Drop this component into your app during integration to print the live connector roster. Pick a short identifier from the `id` or `name` columns and feed it into `useBatchConnect({ connectors: [...] })`.
|
|
84
|
-
|
|
85
|
-
For one-off inspection (no UI):
|
|
86
|
-
|
|
87
|
-
```tsx
|
|
88
|
-
useEffect(() => {
|
|
89
|
-
const all = CHAINS.flatMap((chainType) =>
|
|
90
|
-
useXConnectors({ xChainType: chainType }).map((c) => ({ chainType, id: c.id, name: c.name, isInstalled: c.isInstalled })),
|
|
91
|
-
);
|
|
92
|
-
console.table(all);
|
|
93
|
-
}, []);
|
|
94
|
-
```
|
|
95
|
-
|
|
96
|
-
---
|
|
97
|
-
|
|
98
|
-
## When brand identifiers are the wrong tool
|
|
99
|
-
|
|
100
|
-
Reach for `useXConnectors({ xChainType }).find(c => c.id === '…')` + `useXConnect` directly when:
|
|
101
|
-
|
|
102
|
-
- **The brand list and chain list don't align.** e.g. "Connect Hana on EVM only, even though Hana also covers ICON" — the brand identifier API targets the wallet, not a chain/wallet pair.
|
|
103
|
-
- **You need to disambiguate two wallets with overlapping names.** `'wallet'` would match every wallet-named connector.
|
|
104
|
-
- **You're building a chain picker UI**, not a one-shot batch. Per-chain selection naturally uses `useXConnectors` per chain anyway.
|
|
105
|
-
|
|
106
|
-
See [`../recipes/sub-path-imports.md`](../recipes/sub-path-imports.md) for the worked code path.
|
|
@@ -1,49 +0,0 @@
|
|
|
1
|
-
# Migration: v1 → v2 (Human-readable overview)
|
|
2
|
-
|
|
3
|
-
This folder documents how to migrate an app from v1 to v2 of `@sodax/wallet-sdk-react`. The package name did not change — the breaking changes are in the API surface (provider config, hook signatures, store name, chain class imports). It is the **human-facing** entry point for migration. If you are a coding agent, read [`ai-rules.md`](./ai-rules.md) first.
|
|
4
|
-
|
|
5
|
-
---
|
|
6
|
-
|
|
7
|
-
## What changed at a high level
|
|
8
|
-
|
|
9
|
-
v2 is a near-rewrite of v1 with a focus on three goals:
|
|
10
|
-
|
|
11
|
-
1. **Configurable chain opt-in** — v1 always mounted every chain adapter. v2 lets you opt in per chain by including only the slots you need on `SodaxWalletConfig`.
|
|
12
|
-
2. **Single source of truth for chain config** — v1 spread chain config across `rpcConfig`, `options`, and `initialState`. v2 collapses these into one `config` object on `SodaxWalletProvider`.
|
|
13
|
-
3. **Store-first hooks** — v2 hooks all read from a central Zustand store; no chain-specific React context coupling. This makes hooks composable and testable in isolation.
|
|
14
|
-
|
|
15
|
-
The persisted localStorage key (`xwagmi-store`) is **unchanged** — existing user connections survive the migration boundary.
|
|
16
|
-
|
|
17
|
-
> Full prose on motivations and behavior changes lives in [`breaking-changes.md`](./breaking-changes.md).
|
|
18
|
-
|
|
19
|
-
---
|
|
20
|
-
|
|
21
|
-
## Read order
|
|
22
|
-
|
|
23
|
-
If you are migrating by hand, read in this order:
|
|
24
|
-
|
|
25
|
-
1. [`breaking-changes.md`](./breaking-changes.md) — every breaking change with the WHY behind it.
|
|
26
|
-
2. [`reference/imports.md`](./reference/imports.md) — package and path renames (mechanical).
|
|
27
|
-
3. [`reference/config.md`](./reference/config.md) — `SodaxWalletProvider` config shape (this is the biggest single change).
|
|
28
|
-
4. [`reference/hooks.md`](./reference/hooks.md) — hook signature and rename map.
|
|
29
|
-
5. [`reference/components.md`](./reference/components.md) — component / provider renames.
|
|
30
|
-
6. [`recipes/`](./recipes/) — paired before/after for common patterns (connect button, multi-chain modal, SSR, WalletConnect).
|
|
31
|
-
7. [`checklist.md`](./checklist.md) — final verification pass; tick each item before declaring done.
|
|
32
|
-
|
|
33
|
-
If you are letting a coding agent drive the migration, point it at [`ai-rules.md`](./ai-rules.md) — that file gives the agent its workflow, stop conditions, and verification protocol.
|
|
34
|
-
|
|
35
|
-
---
|
|
36
|
-
|
|
37
|
-
## What is NOT covered here
|
|
38
|
-
|
|
39
|
-
- **Other SODAX packages** (`@sodax/sdk`, `@sodax/dapp-kit`). They have their own migration docs in their respective `ai-exported/` folders.
|
|
40
|
-
- **Behavioral migration of business logic** that isn't tied to wallet hooks — out of scope.
|
|
41
|
-
- **App framework upgrades** (Next.js, Vite versions) — out of scope.
|
|
42
|
-
|
|
43
|
-
---
|
|
44
|
-
|
|
45
|
-
## Getting help
|
|
46
|
-
|
|
47
|
-
If you hit a v1 pattern not covered in `reference/` or `recipes/`, please [open an issue](https://github.com/icon-project/sodax-sdks/issues) with the v1 code snippet — we'll add it to the docs.
|
|
48
|
-
|
|
49
|
-
For internal SODAX maintainers: see `../CLAUDE.md` for architecture context.
|
|
@@ -1,144 +0,0 @@
|
|
|
1
|
-
# AI Rules — v1 → v2 Migration
|
|
2
|
-
|
|
3
|
-
You are migrating a user's app from v1 to v2 of `@sodax/wallet-sdk-react`. The package name did not change — detect v1 by import surface (`useXWagmiStore`, positional hook args, `rpcConfig`/`options`/`initialState` props on `SodaxWalletProvider`, concrete chain class imports from the barrel). Follow this protocol exactly.
|
|
4
|
-
|
|
5
|
-
---
|
|
6
|
-
|
|
7
|
-
## Workflow (do these in order)
|
|
8
|
-
|
|
9
|
-
### 1. Survey
|
|
10
|
-
|
|
11
|
-
Before changing anything, survey the user's project:
|
|
12
|
-
|
|
13
|
-
```bash
|
|
14
|
-
# v1 store usage
|
|
15
|
-
grep -rn "useXWagmiStore" <user-src>
|
|
16
|
-
|
|
17
|
-
# v1 provider props (rpcConfig / options / initialState)
|
|
18
|
-
grep -rn "SodaxWalletProvider" <user-src> -A 5 | grep -E "rpcConfig|initialState|options="
|
|
19
|
-
|
|
20
|
-
# v1 positional hook args (e.g. useXAccount('EVM'))
|
|
21
|
-
grep -rnE "useXAccount\(['\"]" <user-src>
|
|
22
|
-
grep -rnE "useXConnectors\(['\"]" <user-src>
|
|
23
|
-
grep -rnE "useXConnection\(['\"]" <user-src>
|
|
24
|
-
grep -rnE "useXService\(['\"]" <user-src>
|
|
25
|
-
grep -rnE "useWalletProvider\(['\"]" <user-src>
|
|
26
|
-
|
|
27
|
-
# v1 concrete chain class imports from the barrel
|
|
28
|
-
grep -rnE "from '@sodax/wallet-sdk-react'" <user-src> | grep -E "XService|XConnector"
|
|
29
|
-
```
|
|
30
|
-
|
|
31
|
-
Build a list of every file that uses a v1 pattern. Show this list to the user before proceeding.
|
|
32
|
-
|
|
33
|
-
### 2. Bump the package version
|
|
34
|
-
|
|
35
|
-
Update `@sodax/wallet-sdk-react` to the latest v2 release in the user's `package.json`. Run install. **Do not edit any source files yet** — keep TypeScript broken so you can use compiler errors as a worklist.
|
|
36
|
-
|
|
37
|
-
### 3. Migrate the provider first
|
|
38
|
-
|
|
39
|
-
Always migrate `SodaxWalletProvider` (or v1's `XWagmiProviders`) before touching consumer files. The config shape is the biggest change — see [`reference/config.md`](./reference/config.md) and [`recipes/`](./recipes/) for the new pattern. Without a working provider, hooks will fail at runtime even if types pass.
|
|
40
|
-
|
|
41
|
-
### 4. Run typecheck, use errors as worklist
|
|
42
|
-
|
|
43
|
-
```bash
|
|
44
|
-
pnpm checkTs
|
|
45
|
-
```
|
|
46
|
-
|
|
47
|
-
For each error mentioning `@sodax/wallet-sdk-react` or a v1 hook name:
|
|
48
|
-
|
|
49
|
-
1. Look up the symbol in [`reference/imports.md`](./reference/imports.md), [`reference/hooks.md`](./reference/hooks.md), [`reference/config.md`](./reference/config.md), or [`reference/components.md`](./reference/components.md).
|
|
50
|
-
2. If found, apply the mechanical replacement.
|
|
51
|
-
3. If not found, **stop and ask the user**. Do not invent a migration.
|
|
52
|
-
|
|
53
|
-
### 5. Apply recipes for non-mechanical changes
|
|
54
|
-
|
|
55
|
-
Some patterns require structural rewrites, not just symbol swaps. Use the matching recipe file:
|
|
56
|
-
|
|
57
|
-
- Connect button → [`recipes/connect-button.md`](./recipes/connect-button.md)
|
|
58
|
-
- Multi-chain modal → [`recipes/multi-chain-modal.md`](./recipes/multi-chain-modal.md)
|
|
59
|
-
- Next.js SSR setup → [`recipes/ssr-setup.md`](./recipes/ssr-setup.md)
|
|
60
|
-
- WalletConnect → [`recipes/walletconnect-migration.md`](./recipes/walletconnect-migration.md)
|
|
61
|
-
|
|
62
|
-
### 6. Verify with the checklist
|
|
63
|
-
|
|
64
|
-
Loop through every item in [`checklist.md`](./checklist.md). Each item is machine-checkable (most are `grep` commands). Do not skip items. Report results back to the user.
|
|
65
|
-
|
|
66
|
-
---
|
|
67
|
-
|
|
68
|
-
## DO
|
|
69
|
-
|
|
70
|
-
- **DO** read `migration/breaking-changes.md` once at the start to understand the WHY behind changes. This helps you handle ambiguous user code.
|
|
71
|
-
- **DO** preserve user comments, formatting, and unrelated code. Only touch what the migration requires.
|
|
72
|
-
- **DO** update one file at a time, then re-run `pnpm checkTs` to confirm progress.
|
|
73
|
-
- **DO** prefer the official `recipes/` over inventing your own structural rewrite.
|
|
74
|
-
- **DO** treat `reference/*.md` as the only source of truth for symbol mappings. If a mapping is missing, it's a docs gap — flag it.
|
|
75
|
-
- **DO** explicitly check whether the user's project is Next.js (App Router or Pages) before touching providers — SSR config differs.
|
|
76
|
-
|
|
77
|
-
---
|
|
78
|
-
|
|
79
|
-
## DO NOT
|
|
80
|
-
|
|
81
|
-
- **DO NOT** delete v1 imports until the corresponding v2 imports are added and the file typechecks.
|
|
82
|
-
- **DO NOT** rename user files, even if v1 file names look outdated. Keep file paths stable so the user's git history stays clean.
|
|
83
|
-
- **DO NOT** modify tests until source migration is complete — wait for green typecheck first, then update tests as a separate pass.
|
|
84
|
-
- **DO NOT** "improve" surrounding code (refactor, restyle, add error handling, change variable names). Only apply migration changes.
|
|
85
|
-
- **DO NOT** assume v1 prop shapes from memory — always verify against [`reference/config.md`](./reference/config.md). v1 had several optional fields whose defaults differ from v2.
|
|
86
|
-
- **DO NOT** silently drop user features. If v1 used `XWagmiProviders` with `initialState` and v2 has no equivalent, **stop and ask** how to preserve that state initialization.
|
|
87
|
-
- **DO NOT** change the persisted localStorage key (`xwagmi-store`). User connections will be lost across the migration boundary if you do.
|
|
88
|
-
|
|
89
|
-
---
|
|
90
|
-
|
|
91
|
-
## Stop conditions (defer to user)
|
|
92
|
-
|
|
93
|
-
Stop and ask the user before continuing if you encounter any of the following. These cannot be migrated mechanically:
|
|
94
|
-
|
|
95
|
-
| Signal | Why stop |
|
|
96
|
-
|---|---|
|
|
97
|
-
| Custom `XConnector` subclass in user code | v1 and v2 have different abstract method signatures. User must port manually. |
|
|
98
|
-
| Custom `XService` subclass in user code | Same as above. |
|
|
99
|
-
| User reads from `useXWagmiStore` with a selector touching `setXConnection`, `unsetXConnection`, or any v2-internal field (`enabledChains`, `walletProviders`, `chainActions`, …) | These are not part of the v2 public API. Agent must replace direct store reads with public hooks (`useXServices`, `useXConnections`, etc. — see [`reference/imports.md`](./reference/imports.md) § "Store hook removed"). For mutations the user must adopt `useXConnect` / `useXDisconnect` — confirm before substituting. |
|
|
100
|
-
| User passes `rpcConfig`, `options`, or `initialState` to the v1 provider | These are removed in v2. Migration target is the new `config` object. Verify what behavior the user wants preserved. |
|
|
101
|
-
| Test files that mock `XService` or `XConnector` | Mock surface differs. Tests must be updated by hand with the user's intent in mind. |
|
|
102
|
-
| `apps/wallet-modal-example` is referenced | This is internal SODAX scaffolding, not for end users. |
|
|
103
|
-
| User explicitly says "don't change behavior X" | Some v2 changes are intentional behavior shifts (e.g. EVM = single connection across all networks). Confirm before forcing v1 behavior back. |
|
|
104
|
-
|
|
105
|
-
When stopping, **quote the file/line** of the offending code and present the user with concrete options.
|
|
106
|
-
|
|
107
|
-
---
|
|
108
|
-
|
|
109
|
-
## Verification protocol (after every change)
|
|
110
|
-
|
|
111
|
-
```bash
|
|
112
|
-
# 1. Type check
|
|
113
|
-
pnpm checkTs
|
|
114
|
-
|
|
115
|
-
# 2. Verify no v1 patterns remain
|
|
116
|
-
grep -rn "useXWagmiStore\|useXWalletStore" <user-src> # expect empty (v2 barrel doesn't export the store hook under either name — all call sites must use public hooks)
|
|
117
|
-
grep -rnE "SodaxWalletProvider[^>]*\b(rpcConfig|initialState|options)\s*=" <user-src> # expect empty
|
|
118
|
-
grep -rnE "useXAccount\(['\"]" <user-src> # expect empty
|
|
119
|
-
grep -rnE "useXConnectors\(['\"]" <user-src> # expect empty
|
|
120
|
-
grep -rnE "useXConnection\(['\"]" <user-src> # expect empty
|
|
121
|
-
|
|
122
|
-
# 3. Verify v2 provider is mounted with config prop
|
|
123
|
-
grep -rnE "SodaxWalletProvider[^>]*\bconfig\s*=" <user-src> # expect at least one match in app entry
|
|
124
|
-
|
|
125
|
-
# 4. Verify QueryClientProvider wraps SodaxWalletProvider (v2 no longer mounts QueryClient internally)
|
|
126
|
-
# (manual — open the provider file, confirm <QueryClientProvider> wraps <SodaxWalletProvider>)
|
|
127
|
-
```
|
|
128
|
-
|
|
129
|
-
If all four pass and the [`checklist.md`](./checklist.md) is complete, the migration is done.
|
|
130
|
-
|
|
131
|
-
---
|
|
132
|
-
|
|
133
|
-
## Done criteria
|
|
134
|
-
|
|
135
|
-
The migration is complete when:
|
|
136
|
-
|
|
137
|
-
- [ ] `pnpm checkTs` exits clean.
|
|
138
|
-
- [ ] No `useXWagmiStore` or `useXWalletStore` imports remain (v2 does not export the store hook — every call site must use public hooks like `useXServices` / `useXConnections`).
|
|
139
|
-
- [ ] No positional hook args remain (`useXAccount('EVM')` etc).
|
|
140
|
-
- [ ] `SodaxWalletProvider` is mounted with a v2-shaped `config` prop, wrapped by `QueryClientProvider`.
|
|
141
|
-
- [ ] All items in [`checklist.md`](./checklist.md) are checked.
|
|
142
|
-
- [ ] The user has confirmed the connect/disconnect flow works in their dev environment.
|
|
143
|
-
|
|
144
|
-
Do not declare the migration done before all six are true.
|