@sodax/dapp-kit 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.
Files changed (63) hide show
  1. package/README.md +9 -63
  2. package/dist/index.d.ts +11 -4
  3. package/dist/index.mjs +3 -6
  4. package/package.json +31 -19
  5. package/src/providers/SodaxProvider.tsx +15 -11
  6. package/ai-exported/AGENTS.md +0 -134
  7. package/ai-exported/integration/README.md +0 -49
  8. package/ai-exported/integration/ai-rules.md +0 -79
  9. package/ai-exported/integration/architecture.md +0 -274
  10. package/ai-exported/integration/features/README.md +0 -29
  11. package/ai-exported/integration/features/auxiliary-services.md +0 -169
  12. package/ai-exported/integration/features/bitcoin.md +0 -87
  13. package/ai-exported/integration/features/bridge.md +0 -91
  14. package/ai-exported/integration/features/dex.md +0 -152
  15. package/ai-exported/integration/features/migration.md +0 -118
  16. package/ai-exported/integration/features/money-market.md +0 -116
  17. package/ai-exported/integration/features/staking.md +0 -123
  18. package/ai-exported/integration/features/swap.md +0 -101
  19. package/ai-exported/integration/quickstart.md +0 -187
  20. package/ai-exported/integration/recipes/README.md +0 -136
  21. package/ai-exported/integration/recipes/backend-queries.md +0 -157
  22. package/ai-exported/integration/recipes/bitcoin.md +0 -193
  23. package/ai-exported/integration/recipes/bridge.md +0 -174
  24. package/ai-exported/integration/recipes/dex.md +0 -204
  25. package/ai-exported/integration/recipes/invalidations.md +0 -115
  26. package/ai-exported/integration/recipes/migration.md +0 -212
  27. package/ai-exported/integration/recipes/money-market.md +0 -206
  28. package/ai-exported/integration/recipes/mutation-error-handling.md +0 -118
  29. package/ai-exported/integration/recipes/observability.md +0 -93
  30. package/ai-exported/integration/recipes/setup.md +0 -144
  31. package/ai-exported/integration/recipes/staking.md +0 -202
  32. package/ai-exported/integration/recipes/swap.md +0 -272
  33. package/ai-exported/integration/recipes/wallet-connectivity.md +0 -101
  34. package/ai-exported/integration/reference/README.md +0 -12
  35. package/ai-exported/integration/reference/glossary.md +0 -188
  36. package/ai-exported/integration/reference/hooks-index.md +0 -190
  37. package/ai-exported/integration/reference/public-api.md +0 -110
  38. package/ai-exported/integration/reference/querykey-conventions.md +0 -179
  39. package/ai-exported/migration/README.md +0 -60
  40. package/ai-exported/migration/ai-rules.md +0 -81
  41. package/ai-exported/migration/breaking-changes/hook-signatures.md +0 -233
  42. package/ai-exported/migration/breaking-changes/querykey-conventions.md +0 -108
  43. package/ai-exported/migration/breaking-changes/result-handling.md +0 -211
  44. package/ai-exported/migration/breaking-changes/sdk-leakage.md +0 -165
  45. package/ai-exported/migration/checklist.md +0 -89
  46. package/ai-exported/migration/features/README.md +0 -34
  47. package/ai-exported/migration/features/auxiliary-services.md +0 -114
  48. package/ai-exported/migration/features/bitcoin.md +0 -88
  49. package/ai-exported/migration/features/bridge.md +0 -123
  50. package/ai-exported/migration/features/dex.md +0 -101
  51. package/ai-exported/migration/features/migration.md +0 -120
  52. package/ai-exported/migration/features/money-market.md +0 -97
  53. package/ai-exported/migration/features/staking.md +0 -109
  54. package/ai-exported/migration/features/swap.md +0 -118
  55. package/ai-exported/migration/recipes.md +0 -188
  56. package/ai-exported/migration/reference/README.md +0 -15
  57. package/ai-exported/migration/reference/deleted-hooks.md +0 -110
  58. package/ai-exported/migration/reference/error-shape-crosswalk.md +0 -144
  59. package/ai-exported/migration/reference/renamed-hooks.md +0 -66
  60. package/dist/index.cjs +0 -2642
  61. package/dist/index.cjs.map +0 -1
  62. package/dist/index.d.cts +0 -1550
  63. package/dist/index.mjs.map +0 -1
@@ -1,109 +0,0 @@
1
- # Staking migration — v1 → v2 (dapp-kit)
2
-
3
- Pair: [`../../integration/features/staking.md`](../../integration/features/staking.md).
4
-
5
- ## TL;DR
6
-
7
- > Cross-cutting conventions (drop `spokeProvider`, single-object hook init, `mutate(vars)` for domain inputs, `mutateAsyncSafe` ergonomics) — see [`../breaking-changes/hook-signatures.md`](../breaking-changes/hook-signatures.md) and [`../breaking-changes/result-handling.md`](../breaking-changes/result-handling.md). Feature-specific deltas below:
8
-
9
- 1. **All five mutations** (`useStake`, `useUnstake`, `useInstantUnstake`, `useClaim`, `useCancelUnstake`) drop `spokeProvider` from hook init; `walletProvider` flows through `mutate(vars)`.
10
- 2. **Three approve hooks** (`useStakeApprove`, `useUnstakeApprove`, `useInstantUnstakeApprove`) — same shape change. Each approves a different token (SODA for stake; xSODA for unstake/instant).
11
- 3. **`useStakeRatio` return changed.** v2: `Result<[xSodaAmount, previewDepositAmount]>` — a 2-tuple. v1 returned a single bigint.
12
- 4. **`useUnstakingInfo` return shape changed.** v2: `Result<UnstakingInfo>` where `UnstakingInfo = { userUnstakeSodaRequests: UserUnstakeInfo[], totalUnstaking: bigint }`. v1 may have returned just the array — v2 wraps it in an object.
13
- 5. **Action params gained `srcChainKey` + `srcAddress`.** Same SDK-leakage as MM.
14
-
15
- ## Per-method delta
16
-
17
- ### `useStake` (template for all five)
18
-
19
- ```diff
20
- function StakeButton({ amount, srcAddress }) {
21
- - const stake = useStake(spokeProvider);
22
- + const walletProvider = useWalletProvider({ xChainId: ChainKeys.BASE_MAINNET });
23
- + const { mutateAsyncSafe: stake } = useStake();
24
-
25
- const handleStake = async () => {
26
- + if (!walletProvider) return;
27
- - await stake.mutateAsync({ params: { amount, minReceive, action: 'stake' } });
28
- + const result = await stake({
29
- + params: {
30
- + srcChainKey: ChainKeys.BASE_MAINNET,
31
- + srcAddress,
32
- + amount,
33
- + minReceive,
34
- + action: 'stake',
35
- + },
36
- + walletProvider,
37
- + });
38
- + if (!result.ok) return;
39
- + const { srcChainTxHash, dstChainTxHash } = result.value;
40
- };
41
- }
42
- ```
43
-
44
- `useUnstake` / `useInstantUnstake` / `useClaim` / `useCancelUnstake` follow the same pattern with their respective params types.
45
-
46
- ### Approve hooks
47
-
48
- Each of stake / unstake / instantUnstake has its OWN approve hook (different tokens):
49
-
50
- ```diff
51
- - const { approve, isLoading } = useStakeApprove(spokeProvider);
52
- - await approve({ amount, action: 'stake' });
53
- + const { mutateAsync: approve, isPending } = useStakeApprove();
54
- + await approve({ params: { srcChainKey, srcAddress, amount, action: 'stake' }, walletProvider });
55
- ```
56
-
57
- `useUnstakeApprove`, `useInstantUnstakeApprove` — same pattern.
58
-
59
- ### `useStakeRatio` — return type change
60
-
61
- ```diff
62
- - const { data: ratio } = useStakeRatio(amount);
63
- - if (ratio) {
64
- - const xSodaAmount = ratio; // v1 returned single bigint
65
- - /* ... */
66
- - }
67
- + const { data: ratio } = useStakeRatio({ params: { amount } });
68
- + if (ratio?.ok) {
69
- + const [xSodaAmount, previewDepositAmount] = ratio.value; // v2 returns tuple
70
- + }
71
- ```
72
-
73
- ### `useUnstakingInfo` — return shape change
74
-
75
- ```diff
76
- - const { data: requests } = useUnstakingInfo(spokeProvider);
77
- - requests?.map((r) => /* ... */); // v1 was an array
78
- + const { data: result } = useUnstakingInfo({ params: { srcAddress, srcChainKey } });
79
- + if (result?.ok) {
80
- + const { userUnstakeSodaRequests, totalUnstaking } = result.value; // v2 is object
81
- + userUnstakeSodaRequests.map((r) => /* ... */);
82
- + }
83
- ```
84
-
85
- ### `useUnstakingInfoWithPenalty`
86
-
87
- New in v2 — wraps `useUnstakingInfo`'s base shape with a per-request penalty annotation. Skip this section if your v1 codebase didn't compute penalty client-side.
88
-
89
- ```ts
90
- // @ai-snippets-skip
91
- const { data: result } = useUnstakingInfoWithPenalty({ params: { srcAddress, srcChainKey } });
92
- if (result?.ok) {
93
- const { requestsWithPenalty } = result.value; // each adds penalty, penaltyPercentage, claimableAmount
94
- }
95
- ```
96
-
97
- ## Pitfalls
98
-
99
- 1. **`useStakeRatio` returns a tuple, not a single bigint.** v1 was simpler; v2 returns `[xSodaAmount, previewDepositAmount]`. Adjust render code.
100
- 2. **`useStakingInfo` is unwrapped (not Result), but `useUnstakingInfo` IS Result-wrapped.** Asymmetric — check the integration docs per hook.
101
- 3. **`useUnstakingInfoWithPenalty` returns an object with `requestsWithPenalty` array embedded** — don't `.value.map(...)`, use `.value.requestsWithPenalty.map(...)`.
102
- 4. **Unstake has a waiting period.** Display via `useStakingConfig().unstakingPeriod`. Shows up in v1 too, but the read shape may have changed.
103
- 5. **Instant unstake bypasses the waiting period but pays slippage.** Use `useInstantUnstakeRatio` to preview; set `minAmount` in params for slippage protection.
104
-
105
- ## Cross-references
106
-
107
- - [`../../integration/features/staking.md`](../../integration/features/staking.md) — v2 reference.
108
- - [`../../integration/recipes/staking.md`](../../integration/recipes/staking.md) — full v2 worked example.
109
- - [`../../../../sdk/ai-exported/migration/features/staking.md`](../../../../sdk/ai-exported/migration/features/staking.md) — underlying SDK staking migration.
@@ -1,118 +0,0 @@
1
- # Swap migration — v1 → v2 (dapp-kit)
2
-
3
- Pair: [`../../integration/features/swap.md`](../../integration/features/swap.md).
4
-
5
- ## TL;DR
6
-
7
- > Cross-cutting conventions (drop `spokeProvider`, single-object hook init, `mutate(vars)` for domain inputs, `mutateAsyncSafe` ergonomics) — see [`../breaking-changes/hook-signatures.md`](../breaking-changes/hook-signatures.md) and [`../breaking-changes/result-handling.md`](../breaking-changes/result-handling.md). Feature-specific deltas below:
8
-
9
- 1. **Drop `spokeProvider` from `useSwap` and `useSwapApprove` hook init.** Pass `walletProvider` (from `useWalletProvider({ xChainId: chainKey })`) into `mutate(vars)`.
10
- 2. **`useSwapAllowance({ params: { payload, srcChainKey, walletProvider } })`** — query inputs all nest under `params` (no top-level `spokeProvider` or `walletProvider`); the SDK request goes under `params.payload`.
11
- 3. **Approve hook return shape changed.** `{ approve, isLoading } = useSwapApprove(...)` → `{ mutateAsync: approve, isPending } = useSwapApprove()`.
12
- 4. **`mutationFn` throws on SDK `!ok`.** Either wrap `mutateAsync` in `try/catch` or use `mutateAsyncSafe` for `Result<T>` branching.
13
- 5. **Field on `Intent` read shape kept its name.** `Intent.srcChain` / `Intent.dstChain` are still `IntentRelayChainId` (bigint) — distinct from request-side `srcChainKey` / `dstChainKey` on action params.
14
- 6. **`useStatus({ params: { intentTxHash } })` — single-object query shape.** v1's positional version is gone. Key was renamed `intentHash → intentTxHash`. Return is `Result<SolverIntentStatusResponse, SolverErrorResponse> | undefined` — branch on `data?.ok` before reading status fields.
15
-
16
- ## Per-method delta
17
-
18
- ### `useSwap` — execute swap
19
-
20
- ```diff
21
- function SwapButton({ intentParams }: { intentParams: CreateIntentParams }) {
22
- - const swap = useSwap(spokeProvider);
23
- + const walletProvider = useWalletProvider({ xChainId: ChainKeys.BSC_MAINNET });
24
- + const { mutateAsyncSafe: swap, isPending } = useSwap();
25
-
26
- const handleSwap = async () => {
27
- + if (!walletProvider) return;
28
- - const result = await swap.mutateAsync({ params: intentParams });
29
- - if (result.ok) {
30
- - const { intent, intentDeliveryInfo } = result.value;
31
- - /* ... */
32
- - } else {
33
- - toast.error(result.error.message);
34
- - }
35
- + const result = await swap({ params: intentParams, walletProvider });
36
- + if (!result.ok) {
37
- + toast.error(result.error instanceof Error ? result.error.message : 'Swap failed');
38
- + return;
39
- + }
40
- + const { intent, intentDeliveryInfo } = result.value;
41
- + /* ... */
42
- };
43
- }
44
- ```
45
-
46
- ### `useSwapApprove` — return shape
47
-
48
- ```diff
49
- - const { approve, isLoading, error } = useSwapApprove(spokeProvider);
50
- - await approve(intentParams);
51
- + const { mutateAsync: approve, isPending, error } = useSwapApprove();
52
- + await approve({ params: intentParams, walletProvider });
53
- ```
54
-
55
- `isLoading` → `isPending` (React Query 5 convention).
56
-
57
- ### `useSwapAllowance` — payload + srcChainKey + walletProvider all under `params`
58
-
59
- ```diff
60
- - const { data: allowanceResult } = useSwapAllowance({ params: intentParams, spokeProvider });
61
- + const { data: isApproved } = useSwapAllowance({
62
- + params: { payload: intentParams, srcChainKey: ChainKeys.BSC_MAINNET, walletProvider },
63
- + });
64
- + // `data` is `boolean | undefined` (already unwrapped); no `.ok` branch needed.
65
- ```
66
-
67
- ### `useStatus` — single-object shape + param renamed `intentHash → intentTxHash`
68
-
69
- ```diff
70
- - const { data: status } = useStatus(intentHash);
71
- + const { data: status } = useStatus({ params: { intentTxHash } });
72
- + // `data` is `Result<SolverIntentStatusResponse, SolverErrorResponse> | undefined` —
73
- + // branch on `data?.ok` before reading `data.value.<fields>`.
74
- ```
75
-
76
- ### `useQuote` — single-object shape + SDK request nested under `params.payload`
77
-
78
- ```diff
79
- - const { data: quote } = useQuote({
80
- - token_src: SRC_TOKEN,
81
- - token_dst: DST_TOKEN,
82
- - token_src_blockchain_id: BSC_MAINNET_CHAIN_ID,
83
- - token_dst_blockchain_id: ARBITRUM_MAINNET_CHAIN_ID,
84
- - amount,
85
- - quote_type: 'exact_input',
86
- - });
87
- + const { data: quote } = useQuote({
88
- + params: {
89
- + payload: {
90
- + token_src: SRC_TOKEN,
91
- + token_dst: DST_TOKEN,
92
- + token_src_blockchain_id: ChainKeys.BSC_MAINNET,
93
- + token_dst_blockchain_id: ChainKeys.ARBITRUM_MAINNET,
94
- + amount,
95
- + quote_type: 'exact_input',
96
- + },
97
- + },
98
- + });
99
- ```
100
-
101
- `SolverIntentQuoteRequest` shape unchanged. Two v2 changes: SDK request is nested under `params.payload` (not directly under `params`); constants renamed (`*_MAINNET_CHAIN_ID` → `ChainKeys.X_MAINNET`).
102
-
103
- ### `useCreateLimitOrder` / `useCancelLimitOrder` / `useCancelSwap`
104
-
105
- Same shape changes as `useSwap` — drop `spokeProvider`, move domain inputs to `mutate(vars)`.
106
-
107
- ## Pitfalls
108
-
109
- 1. **`Intent.srcChain` / `Intent.dstChain` look like they should rename.** They didn't. Those are read-shape `IntentRelayChainId` (bigint), distinct from request-side `srcChainKey` / `dstChainKey`. Don't grep-replace.
110
- 2. **`useStatus` polling default.** v2 polls every 3 s unconditionally once `intentTxHash` is supplied (it does not auto-stop on terminal states — your UI should disable rendering when no longer needed, or override `queryOptions.refetchInterval: false`). Port any v1 custom polling to `queryOptions.refetchInterval`.
111
- 3. **`useQuote` data is `Result<T>`** — branch on `data?.ok` before reading `data.value.quoted_amount`.
112
-
113
- ## Cross-references
114
-
115
- - [`../../integration/features/swap.md`](../../integration/features/swap.md) — v2 reference.
116
- - [`../../integration/recipes/swap.md`](../../integration/recipes/swap.md) — full v2 worked example.
117
- - [`../breaking-changes/hook-signatures.md`](../breaking-changes/hook-signatures.md), [`../breaking-changes/result-handling.md`](../breaking-changes/result-handling.md) — cross-cutting deltas.
118
- - [`../../../../sdk/ai-exported/migration/features/swap.md`](../../../../sdk/ai-exported/migration/features/swap.md) — underlying SDK swap migration.
@@ -1,188 +0,0 @@
1
- # Migration recipes — `@sodax/dapp-kit` v1 → v2
2
-
3
- Codemods, adapters, and incremental migration patterns. Use these when full conversion in one pass isn't realistic or when you want to mechanize the boring parts.
4
-
5
- ## Codemod 1: chain-id constants → ChainKeys
6
-
7
- ```bash
8
- # From your consumer's repo root:
9
- find src -type f \( -name '*.ts' -o -name '*.tsx' \) | xargs sed -i '' -E 's/\b([A-Z_]+)_MAINNET_CHAIN_ID\b/ChainKeys.\1_MAINNET/g'
10
- ```
11
-
12
- Then add `import { ChainKeys } from '@sodax/sdk'` (or `'@sodax/dapp-kit'` — both work) where needed. tsc will flag missing imports.
13
-
14
- For more sophisticated automation across many files, use ts-morph:
15
-
16
- ```ts
17
- // @ai-snippets-skip
18
- // codemod-chain-ids.ts — run with `tsx codemod-chain-ids.ts`
19
- import { Project, SyntaxKind } from 'ts-morph';
20
-
21
- const project = new Project({ tsConfigFilePath: './tsconfig.json' });
22
-
23
- for (const file of project.getSourceFiles('src/**/*.{ts,tsx}')) {
24
- let needsImport = false;
25
-
26
- file.forEachDescendant((node) => {
27
- if (node.getKind() === SyntaxKind.Identifier) {
28
- const text = node.getText();
29
- const m = text.match(/^([A-Z_]+)_MAINNET_CHAIN_ID$/);
30
- if (m) {
31
- node.replaceWithText(`ChainKeys.${m[1]}_MAINNET`);
32
- needsImport = true;
33
- }
34
- }
35
- });
36
-
37
- if (needsImport && !file.getImportDeclaration('@sodax/sdk')?.getNamedImports().some(n => n.getName() === 'ChainKeys')) {
38
- file.addImportDeclaration({ moduleSpecifier: '@sodax/sdk', namedImports: ['ChainKeys'] });
39
- }
40
- }
41
-
42
- await project.save();
43
- ```
44
-
45
- ## Codemod 2: useSpokeProvider deletion
46
-
47
- `useSpokeProvider` is gone in v2. Delete the import + usage; replace with `useWalletProvider` from `@sodax/wallet-sdk-react`.
48
-
49
- ```bash
50
- # 1. Find all usages first.
51
- grep -rE '\buseSpokeProvider\b' src/
52
-
53
- # 2. Manual delete + rewrite each (no safe sed for this — context varies).
54
- ```
55
-
56
- Per call site, the rewrite:
57
-
58
- ```diff
59
- - import { useSpokeProvider } from '@sodax/dapp-kit';
60
- - const spokeProvider = useSpokeProvider({ chainId: BSC_MAINNET_CHAIN_ID });
61
- + import { useWalletProvider } from '@sodax/wallet-sdk-react';
62
- + import { ChainKeys } from '@sodax/sdk';
63
- + const walletProvider = useWalletProvider({ xChainId: ChainKeys.BSC_MAINNET });
64
- ```
65
-
66
- Then update consumers of `spokeProvider` to use `walletProvider` instead — usually inside `mutate(vars)` payloads, sometimes inside query hook params.
67
-
68
- ## Codemod 3: invalidate*Queries utilities deletion
69
-
70
- Most v1 consumers had `lib/invalidate*Queries.ts` files. Hook-owned invalidations make these obsolete:
71
-
72
- ```bash
73
- # Find them.
74
- grep -rE '(invalidateMmQueries|invalidateSwapQueries|invalidateBridgeQueries|invalidate\w+Queries)' src/
75
-
76
- # For each call site, delete the call. The mutation hook handles invalidation.
77
- ```
78
-
79
- If you have a custom invalidation that dapp-kit's hooks don't know about (e.g. your own analytics view), move it into `mutationOptions.onSuccess`:
80
-
81
- ```diff
82
- const { mutateAsync: supply } = useSupply({
83
- + mutationOptions: {
84
- + onSuccess: async (data, vars) => {
85
- + await queryClient.invalidateQueries({ queryKey: ['my-app', 'analytics'] });
86
- + },
87
- + },
88
- });
89
- - await supply({ params, spokeProvider });
90
- - invalidateMmQueries(queryClient, ...); // delete
91
- - await queryClient.invalidateQueries({ queryKey: ['my-app', 'analytics'] }); // delete
92
- + await supply({ params, walletProvider });
93
- ```
94
-
95
- ## Adapter: Result<T>-shape adapter for legacy error consumers
96
-
97
- If your consumer code has a helper that branches on a v1 error shape (e.g. `error.code` from old per-feature classes), the minimal change is to map v2 onto v1 at the boundary:
98
-
99
- ```ts
100
- // adapters/v1ErrorShape.ts
101
- import { isSodaxError } from '@sodax/dapp-kit';
102
-
103
- // V1 shape: { code, message, data?: { error } }
104
- export function adaptToV1ErrorShape(error: unknown): { code?: string; message?: string; data?: { error?: unknown } } | null {
105
- if (!error) return null;
106
- if (isSodaxError(error)) {
107
- return {
108
- code: error.code,
109
- message: error.message,
110
- data: { error: error.cause },
111
- };
112
- }
113
- if (error instanceof Error) return { code: 'UNKNOWN', message: error.message };
114
- if (typeof error === 'object') return error as { code?: string; message?: string };
115
- return null;
116
- }
117
- ```
118
-
119
- Then your existing v1-shape error handlers keep working:
120
-
121
- ```ts
122
- // @ai-snippets-skip
123
- const { mutateAsync: swap } = useSwap();
124
- try {
125
- await swap({ params, walletProvider });
126
- } catch (e) {
127
- const adapted = adaptToV1ErrorShape(e);
128
- if (adapted?.code === 'INTENT_CREATION_FAILED' /* etc. */) { /* ... */ }
129
- }
130
- ```
131
-
132
- Plan to delete the adapter once you've converted error-handling code site-by-site.
133
-
134
- ## Incremental migration: feature-by-feature
135
-
136
- If the codebase is too large for a single-pass migration, you can convert one feature at a time. The pattern:
137
-
138
- 1. **Pick a low-traffic feature first** (e.g. recovery, partner). It limits blast radius if something breaks.
139
- 2. **Convert that feature's call sites and approve hooks**.
140
- 3. **Run the app, smoke-test the feature**.
141
- 4. **Move on to the next feature**.
142
-
143
- The catch: SDK-level changes are global (e.g. chain-key terminology). You can't do `xChainId` on `XToken` for swap and `chainKey` for staking — both run on the same SDK. Plan to do all SDK-level migrations in one pass first (Phase 1 + 2 of [`checklist.md`](checklist.md)), then per-feature hook-call-site work in any order (Phase 3+).
144
-
145
- ## Incremental migration: keeping v1 wrappers temporarily
146
-
147
- If you have many call sites that share a custom wrapper hook (e.g. one your codebase named `useLegacySwap` calling v1 dapp-kit underneath), you can rewrite the wrapper's body to call v2 internally while keeping the wrapper's name and surface intact. Call sites stay unchanged.
148
-
149
- ```tsx
150
- // Custom wrapper that your codebase already has (with a project-specific name).
151
- // Rewrite its body to call v2 dapp-kit internally; preserve the surface so
152
- // existing call sites don't change yet.
153
-
154
- import { useSwap } from '@sodax/dapp-kit';
155
- import { useWalletProvider } from '@sodax/wallet-sdk-react';
156
- import type { CreateIntentParams } from '@sodax/sdk';
157
-
158
- // Function name starts with `use` because it calls React hooks (`useWalletProvider`,
159
- // `useSwap`). Inside a component, call it like any other hook.
160
- export function useLegacySwapAdapter(spokeProvider: unknown, params: CreateIntentParams) {
161
- const walletProvider = useWalletProvider(/* derive chainKey from spokeProvider */);
162
- const m = useSwap();
163
- return {
164
- swap: async () => {
165
- if (!walletProvider) throw new Error('wallet not connected');
166
- // Adapt v2 throw-on-fail back to v1 success-with-Result shape:
167
- try {
168
- const value = await m.mutateAsync({ params, walletProvider });
169
- return { ok: true, value };
170
- } catch (e) {
171
- return { ok: false, error: e };
172
- }
173
- },
174
- isLoading: m.isPending,
175
- error: m.error,
176
- };
177
- }
178
- ```
179
-
180
- Then convert call sites at your own pace. Delete the wrapper once you're done.
181
-
182
- ## Cross-references
183
-
184
- - [`README.md`](README.md) — overview + glossary.
185
- - [`checklist.md`](checklist.md) — top-down migration checklist.
186
- - [`ai-rules.md`](ai-rules.md) — DO / DO NOT for the agent doing the migration.
187
- - [`breaking-changes/`](breaking-changes/) — cross-cutting deltas in detail.
188
- - [`features/`](features/) — per-feature porting playbooks.
@@ -1,15 +0,0 @@
1
- # Migration reference — `@sodax/dapp-kit` v1 → v2
2
-
3
- Lookup tables for the v1 → v2 delta. Skim during migration to confirm specific renames or removals.
4
-
5
- | File | What's in it |
6
- |---|---|
7
- | [`deleted-hooks.md`](deleted-hooks.md) | v1 hooks that no longer exist in v2 (`useSpokeProvider`, `invalidateMmQueries`, legacy `useMigrate`-style API). |
8
- | [`renamed-hooks.md`](renamed-hooks.md) | Hooks whose name or signature changed (rare — most renames are field-level). |
9
- | [`error-shape-crosswalk.md`](error-shape-crosswalk.md) | v1 error class names → v2 `SodaxError<C>` mapping; how thrown errors look at the consumer level. |
10
-
11
- For SDK-level reference (deleted exports, renames, error code crosswalk), see [`../../../../sdk/ai-exported/migration/reference/`](../../../../sdk/ai-exported/migration/reference/) — the underlying SDK has its own reference tree.
12
-
13
- ## Pair
14
-
15
- This `migration/reference/` tree mirrors [`../../integration/reference/`](../../integration/reference/) (which documents v2 directly). When you need both "what does v2 do" and "what changed from v1" — open both.
@@ -1,110 +0,0 @@
1
- # Deleted hooks — v1 → v2
2
-
3
- Hooks that existed in v1 dapp-kit (or v1-style consumer-side utilities) and have no v2 equivalent.
4
-
5
- ## `useSpokeProvider`
6
-
7
- | | |
8
- |---|---|
9
- | v1 path | `import { useSpokeProvider } from '@sodax/dapp-kit'` |
10
- | v2 status | **DELETED** |
11
- | v2 alternative | Use `useWalletProvider({ xChainId: chainKey })` from `@sodax/wallet-sdk-react`, then pass `walletProvider` directly into `mutate(vars)` for mutations or as a query-hook param. |
12
-
13
- ```diff
14
- - import { useSpokeProvider } from '@sodax/dapp-kit';
15
- - const spokeProvider = useSpokeProvider({ chainId: BSC_MAINNET_CHAIN_ID });
16
- + import { useWalletProvider } from '@sodax/wallet-sdk-react';
17
- + import { ChainKeys } from '@sodax/sdk';
18
- + const walletProvider = useWalletProvider({ xChainId: ChainKeys.BSC_MAINNET });
19
- ```
20
-
21
- The chain key on the action params is what routes to the right per-chain spoke service inside the SDK; there's no "spoke provider" object for consumers to construct or hold.
22
-
23
- ## `useMigrate(spokeProvider)` (and any v1 single-migration-hook variant)
24
-
25
- | | |
26
- |---|---|
27
- | v1 path | A single `useMigrate(spokeProvider)` hook (often commented out by the time consumers tried to use it) |
28
- | v2 status | **DELETED** |
29
- | v2 alternative | Six per-action hooks: `useMigrateIcxToSoda`, `useRevertMigrateSodaToIcx`, `useMigratebnUSD`, `useMigrateBaln`, `useMigrationApprove`, `useMigrationAllowance`. |
30
-
31
- See [`../features/migration.md`](../features/migration.md) for the full split.
32
-
33
- ## Consumer-side `invalidate*Queries` utilities
34
-
35
- | | |
36
- |---|---|
37
- | v1 path | Often a `lib/invalidateMmQueries.ts` (or similar per-feature) file in the consumer codebase |
38
- | v2 status | **No longer needed — DELETE** |
39
- | v2 alternative | Hook-owned invalidations. Each mutation hook invalidates the relevant query keys in its own `onSuccess`. |
40
-
41
- ```diff
42
- - // lib/invalidateMmQueries.ts — DELETE this file
43
- - export function invalidateMmQueries(qc, srcChainKey, userAddress, token) {
44
- - qc.invalidateQueries({ queryKey: ['mm', 'userReservesData', srcChainKey, userAddress] });
45
- - qc.invalidateQueries({ queryKey: ['shared', 'xBalances', srcChainKey] });
46
- - /* ... */
47
- - }
48
-
49
- - // call site — DROP the manual invalidation
50
- - await supply({ params, spokeProvider });
51
- - invalidateMmQueries(queryClient, srcChainKey, userAddress, token);
52
- + // v2 — supply hook invalidates xBalances + userReservesData itself
53
- + await supply({ params, walletProvider });
54
- ```
55
-
56
- For cross-feature invalidations the hook can't know about (e.g. your custom analytics view), use `mutationOptions.onSuccess`:
57
-
58
- ```ts
59
- // @ai-snippets-skip
60
- const { mutateAsync: supply } = useSupply({
61
- mutationOptions: {
62
- onSuccess: async (data, vars) => {
63
- await queryClient.invalidateQueries({ queryKey: ['my-app', 'analytics'] });
64
- },
65
- },
66
- });
67
- ```
68
-
69
- ## Approve hook return shape (`{ approve, isLoading, error }`)
70
-
71
- | | |
72
- |---|---|
73
- | v1 shape | Per-feature: `useFooApprove(spokeProvider) → { approve, isLoading, error }` |
74
- | v2 status | **DELETED** (return shape, not the hooks themselves) |
75
- | v2 alternative | Standard `SafeUseMutationResult` — `mutateAsync` / `mutateAsyncSafe`, `isPending`, `error`. |
76
-
77
- ```diff
78
- - const { approve, isLoading } = useSwapApprove(spokeProvider);
79
- - await approve(params);
80
- + const { mutateAsync: approve, isPending } = useSwapApprove();
81
- + await approve({ params, walletProvider });
82
- ```
83
-
84
- `isLoading` → `isPending` (React Query 5 convention).
85
-
86
- ## v1 individual chain-id constants (SDK-leakage)
87
-
88
- Not strictly hooks, but they used to be importable from `@sodax/sdk` (or `@sodax/dapp-kit` re-export):
89
-
90
- | Constant | v1 value | v2 alternative |
91
- |---|---|---|
92
- | `BSC_MAINNET_CHAIN_ID` | `'0x38.bsc'` | `ChainKeys.BSC_MAINNET` |
93
- | `ARBITRUM_MAINNET_CHAIN_ID` | `'0xa4b1.arbitrum'` | `ChainKeys.ARBITRUM_MAINNET` |
94
- | `BASE_MAINNET_CHAIN_ID` | `'0x2105.base'` | `ChainKeys.BASE_MAINNET` |
95
- | `POLYGON_MAINNET_CHAIN_ID` | `'0x89.polygon'` | `ChainKeys.POLYGON_MAINNET` |
96
- | `ETHEREUM_MAINNET_CHAIN_ID` | `'0x1.ethereum'` | `ChainKeys.ETHEREUM_MAINNET` |
97
- | ... 11 more | ... | All under `ChainKeys.*` namespace |
98
-
99
- Codemod with sed:
100
-
101
- ```bash
102
- find src -type f \( -name '*.ts' -o -name '*.tsx' \) | xargs sed -i '' -E 's/\b([A-Z_]+)_MAINNET_CHAIN_ID\b/ChainKeys.\1_MAINNET/g'
103
- ```
104
-
105
- ## Cross-references
106
-
107
- - [`renamed-hooks.md`](renamed-hooks.md) — hooks whose name/signature changed (different from deletions).
108
- - [`error-shape-crosswalk.md`](error-shape-crosswalk.md) — error class consolidation.
109
- - [`../breaking-changes/hook-signatures.md`](../breaking-changes/hook-signatures.md) — broader hook-shape changes.
110
- - [`../breaking-changes/sdk-leakage.md`](../breaking-changes/sdk-leakage.md) — SDK-level migrations leaking through.