@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,202 @@
|
|
|
1
|
+
# Recipe: Staking
|
|
2
|
+
|
|
3
|
+
SODA token staking via xSODA ERC-4626 vault.
|
|
4
|
+
|
|
5
|
+
**Depends on:** [setup.md](setup.md), [wallet-connectivity.md](wallet-connectivity.md)
|
|
6
|
+
|
|
7
|
+
## Hooks
|
|
8
|
+
|
|
9
|
+
### Mutations
|
|
10
|
+
|
|
11
|
+
| Hook | Purpose |
|
|
12
|
+
|------|---------|
|
|
13
|
+
| `useStake` | Stake SODA, receive xSODA |
|
|
14
|
+
| `useStakeApprove` | Approve SODA for staking |
|
|
15
|
+
| `useUnstake` | Request unstake (waiting period) |
|
|
16
|
+
| `useUnstakeApprove` | Approve xSODA for unstaking |
|
|
17
|
+
| `useInstantUnstake` | Instant unstake with slippage |
|
|
18
|
+
| `useInstantUnstakeApprove` | Approve xSODA for instant unstaking |
|
|
19
|
+
| `useClaim` | Claim SODA after waiting period |
|
|
20
|
+
| `useCancelUnstake` | Cancel pending unstake |
|
|
21
|
+
|
|
22
|
+
### Queries
|
|
23
|
+
|
|
24
|
+
| Hook | Purpose |
|
|
25
|
+
|------|---------|
|
|
26
|
+
| `useStakeAllowance` | Check SODA approval for staking |
|
|
27
|
+
| `useUnstakeAllowance` | Check xSODA approval for unstaking |
|
|
28
|
+
| `useInstantUnstakeAllowance` | Check xSODA approval for instant unstaking |
|
|
29
|
+
| `useStakingInfo` | Staking position (total staked, xSODA balance, value) |
|
|
30
|
+
| `useUnstakingInfo` | Pending unstake requests |
|
|
31
|
+
| `useUnstakingInfoWithPenalty` | Unstake requests with penalty calcs |
|
|
32
|
+
| `useStakingConfig` | Unstaking period, max penalty |
|
|
33
|
+
| `useStakeRatio` | SODA-to-xSODA exchange rate |
|
|
34
|
+
| `useInstantUnstakeRatio` | Instant unstake rate |
|
|
35
|
+
| `useConvertedAssets` | xSODA to SODA conversion |
|
|
36
|
+
|
|
37
|
+
## Staking Dashboard
|
|
38
|
+
|
|
39
|
+
```tsx
|
|
40
|
+
import { useStakingInfo, useStakingConfig, useStakeRatio } from '@sodax/dapp-kit';
|
|
41
|
+
import type { SpokeChainKey } from '@sodax/sdk';
|
|
42
|
+
import { formatUnits } from 'viem';
|
|
43
|
+
|
|
44
|
+
function StakingDashboard({ srcAddress, srcChainKey }: { srcAddress: `0x${string}`; srcChainKey: SpokeChainKey }) {
|
|
45
|
+
const { data: info } = useStakingInfo({ params: { srcAddress, srcChainKey } });
|
|
46
|
+
const { data: config } = useStakingConfig({});
|
|
47
|
+
const { data: ratio } = useStakeRatio({ params: { amount: 1000000000000000000n } });
|
|
48
|
+
|
|
49
|
+
if (!info) return <div>Loading...</div>;
|
|
50
|
+
return (
|
|
51
|
+
<div>
|
|
52
|
+
<p>Total Staked: {formatUnits(info.totalStaked, 18)} SODA</p>
|
|
53
|
+
<p>Your xSODA: {formatUnits(info.userXSodaBalance, 18)}</p>
|
|
54
|
+
<p>Your Value: {formatUnits(info.userXSodaValue, 18)} SODA</p>
|
|
55
|
+
{ratio && <p>Rate: 1 SODA = {formatUnits(ratio[0], 18)} xSODA</p>}
|
|
56
|
+
{config && <p>Unstaking: {(Number(config.unstakingPeriod) / 86400).toFixed(1)} days</p>}
|
|
57
|
+
</div>
|
|
58
|
+
);
|
|
59
|
+
}
|
|
60
|
+
```
|
|
61
|
+
|
|
62
|
+
## Stake
|
|
63
|
+
|
|
64
|
+
```tsx
|
|
65
|
+
import { useState } from 'react';
|
|
66
|
+
import { useStake, useStakeAllowance, useStakeApprove, useStakeRatio } from '@sodax/dapp-kit';
|
|
67
|
+
import { useWalletProvider } from '@sodax/wallet-sdk-react';
|
|
68
|
+
import { ChainKeys } from '@sodax/sdk';
|
|
69
|
+
import { parseUnits, formatUnits, type Address } from 'viem';
|
|
70
|
+
|
|
71
|
+
function StakeForm({ srcAddress }: { srcAddress: Address }) {
|
|
72
|
+
const [amount, setAmount] = useState('');
|
|
73
|
+
const chainKey = ChainKeys.BASE_MAINNET;
|
|
74
|
+
const walletProvider = useWalletProvider({ xChainId: chainKey });
|
|
75
|
+
const parsedAmount = amount ? parseUnits(amount, 18) : 0n;
|
|
76
|
+
|
|
77
|
+
const { data: ratio } = useStakeRatio({ params: { amount: parsedAmount } });
|
|
78
|
+
|
|
79
|
+
const stakeParams = parsedAmount > 0n
|
|
80
|
+
? { srcChainKey: chainKey, srcAddress, amount: parsedAmount, minReceive: ratio ? (ratio[0] * 95n) / 100n : 0n, action: 'stake' as const }
|
|
81
|
+
: undefined;
|
|
82
|
+
|
|
83
|
+
// useStakeAllowance wraps `Omit<StakeParams, 'action'>` under params.payload. Read-only,
|
|
84
|
+
// no walletProvider needed (calls `staking.isAllowanceValid` with `raw: true` internally).
|
|
85
|
+
const { data: isApproved } = useStakeAllowance({
|
|
86
|
+
params: stakeParams
|
|
87
|
+
? { payload: { srcChainKey: chainKey, srcAddress, amount: parsedAmount, minReceive: stakeParams.minReceive } }
|
|
88
|
+
: undefined,
|
|
89
|
+
});
|
|
90
|
+
const { mutateAsync: approve, isPending: isApproving } = useStakeApprove();
|
|
91
|
+
const { mutateAsync: stake, isPending: isStaking } = useStake();
|
|
92
|
+
|
|
93
|
+
const handleStake = async () => {
|
|
94
|
+
if (!stakeParams || !walletProvider) return;
|
|
95
|
+
try {
|
|
96
|
+
if (!isApproved) await approve({ params: stakeParams, walletProvider });
|
|
97
|
+
const txHashPair = await stake({ params: stakeParams, walletProvider });
|
|
98
|
+
console.log('Staked:', txHashPair);
|
|
99
|
+
} catch (e) {
|
|
100
|
+
console.error(e);
|
|
101
|
+
}
|
|
102
|
+
};
|
|
103
|
+
|
|
104
|
+
return (
|
|
105
|
+
<div>
|
|
106
|
+
<input placeholder="SODA amount" value={amount} onChange={(e) => setAmount(e.target.value)} />
|
|
107
|
+
{ratio && <p>~{formatUnits(ratio[0], 18)} xSODA</p>}
|
|
108
|
+
<button onClick={handleStake} disabled={isStaking || isApproving || !stakeParams || !walletProvider}>
|
|
109
|
+
{isApproving ? 'Approving...' : isStaking ? 'Staking...' : 'Stake'}
|
|
110
|
+
</button>
|
|
111
|
+
</div>
|
|
112
|
+
);
|
|
113
|
+
}
|
|
114
|
+
```
|
|
115
|
+
|
|
116
|
+
## Unstake + Claim
|
|
117
|
+
|
|
118
|
+
```tsx
|
|
119
|
+
import { useUnstakingInfoWithPenalty, useClaim } from '@sodax/dapp-kit';
|
|
120
|
+
import { useWalletProvider } from '@sodax/wallet-sdk-react';
|
|
121
|
+
import { ChainKeys } from '@sodax/sdk';
|
|
122
|
+
import { formatUnits, type Address } from 'viem';
|
|
123
|
+
|
|
124
|
+
function UnstakePanel({ srcAddress }: { srcAddress: Address }) {
|
|
125
|
+
const chainKey = ChainKeys.BASE_MAINNET;
|
|
126
|
+
const walletProvider = useWalletProvider({ xChainId: chainKey });
|
|
127
|
+
const { data: info } = useUnstakingInfoWithPenalty({ params: { srcAddress, srcChainKey: chainKey } });
|
|
128
|
+
const { mutateAsync: claim } = useClaim();
|
|
129
|
+
|
|
130
|
+
return (
|
|
131
|
+
<div>
|
|
132
|
+
{info?.requestsWithPenalty.map((req, i) => (
|
|
133
|
+
<div key={i}>
|
|
134
|
+
<p>{formatUnits(req.claimableAmount, 18)} SODA claimable (penalty: {req.penaltyPercentage}%)</p>
|
|
135
|
+
<button
|
|
136
|
+
onClick={() => walletProvider && claim({
|
|
137
|
+
// req.id is the requestId on the UserUnstakeInfo shape; req.request holds the
|
|
138
|
+
// original UnstakeSodaRequest. ClaimParams takes the id and the post-penalty amount.
|
|
139
|
+
params: { srcChainKey: chainKey, srcAddress, requestId: req.id, amount: req.claimableAmount, action: 'claim' },
|
|
140
|
+
walletProvider,
|
|
141
|
+
})}
|
|
142
|
+
>
|
|
143
|
+
Claim
|
|
144
|
+
</button>
|
|
145
|
+
</div>
|
|
146
|
+
))}
|
|
147
|
+
</div>
|
|
148
|
+
);
|
|
149
|
+
}
|
|
150
|
+
```
|
|
151
|
+
|
|
152
|
+
## Instant Unstake
|
|
153
|
+
|
|
154
|
+
```tsx
|
|
155
|
+
import { useInstantUnstake, useInstantUnstakeRatio } from '@sodax/dapp-kit';
|
|
156
|
+
import { useWalletProvider } from '@sodax/wallet-sdk-react';
|
|
157
|
+
import { ChainKeys } from '@sodax/sdk';
|
|
158
|
+
import { type Address } from 'viem';
|
|
159
|
+
|
|
160
|
+
function InstantUnstakeButton({ xSodaAmount, srcAddress }: { xSodaAmount: bigint; srcAddress: Address }) {
|
|
161
|
+
const chainKey = ChainKeys.BASE_MAINNET;
|
|
162
|
+
const walletProvider = useWalletProvider({ xChainId: chainKey });
|
|
163
|
+
const { data: ratio } = useInstantUnstakeRatio({ params: { amount: xSodaAmount } });
|
|
164
|
+
const { mutateAsync: instantUnstake, isPending } = useInstantUnstake();
|
|
165
|
+
|
|
166
|
+
return (
|
|
167
|
+
<button
|
|
168
|
+
disabled={isPending || !walletProvider}
|
|
169
|
+
onClick={() => walletProvider && instantUnstake({
|
|
170
|
+
params: {
|
|
171
|
+
srcChainKey: chainKey,
|
|
172
|
+
srcAddress,
|
|
173
|
+
amount: xSodaAmount,
|
|
174
|
+
minAmount: ratio ? (ratio * 95n) / 100n : 0n,
|
|
175
|
+
action: 'instantUnstake',
|
|
176
|
+
},
|
|
177
|
+
walletProvider,
|
|
178
|
+
})}
|
|
179
|
+
>
|
|
180
|
+
{isPending ? 'Processing...' : 'Instant Unstake'}
|
|
181
|
+
</button>
|
|
182
|
+
);
|
|
183
|
+
}
|
|
184
|
+
```
|
|
185
|
+
|
|
186
|
+
## Types
|
|
187
|
+
|
|
188
|
+
```typescript
|
|
189
|
+
type StakeParams<K> = { srcChainKey: K; srcAddress: Address; amount: bigint; minReceive: bigint; action: 'stake' };
|
|
190
|
+
type UnstakeParams<K> = { srcChainKey: K; srcAddress: Address; amount: bigint; action: 'unstake' };
|
|
191
|
+
type InstantUnstakeParams<K> = { srcChainKey: K; srcAddress: Address; amount: bigint; minAmount: bigint; action: 'instantUnstake' };
|
|
192
|
+
type ClaimParams<K> = { srcChainKey: K; srcAddress: Address; requestId: bigint; amount: bigint; action: 'claim' };
|
|
193
|
+
type CancelUnstakeParams<K> = { srcChainKey: K; srcAddress: Address; requestId: bigint; action: 'cancelUnstake' };
|
|
194
|
+
// All wrapped as: { params: ParamsType, walletProvider }
|
|
195
|
+
```
|
|
196
|
+
|
|
197
|
+
## Notes
|
|
198
|
+
|
|
199
|
+
- **Unstaking period**: configurable, check `useStakingConfig`.
|
|
200
|
+
- **Penalty**: linear from `maxPenalty` to 0 over the unstaking period.
|
|
201
|
+
- **Instant unstake**: no waiting, but pays slippage via StakingRouter.
|
|
202
|
+
- Query hooks (`useStakingInfo`, `useUnstakingInfoWithPenalty`, etc.) take `{ params: { srcAddress, srcChainKey } }` — they derive the hub wallet internally.
|
|
@@ -0,0 +1,272 @@
|
|
|
1
|
+
# Recipe: Swap
|
|
2
|
+
|
|
3
|
+
Cross-chain token swaps via the intent-based solver.
|
|
4
|
+
|
|
5
|
+
**Depends on:** [setup.md](setup.md), [wallet-connectivity.md](wallet-connectivity.md)
|
|
6
|
+
|
|
7
|
+
## Hooks
|
|
8
|
+
|
|
9
|
+
| Hook | Type | Purpose |
|
|
10
|
+
|------|------|---------|
|
|
11
|
+
| `useQuote` | Query | Real-time swap quote (auto-refreshes 3s) |
|
|
12
|
+
| `useSwap` | Mutation | Execute a complete cross-chain swap |
|
|
13
|
+
| `useSwapAllowance` | Query | Check if token approval is needed |
|
|
14
|
+
| `useSwapApprove` | Mutation | Approve tokens for the swap contract |
|
|
15
|
+
| `useStatus` | Query | Track intent execution status |
|
|
16
|
+
| `useCancelSwap` | Mutation | Cancel an active swap intent |
|
|
17
|
+
| `useCreateLimitOrder` | Mutation | Create a limit order (no deadline) |
|
|
18
|
+
| `useCancelLimitOrder` | Mutation | Cancel an active limit order |
|
|
19
|
+
|
|
20
|
+
## Get a Quote
|
|
21
|
+
|
|
22
|
+
```tsx
|
|
23
|
+
import { useQuote } from '@sodax/dapp-kit';
|
|
24
|
+
import { ChainKeys } from '@sodax/sdk';
|
|
25
|
+
|
|
26
|
+
function SwapQuote({ inputAmount }: { inputAmount: bigint }) {
|
|
27
|
+
const { data: quoteResult, isLoading } = useQuote({
|
|
28
|
+
params: {
|
|
29
|
+
payload: inputAmount > 0n
|
|
30
|
+
? {
|
|
31
|
+
token_src: '0x2170Ed0880ac9A755fd29B2688956BD959F933F8',
|
|
32
|
+
token_dst: '0x2f2a2543B76A4166549F7aaB2e75Bef0aefC5B0f',
|
|
33
|
+
token_src_blockchain_id: ChainKeys.BSC_MAINNET,
|
|
34
|
+
token_dst_blockchain_id: ChainKeys.ARBITRUM_MAINNET,
|
|
35
|
+
amount: inputAmount,
|
|
36
|
+
quote_type: 'exact_input',
|
|
37
|
+
}
|
|
38
|
+
: undefined,
|
|
39
|
+
},
|
|
40
|
+
});
|
|
41
|
+
|
|
42
|
+
if (isLoading) return <div>Fetching quote...</div>;
|
|
43
|
+
if (quoteResult?.ok) return <div>Output: {quoteResult.value.quoted_amount}</div>;
|
|
44
|
+
return null;
|
|
45
|
+
}
|
|
46
|
+
```
|
|
47
|
+
|
|
48
|
+
## Check Allowance + Approve
|
|
49
|
+
|
|
50
|
+
```tsx
|
|
51
|
+
import { useSwapAllowance, useSwapApprove } from '@sodax/dapp-kit';
|
|
52
|
+
import { useWalletProvider } from '@sodax/wallet-sdk-react';
|
|
53
|
+
import { ChainKeys } from '@sodax/sdk';
|
|
54
|
+
import type { CreateIntentParams } from '@sodax/sdk';
|
|
55
|
+
|
|
56
|
+
function SwapApproval({ intentParams }: { intentParams: CreateIntentParams }) {
|
|
57
|
+
const walletProvider = useWalletProvider({ xChainId: ChainKeys.BSC_MAINNET });
|
|
58
|
+
|
|
59
|
+
// useSwapAllowance wraps the request under params.payload and takes walletProvider + srcChainKey
|
|
60
|
+
// alongside (all under `params`, not at the top level).
|
|
61
|
+
const { data: isApproved } = useSwapAllowance({
|
|
62
|
+
params: {
|
|
63
|
+
payload: intentParams,
|
|
64
|
+
srcChainKey: ChainKeys.BSC_MAINNET,
|
|
65
|
+
walletProvider,
|
|
66
|
+
},
|
|
67
|
+
});
|
|
68
|
+
const { mutateAsync: approve, isPending } = useSwapApprove();
|
|
69
|
+
|
|
70
|
+
// useSwapAllowance data is `boolean | undefined` (already unwrapped from Result by the hook).
|
|
71
|
+
if (isApproved) return null;
|
|
72
|
+
return (
|
|
73
|
+
<button onClick={() => walletProvider && approve({ params: intentParams, walletProvider })} disabled={isPending}>
|
|
74
|
+
{isPending ? 'Approving...' : 'Approve Token'}
|
|
75
|
+
</button>
|
|
76
|
+
);
|
|
77
|
+
}
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
## Execute Swap
|
|
81
|
+
|
|
82
|
+
```tsx
|
|
83
|
+
import { useSwap } from '@sodax/dapp-kit';
|
|
84
|
+
import { useWalletProvider } from '@sodax/wallet-sdk-react';
|
|
85
|
+
import { ChainKeys } from '@sodax/sdk';
|
|
86
|
+
import type { CreateIntentParams } from '@sodax/sdk';
|
|
87
|
+
|
|
88
|
+
function SwapButton({ intentParams }: { intentParams: CreateIntentParams }) {
|
|
89
|
+
const walletProvider = useWalletProvider({ xChainId: ChainKeys.BSC_MAINNET });
|
|
90
|
+
const { mutateAsync: swap, isPending } = useSwap();
|
|
91
|
+
|
|
92
|
+
const handleSwap = async () => {
|
|
93
|
+
if (!walletProvider) return;
|
|
94
|
+
try {
|
|
95
|
+
const { solverExecutionResponse, intent, intentDeliveryInfo } = await swap({
|
|
96
|
+
params: intentParams,
|
|
97
|
+
walletProvider,
|
|
98
|
+
});
|
|
99
|
+
console.log('Swap successful!', solverExecutionResponse);
|
|
100
|
+
} catch (e) {
|
|
101
|
+
// surfaced via mutation.error / onError
|
|
102
|
+
}
|
|
103
|
+
};
|
|
104
|
+
|
|
105
|
+
return (
|
|
106
|
+
<button onClick={handleSwap} disabled={isPending || !walletProvider}>
|
|
107
|
+
{isPending ? 'Swapping...' : 'Swap'}
|
|
108
|
+
</button>
|
|
109
|
+
);
|
|
110
|
+
}
|
|
111
|
+
```
|
|
112
|
+
|
|
113
|
+
## Full Example
|
|
114
|
+
|
|
115
|
+
```tsx
|
|
116
|
+
import { useState } from 'react';
|
|
117
|
+
import { useQuote, useSwap, useSwapAllowance, useSwapApprove } from '@sodax/dapp-kit';
|
|
118
|
+
import { useWalletProvider } from '@sodax/wallet-sdk-react';
|
|
119
|
+
import { ChainKeys } from '@sodax/sdk';
|
|
120
|
+
import type { CreateIntentParams, SolverIntentQuoteRequest } from '@sodax/sdk';
|
|
121
|
+
import { parseUnits } from 'viem';
|
|
122
|
+
|
|
123
|
+
const SRC_TOKEN = '0x2170Ed0880ac9A755fd29B2688956BD959F933F8';
|
|
124
|
+
const DST_TOKEN = '0x2f2a2543B76A4166549F7aaB2e75Bef0aefC5B0f';
|
|
125
|
+
|
|
126
|
+
export function SwapPage() {
|
|
127
|
+
const [inputAmount, setInputAmount] = useState('');
|
|
128
|
+
const walletProvider = useWalletProvider({ xChainId: ChainKeys.BSC_MAINNET });
|
|
129
|
+
const parsedAmount = inputAmount ? parseUnits(inputAmount, 18) : 0n;
|
|
130
|
+
|
|
131
|
+
// 1. Quote — useQuote takes { params: { payload: SolverIntentQuoteRequest } }.
|
|
132
|
+
const { data: quoteResult, isLoading: isQuoting } = useQuote({
|
|
133
|
+
params: {
|
|
134
|
+
payload: parsedAmount > 0n
|
|
135
|
+
? {
|
|
136
|
+
token_src: SRC_TOKEN,
|
|
137
|
+
token_dst: DST_TOKEN,
|
|
138
|
+
token_src_blockchain_id: ChainKeys.BSC_MAINNET,
|
|
139
|
+
token_dst_blockchain_id: ChainKeys.ARBITRUM_MAINNET,
|
|
140
|
+
amount: parsedAmount,
|
|
141
|
+
quote_type: 'exact_input',
|
|
142
|
+
}
|
|
143
|
+
: undefined,
|
|
144
|
+
},
|
|
145
|
+
});
|
|
146
|
+
|
|
147
|
+
// 2. Build intent params. The request-side fields are `srcChainKey` / `dstChainKey`
|
|
148
|
+
// (distinct from the read-side `Intent.srcChain` / `Intent.dstChain` which are
|
|
149
|
+
// `IntentRelayChainId` bigints — a separate shape).
|
|
150
|
+
const intentParams: CreateIntentParams | undefined =
|
|
151
|
+
quoteResult?.ok
|
|
152
|
+
? {
|
|
153
|
+
inputToken: SRC_TOKEN,
|
|
154
|
+
outputToken: DST_TOKEN,
|
|
155
|
+
inputAmount: parsedAmount,
|
|
156
|
+
minOutputAmount: BigInt(quoteResult.value.quoted_amount),
|
|
157
|
+
deadline: 0n,
|
|
158
|
+
allowPartialFill: false,
|
|
159
|
+
srcChainKey: ChainKeys.BSC_MAINNET,
|
|
160
|
+
dstChainKey: ChainKeys.ARBITRUM_MAINNET,
|
|
161
|
+
srcAddress: '0x0000000000000000000000000000000000000000', // connected wallet address
|
|
162
|
+
dstAddress: '0x0000000000000000000000000000000000000000', // destination address
|
|
163
|
+
solver: '0x0000000000000000000000000000000000000000',
|
|
164
|
+
data: '0x',
|
|
165
|
+
}
|
|
166
|
+
: undefined;
|
|
167
|
+
|
|
168
|
+
// 3. Allowance — useSwapAllowance nests payload + srcChainKey + walletProvider under params.
|
|
169
|
+
const { data: isApproved } = useSwapAllowance({
|
|
170
|
+
params: intentParams
|
|
171
|
+
? { payload: intentParams, srcChainKey: ChainKeys.BSC_MAINNET, walletProvider }
|
|
172
|
+
: undefined,
|
|
173
|
+
});
|
|
174
|
+
|
|
175
|
+
// 4. Approve + Swap (using mutateAsyncSafe — no try/catch, no unhandled rejections)
|
|
176
|
+
const { mutateAsyncSafe: approve, isPending: isApproving } = useSwapApprove();
|
|
177
|
+
const { mutateAsyncSafe: swap, isPending: isSwapping } = useSwap();
|
|
178
|
+
|
|
179
|
+
const handleSwap = async () => {
|
|
180
|
+
if (!intentParams || !walletProvider) return;
|
|
181
|
+
if (!isApproved) {
|
|
182
|
+
const r = await approve({ params: intentParams, walletProvider });
|
|
183
|
+
if (!r.ok) { alert(r.error instanceof Error ? r.error.message : 'Approve failed'); return; }
|
|
184
|
+
}
|
|
185
|
+
const r = await swap({ params: intentParams, walletProvider });
|
|
186
|
+
if (r.ok) alert('Swap successful!');
|
|
187
|
+
else alert(r.error instanceof Error ? r.error.message : 'Swap failed');
|
|
188
|
+
};
|
|
189
|
+
|
|
190
|
+
return (
|
|
191
|
+
<div>
|
|
192
|
+
<input placeholder="Amount" value={inputAmount} onChange={(e) => setInputAmount(e.target.value)} />
|
|
193
|
+
{isQuoting && <p>Fetching quote...</p>}
|
|
194
|
+
{quoteResult?.ok && <p>Output: {quoteResult.value.quoted_amount}</p>}
|
|
195
|
+
<button onClick={handleSwap} disabled={isSwapping || isApproving || !intentParams}>
|
|
196
|
+
{isApproving ? 'Approving...' : isSwapping ? 'Swapping...' : 'Swap'}
|
|
197
|
+
</button>
|
|
198
|
+
</div>
|
|
199
|
+
);
|
|
200
|
+
}
|
|
201
|
+
```
|
|
202
|
+
|
|
203
|
+
## Limit Orders
|
|
204
|
+
|
|
205
|
+
```tsx
|
|
206
|
+
import { useCreateLimitOrder, useCancelLimitOrder } from '@sodax/dapp-kit';
|
|
207
|
+
import type { Intent } from '@sodax/sdk';
|
|
208
|
+
|
|
209
|
+
const { mutateAsync: createLimitOrder } = useCreateLimitOrder();
|
|
210
|
+
const { mutateAsync: cancelLimitOrder } = useCancelLimitOrder();
|
|
211
|
+
|
|
212
|
+
// Limit orders have no deadline, must be cancelled manually.
|
|
213
|
+
// `useCancelLimitOrder` TVars are FLAT: `{ srcChainKey, intent, walletProvider }` (no `params` wrapper).
|
|
214
|
+
async function flow(intent: Intent) {
|
|
215
|
+
if (!walletProvider) return;
|
|
216
|
+
await createLimitOrder({ params: limitOrderParams, walletProvider });
|
|
217
|
+
await cancelLimitOrder({ srcChainKey, intent, walletProvider });
|
|
218
|
+
}
|
|
219
|
+
```
|
|
220
|
+
|
|
221
|
+
## Customize TanStack Query behavior
|
|
222
|
+
|
|
223
|
+
Every mutation hook accepts an optional `mutationOptions` slot for consumers to override TanStack Query knobs (`retry`, `onError`, `mutationKey`, etc.). The hook's `mutationFn` throws on SDK failure (so `mutation.error`, `onError`, and `retry` engage natively); its own `onSuccess` invalidations run first on real success, then the consumer's `onSuccess` is awaited.
|
|
224
|
+
|
|
225
|
+
```tsx
|
|
226
|
+
import { useSwap } from '@sodax/dapp-kit';
|
|
227
|
+
import { useIsMutating } from '@tanstack/react-query';
|
|
228
|
+
|
|
229
|
+
const { mutateAsync: swap, isError, error } = useSwap({
|
|
230
|
+
mutationOptions: {
|
|
231
|
+
retry: 5,
|
|
232
|
+
onError: err => toast.error(err.message),
|
|
233
|
+
onSuccess: swapResponse => {
|
|
234
|
+
// Runs AFTER dapp-kit's xBalances invalidations — only on confirmed success.
|
|
235
|
+
trackSwap(swapResponse);
|
|
236
|
+
},
|
|
237
|
+
},
|
|
238
|
+
});
|
|
239
|
+
|
|
240
|
+
// Track in-flight swaps anywhere in the app via the default mutationKey
|
|
241
|
+
const swapsInFlight = useIsMutating({ mutationKey: ['swap'] });
|
|
242
|
+
console.log({ swap, isError, error, swapsInFlight });
|
|
243
|
+
```
|
|
244
|
+
|
|
245
|
+
## Gotchas
|
|
246
|
+
|
|
247
|
+
### Token list has duplicate addresses
|
|
248
|
+
|
|
249
|
+
`getSupportedSolverTokens()` can return multiple tokens sharing the same contract address (same token on different chains). When rendering token lists, use a composite key like `${token.address}-${token.blockchain_id}` — not `token.address` alone.
|
|
250
|
+
|
|
251
|
+
### Balance display
|
|
252
|
+
|
|
253
|
+
Balances come from `@sodax/wallet-sdk-react`, not from dapp-kit. See `wallet-connectivity.md` for `useXBalances`.
|
|
254
|
+
|
|
255
|
+
## Types
|
|
256
|
+
|
|
257
|
+
```typescript
|
|
258
|
+
type CreateIntentParams = {
|
|
259
|
+
inputToken: string;
|
|
260
|
+
outputToken: string;
|
|
261
|
+
inputAmount: bigint;
|
|
262
|
+
minOutputAmount: bigint;
|
|
263
|
+
deadline: bigint; // 0n = no deadline
|
|
264
|
+
allowPartialFill: boolean;
|
|
265
|
+
srcChain: SpokeChainId;
|
|
266
|
+
dstChain: SpokeChainId;
|
|
267
|
+
srcAddress: string;
|
|
268
|
+
dstAddress: string;
|
|
269
|
+
solver: Address; // address(0) = any solver
|
|
270
|
+
data: Hex;
|
|
271
|
+
};
|
|
272
|
+
```
|
|
@@ -0,0 +1,101 @@
|
|
|
1
|
+
# Recipe: Wallet Connectivity
|
|
2
|
+
|
|
3
|
+
Connect wallets and pass wallet providers to feature hooks.
|
|
4
|
+
|
|
5
|
+
**Depends on:** [setup.md](setup.md)
|
|
6
|
+
|
|
7
|
+
## Hooks
|
|
8
|
+
|
|
9
|
+
| Hook | Package | Type | Purpose |
|
|
10
|
+
|------|---------|------|---------|
|
|
11
|
+
| `useWalletProvider` | `@sodax/wallet-sdk-react` | Utility | Get wallet provider for a chain from connected wallet |
|
|
12
|
+
| `useHubProvider` | `@sodax/dapp-kit` | Utility | Access the hub chain (Sonic) provider |
|
|
13
|
+
| `useDeriveUserWalletAddress` | `@sodax/dapp-kit` | Query | Derive hub wallet address from spoke address (CREATE3) |
|
|
14
|
+
| `useGetUserHubWalletAddress` | `@sodax/dapp-kit` | Query | Derive hub wallet address via wallet router |
|
|
15
|
+
| `useXBalances` | `@sodax/dapp-kit` | Query | Cross-chain token balances for an address |
|
|
16
|
+
| `useEstimateGas` | `@sodax/dapp-kit` | Mutation | Estimate gas for raw transactions |
|
|
17
|
+
| `useStellarTrustlineCheck` | `@sodax/dapp-kit` | Query | Check if Stellar account has sufficient trustline |
|
|
18
|
+
| `useRequestTrustline` | `@sodax/dapp-kit` | Mutation | Request a Stellar trustline for a token |
|
|
19
|
+
|
|
20
|
+
## Connect a Wallet
|
|
21
|
+
|
|
22
|
+
`@sodax/wallet-sdk-react` provides per-chain wallet hooks:
|
|
23
|
+
|
|
24
|
+
```tsx
|
|
25
|
+
// @ai-snippets-skip
|
|
26
|
+
import { useEvmWallet } from '@sodax/wallet-sdk-react';
|
|
27
|
+
|
|
28
|
+
function ConnectButton() {
|
|
29
|
+
const { connect, disconnect, address, isConnected } = useEvmWallet();
|
|
30
|
+
|
|
31
|
+
if (isConnected) {
|
|
32
|
+
return (
|
|
33
|
+
<div>
|
|
34
|
+
<span>{address}</span>
|
|
35
|
+
<button onClick={disconnect}>Disconnect</button>
|
|
36
|
+
</div>
|
|
37
|
+
);
|
|
38
|
+
}
|
|
39
|
+
return <button onClick={() => connect()}>Connect Wallet</button>;
|
|
40
|
+
}
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
## Get a Wallet Provider
|
|
44
|
+
|
|
45
|
+
`useWalletProvider` returns a typed wallet provider for a specific chain. Pass it directly to feature hook mutation calls:
|
|
46
|
+
|
|
47
|
+
```tsx
|
|
48
|
+
import { useWalletProvider } from '@sodax/wallet-sdk-react';
|
|
49
|
+
import { ChainKeys } from '@sodax/sdk';
|
|
50
|
+
|
|
51
|
+
function MyFeature() {
|
|
52
|
+
const walletProvider = useWalletProvider({ xChainId: ChainKeys.BSC_MAINNET });
|
|
53
|
+
// undefined until wallet is connected for that chain
|
|
54
|
+
// Pass as: useSwap() then swap({ params, walletProvider })
|
|
55
|
+
}
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
## Fetch Token Balances
|
|
59
|
+
|
|
60
|
+
`useXBalances` from `@sodax/dapp-kit` fetches on-chain balances for a wallet address:
|
|
61
|
+
|
|
62
|
+
```tsx
|
|
63
|
+
import { useXBalances } from '@sodax/dapp-kit';
|
|
64
|
+
import { useXService, getXChainType } from '@sodax/wallet-sdk-react';
|
|
65
|
+
import { ChainKeys, type XToken } from '@sodax/sdk';
|
|
66
|
+
|
|
67
|
+
function TokenBalance({ address, xTokens }: { address: string; xTokens: readonly XToken[] }) {
|
|
68
|
+
const xChainId = ChainKeys.BSC_MAINNET;
|
|
69
|
+
// `useXBalances` requires an `xService` from `@sodax/wallet-sdk-react` plus the chain key,
|
|
70
|
+
// the token list to read, and the user's address — all four fields are part of `params`.
|
|
71
|
+
const xService = useXService({ xChainType: getXChainType(xChainId) });
|
|
72
|
+
const { data: balances } = useXBalances({
|
|
73
|
+
params: { xService, xChainId, xTokens, address },
|
|
74
|
+
});
|
|
75
|
+
|
|
76
|
+
// balances is a map of token address → balance (bigint)
|
|
77
|
+
}
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
## Use Wallet Provider in Feature Hooks
|
|
81
|
+
|
|
82
|
+
All mutation hooks accept no arguments at initialization level. The `walletProvider` flows through `mutate(vars)`:
|
|
83
|
+
|
|
84
|
+
```tsx
|
|
85
|
+
import { useSwap } from '@sodax/dapp-kit';
|
|
86
|
+
import { useWalletProvider } from '@sodax/wallet-sdk-react';
|
|
87
|
+
import { ChainKeys } from '@sodax/sdk';
|
|
88
|
+
|
|
89
|
+
function SwapButton() {
|
|
90
|
+
const walletProvider = useWalletProvider({ xChainId: ChainKeys.BSC_MAINNET });
|
|
91
|
+
const { mutateAsync: swap, isPending } = useSwap();
|
|
92
|
+
|
|
93
|
+
const handleSwap = async () => {
|
|
94
|
+
if (!walletProvider) return;
|
|
95
|
+
const result = await swap({ params: intentParams, walletProvider });
|
|
96
|
+
// ...
|
|
97
|
+
};
|
|
98
|
+
}
|
|
99
|
+
```
|
|
100
|
+
|
|
101
|
+
This pattern is consistent across all features: `useSwap`, `useBridge`, `useSupply`, `useStake`, `useDexDeposit`, etc.
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
# Reference — `@sodax/dapp-kit` v2
|
|
2
|
+
|
|
3
|
+
Lookup tables. Read while writing code; not a tutorial.
|
|
4
|
+
|
|
5
|
+
| File | What's in it |
|
|
6
|
+
|---|---|
|
|
7
|
+
| [`hooks-index.md`](hooks-index.md) | Comprehensive hook table (organized by feature, with hook type and purpose). |
|
|
8
|
+
| [`querykey-conventions.md`](querykey-conventions.md) | Mandatory queryKey/mutationKey shape rules + per-feature key tables. |
|
|
9
|
+
| [`public-api.md`](public-api.md) | What `@sodax/dapp-kit` exports + import rules. |
|
|
10
|
+
| [`glossary.md`](glossary.md) | Type aliases (`ReadHookParams`, `MutationHookParams`, `SafeUseMutationResult`, `MutationHookOptions`, etc.). |
|
|
11
|
+
|
|
12
|
+
For full SDK reference (chain keys, error codes, `Sodax` class surface, wallet provider interfaces), see [`../../../../sdk/ai-exported/integration/reference/`](../../../../sdk/ai-exported/integration/reference/) — `@sodax/dapp-kit` re-exports the SDK's public surface, so those types are reachable from `@sodax/dapp-kit` directly.
|