@baseline-markets/sdk 1.1.0 → 1.2.0

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/dist/index.js CHANGED
@@ -1,7 +1,12 @@
1
- import { toHex, getContract, BaseError, UserRejectedRequestError, InsufficientFundsError, ContractFunctionRevertedError, HttpRequestError, WebSocketRequestError, SocketClosedError, TimeoutError, decodeErrorResult, encodeFunctionData, isAddress } from 'viem';
2
- import { baseSepolia, base, mainnet } from 'viem/chains';
1
+ import { toHex, isAddress, decodeFunctionResult, encodeFunctionData, getContract, BaseError, UserRejectedRequestError, InsufficientFundsError, ContractFunctionRevertedError, HttpRequestError, WebSocketRequestError, SocketClosedError, TimeoutError, decodeErrorResult } from 'viem';
2
+ import { hyperEvm, baseSepolia, base, mainnet } from 'viem/chains';
3
+ import { sendCalls, waitForCallsStatus } from 'viem/actions';
3
4
 
4
- // ../contracts/abis/external/chainlinkOracle.ts
5
+ var __defProp = Object.defineProperty;
6
+ var __export = (target, all) => {
7
+ for (var name in all)
8
+ __defProp(target, name, { get: all[name], enumerable: true });
9
+ };
5
10
 
6
11
  // ../contracts/abis/external/erc20.ts
7
12
  var erc20 = [
@@ -2740,6 +2745,8 @@ var externalAbis = {
2740
2745
  [base.id]: {
2741
2746
  },
2742
2747
  [baseSepolia.id]: {
2748
+ },
2749
+ [hyperEvm.id]: {
2743
2750
  }
2744
2751
  });
2745
2752
  ({
@@ -2748,6 +2755,8 @@ var externalAbis = {
2748
2755
  [base.id]: {
2749
2756
  },
2750
2757
  [baseSepolia.id]: {
2758
+ },
2759
+ [hyperEvm.id]: {
2751
2760
  }
2752
2761
  });
2753
2762
  var relayAddress = "0xc81Fd894C0acE037d133aF4886550aC8133568E8";
@@ -2763,6 +2772,10 @@ var addressBook_default = {
2763
2772
  [baseSepolia.id]: {
2764
2773
  address: relayAddress,
2765
2774
  block: 40585325
2775
+ },
2776
+ [hyperEvm.id]: {
2777
+ address: relayAddress,
2778
+ block: 37892152
2766
2779
  }
2767
2780
  };
2768
2781
  var ContractFactory = class {
@@ -2834,24 +2847,98 @@ var ContractFactory = class {
2834
2847
 
2835
2848
  // ../contracts/index.ts
2836
2849
  var supportedChainIds = Object.keys(addressBook_default).map(Number);
2850
+
2851
+ // src/calls/index.ts
2852
+ var calls_exports = {};
2853
+ __export(calls_exports, {
2854
+ MAX_UINT256: () => MAX_UINT256,
2855
+ WAD: () => WAD,
2856
+ ZERO_BYTES32: () => ZERO_BYTES32,
2857
+ approvalCalls: () => approvalCalls,
2858
+ buildLaunchCalls: () => buildLaunchCalls,
2859
+ createCallsApi: () => createCallsApi,
2860
+ encodeStandardLaunchCalls: () => encodeStandardLaunchCalls,
2861
+ encodeZrpLaunchCalls: () => encodeZrpLaunchCalls,
2862
+ serializeCalls: () => serializeCalls,
2863
+ simulateCalls: () => simulateCalls,
2864
+ validateLaunchCallInput: () => validateLaunchCallInput
2865
+ });
2866
+
2867
+ // src/utils/native.ts
2868
+ function shouldUseNative(explicit, config) {
2869
+ return explicit ?? !!config?.defaultUseNative;
2870
+ }
2871
+ function valueForNative(useNative, amount) {
2872
+ return useNative ? amount : void 0;
2873
+ }
2874
+ async function simulateCalls(publicClient, calls, opts) {
2875
+ const simulation = await publicClient.simulateCalls({
2876
+ account: opts?.account,
2877
+ calls
2878
+ });
2879
+ if (simulation.results.length !== calls.length) {
2880
+ throw new Error(
2881
+ `Call simulation returned ${simulation.results.length} results for ${calls.length} calls`
2882
+ );
2883
+ }
2884
+ return simulation.results.map((result, index) => {
2885
+ if (!result) {
2886
+ throw new Error(`Call simulation ${index} did not return a result`);
2887
+ }
2888
+ if (result.status === "failure") throw result.error;
2889
+ const call = calls[index];
2890
+ if (!call?.decode) return result.data;
2891
+ return call.decode(result.data);
2892
+ });
2893
+ }
2894
+ function contractCall(input) {
2895
+ return {
2896
+ to: input.to,
2897
+ data: encodeFunctionData({
2898
+ abi: input.abi,
2899
+ functionName: input.functionName,
2900
+ args: input.args
2901
+ }),
2902
+ value: input.value,
2903
+ decode: (data) => {
2904
+ const result = decodeFunctionResult({
2905
+ abi: input.abi,
2906
+ functionName: input.functionName,
2907
+ data
2908
+ });
2909
+ return input.mapResult ? input.mapResult(result) : result;
2910
+ }
2911
+ };
2912
+ }
2913
+ function serializeCalls(calls) {
2914
+ return calls.map((call) => ({
2915
+ to: call.to,
2916
+ data: call.data,
2917
+ value: toHex(call.value ?? 0n)
2918
+ }));
2919
+ }
2920
+ var WAD = 10n ** 18n;
2921
+ var ZERO_BYTES32 = "0x0000000000000000000000000000000000000000000000000000000000000000";
2922
+ var DEFAULT_SWAP_FEE_PCT = WAD / 100n;
2923
+ var MIN_SWAP_FEE_PCT = 1500000000000000n;
2924
+ var MAX_SWAP_FEE_PCT = WAD / 2n;
2925
+ var MIN_TOTAL_SUPPLY = 10000n * WAD;
2926
+ var MAX_TOTAL_SUPPLY = 20282409603651670423947251286015n;
2927
+ var MIN_INVARIANT = 3n * WAD;
2837
2928
  function encodeBaseLaunchCalls(input) {
2838
2929
  return [
2839
- {
2930
+ contractCall({
2840
2931
  to: input.relay,
2841
- data: encodeFunctionData({
2842
- abi: mercuryAbis.bFactory,
2843
- functionName: "createBToken",
2844
- args: [input.name, input.symbol, input.totalSupply, input.salt]
2845
- })
2846
- },
2847
- {
2932
+ abi: mercuryAbis.bFactory,
2933
+ functionName: "createBToken",
2934
+ args: [input.name, input.symbol, input.totalSupply, input.salt]
2935
+ }),
2936
+ contractCall({
2848
2937
  to: input.bToken,
2849
- data: encodeFunctionData({
2850
- abi: externalAbis.erc20,
2851
- functionName: "approve",
2852
- args: [input.relay, input.bTokenApprovalAmount]
2853
- })
2854
- }
2938
+ abi: externalAbis.erc20,
2939
+ functionName: "approve",
2940
+ args: [input.relay, input.bTokenApprovalAmount]
2941
+ })
2855
2942
  ];
2856
2943
  }
2857
2944
  function encodeZrpLaunchCalls(input) {
@@ -2860,14 +2947,12 @@ function encodeZrpLaunchCalls(input) {
2860
2947
  ...input,
2861
2948
  bTokenApprovalAmount: input.params.initialPoolBTokens
2862
2949
  }),
2863
- {
2950
+ contractCall({
2864
2951
  to: input.relay,
2865
- data: encodeFunctionData({
2866
- abi: mercuryAbis.bFactory,
2867
- functionName: "createPoolFromInvariant",
2868
- args: [input.params]
2869
- })
2870
- }
2952
+ abi: mercuryAbis.bFactory,
2953
+ functionName: "createPoolFromInvariant",
2954
+ args: [input.params]
2955
+ })
2871
2956
  ];
2872
2957
  }
2873
2958
  function encodeStandardLaunchCalls(input) {
@@ -2876,36 +2961,81 @@ function encodeStandardLaunchCalls(input) {
2876
2961
  ...input,
2877
2962
  bTokenApprovalAmount: input.params.initialPoolBTokens
2878
2963
  }),
2879
- {
2964
+ contractCall({
2880
2965
  to: input.reserve,
2881
- data: encodeFunctionData({
2882
- abi: externalAbis.erc20,
2883
- functionName: "approve",
2884
- args: [input.relay, input.params.initialPoolReserves]
2885
- })
2886
- },
2887
- {
2966
+ abi: externalAbis.erc20,
2967
+ functionName: "approve",
2968
+ args: [input.relay, input.params.initialPoolReserves]
2969
+ }),
2970
+ contractCall({
2888
2971
  to: input.relay,
2889
- data: encodeFunctionData({
2890
- abi: mercuryAbis.bFactory,
2891
- functionName: "createPool",
2892
- args: [input.params]
2893
- })
2894
- }
2972
+ abi: mercuryAbis.bFactory,
2973
+ functionName: "createPool",
2974
+ args: [input.params]
2975
+ })
2895
2976
  ];
2896
2977
  }
2897
-
2898
- // src/launch/constants.ts
2899
- var WAD = 10n ** 18n;
2900
- var ZERO_BYTES32 = "0x0000000000000000000000000000000000000000000000000000000000000000";
2901
- var DEFAULT_SWAP_FEE_PCT = WAD / 100n;
2902
- var MIN_SWAP_FEE_PCT = 1500000000000000n;
2903
- var MAX_SWAP_FEE_PCT = WAD / 2n;
2904
- var MIN_TOTAL_SUPPLY = 10000n * WAD;
2905
- var MAX_TOTAL_SUPPLY = 20282409603651670423947251286015n;
2906
- var MIN_INVARIANT = 3n * WAD;
2907
-
2908
- // src/launch/validate.ts
2978
+ function buildLaunchCalls(input) {
2979
+ const salt = normalizeSalt(input.salt);
2980
+ const { mode, swapFeePct, feeRecipient } = resolveLaunchDefaults(input);
2981
+ if (mode === "zrp") {
2982
+ const params2 = {
2983
+ bToken: input.bToken,
2984
+ initialPoolBTokens: input.initialPoolBTokens,
2985
+ reserve: input.reserve,
2986
+ initialInvariant: MIN_INVARIANT,
2987
+ creator: input.creator,
2988
+ feeRecipient,
2989
+ creatorFeePct: input.creatorFeePct,
2990
+ swapFeePct,
2991
+ createHook: true
2992
+ };
2993
+ return encodeZrpLaunchCalls({
2994
+ relay: input.relay,
2995
+ bToken: input.bToken,
2996
+ name: input.name,
2997
+ symbol: input.symbol,
2998
+ totalSupply: input.totalSupply,
2999
+ salt,
3000
+ params: params2
3001
+ });
3002
+ }
3003
+ const initialPoolReserves = input.initialPoolReserves ?? 0n;
3004
+ const circulatingSupply = input.totalSupply - input.initialPoolBTokens;
3005
+ const reservesWad = toWad(initialPoolReserves, input.reserveDecimals ?? 18);
3006
+ const circulatingWad = toWad(circulatingSupply, 18);
3007
+ const bookPrice = divWad(reservesWad, circulatingWad);
3008
+ const params = {
3009
+ bToken: input.bToken,
3010
+ initialPoolBTokens: input.initialPoolBTokens,
3011
+ reserve: input.reserve,
3012
+ initialPoolReserves,
3013
+ initialActivePrice: bookPrice + 1n,
3014
+ initialBLV: 0n,
3015
+ creator: input.creator,
3016
+ feeRecipient,
3017
+ creatorFeePct: input.creatorFeePct,
3018
+ swapFeePct,
3019
+ createHook: true,
3020
+ claimMerkleRoot: ZERO_BYTES32,
3021
+ initialCollateral: 0n,
3022
+ initialDebt: 0n
3023
+ };
3024
+ return encodeStandardLaunchCalls({
3025
+ relay: input.relay,
3026
+ bToken: input.bToken,
3027
+ reserve: input.reserve,
3028
+ name: input.name,
3029
+ symbol: input.symbol,
3030
+ totalSupply: input.totalSupply,
3031
+ salt,
3032
+ params
3033
+ });
3034
+ }
3035
+ function validateLaunchCallInput(input) {
3036
+ normalizeSalt(input.salt);
3037
+ resolveLaunchDefaults(input);
3038
+ }
2909
3039
  function normalizeSalt(salt) {
2910
3040
  if (!salt) return ZERO_BYTES32;
2911
3041
  if (!/^0x[a-fA-F0-9]{64}$/.test(salt)) {
@@ -2913,24 +3043,6 @@ function normalizeSalt(salt) {
2913
3043
  }
2914
3044
  return salt;
2915
3045
  }
2916
- function validateAddress(address, label) {
2917
- if (!isAddress(address)) throw new Error(`${label} must be a valid address`);
2918
- }
2919
- function validateTokenText(name, symbol) {
2920
- if (name.trim().length === 0) throw new Error("name is required");
2921
- if (symbol.trim().length === 0) throw new Error("symbol is required");
2922
- if (new TextEncoder().encode(name).length > 30) {
2923
- throw new Error("name exceeds 30 bytes");
2924
- }
2925
- if (new TextEncoder().encode(symbol).length > 30) {
2926
- throw new Error("symbol exceeds 30 bytes");
2927
- }
2928
- }
2929
- function validateDecimals(decimals, label) {
2930
- if (!Number.isInteger(decimals) || decimals < 0 || decimals > 18) {
2931
- throw new Error(`${label} must be an integer between 0 and 18`);
2932
- }
2933
- }
2934
3046
  function resolveLaunchDefaults(input) {
2935
3047
  const mode = input.mode ?? "zrp";
2936
3048
  if (mode !== "zrp" && mode !== "standard") {
@@ -2980,66 +3092,23 @@ function resolveLaunchDefaults(input) {
2980
3092
  }
2981
3093
  return { mode, swapFeePct, feeRecipient };
2982
3094
  }
2983
-
2984
- // src/launch/calls.ts
2985
- function buildLaunchCalls(input) {
2986
- const salt = normalizeSalt(input.salt);
2987
- const { mode, swapFeePct, feeRecipient } = resolveLaunchDefaults(input);
2988
- if (mode === "zrp") {
2989
- const params2 = {
2990
- bToken: input.bToken,
2991
- initialPoolBTokens: input.initialPoolBTokens,
2992
- reserve: input.reserve,
2993
- initialInvariant: MIN_INVARIANT,
2994
- creator: input.creator,
2995
- feeRecipient,
2996
- creatorFeePct: input.creatorFeePct,
2997
- swapFeePct,
2998
- createHook: true
2999
- };
3000
- return encodeZrpLaunchCalls({
3001
- relay: input.relay,
3002
- bToken: input.bToken,
3003
- name: input.name,
3004
- symbol: input.symbol,
3005
- totalSupply: input.totalSupply,
3006
- salt,
3007
- params: params2
3008
- });
3095
+ function validateAddress(address, label) {
3096
+ if (!isAddress(address)) throw new Error(`${label} must be a valid address`);
3097
+ }
3098
+ function validateTokenText(name, symbol) {
3099
+ if (name.trim().length === 0) throw new Error("name is required");
3100
+ if (symbol.trim().length === 0) throw new Error("symbol is required");
3101
+ if (new TextEncoder().encode(name).length > 30) {
3102
+ throw new Error("name exceeds 30 bytes");
3103
+ }
3104
+ if (new TextEncoder().encode(symbol).length > 30) {
3105
+ throw new Error("symbol exceeds 30 bytes");
3106
+ }
3107
+ }
3108
+ function validateDecimals(decimals, label) {
3109
+ if (!Number.isInteger(decimals) || decimals < 0 || decimals > 18) {
3110
+ throw new Error(`${label} must be an integer between 0 and 18`);
3009
3111
  }
3010
- const initialPoolReserves = input.initialPoolReserves ?? 0n;
3011
- const circulatingSupply = input.totalSupply - input.initialPoolBTokens;
3012
- const reservesWad = toWad(initialPoolReserves, input.reserveDecimals ?? 18);
3013
- const circulatingWad = toWad(circulatingSupply, 18);
3014
- const bookPrice = divWad(reservesWad, circulatingWad);
3015
- const initialActivePrice = bookPrice + 1n;
3016
- const initialBLV = 0n;
3017
- const params = {
3018
- bToken: input.bToken,
3019
- initialPoolBTokens: input.initialPoolBTokens,
3020
- reserve: input.reserve,
3021
- initialPoolReserves,
3022
- initialActivePrice,
3023
- initialBLV,
3024
- creator: input.creator,
3025
- feeRecipient,
3026
- creatorFeePct: input.creatorFeePct,
3027
- swapFeePct,
3028
- createHook: true,
3029
- claimMerkleRoot: ZERO_BYTES32,
3030
- initialCollateral: 0n,
3031
- initialDebt: 0n
3032
- };
3033
- return encodeStandardLaunchCalls({
3034
- relay: input.relay,
3035
- bToken: input.bToken,
3036
- reserve: input.reserve,
3037
- name: input.name,
3038
- symbol: input.symbol,
3039
- totalSupply: input.totalSupply,
3040
- salt,
3041
- params
3042
- });
3043
3112
  }
3044
3113
  function toWad(amount, decimals) {
3045
3114
  return amount * 10n ** BigInt(18 - decimals);
@@ -3047,9 +3116,157 @@ function toWad(amount, decimals) {
3047
3116
  function divWad(numerator, denominator) {
3048
3117
  return numerator * WAD / denominator;
3049
3118
  }
3050
- function validateLaunchCallInput(input) {
3051
- normalizeSalt(input.salt);
3052
- resolveLaunchDefaults(input);
3119
+
3120
+ // src/calls/index.ts
3121
+ var MAX_UINT256 = 2n ** 256n - 1n;
3122
+ function createCallsApi(input) {
3123
+ const relay = () => input.getRelay();
3124
+ return {
3125
+ launch: input.launch,
3126
+ factory: {
3127
+ createBToken: (name, symbol, totalSupply, salt) => contractCall({
3128
+ to: relay(),
3129
+ abi: mercuryAbis.bFactory,
3130
+ functionName: "createBToken",
3131
+ args: [name, symbol, totalSupply, salt]
3132
+ }),
3133
+ createPool: (params) => contractCall({
3134
+ to: relay(),
3135
+ abi: mercuryAbis.bFactory,
3136
+ functionName: "createPool",
3137
+ args: [params]
3138
+ }),
3139
+ createPoolFromInvariant: (params) => contractCall({
3140
+ to: relay(),
3141
+ abi: mercuryAbis.bFactory,
3142
+ functionName: "createPoolFromInvariant",
3143
+ args: [params]
3144
+ })
3145
+ },
3146
+ swap: {
3147
+ buyTokensExactOut: (bToken, amountOut, limitAmount, opts) => contractCall({
3148
+ to: relay(),
3149
+ abi: mercuryAbis.bSwap,
3150
+ functionName: "buyTokensExactOut",
3151
+ args: [bToken, amountOut, limitAmount],
3152
+ value: valueForNative(
3153
+ shouldUseNative(opts?.useNative, input.getConfig()),
3154
+ limitAmount
3155
+ )
3156
+ }),
3157
+ buyTokensExactIn: (bToken, amountIn, limitAmount) => contractCall({
3158
+ to: relay(),
3159
+ abi: mercuryAbis.bSwap,
3160
+ functionName: "buyTokensExactIn",
3161
+ args: [bToken, amountIn, limitAmount]
3162
+ }),
3163
+ sellTokensExactIn: (bToken, amountIn, limitAmount) => contractCall({
3164
+ to: relay(),
3165
+ abi: mercuryAbis.bSwap,
3166
+ functionName: "sellTokensExactIn",
3167
+ args: [bToken, amountIn, limitAmount]
3168
+ }),
3169
+ sellTokensExactOut: (bToken, amountOut, limitAmount) => contractCall({
3170
+ to: relay(),
3171
+ abi: mercuryAbis.bSwap,
3172
+ functionName: "sellTokensExactOut",
3173
+ args: [bToken, amountOut, limitAmount]
3174
+ })
3175
+ },
3176
+ staking: {
3177
+ deposit: (bToken, user, amount) => contractCall({
3178
+ to: relay(),
3179
+ abi: mercuryAbis.bStaking,
3180
+ functionName: "deposit",
3181
+ args: [bToken, user, amount]
3182
+ }),
3183
+ withdraw: (bToken, amount) => contractCall({
3184
+ to: relay(),
3185
+ abi: mercuryAbis.bStaking,
3186
+ functionName: "withdraw",
3187
+ args: [bToken, amount]
3188
+ }),
3189
+ claim: (bToken, user, asNative = false) => contractCall({
3190
+ to: relay(),
3191
+ abi: mercuryAbis.bStaking,
3192
+ functionName: "claim",
3193
+ args: [bToken, user, asNative]
3194
+ })
3195
+ },
3196
+ credit: {
3197
+ borrow: (bToken, amount, recipient, opts) => contractCall({
3198
+ to: relay(),
3199
+ abi: mercuryAbis.bCredit,
3200
+ functionName: opts?.outputNative ? "borrowNative" : "borrow",
3201
+ args: [bToken, amount, recipient]
3202
+ }),
3203
+ repay: (bToken, reservesIn, recipient, opts) => {
3204
+ const useNative = shouldUseNative(opts?.useNative, input.getConfig());
3205
+ return contractCall({
3206
+ to: relay(),
3207
+ abi: mercuryAbis.bCredit,
3208
+ functionName: useNative ? "repayWithNative" : "repay",
3209
+ args: useNative ? [bToken, recipient] : [bToken, reservesIn, recipient],
3210
+ value: useNative ? reservesIn : void 0
3211
+ });
3212
+ },
3213
+ leverage: (bToken, totalCollateral, collateralIn, maxSwapReservesIn) => contractCall({
3214
+ to: relay(),
3215
+ abi: mercuryAbis.bCredit,
3216
+ functionName: "leverage",
3217
+ args: [bToken, totalCollateral, collateralIn, maxSwapReservesIn]
3218
+ }),
3219
+ deleverage: (bToken, collateralToSell, minSwapReservesOut) => contractCall({
3220
+ to: relay(),
3221
+ abi: mercuryAbis.bCredit,
3222
+ functionName: "deleverage",
3223
+ args: [bToken, collateralToSell, minSwapReservesOut],
3224
+ mapResult: ([collateralRedeemed, debtRepaid, refund]) => ({
3225
+ collateralRedeemed,
3226
+ debtRepaid,
3227
+ refund
3228
+ })
3229
+ })
3230
+ },
3231
+ approval: {
3232
+ approve: (token, spender, amount) => contractCall({
3233
+ to: token,
3234
+ abi: externalAbis.erc20,
3235
+ functionName: "approve",
3236
+ args: [spender, amount]
3237
+ }),
3238
+ ensure: async (token, spender, required, opts) => {
3239
+ const owner = opts?.owner ?? input.getAccount();
3240
+ const policy = opts?.policy ?? input.getConfig()?.approvals ?? "infinite";
3241
+ const currentAllowance = await input.getAllowance(
3242
+ token,
3243
+ owner,
3244
+ spender
3245
+ );
3246
+ return approvalCalls({
3247
+ token,
3248
+ spender,
3249
+ required,
3250
+ currentAllowance,
3251
+ policy
3252
+ });
3253
+ }
3254
+ }
3255
+ };
3256
+ }
3257
+ function approvalCalls(input) {
3258
+ if (input.currentAllowance >= input.required) return [];
3259
+ return [
3260
+ contractCall({
3261
+ to: input.token,
3262
+ abi: externalAbis.erc20,
3263
+ functionName: "approve",
3264
+ args: [
3265
+ input.spender,
3266
+ input.policy === "infinite" ? MAX_UINT256 : input.required
3267
+ ]
3268
+ })
3269
+ ];
3053
3270
  }
3054
3271
  var SDKError = class extends Error {
3055
3272
  kind = "unknown";
@@ -3143,6 +3360,17 @@ async function requireWallet(wallet) {
3143
3360
  });
3144
3361
  return wallet;
3145
3362
  }
3363
+ function resolveWriteAccount(wallet, sender) {
3364
+ const walletAccount = wallet.account;
3365
+ if (!walletAccount) return sender;
3366
+ if (walletAccount.address.toLowerCase() !== sender.toLowerCase()) {
3367
+ throw new SDKError(
3368
+ `Wallet account ${walletAccount.address} cannot sign for requested account ${sender}`,
3369
+ { kind: "wallet" }
3370
+ );
3371
+ }
3372
+ return walletAccount;
3373
+ }
3146
3374
  async function simulateAndWrite({
3147
3375
  publicClient,
3148
3376
  walletClient,
@@ -3171,7 +3399,82 @@ async function simulateAndWrite({
3171
3399
  account: sender,
3172
3400
  value
3173
3401
  });
3174
- const hash = await wallet.writeContract(simulation.request);
3402
+ const hash = await wallet.writeContract({
3403
+ ...simulation.request,
3404
+ account: resolveWriteAccount(wallet, sender)
3405
+ });
3406
+ if (confirmations) {
3407
+ const receipt = await publicClient.waitForTransactionReceipt({
3408
+ hash,
3409
+ confirmations
3410
+ });
3411
+ if (receipt.status === "reverted") {
3412
+ throw new SDKError("Transaction reverted on-chain", {
3413
+ kind: "reverted",
3414
+ cause: { hash, receipt }
3415
+ });
3416
+ }
3417
+ }
3418
+ return hash;
3419
+ } catch (e) {
3420
+ onSimulateError?.(e);
3421
+ throw classifyTxError(e);
3422
+ }
3423
+ }
3424
+ async function executeCalls({
3425
+ publicClient,
3426
+ walletClient,
3427
+ calls,
3428
+ account,
3429
+ confirmations,
3430
+ onSimulateError
3431
+ }) {
3432
+ const wallet = await requireWallet(walletClient);
3433
+ const sender = account ?? wallet.account?.address;
3434
+ if (!sender) {
3435
+ throw new SDKError(
3436
+ "No account provided and wallet missing default account",
3437
+ {
3438
+ kind: "wallet"
3439
+ }
3440
+ );
3441
+ }
3442
+ if (calls.length === 0) {
3443
+ throw new SDKError("At least one call is required", { kind: "unknown" });
3444
+ }
3445
+ try {
3446
+ const simulation = await publicClient.simulateCalls({
3447
+ account: sender,
3448
+ calls
3449
+ });
3450
+ for (const [index, result] of simulation.results.entries()) {
3451
+ if (!result) {
3452
+ throw new SDKError(`Call simulation ${index} did not return a result`);
3453
+ }
3454
+ if (result.status === "failure") {
3455
+ const error = classifyTxError(result.error);
3456
+ if (error.kind === "unknown" && result.error instanceof Error) {
3457
+ throw new SDKError(result.error.message, {
3458
+ kind: "reverted",
3459
+ cause: result.error
3460
+ });
3461
+ }
3462
+ throw error;
3463
+ }
3464
+ }
3465
+ const { id } = await sendCalls(wallet, {
3466
+ account: resolveWriteAccount(wallet, sender),
3467
+ calls,
3468
+ experimental_fallback: true
3469
+ });
3470
+ const status = await waitForCallsStatus(wallet, {
3471
+ id,
3472
+ throwOnFailure: true
3473
+ });
3474
+ const hash = status.receipts?.[0]?.transactionHash;
3475
+ if (!hash) {
3476
+ throw new SDKError("Calls bundle did not return a transaction hash");
3477
+ }
3175
3478
  if (confirmations) {
3176
3479
  const receipt = await publicClient.waitForTransactionReceipt({
3177
3480
  hash,
@@ -3206,34 +3509,6 @@ async function getAllowance(client, token, owner, spender) {
3206
3509
  });
3207
3510
  return allowance;
3208
3511
  }
3209
- async function ensureAllowance(params) {
3210
- const current = await getAllowance(
3211
- params.publicClient,
3212
- params.token,
3213
- params.owner,
3214
- params.spender
3215
- );
3216
- if (current >= params.required) return;
3217
- const amount = params.policy === "infinite" ? 2n ** 256n - 1n : params.required;
3218
- await simulateAndWrite({
3219
- publicClient: params.publicClient,
3220
- walletClient: params.walletClient,
3221
- address: params.token,
3222
- abi: externalAbis.erc20,
3223
- functionName: "approve",
3224
- args: [params.spender, amount],
3225
- account: params.owner,
3226
- confirmations: params.confirmations
3227
- });
3228
- }
3229
-
3230
- // src/utils/native.ts
3231
- function shouldUseNative(explicit, config) {
3232
- return explicit ?? !!config?.defaultUseNative;
3233
- }
3234
- function valueForNative(useNative, amount) {
3235
- return useNative ? amount : void 0;
3236
- }
3237
3512
 
3238
3513
  // src/baseline-sdk.ts
3239
3514
  var ZERO_ADDRESS = "0x0000000000000000000000000000000000000000";
@@ -3242,9 +3517,13 @@ var BaselineSDK = class _BaselineSDK {
3242
3517
  walletClient;
3243
3518
  config;
3244
3519
  readFactory;
3245
- calls = {
3520
+ calls = createCallsApi({
3521
+ getRelay: () => this.proxy,
3522
+ getConfig: () => this.config,
3523
+ getAccount: () => this.getAccount(),
3524
+ getAllowance: (token, owner, spender) => this.getAllowance(token, owner, spender),
3246
3525
  launch: (input, opts) => this.launchCalls(input, opts)
3247
- };
3526
+ });
3248
3527
  getAccount(opts) {
3249
3528
  const account = opts?.account ?? this.walletClient?.account?.address;
3250
3529
  if (!account) {
@@ -3295,7 +3574,10 @@ var BaselineSDK = class _BaselineSDK {
3295
3574
  account
3296
3575
  });
3297
3576
  const wallet = this.requireWallet();
3298
- const hash = await wallet.writeContract(request);
3577
+ const hash = await wallet.writeContract({
3578
+ ...request,
3579
+ account: resolveWriteAccount(wallet, account)
3580
+ });
3299
3581
  if (opts?.confirmations)
3300
3582
  await this.publicClient.waitForTransactionReceipt({
3301
3583
  hash,
@@ -3361,7 +3643,7 @@ var BaselineSDK = class _BaselineSDK {
3361
3643
  bToken: "0x0000000000000000000000000000000000000000",
3362
3644
  salt
3363
3645
  });
3364
- const bToken = await this.precomputeBTokenAddress({
3646
+ const bToken = opts?.precomputedBToken ?? await this.precomputeBTokenAddress({
3365
3647
  name: input.name,
3366
3648
  symbol: input.symbol,
3367
3649
  totalSupply: input.totalSupply,
@@ -3414,18 +3696,22 @@ var BaselineSDK = class _BaselineSDK {
3414
3696
  }
3415
3697
  // ---------- Swap execution ----------
3416
3698
  async buyTokensExactOut(bToken, amountOut, limitAmount, opts) {
3417
- const useNative = shouldUseNative(opts?.useNative, this.config);
3418
3699
  const account = this.getAccount(opts);
3419
- const value = valueForNative(useNative, limitAmount);
3700
+ const call = this.calls.swap.buyTokensExactOut(
3701
+ bToken,
3702
+ amountOut,
3703
+ limitAmount,
3704
+ opts
3705
+ );
3420
3706
  return simulateAndWrite({
3421
3707
  publicClient: this.publicClient,
3422
3708
  walletClient: this.walletClient,
3423
- address: this.proxy,
3709
+ address: call.to,
3424
3710
  abi: mercuryAbis.bSwap,
3425
3711
  functionName: "buyTokensExactOut",
3426
3712
  args: [bToken, amountOut, limitAmount],
3427
3713
  account,
3428
- value,
3714
+ value: call.value,
3429
3715
  confirmations: opts?.confirmations,
3430
3716
  onSimulateError: opts?.onSimulateError
3431
3717
  });
@@ -3490,23 +3776,20 @@ var BaselineSDK = class _BaselineSDK {
3490
3776
  }
3491
3777
  async withdraw(bToken, amount, opts) {
3492
3778
  const account = this.getAccount(opts);
3493
- return simulateAndWrite({
3779
+ return executeCalls({
3494
3780
  publicClient: this.publicClient,
3495
3781
  walletClient: this.walletClient,
3496
- address: this.proxy,
3497
- abi: mercuryAbis.bStaking,
3498
- functionName: "withdraw",
3499
- args: [bToken, amount],
3782
+ calls: [this.calls.staking.withdraw(bToken, amount)],
3500
3783
  account,
3501
3784
  confirmations: opts?.confirmations,
3502
3785
  onSimulateError: opts?.onSimulateError
3503
3786
  });
3504
3787
  }
3505
3788
  async claim(bToken, opts) {
3506
- const wallet = this.requireWallet();
3507
3789
  const account = this.getAccount(opts);
3508
3790
  const user = opts?.user ?? account;
3509
3791
  const asNative = opts?.asNative ?? false;
3792
+ const wallet = this.requireWallet();
3510
3793
  try {
3511
3794
  const { result, request } = await this.publicClient.simulateContract({
3512
3795
  address: this.proxy,
@@ -3515,7 +3798,10 @@ var BaselineSDK = class _BaselineSDK {
3515
3798
  args: [bToken, user, asNative],
3516
3799
  account
3517
3800
  });
3518
- const hash = await wallet.writeContract(request);
3801
+ const hash = await wallet.writeContract({
3802
+ ...request,
3803
+ account: resolveWriteAccount(wallet, account)
3804
+ });
3519
3805
  if (opts?.confirmations)
3520
3806
  await this.publicClient.waitForTransactionReceipt({
3521
3807
  hash,
@@ -3566,13 +3852,12 @@ var BaselineSDK = class _BaselineSDK {
3566
3852
  }
3567
3853
  async borrow(bToken, amount, recipient, opts) {
3568
3854
  const account = this.getAccount(opts);
3569
- const functionName = opts?.outputNative ? "borrowNative" : "borrow";
3570
3855
  return simulateAndWrite({
3571
3856
  publicClient: this.publicClient,
3572
3857
  walletClient: this.walletClient,
3573
3858
  address: this.proxy,
3574
3859
  abi: mercuryAbis.bCredit,
3575
- functionName,
3860
+ functionName: opts?.outputNative ? "borrowNative" : "borrow",
3576
3861
  args: [bToken, amount, recipient],
3577
3862
  account,
3578
3863
  confirmations: opts?.confirmations,
@@ -3580,20 +3865,18 @@ var BaselineSDK = class _BaselineSDK {
3580
3865
  });
3581
3866
  }
3582
3867
  async repay(bToken, reservesIn, recipient, opts) {
3583
- const useNative = shouldUseNative(opts?.useNative, this.config);
3584
3868
  const account = this.getAccount(opts);
3585
- const functionName = useNative ? "repayWithNative" : "repay";
3586
- const args = useNative ? [bToken, recipient] : [bToken, reservesIn, recipient];
3587
- const value = valueForNative(useNative, reservesIn);
3869
+ const call = this.calls.credit.repay(bToken, reservesIn, recipient, opts);
3870
+ const useNative = shouldUseNative(opts?.useNative, this.config);
3588
3871
  return simulateAndWrite({
3589
3872
  publicClient: this.publicClient,
3590
3873
  walletClient: this.walletClient,
3591
- address: this.proxy,
3874
+ address: call.to,
3592
3875
  abi: mercuryAbis.bCredit,
3593
- functionName,
3594
- args,
3876
+ functionName: useNative ? "repayWithNative" : "repay",
3877
+ args: useNative ? [bToken, recipient] : [bToken, reservesIn, recipient],
3595
3878
  account,
3596
- value,
3879
+ value: call.value,
3597
3880
  confirmations: opts?.confirmations,
3598
3881
  onSimulateError: opts?.onSimulateError
3599
3882
  });
@@ -3682,6 +3965,15 @@ var BaselineSDK = class _BaselineSDK {
3682
3965
  userAccumulator
3683
3966
  };
3684
3967
  }
3968
+ async getEarned(bToken, user) {
3969
+ const earned = await this.publicClient.readContract({
3970
+ address: this.proxy,
3971
+ abi: mercuryAbis.bStaking,
3972
+ functionName: "getEarned",
3973
+ args: [bToken, user]
3974
+ });
3975
+ return earned;
3976
+ }
3685
3977
  async getCreditAccount(bToken, user) {
3686
3978
  const [collateral, debt] = await this.publicClient.readContract({
3687
3979
  address: this.proxy,
@@ -3721,21 +4013,17 @@ var BaselineSDK = class _BaselineSDK {
3721
4013
  async ensureApproval(token, spender, required, opts) {
3722
4014
  const account = this.getAccount(opts);
3723
4015
  const policy = opts?.policy ?? this.config?.approvals ?? "infinite";
3724
- await ensureAllowance({
3725
- publicClient: this.publicClient,
3726
- walletClient: this.walletClient,
3727
- token,
4016
+ const calls = await this.calls.approval.ensure(token, spender, required, {
3728
4017
  owner: account,
3729
- spender,
3730
- required,
3731
- policy,
3732
- confirmations: opts?.confirmations
4018
+ policy
3733
4019
  });
4020
+ const [call] = calls;
4021
+ if (!call) return;
4022
+ const amount = policy === "infinite" ? 2n ** 256n - 1n : required;
4023
+ await this.approve(token, spender, amount, opts);
3734
4024
  }
3735
4025
  // ---------- Lens queries ----------
3736
4026
  async getBTokenInfo(bToken) {
3737
- const bytecode = await this.publicClient.getBytecode({ address: bToken });
3738
- const hasBytecode = !!bytecode && bytecode !== "0x";
3739
4027
  const results = await this.publicClient.multicall({
3740
4028
  allowFailure: true,
3741
4029
  contracts: [
@@ -3822,14 +4110,10 @@ var BaselineSDK = class _BaselineSDK {
3822
4110
  const reserveDecimals = normalizeQuoteState(
3823
4111
  result(12)
3824
4112
  )?.reserveDecimals;
3825
- const hasBaselineState = reserve !== void 0 && reserve.toLowerCase() !== ZERO_ADDRESS && maker !== void 0;
3826
- const status = !hasBytecode ? "not_deployed" : !hasBaselineState ? "contract_only" : maker.initialized ? "initialized" : "baseline_uninitialized";
3827
4113
  return {
3828
4114
  chainId: this.chainId,
3829
4115
  relay: this.proxy,
3830
4116
  bToken,
3831
- status,
3832
- bytecode: hasBytecode,
3833
4117
  name,
3834
4118
  symbol,
3835
4119
  decimals,
@@ -3845,6 +4129,15 @@ var BaselineSDK = class _BaselineSDK {
3845
4129
  maker
3846
4130
  };
3847
4131
  }
4132
+ async getBTokenStatus(bToken, info) {
4133
+ const bytecode = await this.publicClient.getCode({ address: bToken });
4134
+ const hasBytecode = !!bytecode && bytecode !== "0x";
4135
+ const tokenInfo = info ?? await this.getBTokenInfo(bToken);
4136
+ const hasBaselineState = tokenInfo.reserve !== void 0 && tokenInfo.reserve.toLowerCase() !== ZERO_ADDRESS && tokenInfo.maker !== void 0;
4137
+ const maker = tokenInfo.maker;
4138
+ const status = !hasBytecode ? "not_deployed" : !hasBaselineState ? "contract_only" : maker?.initialized ? "initialized" : "baseline_uninitialized";
4139
+ return { status, bytecode: hasBytecode };
4140
+ }
3848
4141
  async getReserve(bToken) {
3849
4142
  const reserve = await this.publicClient.readContract({
3850
4143
  address: this.proxy,
@@ -3906,12 +4199,21 @@ function normalizeQuoteState(value) {
3906
4199
  const reserveDecimals = Array.isArray(value) ? value[6] : value.reserveDecimals;
3907
4200
  return typeof reserveDecimals === "number" ? { reserveDecimals } : void 0;
3908
4201
  }
3909
- function serializeCalls(calls) {
3910
- return calls.map((call) => ({
3911
- to: call.to,
3912
- data: call.data,
3913
- value: toHex(call.value ?? 0n)
3914
- }));
4202
+
4203
+ // src/utils/slippage.ts
4204
+ function maxInWithSlippage(amountIn, slippageBps) {
4205
+ if (slippageBps < 0) throw new Error("slippageBps must be >= 0");
4206
+ return amountIn * BigInt(1e4 + slippageBps) / 10000n;
3915
4207
  }
4208
+ function minOutWithSlippage(amountOut, slippageBps) {
4209
+ if (slippageBps < 0) throw new Error("slippageBps must be >= 0");
4210
+ const numerator = amountOut * 10000n;
4211
+ const denom = BigInt(1e4 + slippageBps);
4212
+ return numerator / denom;
4213
+ }
4214
+
4215
+ // index.ts
4216
+ var abis = mercuryAbis;
4217
+ var supportedChainIds2 = supportedChainIds;
3916
4218
 
3917
- export { BaselineSDK, SDKError, mercuryAbis as abis, serializeCalls, supportedChainIds };
4219
+ export { BaselineSDK, SDKError, abis, calls_exports as calls, maxInWithSlippage, minOutWithSlippage, serializeCalls, simulateCalls, supportedChainIds2 as supportedChainIds };