@sodax/dapp-kit 1.5.7-beta → 2.0.0-rc.2
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 +300 -422
- package/ai-exported/AGENTS.md +134 -0
- package/ai-exported/integration/README.md +49 -0
- package/ai-exported/integration/ai-rules.md +79 -0
- package/ai-exported/integration/architecture.md +274 -0
- package/ai-exported/integration/features/README.md +29 -0
- package/ai-exported/integration/features/auxiliary-services.md +169 -0
- package/ai-exported/integration/features/bitcoin.md +87 -0
- package/ai-exported/integration/features/bridge.md +91 -0
- package/ai-exported/integration/features/dex.md +152 -0
- package/ai-exported/integration/features/migration.md +118 -0
- package/ai-exported/integration/features/money-market.md +116 -0
- package/ai-exported/integration/features/staking.md +123 -0
- package/ai-exported/integration/features/swap.md +101 -0
- package/ai-exported/integration/quickstart.md +187 -0
- package/ai-exported/integration/recipes/README.md +136 -0
- package/ai-exported/integration/recipes/backend-queries.md +157 -0
- package/ai-exported/integration/recipes/bitcoin.md +193 -0
- package/ai-exported/integration/recipes/bridge.md +174 -0
- package/ai-exported/integration/recipes/dex.md +204 -0
- package/ai-exported/integration/recipes/invalidations.md +115 -0
- package/ai-exported/integration/recipes/migration.md +212 -0
- package/ai-exported/integration/recipes/money-market.md +206 -0
- package/ai-exported/integration/recipes/mutation-error-handling.md +118 -0
- package/ai-exported/integration/recipes/observability.md +93 -0
- package/ai-exported/integration/recipes/setup.md +144 -0
- package/ai-exported/integration/recipes/staking.md +202 -0
- package/ai-exported/integration/recipes/swap.md +272 -0
- package/ai-exported/integration/recipes/wallet-connectivity.md +101 -0
- package/ai-exported/integration/reference/README.md +12 -0
- package/ai-exported/integration/reference/glossary.md +188 -0
- package/ai-exported/integration/reference/hooks-index.md +190 -0
- package/ai-exported/integration/reference/public-api.md +110 -0
- package/ai-exported/integration/reference/querykey-conventions.md +179 -0
- package/ai-exported/migration/README.md +60 -0
- package/ai-exported/migration/ai-rules.md +81 -0
- package/ai-exported/migration/breaking-changes/hook-signatures.md +233 -0
- package/ai-exported/migration/breaking-changes/querykey-conventions.md +108 -0
- package/ai-exported/migration/breaking-changes/result-handling.md +211 -0
- package/ai-exported/migration/breaking-changes/sdk-leakage.md +165 -0
- package/ai-exported/migration/checklist.md +89 -0
- package/ai-exported/migration/features/README.md +34 -0
- package/ai-exported/migration/features/auxiliary-services.md +114 -0
- package/ai-exported/migration/features/bitcoin.md +88 -0
- package/ai-exported/migration/features/bridge.md +123 -0
- package/ai-exported/migration/features/dex.md +101 -0
- package/ai-exported/migration/features/migration.md +120 -0
- package/ai-exported/migration/features/money-market.md +97 -0
- package/ai-exported/migration/features/staking.md +109 -0
- package/ai-exported/migration/features/swap.md +118 -0
- package/ai-exported/migration/recipes.md +188 -0
- package/ai-exported/migration/reference/README.md +15 -0
- package/ai-exported/migration/reference/deleted-hooks.md +110 -0
- package/ai-exported/migration/reference/error-shape-crosswalk.md +144 -0
- package/ai-exported/migration/reference/renamed-hooks.md +66 -0
- package/dist/index.cjs +2642 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.cts +1550 -0
- package/dist/index.d.ts +1020 -2051
- package/dist/index.mjs +1581 -1531
- package/dist/index.mjs.map +1 -1
- package/package.json +21 -11
- package/src/contexts/index.ts +0 -3
- package/src/hooks/_mutationContract.test.ts +99 -0
- package/src/hooks/backend/README.md +2 -2
- package/src/hooks/backend/index.ts +13 -13
- package/src/hooks/backend/unwrapResult.ts +1 -0
- package/src/hooks/backend/useBackendAllMoneyMarketAssets.ts +13 -45
- package/src/hooks/backend/useBackendAllMoneyMarketBorrowers.ts +29 -59
- package/src/hooks/backend/useBackendIntentByHash.ts +21 -47
- package/src/hooks/backend/useBackendIntentByTxHash.ts +23 -50
- package/src/hooks/backend/useBackendMoneyMarketAsset.ts +21 -54
- package/src/hooks/backend/useBackendMoneyMarketAssetBorrowers.ts +30 -57
- package/src/hooks/backend/useBackendMoneyMarketAssetSuppliers.ts +31 -58
- package/src/hooks/backend/useBackendMoneyMarketPosition.ts +22 -38
- package/src/hooks/backend/useBackendOrderbook.ts +27 -49
- package/src/hooks/backend/useBackendSubmitSwapTx.ts +30 -36
- package/src/hooks/backend/useBackendSubmitSwapTxStatus.ts +38 -58
- package/src/hooks/backend/useBackendUserIntents.ts +25 -63
- package/src/hooks/bitcoin/index.ts +9 -8
- package/src/hooks/bitcoin/useBitcoinBalance.ts +20 -5
- package/src/hooks/bitcoin/useExpiredUtxos.ts +26 -16
- package/src/hooks/bitcoin/useFundTradingWallet.ts +33 -30
- package/src/hooks/bitcoin/useRadfiAuth.ts +43 -40
- package/src/hooks/bitcoin/useRadfiSession.ts +53 -59
- package/src/hooks/bitcoin/useRadfiWithdraw.ts +35 -53
- package/src/hooks/bitcoin/useRenewUtxos.ts +30 -50
- package/src/hooks/bitcoin/useTradingWallet.ts +1 -1
- package/src/hooks/bitcoin/useTradingWalletBalance.ts +25 -14
- package/src/hooks/bridge/index.ts +5 -5
- package/src/hooks/bridge/useBridge.ts +29 -55
- package/src/hooks/bridge/useBridgeAllowance.ts +38 -38
- package/src/hooks/bridge/useBridgeApprove.ts +32 -57
- package/src/hooks/bridge/useGetBridgeableAmount.ts +23 -37
- package/src/hooks/bridge/useGetBridgeableTokens.ts +27 -50
- package/src/hooks/dex/index.ts +16 -16
- package/src/hooks/dex/useClaimRewards.ts +35 -54
- package/src/hooks/dex/useCreateDecreaseLiquidityParams.ts +7 -20
- package/src/hooks/dex/useCreateDepositParams.ts +7 -21
- package/src/hooks/dex/useCreateSupplyLiquidityParams.ts +13 -28
- package/src/hooks/dex/useCreateWithdrawParams.ts +7 -20
- package/src/hooks/dex/useDecreaseLiquidity.ts +40 -66
- package/src/hooks/dex/useDexAllowance.ts +29 -75
- package/src/hooks/dex/useDexApprove.ts +32 -43
- package/src/hooks/dex/useDexDeposit.ts +42 -49
- package/src/hooks/dex/useDexWithdraw.ts +32 -43
- package/src/hooks/dex/useLiquidityAmounts.ts +13 -82
- package/src/hooks/dex/usePoolBalances.ts +50 -72
- package/src/hooks/dex/usePoolData.ts +17 -43
- package/src/hooks/dex/usePools.ts +11 -38
- package/src/hooks/dex/usePositionInfo.ts +27 -62
- package/src/hooks/dex/useSupplyLiquidity.ts +80 -75
- package/src/hooks/index.ts +12 -10
- package/src/hooks/migrate/index.ts +13 -4
- package/src/hooks/migrate/useMigrateBaln.ts +42 -0
- package/src/hooks/migrate/useMigrateIcxToSoda.ts +44 -0
- package/src/hooks/migrate/useMigratebnUSD.ts +47 -0
- package/src/hooks/migrate/useMigrationAllowance.ts +76 -0
- package/src/hooks/migrate/useMigrationApprove.ts +66 -0
- package/src/hooks/migrate/useRevertMigrateSodaToIcx.ts +39 -0
- package/src/hooks/mm/index.ts +14 -12
- package/src/hooks/mm/useAToken.ts +25 -41
- package/src/hooks/mm/useATokensBalances.ts +29 -60
- package/src/hooks/mm/useBorrow.ts +38 -56
- package/src/hooks/mm/useMMAllowance.ts +37 -73
- package/src/hooks/mm/useMMApprove.ts +36 -43
- package/src/hooks/mm/useRepay.ts +33 -53
- package/src/hooks/mm/useReservesData.ts +12 -38
- package/src/hooks/mm/useReservesHumanized.ts +12 -31
- package/src/hooks/mm/useReservesList.ts +11 -31
- package/src/hooks/mm/useReservesUsdFormat.ts +15 -35
- package/src/hooks/mm/useSupply.ts +45 -51
- package/src/hooks/mm/useUserFormattedSummary.ts +32 -84
- package/src/hooks/mm/useUserReservesData.ts +27 -77
- package/src/hooks/mm/useWithdraw.ts +38 -54
- package/src/hooks/partner/index.ts +6 -0
- package/src/hooks/partner/useApproveToken.ts +42 -0
- package/src/hooks/partner/useFeeClaimSwap.ts +38 -0
- package/src/hooks/partner/useFetchAssetsBalances.ts +37 -0
- package/src/hooks/partner/useGetAutoSwapPreferences.ts +37 -0
- package/src/hooks/partner/useIsTokenApproved.ts +39 -0
- package/src/hooks/partner/useSetSwapPreference.ts +50 -0
- package/src/hooks/provider/index.ts +1 -2
- package/src/hooks/provider/useHubProvider.ts +1 -1
- package/src/hooks/recovery/index.ts +2 -0
- package/src/hooks/recovery/useHubAssetBalances.ts +43 -0
- package/src/hooks/recovery/useWithdrawHubAsset.ts +48 -0
- package/src/hooks/shared/index.ts +10 -6
- package/src/hooks/shared/types.ts +77 -0
- package/src/hooks/shared/unwrapResult.ts +19 -0
- package/src/hooks/shared/useDeriveUserWalletAddress.ts +22 -40
- package/src/hooks/shared/useEstimateGas.ts +18 -15
- package/src/hooks/shared/useGetUserHubWalletAddress.ts +25 -26
- package/src/hooks/shared/useRequestTrustline.ts +28 -61
- package/src/hooks/shared/useSafeMutation.test.ts +43 -0
- package/src/hooks/shared/useSafeMutation.ts +68 -0
- package/src/hooks/shared/useSodaxContext.ts +1 -1
- package/src/hooks/shared/useStellarTrustlineCheck.ts +30 -64
- package/src/hooks/shared/useXBalances.test.ts +113 -0
- package/src/hooks/shared/useXBalances.ts +61 -0
- package/src/hooks/staking/index.ts +18 -18
- package/src/hooks/staking/useCancelUnstake.ts +30 -41
- package/src/hooks/staking/useClaim.ts +27 -36
- package/src/hooks/staking/useConvertedAssets.ts +24 -34
- package/src/hooks/staking/useInstantUnstake.ts +33 -40
- package/src/hooks/staking/useInstantUnstakeAllowance.ts +37 -45
- package/src/hooks/staking/useInstantUnstakeApprove.ts +42 -42
- package/src/hooks/staking/useInstantUnstakeRatio.ts +24 -41
- package/src/hooks/staking/useStake.ts +32 -37
- package/src/hooks/staking/useStakeAllowance.ts +30 -43
- package/src/hooks/staking/useStakeApprove.ts +40 -40
- package/src/hooks/staking/useStakeRatio.ts +24 -40
- package/src/hooks/staking/useStakingConfig.ts +14 -27
- package/src/hooks/staking/useStakingInfo.ts +30 -38
- package/src/hooks/staking/useUnstake.ts +29 -43
- package/src/hooks/staking/useUnstakeAllowance.ts +37 -44
- package/src/hooks/staking/useUnstakeApprove.ts +40 -43
- package/src/hooks/staking/useUnstakingInfo.ts +29 -41
- package/src/hooks/staking/useUnstakingInfoWithPenalty.ts +31 -47
- package/src/hooks/swap/index.ts +8 -8
- package/src/hooks/swap/useCancelLimitOrder.ts +24 -41
- package/src/hooks/swap/useCancelSwap.ts +24 -33
- package/src/hooks/swap/useCreateLimitOrder.ts +29 -62
- package/src/hooks/swap/useQuote.ts +17 -43
- package/src/hooks/swap/useStatus.ts +22 -29
- package/src/hooks/swap/useSwap.ts +31 -49
- package/src/hooks/swap/useSwapAllowance.ts +38 -35
- package/src/hooks/swap/useSwapApprove.ts +48 -57
- package/src/index.ts +5 -3
- package/src/providers/SodaxProvider.tsx +17 -11
- package/src/providers/createSodaxQueryClient.ts +96 -0
- package/src/providers/index.ts +2 -1
- package/src/utils/dex-utils.ts +27 -5
- package/src/utils/index.ts +1 -1
- package/dist/index.d.mts +0 -2581
- package/dist/index.js +0 -2574
- package/dist/index.js.map +0 -1
- package/src/hooks/migrate/types.ts +0 -15
- package/src/hooks/migrate/useMigrate.tsx +0 -110
- package/src/hooks/migrate/useMigrationAllowance.tsx +0 -79
- package/src/hooks/migrate/useMigrationApprove.tsx +0 -129
- package/src/hooks/provider/useSpokeProvider.ts +0 -172
|
@@ -0,0 +1,169 @@
|
|
|
1
|
+
# Auxiliary services — `@sodax/dapp-kit`
|
|
2
|
+
|
|
3
|
+
Smaller surfaces grouped together: partner fee claiming, recovery, backend queries (read-only data hooks), and shared utilities.
|
|
4
|
+
|
|
5
|
+
Pair: [`../../migration/features/auxiliary-services.md`](../../migration/features/auxiliary-services.md).
|
|
6
|
+
|
|
7
|
+
## Partner
|
|
8
|
+
|
|
9
|
+
Partner fee claiming and auto-swap preferences.
|
|
10
|
+
|
|
11
|
+
```ts
|
|
12
|
+
// @ai-snippets-skip
|
|
13
|
+
useFetchAssetsBalances({ params, queryOptions }); // Partner asset balances
|
|
14
|
+
useGetAutoSwapPreferences({ params, queryOptions });
|
|
15
|
+
useIsTokenApproved({ params: { payload: FeeTokenApproveParams }, queryOptions });
|
|
16
|
+
useApproveToken({ mutationOptions });
|
|
17
|
+
useSetSwapPreference({ mutationOptions });
|
|
18
|
+
useFeeClaimSwap({ mutationOptions }); // Claim partner fees via swap
|
|
19
|
+
```
|
|
20
|
+
|
|
21
|
+
`useFeeClaimSwap` returns `SafeUseMutationResult<IntentAutoSwapResult, Error, UseFeeClaimSwapVars>` — the success value is `IntentAutoSwapResult` (NOT `SwapResponse`). TVars are `Omit<PartnerFeeClaimSwapAction<HubChainKey, false>, 'raw'>`.
|
|
22
|
+
|
|
23
|
+
## Recovery
|
|
24
|
+
|
|
25
|
+
Withdraw stuck hub-wallet assets back to a spoke chain.
|
|
26
|
+
|
|
27
|
+
```ts
|
|
28
|
+
// @ai-snippets-skip
|
|
29
|
+
useHubAssetBalances({ params, queryOptions }); // List assets stuck on hub
|
|
30
|
+
useWithdrawHubAsset({ mutationOptions });
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
## Backend queries (read-only data)
|
|
34
|
+
|
|
35
|
+
No wallet connection required.
|
|
36
|
+
|
|
37
|
+
### Intent tracking
|
|
38
|
+
|
|
39
|
+
```ts
|
|
40
|
+
// @ai-snippets-skip
|
|
41
|
+
useBackendIntentByTxHash({ params, queryOptions }); // Polls 1s once a txHash is supplied
|
|
42
|
+
useBackendIntentByHash({ params, queryOptions });
|
|
43
|
+
useBackendUserIntents({ params, queryOptions }); // Date-filtered user history; data is { items: IntentResponse[], total, offset, limit }
|
|
44
|
+
```
|
|
45
|
+
|
|
46
|
+
### Orderbook
|
|
47
|
+
|
|
48
|
+
```ts
|
|
49
|
+
// @ai-snippets-skip
|
|
50
|
+
// `pagination` MUST be nested under `params` — top-level pagination is invalid.
|
|
51
|
+
useBackendOrderbook({ params: { pagination: { offset, limit } }, queryOptions }); // staleTime 30s; no auto-refresh
|
|
52
|
+
```
|
|
53
|
+
|
|
54
|
+
### Money market data
|
|
55
|
+
|
|
56
|
+
```ts
|
|
57
|
+
// @ai-snippets-skip
|
|
58
|
+
useBackendMoneyMarketPosition({ params, queryOptions });
|
|
59
|
+
useBackendMoneyMarketAsset({ params, queryOptions });
|
|
60
|
+
useBackendAllMoneyMarketAssets({ queryOptions });
|
|
61
|
+
useBackendMoneyMarketAssetSuppliers({ params, queryOptions });
|
|
62
|
+
useBackendMoneyMarketAssetBorrowers({ params, queryOptions });
|
|
63
|
+
// Pagination required — without it the query is disabled.
|
|
64
|
+
useBackendAllMoneyMarketBorrowers({ params: { pagination: { offset, limit } }, queryOptions });
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
### Swap submission
|
|
68
|
+
|
|
69
|
+
```ts
|
|
70
|
+
// @ai-snippets-skip
|
|
71
|
+
useBackendSubmitSwapTx({ mutationOptions }); // Mutation
|
|
72
|
+
useBackendSubmitSwapTxStatus({ params, queryOptions }); // Query — check submitted status
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
`useBackendSubmitSwapTx` is a mutation hook — per-call config (e.g. backend base URL) flows through `mutate(vars)`:
|
|
76
|
+
|
|
77
|
+
```ts
|
|
78
|
+
// @ai-snippets-skip
|
|
79
|
+
const { mutateAsync: submitSwapTx } = useBackendSubmitSwapTx();
|
|
80
|
+
await submitSwapTx({ request: swapPayload, apiConfig: { baseURL: 'https://...' } });
|
|
81
|
+
```
|
|
82
|
+
|
|
83
|
+
## Shared utilities
|
|
84
|
+
|
|
85
|
+
Cross-cutting hooks used by other features.
|
|
86
|
+
|
|
87
|
+
```ts
|
|
88
|
+
// @ai-snippets-skip
|
|
89
|
+
useSodaxContext(); // Access the Sodax SDK instance
|
|
90
|
+
useHubProvider(); // Hub chain (Sonic) provider
|
|
91
|
+
useXBalances({ params, queryOptions }); // Cross-chain token balances
|
|
92
|
+
useDeriveUserWalletAddress({ params, queryOptions }); // Hub wallet address (CREATE3)
|
|
93
|
+
useGetUserHubWalletAddress({ params, queryOptions }); // Hub wallet via wallet router
|
|
94
|
+
useEstimateGas({ mutationOptions }); // Gas estimation for raw tx
|
|
95
|
+
useStellarTrustlineCheck({ params, queryOptions });
|
|
96
|
+
useRequestTrustline({ mutationOptions });
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
### `useXBalances` shape
|
|
100
|
+
|
|
101
|
+
```ts
|
|
102
|
+
// @ai-snippets-skip
|
|
103
|
+
type UseXBalancesParams = ReadHookParams<Record<string, bigint>, {
|
|
104
|
+
xService: IXServiceBase | undefined; // From @sodax/wallet-sdk-react's useXService
|
|
105
|
+
xChainId: SpokeChainKey | undefined;
|
|
106
|
+
xTokens: readonly XToken[]; // Tokens to fetch balances for
|
|
107
|
+
address: string | undefined;
|
|
108
|
+
}>;
|
|
109
|
+
```
|
|
110
|
+
|
|
111
|
+
Note: the **request-side** field is `xChainId` (kept for the cross-chain abstraction it overlays). This is distinct from the v2-renamed token-side `chainKey` — don't conflate them.
|
|
112
|
+
|
|
113
|
+
Consumer must supply `xService` from `@sodax/wallet-sdk-react`:
|
|
114
|
+
|
|
115
|
+
```tsx
|
|
116
|
+
// @ai-snippets-skip
|
|
117
|
+
import { useXService, getXChainType } from '@sodax/wallet-sdk-react';
|
|
118
|
+
const xService = useXService({ xChainType: getXChainType(xChainId) });
|
|
119
|
+
const { data: balances } = useXBalances({ params: { xService, xChainId, xTokens, address } });
|
|
120
|
+
```
|
|
121
|
+
|
|
122
|
+
### Stellar trustlines
|
|
123
|
+
|
|
124
|
+
Stellar accounts that have never held an asset have no trustline — receiving will fail. Pre-flight with `useStellarTrustlineCheck`; fix with `useRequestTrustline`:
|
|
125
|
+
|
|
126
|
+
```ts
|
|
127
|
+
// @ai-snippets-skip — illustrative only; real types pulled into agents below.
|
|
128
|
+
// useStellarTrustlineCheck takes { token, amount, chainId, walletProvider } under params.
|
|
129
|
+
// `chainId` here is a `SpokeChainKey` (typed loosely so consumers can pass any chain key —
|
|
130
|
+
// the hook returns `true` for non-Stellar chains, making it safe to gate on conditionally).
|
|
131
|
+
const { data: hasTrustline } = useStellarTrustlineCheck({
|
|
132
|
+
params: { token, amount, chainId: ChainKeys.STELLAR_MAINNET, walletProvider },
|
|
133
|
+
});
|
|
134
|
+
|
|
135
|
+
// useRequestTrustline is NOT a canonical mutation hook — it takes a single positional
|
|
136
|
+
// `token` arg and returns { requestTrustline, isLoading, isRequested, error, data }.
|
|
137
|
+
// The `requestTrustline` callback signature is:
|
|
138
|
+
// ({ token, amount, srcChainKey, walletProvider }) => Promise<string>
|
|
139
|
+
// NOTE: fields are `token` / `amount` / `srcChainKey` / `walletProvider` — NOT
|
|
140
|
+
// `account` / `asset`. Pass a StellarChainKey for srcChainKey.
|
|
141
|
+
const { requestTrustline, isLoading } = useRequestTrustline(token);
|
|
142
|
+
if (hasTrustline === false) {
|
|
143
|
+
await requestTrustline({ token, amount, srcChainKey: ChainKeys.STELLAR_MAINNET, walletProvider });
|
|
144
|
+
}
|
|
145
|
+
```
|
|
146
|
+
|
|
147
|
+
## Default polling intervals
|
|
148
|
+
|
|
149
|
+
| Hook | Polling | Notes |
|
|
150
|
+
|---|---|---|
|
|
151
|
+
| `useBackendIntentByTxHash` | 1s | once a `txHash` is supplied (refetch is unconditional, not "while pending") |
|
|
152
|
+
| `useBackendSubmitSwapTxStatus` | varies | poll stops on `executed` / `failed` |
|
|
153
|
+
| `useBackendOrderbook` | none | `staleTime: 30s` — fresh-window, no background refetch |
|
|
154
|
+
| `useExpiredUtxos` (bitcoin) | 60s | refetchInterval |
|
|
155
|
+
| `useQuote` (swap) | 3s | refetchInterval |
|
|
156
|
+
| `useStatus` (swap) | 3s | refetchInterval |
|
|
157
|
+
| `useSwapAllowance` (swap) | 2s | refetchInterval |
|
|
158
|
+
| `useMMAllowance` (mm) | 5s | refetchInterval; `enabled: false` for borrow/withdraw actions |
|
|
159
|
+
| Reserves data (mm) | 5s | `useReservesData` / `useReservesHumanized` / user position hooks |
|
|
160
|
+
| Most others | None | |
|
|
161
|
+
|
|
162
|
+
All overridable via `queryOptions.refetchInterval`.
|
|
163
|
+
|
|
164
|
+
## Cross-references
|
|
165
|
+
|
|
166
|
+
- [`../recipes/backend-queries.md`](../recipes/backend-queries.md) — worked examples for intent tracking, orderbook, MM data.
|
|
167
|
+
- [`../recipes/wallet-connectivity.md`](../recipes/wallet-connectivity.md) — `useXBalances` worked example.
|
|
168
|
+
- [`../../migration/features/auxiliary-services.md`](../../migration/features/auxiliary-services.md) — v1 → v2 porting.
|
|
169
|
+
- [`../../../../sdk/ai-exported/integration/features/auxiliary-services.md`](../../../../sdk/ai-exported/integration/features/auxiliary-services.md) — underlying SDK auxiliary surfaces (partner, recovery, backendApi).
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
# Bitcoin (Radfi) — `@sodax/dapp-kit`
|
|
2
|
+
|
|
3
|
+
Bitcoin trading via the Radfi protocol — authenticate, fund a trading wallet, withdraw, manage UTXOs. **Dapp-kit-unique surface** (no SDK equivalent — these flows are React-shaped).
|
|
4
|
+
|
|
5
|
+
Pair: [`../../migration/features/bitcoin.md`](../../migration/features/bitcoin.md).
|
|
6
|
+
|
|
7
|
+
## Hook surface
|
|
8
|
+
|
|
9
|
+
```ts
|
|
10
|
+
// @ai-snippets-skip
|
|
11
|
+
// Session lifecycle
|
|
12
|
+
useRadfiAuth({ mutationOptions }); // Authenticate via BIP322 signing
|
|
13
|
+
useRadfiSession(walletProvider); // Manage full lifecycle (login, refresh, auto-refresh)
|
|
14
|
+
useTradingWallet(walletAddress); // Synchronous: read persisted session
|
|
15
|
+
|
|
16
|
+
// Balances
|
|
17
|
+
useBitcoinBalance({ params: { address, rpcUrl? }, queryOptions }); // Personal wallet (default mempool.space)
|
|
18
|
+
useTradingWalletBalance({ params: { walletProvider, tradingAddress }, queryOptions }); // Radfi API
|
|
19
|
+
|
|
20
|
+
// Operations
|
|
21
|
+
useFundTradingWallet({ mutationOptions });
|
|
22
|
+
useRadfiWithdraw({ mutationOptions });
|
|
23
|
+
useExpiredUtxos({ params: { walletProvider, tradingAddress }, queryOptions }); // Polls 60s
|
|
24
|
+
useRenewUtxos({ mutationOptions });
|
|
25
|
+
```
|
|
26
|
+
|
|
27
|
+
## Session flow
|
|
28
|
+
|
|
29
|
+
Radfi requires authentication before trading operations. `useRadfiSession` handles the full lifecycle:
|
|
30
|
+
|
|
31
|
+
```ts
|
|
32
|
+
// @ai-snippets-skip
|
|
33
|
+
const { walletAddress, isAuthed, tradingAddress, login, isLoginPending } = useRadfiSession(walletProvider);
|
|
34
|
+
```
|
|
35
|
+
|
|
36
|
+
Lifecycle behavior:
|
|
37
|
+
- On mount: refreshes token to validate existing session
|
|
38
|
+
- Every 5 min: auto-refreshes access token
|
|
39
|
+
- If refresh fails: clears session, sets `isAuthed = false`
|
|
40
|
+
- Session persisted in localStorage (keyed by wallet address)
|
|
41
|
+
|
|
42
|
+
## Mutation TVars
|
|
43
|
+
|
|
44
|
+
```ts
|
|
45
|
+
// @ai-snippets-skip
|
|
46
|
+
// useFundTradingWallet
|
|
47
|
+
type FundTradingWalletVars = { amount: bigint; walletProvider: IBitcoinWalletProvider };
|
|
48
|
+
|
|
49
|
+
// useRadfiWithdraw
|
|
50
|
+
type RadfiWithdrawVars = {
|
|
51
|
+
amount: string;
|
|
52
|
+
tokenId: string; // e.g. '0:0'
|
|
53
|
+
withdrawTo: string; // user's personal BTC address
|
|
54
|
+
walletProvider: IBitcoinWalletProvider;
|
|
55
|
+
};
|
|
56
|
+
|
|
57
|
+
// useRenewUtxos
|
|
58
|
+
type RenewUtxosVars = { txIdVouts: string[]; walletProvider: IBitcoinWalletProvider };
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
## Return shapes
|
|
62
|
+
|
|
63
|
+
| Hook | Returns |
|
|
64
|
+
|---|---|
|
|
65
|
+
| `useRadfiAuth` | `SafeUseMutationResult<RadfiAuthResult, Error, UseRadfiAuthVars>` where `RadfiAuthResult = { accessToken, refreshToken, tradingAddress }` (3 fields, NOT `RadfiSession` — the hook persists `publicKey` to localStorage internally but doesn't return it) |
|
|
66
|
+
| `useFundTradingWallet` | `SafeUseMutationResult<TxId, Error, ...>` |
|
|
67
|
+
| `useRadfiWithdraw` | `SafeUseMutationResult<{ txId, fee }, Error, ...>` |
|
|
68
|
+
| `useRenewUtxos` | `SafeUseMutationResult<TxId, Error, ...>` |
|
|
69
|
+
| `useRadfiSession` | `{ walletAddress, isAuthed, tradingAddress, login, isLoginPending }` (utility, not Query/Mutation) |
|
|
70
|
+
| `useTradingWallet` | `{ tradingAddress: string \| undefined }` (synchronous from localStorage) |
|
|
71
|
+
| `useBitcoinBalance` | `UseQueryResult<bigint, Error>` (BTC balance in sats; default Esplora is mempool.space, override via `rpcUrl`) |
|
|
72
|
+
| `useTradingWalletBalance` | `UseQueryResult<RadfiWalletBalance, Error>` where `RadfiWalletBalance = { btcSatoshi: bigint; pendingSatoshi: bigint; externalPendingSatoshi: bigint; totalUtxos: number }` |
|
|
73
|
+
| `useExpiredUtxos` | `UseQueryResult<RadfiUtxo[], Error>` where `RadfiUtxo = { _id, txid, vout, txidVout, satoshi, amount, address, isSpent, status, source, runes? }` |
|
|
74
|
+
|
|
75
|
+
## Gotchas
|
|
76
|
+
|
|
77
|
+
1. **Authentication required before any trading operation.** `useRadfiSession` manages this automatically — gate buttons on `isAuthed`.
|
|
78
|
+
2. **Trading wallet is created during first authentication** — not a separate step.
|
|
79
|
+
3. **`useTradingWallet(walletAddress)` is synchronous** (no network call). It reads persisted Radfi session from localStorage. Use it when you don't have a `walletProvider` available yet but need the trading address.
|
|
80
|
+
4. **PSBT signing flow for withdrawals.** Radfi server builds an unsigned PSBT, the user signs locally via the wallet provider, then submits back for co-signing and broadcast. The dapp-kit hook orchestrates this — consumers don't see PSBTs directly.
|
|
81
|
+
5. **Session tokens are for API rate-limiting, not asset access.** Stored in localStorage keyed by wallet address. Compromise of localStorage data doesn't affect funds.
|
|
82
|
+
6. **`useExpiredUtxos` polls every 60s** — set `queryOptions.refetchInterval: false` to disable while UI is hidden.
|
|
83
|
+
|
|
84
|
+
## Cross-references
|
|
85
|
+
|
|
86
|
+
- [`../recipes/bitcoin.md`](../recipes/bitcoin.md) — full worked examples (session, fund, withdraw, UTXO management).
|
|
87
|
+
- [`../../migration/features/bitcoin.md`](../../migration/features/bitcoin.md) — v1 → v2 porting (mostly hook signature shape changes; flow stays the same).
|
|
@@ -0,0 +1,91 @@
|
|
|
1
|
+
# Bridge — `@sodax/dapp-kit`
|
|
2
|
+
|
|
3
|
+
Cross-chain token transfers via the hub-and-spoke vault architecture.
|
|
4
|
+
|
|
5
|
+
Pair: [`../../migration/features/bridge.md`](../../migration/features/bridge.md).
|
|
6
|
+
|
|
7
|
+
## Hook surface
|
|
8
|
+
|
|
9
|
+
```ts
|
|
10
|
+
// @ai-snippets-skip
|
|
11
|
+
// Mutation
|
|
12
|
+
useBridge({ mutationOptions });
|
|
13
|
+
useBridgeApprove({ mutationOptions });
|
|
14
|
+
|
|
15
|
+
// Queries
|
|
16
|
+
// useBridgeAllowance nests payload + walletProvider under params (NOT at top level)
|
|
17
|
+
useBridgeAllowance({ params: { payload: CreateBridgeIntentParams<K>, walletProvider }, queryOptions });
|
|
18
|
+
useGetBridgeableAmount({ params: { from: XToken, to: XToken }, queryOptions });
|
|
19
|
+
useGetBridgeableTokens({ params: { from: SpokeChainKey, to: SpokeChainKey, token: string }, queryOptions });
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
## Mutation params
|
|
23
|
+
|
|
24
|
+
```ts
|
|
25
|
+
// @ai-snippets-skip
|
|
26
|
+
type CreateBridgeIntentParams<K extends SpokeChainKey = SpokeChainKey> = {
|
|
27
|
+
srcChainKey: K;
|
|
28
|
+
srcAddress: string;
|
|
29
|
+
srcToken: string;
|
|
30
|
+
amount: bigint;
|
|
31
|
+
dstChainKey: SpokeChainKey;
|
|
32
|
+
dstToken: string;
|
|
33
|
+
recipient: string; // non-encoded recipient address on the destination chain
|
|
34
|
+
};
|
|
35
|
+
|
|
36
|
+
const { mutateAsyncSafe: bridge } = useBridge();
|
|
37
|
+
const result = await bridge({ params, walletProvider });
|
|
38
|
+
if (!result.ok) return;
|
|
39
|
+
const { srcChainTxHash, dstChainTxHash } = result.value; // TxHashPair
|
|
40
|
+
```
|
|
41
|
+
|
|
42
|
+
## Query params
|
|
43
|
+
|
|
44
|
+
```ts
|
|
45
|
+
// @ai-snippets-skip
|
|
46
|
+
// useBridgeAllowance — payload + walletProvider nested under params
|
|
47
|
+
type UseBridgeAllowanceParams<K extends SpokeChainKey> = ReadHookParams<
|
|
48
|
+
boolean,
|
|
49
|
+
{
|
|
50
|
+
payload: CreateBridgeIntentParams<K> | undefined;
|
|
51
|
+
walletProvider: GetWalletProviderType<K> | undefined;
|
|
52
|
+
}
|
|
53
|
+
>;
|
|
54
|
+
|
|
55
|
+
// useGetBridgeableAmount — flat: pair of XToken objects
|
|
56
|
+
type UseGetBridgeableAmountParams = ReadHookParams<BridgeLimit, {
|
|
57
|
+
from: XToken | undefined;
|
|
58
|
+
to: XToken | undefined;
|
|
59
|
+
}>;
|
|
60
|
+
// BridgeLimit = { amount: bigint; decimals: number; type: 'DEPOSIT_LIMIT' | 'WITHDRAWAL_LIMIT' }
|
|
61
|
+
|
|
62
|
+
// useGetBridgeableTokens — flat: (from, to, token)
|
|
63
|
+
type UseGetBridgeableTokensParams = ReadHookParams<XToken[], {
|
|
64
|
+
from: SpokeChainKey | undefined;
|
|
65
|
+
to: SpokeChainKey | undefined;
|
|
66
|
+
token: string | undefined;
|
|
67
|
+
}>;
|
|
68
|
+
```
|
|
69
|
+
|
|
70
|
+
## Return shapes
|
|
71
|
+
|
|
72
|
+
| Hook | Returns |
|
|
73
|
+
|---|---|
|
|
74
|
+
| `useBridge` | `SafeUseMutationResult<TxHashPair, Error, ...>` (`{ srcChainTxHash, dstChainTxHash }`) |
|
|
75
|
+
| `useBridgeApprove` | `SafeUseMutationResult<TxReturnType<K, false>, Error, UseBridgeApproveVars<K>>` — chain-keyed receipt union (EVM/Stellar/Sui differ) |
|
|
76
|
+
| `useBridgeAllowance` | `UseQueryResult<boolean, Error>` — already unwrapped; on SDK `!ok` the queryFn returns `false` (does NOT throw), so `isError` stays clean |
|
|
77
|
+
| `useGetBridgeableAmount` | `UseQueryResult<BridgeLimit, Error>` (richer than v1's bare `bigint`) |
|
|
78
|
+
| `useGetBridgeableTokens` | `UseQueryResult<XToken[], Error>` |
|
|
79
|
+
|
|
80
|
+
## Gotchas
|
|
81
|
+
|
|
82
|
+
1. **`useGetBridgeableAmount` takes XToken objects, not addresses + chain ids.** Each `XToken` carries its own `chainKey`. v1 took 4 separate args; v2 takes 2 objects.
|
|
83
|
+
2. **`useGetBridgeableAmount` value is `BridgeLimit`, not a bare bigint.** Access `result.value.amount` and `result.value.decimals` for the limit + scale.
|
|
84
|
+
3. **Tokens are bridgeable iff they share the same vault on the hub.** Use `useGetBridgeableTokens` to enumerate compatible destinations for a given source — passing an incompatible pair to `bridge()` rejects with `VALIDATION_FAILED`.
|
|
85
|
+
4. **`bridge()` returns `TxHashPair`, not a tuple.** Destructure as `{ srcChainTxHash, dstChainTxHash }` — never `[a, b]`.
|
|
86
|
+
|
|
87
|
+
## Cross-references
|
|
88
|
+
|
|
89
|
+
- [`../recipes/bridge.md`](../recipes/bridge.md) — full worked example.
|
|
90
|
+
- [`../../migration/features/bridge.md`](../../migration/features/bridge.md) — v1 → v2 porting.
|
|
91
|
+
- [`../../../../sdk/ai-exported/integration/features/bridge.md`](../../../../sdk/ai-exported/integration/features/bridge.md) — underlying SDK bridge surface.
|
|
@@ -0,0 +1,152 @@
|
|
|
1
|
+
# DEX — `@sodax/dapp-kit`
|
|
2
|
+
|
|
3
|
+
Concentrated-liquidity DEX (similar to Uniswap V3). Two-step flow: deposit assets to mint pool tokens, then supply liquidity to a position.
|
|
4
|
+
|
|
5
|
+
Pair: [`../../migration/features/dex.md`](../../migration/features/dex.md).
|
|
6
|
+
|
|
7
|
+
## Hook surface
|
|
8
|
+
|
|
9
|
+
```ts
|
|
10
|
+
// @ai-snippets-skip
|
|
11
|
+
// Asset deposit / withdraw (spoke ↔ hub pool tokens)
|
|
12
|
+
useDexDeposit({ mutationOptions });
|
|
13
|
+
useDexWithdraw({ mutationOptions });
|
|
14
|
+
useDexAllowance({ params: { payload: CreateAssetDepositParams<K> }, queryOptions });
|
|
15
|
+
useDexApprove({ mutationOptions });
|
|
16
|
+
usePoolBalances({ params, queryOptions });
|
|
17
|
+
|
|
18
|
+
// Liquidity (pool tokens ↔ position)
|
|
19
|
+
useSupplyLiquidity({ mutationOptions }); // Mint new or increase existing
|
|
20
|
+
useDecreaseLiquidity({ mutationOptions });
|
|
21
|
+
useClaimRewards({ mutationOptions });
|
|
22
|
+
|
|
23
|
+
// Reads
|
|
24
|
+
usePools({ queryOptions });
|
|
25
|
+
usePoolData({ params, queryOptions });
|
|
26
|
+
usePositionInfo({ params, queryOptions });
|
|
27
|
+
useLiquidityAmounts({ params, queryOptions });
|
|
28
|
+
|
|
29
|
+
// Param builders (compute derived params client-side) — these take a FLAT props object,
|
|
30
|
+
// NOT a `{ params }` wrapper. They return memoized derived params that the consumer adds
|
|
31
|
+
// `srcChainKey` + `srcAddress` to at the mutation call site.
|
|
32
|
+
useCreateDepositParams({ tokenIndex, amount, poolData, poolSpokeAssets, dst? });
|
|
33
|
+
useCreateWithdrawParams({ tokenIndex, amount, poolData, poolSpokeAssets, dst? });
|
|
34
|
+
useCreateSupplyLiquidityParams({ poolData, poolKey, minPrice, maxPrice, liquidityToken0Amount, liquidityToken1Amount, slippageTolerance, positionId?, isValidPosition? });
|
|
35
|
+
useCreateDecreaseLiquidityParams({ /* see source for fields */ });
|
|
36
|
+
```
|
|
37
|
+
|
|
38
|
+
## SDK param types (passed via `mutate({ params, walletProvider })`)
|
|
39
|
+
|
|
40
|
+
Each dex mutation hook's TVars is `{ params: <SDKParamsType>, walletProvider, timeout? }`. The SDK param types below are what goes INSIDE `params` — they are not the TVars themselves.
|
|
41
|
+
|
|
42
|
+
```ts
|
|
43
|
+
// @ai-snippets-skip
|
|
44
|
+
// Deposit / withdraw — spoke chain assets → hub pool tokens (or vice versa)
|
|
45
|
+
type CreateAssetDepositParams<K> = {
|
|
46
|
+
srcChainKey: K;
|
|
47
|
+
srcAddress: GetAddressType<K>;
|
|
48
|
+
asset: string; // spoke-chain asset address
|
|
49
|
+
amount: bigint;
|
|
50
|
+
poolToken: string; // hub-side pool token (vault) address
|
|
51
|
+
dst?: { chainKey: SpokeChainKey; address: string };
|
|
52
|
+
};
|
|
53
|
+
|
|
54
|
+
// Supply liquidity — `useSupplyLiquidity` fans out internally to mint-new vs
|
|
55
|
+
// increase-existing based on params.tokenId + params.isValidPosition.
|
|
56
|
+
// The TVars `params` field is `UseCreateSupplyLiquidityParamsResult & { srcChainKey, srcAddress }`
|
|
57
|
+
// (the memoized output of `useCreateSupplyLiquidityParams` + the chain/address pair).
|
|
58
|
+
// Underlying SDK type ClSupplyParams<K> (for mint-new) has NO tokenId field:
|
|
59
|
+
type ClSupplyParams<K> = {
|
|
60
|
+
srcChainKey: K;
|
|
61
|
+
srcAddress: GetAddressType<K>;
|
|
62
|
+
poolKey: PoolKey;
|
|
63
|
+
tickLower: bigint;
|
|
64
|
+
tickUpper: bigint;
|
|
65
|
+
liquidity: bigint;
|
|
66
|
+
amount0Max: bigint;
|
|
67
|
+
amount1Max: bigint;
|
|
68
|
+
sqrtPriceX96: bigint;
|
|
69
|
+
};
|
|
70
|
+
// And ClIncreaseLiquidityParams<K> = ClSupplyParams<K> & { tokenId: bigint }
|
|
71
|
+
// for the increase-existing branch.
|
|
72
|
+
|
|
73
|
+
// Decrease liquidity
|
|
74
|
+
type ClDecreaseLiquidityParams<K> = {
|
|
75
|
+
srcChainKey: K;
|
|
76
|
+
srcAddress: GetAddressType<K>;
|
|
77
|
+
poolKey: PoolKey;
|
|
78
|
+
tokenId: bigint;
|
|
79
|
+
liquidity: bigint;
|
|
80
|
+
amount0Min: bigint;
|
|
81
|
+
amount1Min: bigint;
|
|
82
|
+
};
|
|
83
|
+
|
|
84
|
+
// Claim rewards
|
|
85
|
+
type ClClaimRewardsParams<K> = {
|
|
86
|
+
srcChainKey: K;
|
|
87
|
+
srcAddress: GetAddressType<K>;
|
|
88
|
+
poolKey: PoolKey;
|
|
89
|
+
tokenId: bigint;
|
|
90
|
+
tickLower: bigint;
|
|
91
|
+
tickUpper: bigint;
|
|
92
|
+
};
|
|
93
|
+
```
|
|
94
|
+
|
|
95
|
+
## Param builders
|
|
96
|
+
|
|
97
|
+
The `useCreate*Params` hooks compute the right derived params client-side (e.g. ERC-4626 share conversions for deposit, current tick range for liquidity). Spread the result into the mutation:
|
|
98
|
+
|
|
99
|
+
```ts
|
|
100
|
+
// @ai-snippets-skip — illustrative; `useCreateSupplyLiquidityParams` takes a FLAT props
|
|
101
|
+
// object (not `{ params }`-wrapped). The consumer adds `srcChainKey` + `srcAddress` at
|
|
102
|
+
// the mutation call site.
|
|
103
|
+
const supplyResult = useCreateSupplyLiquidityParams({
|
|
104
|
+
poolData,
|
|
105
|
+
poolKey,
|
|
106
|
+
minPrice,
|
|
107
|
+
maxPrice,
|
|
108
|
+
liquidityToken0Amount,
|
|
109
|
+
liquidityToken1Amount,
|
|
110
|
+
slippageTolerance,
|
|
111
|
+
positionId, // optional, for increase-existing
|
|
112
|
+
isValidPosition, // optional, gates the increase-existing branch
|
|
113
|
+
});
|
|
114
|
+
|
|
115
|
+
const { mutateAsync: supply } = useSupplyLiquidity();
|
|
116
|
+
if (supplyResult && walletProvider) {
|
|
117
|
+
await supply({
|
|
118
|
+
params: { ...supplyResult, srcChainKey, srcAddress },
|
|
119
|
+
walletProvider,
|
|
120
|
+
});
|
|
121
|
+
}
|
|
122
|
+
```
|
|
123
|
+
|
|
124
|
+
## Return shapes
|
|
125
|
+
|
|
126
|
+
| Hook | Returns |
|
|
127
|
+
|---|---|
|
|
128
|
+
| `useDexDeposit` / `useDexWithdraw` | `SafeUseMutationResult<TxHashPair, Error, UseDex(Deposit\|Withdraw)Vars<K>>` (TVars = `{ params, walletProvider, ...optional }`) |
|
|
129
|
+
| `useDexApprove` | `SafeUseMutationResult<TxReturnType<K, false>, Error, UseDexApproveVars<K>>` — chain-keyed receipt union |
|
|
130
|
+
| `useSupplyLiquidity` (mint or increase) | `SafeUseMutationResult<TxHashPair, Error, UseSupplyLiquidityVars<K>>` — single shape for both branches; fan-out happens inside the hook |
|
|
131
|
+
| `useDecreaseLiquidity` / `useClaimRewards` | `SafeUseMutationResult<TxHashPair, Error, ...>` |
|
|
132
|
+
| `useDexAllowance` | `UseQueryResult<boolean, Error>` (already unwrapped; throws on SDK `!ok`) |
|
|
133
|
+
| `usePools` | `UseQueryResult<PoolKey[], Error>` — `staleTime: Infinity` (no auto-refresh; pools are static config) |
|
|
134
|
+
| `usePoolData` | `UseQueryResult<PoolData, Error>` |
|
|
135
|
+
| `usePositionInfo` | `UseQueryResult<{ positionInfo: ClPositionInfo, isValid: boolean }, Error>` — `tokenId` param is `string \| null` (NOT bigint) |
|
|
136
|
+
| `usePoolBalances` | `UseQueryResult<{ token0Balance: bigint; token1Balance: bigint }, Error>` |
|
|
137
|
+
| `useLiquidityAmounts` | Direct synchronous calculation (memoized via `useMemo`) — not a React Query hook |
|
|
138
|
+
|
|
139
|
+
## Gotchas
|
|
140
|
+
|
|
141
|
+
1. **Two-step flow: deposit, then supply.** First `useDexDeposit` brings the spoke asset to the hub as pool-token shares (ERC-4626). Then `useSupplyLiquidity` uses those shares to mint or grow a position. UI flows usually combine them.
|
|
142
|
+
2. **`useSupplyLiquidity` handles both mint-new and increase-existing.** If `params.tokenId` is provided AND that position is valid for the pool, it increases. Otherwise it mints a new position. Use `useCreateSupplyLiquidityParams` to handle the routing.
|
|
143
|
+
3. **Ticks are logarithmic.** `tickLower` / `tickUpper` are not prices — they're indices. Convert with viem's `Q96` math or the SDK's helpers.
|
|
144
|
+
4. **`usePools` never auto-refreshes.** Pools are static config — fetch once. Override `queryOptions.refetchInterval` only if you really know your config changed.
|
|
145
|
+
5. **`useDexAllowance` doesn't take `walletProvider`.** Read-only — derives the user from `srcAddress` in `params`.
|
|
146
|
+
6. **`useClaimRewards` operates per-position.** If you need to claim across multiple positions, call it once per `tokenId`. The hook invalidates the corresponding `usePositionInfo` after success.
|
|
147
|
+
|
|
148
|
+
## Cross-references
|
|
149
|
+
|
|
150
|
+
- [`../recipes/dex.md`](../recipes/dex.md) — full worked examples.
|
|
151
|
+
- [`../../migration/features/dex.md`](../../migration/features/dex.md) — v1 → v2 porting.
|
|
152
|
+
- [`../../../../sdk/ai-exported/integration/features/dex.md`](../../../../sdk/ai-exported/integration/features/dex.md) — underlying SDK DEX surface.
|
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
# Migration — `@sodax/dapp-kit`
|
|
2
|
+
|
|
3
|
+
Token migration: ICX/wICX → SODA, BALN → SODA, legacy bnUSD ↔ new bnUSD. Six per-action hooks plus shared allowance/approve.
|
|
4
|
+
|
|
5
|
+
Pair: [`../../migration/features/migration.md`](../../migration/features/migration.md).
|
|
6
|
+
|
|
7
|
+
## Hook surface
|
|
8
|
+
|
|
9
|
+
```ts
|
|
10
|
+
// @ai-snippets-skip — hook-surface listing; `<inner>` is a type placeholder, not real code
|
|
11
|
+
// Mutations (one per action)
|
|
12
|
+
useMigrateIcxToSoda({ mutationOptions });
|
|
13
|
+
useRevertMigrateSodaToIcx({ mutationOptions });
|
|
14
|
+
useMigratebnUSD({ mutationOptions }); // Bidirectional (auto-detects direction)
|
|
15
|
+
useMigrateBaln({ mutationOptions });
|
|
16
|
+
|
|
17
|
+
// Allowance + approve (action-discriminated)
|
|
18
|
+
useMigrationApprove({ mutationOptions });
|
|
19
|
+
// useMigrationAllowance — params nest `{ params: <inner-migration-params>, action }` under the outer `params`
|
|
20
|
+
useMigrationAllowance({ params: { params: <inner>, action: 'migrate' | 'revert' }, queryOptions });
|
|
21
|
+
```
|
|
22
|
+
|
|
23
|
+
## Mutation params
|
|
24
|
+
|
|
25
|
+
```ts
|
|
26
|
+
// @ai-snippets-skip
|
|
27
|
+
// useMigrateIcxToSoda — wICX (ICON) → SODA (Sonic)
|
|
28
|
+
type IcxMigrateParams = {
|
|
29
|
+
srcChainKey: IconChainKey; // typeof ChainKeys.ICON_MAINNET
|
|
30
|
+
srcAddress: IconAddress; // `hx${string}` | `cx${string}`
|
|
31
|
+
address: IcxTokenType; // narrow union: wICX address OR native-ICX address
|
|
32
|
+
amount: bigint;
|
|
33
|
+
dstAddress: Address; // `0x${string}` — Sonic recipient
|
|
34
|
+
};
|
|
35
|
+
|
|
36
|
+
// useRevertMigrateSodaToIcx — SODA (Sonic) → wICX (ICON)
|
|
37
|
+
type IcxCreateRevertMigrationParams = {
|
|
38
|
+
srcChainKey: SonicChainKey; // typeof ChainKeys.SONIC_MAINNET
|
|
39
|
+
srcAddress: Address; // `0x${string}` — Sonic
|
|
40
|
+
amount: bigint;
|
|
41
|
+
dstAddress: IconEoaAddress; // `hx${string}` — ICON recipient
|
|
42
|
+
};
|
|
43
|
+
|
|
44
|
+
// useMigratebnUSD — bidirectional, swap srcbnUSD/dstbnUSD + chains for the other direction
|
|
45
|
+
type UnifiedBnUSDMigrateParams<K extends SpokeChainKey> = {
|
|
46
|
+
srcChainKey: K;
|
|
47
|
+
srcAddress: string; // SDK keeps this loose (cross-chain)
|
|
48
|
+
srcbnUSD: string; // legacy or new bnUSD
|
|
49
|
+
dstChainKey: SpokeChainKey;
|
|
50
|
+
dstbnUSD: string; // the other one
|
|
51
|
+
amount: bigint;
|
|
52
|
+
dstAddress: string;
|
|
53
|
+
};
|
|
54
|
+
|
|
55
|
+
// useMigrateBaln — BALN (ICON) → SODA with optional lock
|
|
56
|
+
type BalnMigrateParams = {
|
|
57
|
+
srcChainKey: IconChainKey;
|
|
58
|
+
srcAddress: IconAddress;
|
|
59
|
+
amount: bigint;
|
|
60
|
+
lockupPeriod: LockupPeriod; // enum (values in SECONDS), see below
|
|
61
|
+
dstAddress: Address;
|
|
62
|
+
stake: boolean; // REQUIRED — auto-stake migrated SODA into xSODA vault
|
|
63
|
+
};
|
|
64
|
+
|
|
65
|
+
// `LockupPeriod` is an enum with 5 members (values are in seconds, NOT months):
|
|
66
|
+
// NO_LOCKUP = 0 (0.5x reward multiplier)
|
|
67
|
+
// SIX_MONTHS = 6 * 30 * 24 * 60 * 60 (0.75x)
|
|
68
|
+
// TWELVE_MONTHS = 12 * 30 * 24 * 60 * 60 (1.0x)
|
|
69
|
+
// EIGHTEEN_MONTHS = 18 * 30 * 24 * 60 * 60 (1.25x)
|
|
70
|
+
// TWENTY_FOUR_MONTHS = 24 * 30 * 24 * 60 * 60 (1.5x)
|
|
71
|
+
|
|
72
|
+
// All wrapped as TVars: { params: <ParamsType>, walletProvider }
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
## Allowance / approve
|
|
76
|
+
|
|
77
|
+
The migration approve/allowance hooks are **action-discriminated** — same hook handles all migrations, with `action` disambiguating which token is being approved:
|
|
78
|
+
|
|
79
|
+
```ts
|
|
80
|
+
// @ai-snippets-skip
|
|
81
|
+
const { data: isApproved } = useMigrationAllowance({
|
|
82
|
+
params: { params: bnUSDParams, action: 'migrate' }, // 'migrate' | 'revert'
|
|
83
|
+
});
|
|
84
|
+
const { mutateAsync: approve } = useMigrationApprove();
|
|
85
|
+
await approve({ params: bnUSDParams, walletProvider, action: 'migrate' });
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
## Migration paths summary
|
|
89
|
+
|
|
90
|
+
| Migration | Approval needed? | Hook |
|
|
91
|
+
|---|---|---|
|
|
92
|
+
| ICX/wICX (ICON) → SODA | No (ICON has no ERC-20 allowance) | `useMigrateIcxToSoda` |
|
|
93
|
+
| SODA → wICX (revert) | Yes | `useRevertMigrateSodaToIcx` + `useMigrationApprove({ action: 'revert' })` |
|
|
94
|
+
| Legacy bnUSD ↔ new bnUSD (EVM) | Yes | `useMigratebnUSD` + `useMigrationApprove({ action: 'migrate' })` |
|
|
95
|
+
| Legacy bnUSD (Stellar/Sui) ↔ new bnUSD | Maybe (depends on chain) | Same as above |
|
|
96
|
+
| BALN (ICON) → SODA | No | `useMigrateBaln` |
|
|
97
|
+
|
|
98
|
+
## Return shapes
|
|
99
|
+
|
|
100
|
+
| Hook | Returns |
|
|
101
|
+
|---|---|
|
|
102
|
+
| `useMigrateIcxToSoda` / `useRevertMigrateSodaToIcx` / `useMigratebnUSD` / `useMigrateBaln` | `SafeUseMutationResult<TxHashPair, Error, ...>` |
|
|
103
|
+
| `useMigrationApprove` | `SafeUseMutationResult<TxReturnType<K, false>, Error, ...>` — chain-keyed receipt union (EVM/Stellar differ) |
|
|
104
|
+
| `useMigrationAllowance` | `UseQueryResult<boolean, Error>` (already unwrapped) |
|
|
105
|
+
|
|
106
|
+
## Gotchas
|
|
107
|
+
|
|
108
|
+
1. **`useMigratebnUSD` is bidirectional.** v2 detects direction from `(srcbnUSD, dstbnUSD)` token addresses. To go the other direction, swap the params; no separate hook.
|
|
109
|
+
2. **BALN `lockupPeriod` is the `LockupPeriod` enum, NOT a literal number union.** Use `LockupPeriod.NO_LOCKUP`, `LockupPeriod.SIX_MONTHS`, `LockupPeriod.TWELVE_MONTHS`, `LockupPeriod.EIGHTEEN_MONTHS`, or `LockupPeriod.TWENTY_FOUR_MONTHS`. Enum values are in **seconds** (e.g. `TWELVE_MONTHS = 12 * 30 * 24 * 60 * 60`), not months. Reward multiplier ranges 0.5x (no lockup) → 1.5x (24 months). Also note: `BalnMigrateParams` requires `stake: boolean` — set `true` to auto-stake migrated SODA into the xSODA vault.
|
|
110
|
+
3. **ICON-side migrations don't need approval.** ICON has no ERC-20 allowance mechanism.
|
|
111
|
+
4. **`useRevertMigrateSodaToIcx` requires SODA approval on Sonic.** Use `useMigrationAllowance` + `useMigrationApprove` with `action: 'revert'`.
|
|
112
|
+
5. **`useMigratebnUSD` errors include `direction: 'forward' | 'reverse'` on context.** When surfacing errors, distinguish forward vs reverse for clearer messaging.
|
|
113
|
+
|
|
114
|
+
## Cross-references
|
|
115
|
+
|
|
116
|
+
- [`../recipes/migration.md`](../recipes/migration.md) — full worked examples.
|
|
117
|
+
- [`../../migration/features/migration.md`](../../migration/features/migration.md) — v1 → v2 porting (the v1 dapp-kit had a single `useMigrate(spokeProvider)`-style hook; v2 split into 6).
|
|
118
|
+
- [`../../../../sdk/ai-exported/integration/features/icx-bnusd-baln.md`](../../../../sdk/ai-exported/integration/features/icx-bnusd-baln.md) — underlying SDK migration surface.
|