@continuumdao/ctm-mpc-defi 0.2.0 → 0.2.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 +20 -78
- package/dist/agent/catalog.cjs +563 -5
- package/dist/agent/catalog.cjs.map +1 -1
- package/dist/agent/catalog.d.ts +166 -20
- package/dist/agent/catalog.js +551 -7
- package/dist/agent/catalog.js.map +1 -1
- package/dist/agent/skills/aave-v4/SKILL.md +43 -0
- package/dist/agent/skills/curve-dao/SKILL.md +13 -0
- package/dist/agent/skills/ethena/SKILL.md +10 -0
- package/dist/agent/skills/euler-v2/SKILL.md +10 -0
- package/dist/agent/skills/lido/SKILL.md +22 -0
- package/dist/agent/skills/maple-syrup/SKILL.md +10 -0
- package/dist/agent/skills/sky/SKILL.md +10 -0
- package/dist/agent/skills/uniswap-v4/SKILL.md +22 -0
- package/dist/chains/evm/index.cjs +79 -224
- package/dist/chains/evm/index.cjs.map +1 -1
- package/dist/chains/evm/index.d.ts +26 -26
- package/dist/chains/evm/index.js +69 -209
- package/dist/chains/evm/index.js.map +1 -1
- package/dist/chains/near/index.d.ts +1 -1
- package/dist/chains/solana/index.d.ts +1 -1
- package/dist/core/index.cjs +68 -106
- package/dist/core/index.cjs.map +1 -1
- package/dist/core/index.d.ts +21 -36
- package/dist/core/index.js +57 -96
- package/dist/core/index.js.map +1 -1
- package/dist/{envelope-CcE5Cz_q.d.ts → envelope-CpBUh9eP.d.ts} +1 -1
- package/dist/index.cjs +356 -1855
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +7 -11
- package/dist/index.js +332 -1826
- package/dist/index.js.map +1 -1
- package/dist/protocols/evm/aave-v4/index.cjs +1152 -669
- package/dist/protocols/evm/aave-v4/index.cjs.map +1 -1
- package/dist/protocols/evm/aave-v4/index.d.ts +418 -3
- package/dist/protocols/evm/aave-v4/index.js +1126 -670
- package/dist/protocols/evm/aave-v4/index.js.map +1 -1
- package/dist/protocols/evm/curve-dao/index.cjs +257 -131
- package/dist/protocols/evm/curve-dao/index.cjs.map +1 -1
- package/dist/protocols/evm/curve-dao/index.d.ts +69 -5
- package/dist/protocols/evm/curve-dao/index.js +242 -124
- package/dist/protocols/evm/curve-dao/index.js.map +1 -1
- package/dist/protocols/evm/ethena/index.cjs +394 -402
- package/dist/protocols/evm/ethena/index.cjs.map +1 -1
- package/dist/protocols/evm/ethena/index.d.ts +47 -3
- package/dist/protocols/evm/ethena/index.js +390 -404
- package/dist/protocols/evm/ethena/index.js.map +1 -1
- package/dist/protocols/evm/euler-v2/index.cjs +2810 -1191
- package/dist/protocols/evm/euler-v2/index.cjs.map +1 -1
- package/dist/protocols/evm/euler-v2/index.d.ts +465 -3
- package/dist/protocols/evm/euler-v2/index.js +2761 -1192
- package/dist/protocols/evm/euler-v2/index.js.map +1 -1
- package/dist/protocols/evm/lido/index.cjs +351 -236
- package/dist/protocols/evm/lido/index.cjs.map +1 -1
- package/dist/protocols/evm/lido/index.d.ts +34 -4
- package/dist/protocols/evm/lido/index.js +348 -238
- package/dist/protocols/evm/lido/index.js.map +1 -1
- package/dist/protocols/evm/maple/index.cjs +390 -395
- package/dist/protocols/evm/maple/index.cjs.map +1 -1
- package/dist/protocols/evm/maple/index.d.ts +23 -3
- package/dist/protocols/evm/maple/index.js +390 -397
- package/dist/protocols/evm/maple/index.js.map +1 -1
- package/dist/protocols/evm/sky/index.cjs +454 -232
- package/dist/protocols/evm/sky/index.cjs.map +1 -1
- package/dist/protocols/evm/sky/index.d.ts +57 -3
- package/dist/protocols/evm/sky/index.js +444 -231
- package/dist/protocols/evm/sky/index.js.map +1 -1
- package/dist/protocols/evm/uniswap-v4/index.cjs +423 -658
- package/dist/protocols/evm/uniswap-v4/index.cjs.map +1 -1
- package/dist/protocols/evm/uniswap-v4/index.d.ts +3 -4
- package/dist/protocols/evm/uniswap-v4/index.js +422 -657
- package/dist/protocols/evm/uniswap-v4/index.js.map +1 -1
- package/dist/{registry-oMKlO_5z.d.ts → registry-Bv5o37_w.d.ts} +1 -1
- package/dist/{types-Ce2qNHai.d.cts → types-BfjWdw1j.d.ts} +3 -1
- package/dist/{types-5u863Fd9.d.ts → types-DUeNJLr9.d.ts} +1 -1
- package/package.json +7 -6
- package/dist/agent/catalog.d.cts +0 -939
- package/dist/chains/evm/index.d.cts +0 -64
- package/dist/chains/near/index.d.cts +0 -37
- package/dist/chains/solana/index.d.cts +0 -40
- package/dist/core/index.d.cts +0 -43
- package/dist/envelope-DYDPnrHZ.d.cts +0 -35
- package/dist/index.d.cts +0 -16
- package/dist/keygen-CfNp8yKJ.d.cts +0 -9
- package/dist/keygen-DsINazx8.d.ts +0 -9
- package/dist/nodeRead-BnmSaMGO.d.cts +0 -8
- package/dist/nodeRead-BnmSaMGO.d.ts +0 -8
- package/dist/protocols/evm/aave-v4/index.d.cts +0 -500
- package/dist/protocols/evm/curve-dao/index.d.cts +0 -147
- package/dist/protocols/evm/ethena/index.d.cts +0 -161
- package/dist/protocols/evm/euler-v2/index.d.cts +0 -317
- package/dist/protocols/evm/lido/index.d.cts +0 -120
- package/dist/protocols/evm/maple/index.d.cts +0 -109
- package/dist/protocols/evm/sky/index.d.cts +0 -218
- package/dist/protocols/evm/uniswap-v4/index.d.cts +0 -324
- package/dist/registry-BwZoE668.d.cts +0 -8
- package/dist/txParams-BC7ogvdR.d.cts +0 -19
- package/dist/txParams-BC7ogvdR.d.ts +0 -19
- package/dist/types-B8idm_gu.d.cts +0 -34
- package/dist/types-Ce2qNHai.d.ts +0 -57
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
3
|
var viem = require('viem');
|
|
4
|
+
var continuumNodeSdk = require('@continuumdao/continuum-node-sdk');
|
|
4
5
|
|
|
5
6
|
// src/core/registry.ts
|
|
6
7
|
var modules = [];
|
|
@@ -25,266 +26,291 @@ var SKY_LOCKSTAKE_DEFAULT_FARM_REF = 1;
|
|
|
25
26
|
var SKY_LOCKSTAKE_UI_COLLATERAL_FACTOR = 0.65;
|
|
26
27
|
var SKY_TOKEN_DECIMALS = 18;
|
|
27
28
|
var USDS_DECIMALS = 18;
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
const
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
rpcUrls: { default: { http: [url] } }
|
|
38
|
-
});
|
|
39
|
-
const publicClient = viem.createPublicClient({
|
|
40
|
-
chain,
|
|
41
|
-
transport: viem.http(url)
|
|
42
|
-
});
|
|
43
|
-
const getGasPriceGwei = async () => {
|
|
44
|
-
const gasPriceWei = await publicClient.getGasPrice();
|
|
45
|
-
return parseFloat(viem.formatUnits(gasPriceWei, 9));
|
|
46
|
-
};
|
|
47
|
-
try {
|
|
48
|
-
const block = await publicClient.getBlock({ blockTag: "latest" });
|
|
49
|
-
const baseFeePerGas = block?.baseFeePerGas;
|
|
50
|
-
if (baseFeePerGas == null || baseFeePerGas === void 0) {
|
|
51
|
-
const gasPriceGwei2 = await getGasPriceGwei();
|
|
52
|
-
return { isEip1559: false, gasPriceGwei: gasPriceGwei2 };
|
|
53
|
-
}
|
|
54
|
-
const baseFeeGwei = parseFloat(viem.formatUnits(baseFeePerGas, 9));
|
|
55
|
-
let priorityFeeGwei;
|
|
56
|
-
try {
|
|
57
|
-
const priorityWei = await publicClient.estimateMaxPriorityFeePerGas();
|
|
58
|
-
priorityFeeGwei = parseFloat(viem.formatUnits(priorityWei, 9));
|
|
59
|
-
} catch {
|
|
60
|
-
}
|
|
61
|
-
const gasPriceGwei = await getGasPriceGwei();
|
|
62
|
-
return {
|
|
63
|
-
isEip1559: true,
|
|
64
|
-
baseFeeGwei,
|
|
65
|
-
priorityFeeGwei,
|
|
66
|
-
gasPriceGwei
|
|
67
|
-
};
|
|
68
|
-
} catch {
|
|
69
|
-
try {
|
|
70
|
-
const gasPriceWei = await publicClient.getGasPrice();
|
|
71
|
-
const gasPriceGwei = parseFloat(viem.formatUnits(gasPriceWei, 9));
|
|
72
|
-
return { isEip1559: false, gasPriceGwei };
|
|
73
|
-
} catch {
|
|
74
|
-
return { isEip1559: false };
|
|
75
|
-
}
|
|
76
|
-
}
|
|
29
|
+
|
|
30
|
+
// src/core/purpose.ts
|
|
31
|
+
function mergePurposeText(purposeText, purposeSuffix) {
|
|
32
|
+
const t = purposeText.trim();
|
|
33
|
+
const suffix = (purposeSuffix ?? "").trim();
|
|
34
|
+
if (!suffix) return t;
|
|
35
|
+
return t ? `${t}
|
|
36
|
+
|
|
37
|
+
${suffix}` : suffix;
|
|
77
38
|
}
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
39
|
+
|
|
40
|
+
// src/core/envelope.ts
|
|
41
|
+
function finalizeMultisign(input) {
|
|
42
|
+
const { keyGen, destinationChainID, legs } = input;
|
|
43
|
+
if (legs.length === 0) {
|
|
44
|
+
throw new Error("finalizeMultisign requires at least one leg");
|
|
83
45
|
}
|
|
84
|
-
|
|
85
|
-
|
|
46
|
+
const ph = (keyGen.pubkeyhex ?? "").trim();
|
|
47
|
+
if (!ph) throw new Error("keyGen pubKey (pubkeyhex) is required");
|
|
48
|
+
const keyList = keyGen.keylist ?? [];
|
|
49
|
+
const clientId = continuumNodeSdk.getClientIdFromKeyGenResult(keyGen);
|
|
50
|
+
const first = legs[0];
|
|
51
|
+
const messageHashes = legs.map((l) => l.msgHash);
|
|
52
|
+
const messageRawBatch = legs.map((l) => l.msgRaw);
|
|
53
|
+
const batchMeta = legs.map((l) => ({
|
|
54
|
+
destinationAddress: l.destinationAddress,
|
|
55
|
+
signatureText: l.signatureText,
|
|
56
|
+
...l.audit
|
|
57
|
+
}));
|
|
58
|
+
const proposalTxParams = legs.map((l) => l.proposalTxParams).filter((p) => p != null && typeof p === "object");
|
|
59
|
+
const extraPayload = {
|
|
60
|
+
batchMeta,
|
|
61
|
+
...input.extraJSON ?? {}
|
|
62
|
+
};
|
|
63
|
+
const extraJSON = JSON.stringify(extraPayload);
|
|
64
|
+
const bodyForSign = {
|
|
65
|
+
keyList,
|
|
66
|
+
pubKey: ph,
|
|
67
|
+
msgHash: messageHashes[0],
|
|
68
|
+
msgRaw: first.msgRaw,
|
|
69
|
+
destinationChainID,
|
|
70
|
+
destinationAddress: input.destinationAddress ?? first.destinationAddress,
|
|
71
|
+
extraJSON,
|
|
72
|
+
signatureText: first.signatureText,
|
|
73
|
+
purpose: mergePurposeText(input.purposeText, input.purposeSuffix),
|
|
74
|
+
...first.feeSnapshot
|
|
75
|
+
};
|
|
76
|
+
if (legs.length > 1) {
|
|
77
|
+
bodyForSign.messageHashes = messageHashes;
|
|
78
|
+
bodyForSign.messageRawBatch = messageRawBatch;
|
|
86
79
|
}
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
// src/chains/evm/txParams.ts
|
|
94
|
-
function gasLimitFromEstimateAndChainConfig(estimatedGas, chainGasLimit) {
|
|
95
|
-
if (chainGasLimit == null || !Number.isFinite(chainGasLimit) || chainGasLimit <= 0) {
|
|
96
|
-
return estimatedGas;
|
|
80
|
+
if (proposalTxParams.length > 0) {
|
|
81
|
+
bodyForSign.proposalTxParams = proposalTxParams;
|
|
82
|
+
}
|
|
83
|
+
const valueWei = first.valueWei;
|
|
84
|
+
if (valueWei != null && valueWei > 0n) {
|
|
85
|
+
bodyForSign.value = valueWei.toString();
|
|
97
86
|
}
|
|
98
|
-
|
|
99
|
-
return
|
|
87
|
+
if (clientId) bodyForSign.clientId = clientId;
|
|
88
|
+
return { bodyForSign, messageToSign: JSON.stringify(bodyForSign) };
|
|
100
89
|
}
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
const map = data?.ClientKeys;
|
|
105
|
-
if (!map || typeof map !== "object") return null;
|
|
106
|
-
for (const v of Object.values(map)) {
|
|
107
|
-
if (typeof v === "string" && v.trim()) return v.trim();
|
|
90
|
+
function routerSwapGasLimitFromEstimate(estimatedGas, chainGasLimit) {
|
|
91
|
+
if (chainGasLimit != null && Number.isFinite(chainGasLimit) && chainGasLimit > 0) {
|
|
92
|
+
return continuumNodeSdk.gasLimitFromEstimateAndChainConfig(estimatedGas, chainGasLimit);
|
|
108
93
|
}
|
|
109
|
-
return
|
|
94
|
+
return (estimatedGas * 12n + 9n) / 10n;
|
|
110
95
|
}
|
|
111
96
|
|
|
112
|
-
// src/
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
if (s.indexOf("e") !== -1 || s.indexOf("E") !== -1) return n.toFixed(9).replace(/\.?0+$/, "") || "0";
|
|
145
|
-
return s;
|
|
146
|
-
}
|
|
147
|
-
async function appendSerializedSkyBatch(args) {
|
|
148
|
-
const ph = (args.keyGen.pubkeyhex ?? "").trim();
|
|
149
|
-
if (!ph) throw new Error("keyGen pubKey (pubkeyhex) is required");
|
|
150
|
-
const keyList = args.keyGen.keylist ?? [];
|
|
151
|
-
const clientId = firstClientIdFromKeyGen(args.keyGen);
|
|
152
|
-
const feeParams = await fetchChainFeeParams(args.rpcUrl, args.chainId);
|
|
153
|
-
const legacy = Boolean(args.chainDetail?.legacy) || !feeParams.isEip1559;
|
|
154
|
-
const latestBaseFeeWei = !legacy ? (await args.publicClient.getBlock({ blockTag: "latest" })).baseFeePerGas ?? 0n : 0n;
|
|
155
|
-
const useCustomGas = args.useCustomGas;
|
|
156
|
-
const gasLimitConfig = useCustomGas && args.chainDetail?.gasLimit != null ? Number(args.chainDetail.gasLimit) : void 0;
|
|
157
|
-
const gasFeeMultiplier = useCustomGas && args.chainDetail?.gasMultiplier != null ? Number(args.chainDetail.gasMultiplier) : void 0;
|
|
158
|
-
const baseNonce = await args.publicClient.getTransactionCount({ address: args.executor, blockTag: "pending" });
|
|
159
|
-
const messageHashes = [];
|
|
160
|
-
const messageRawBatch = [];
|
|
161
|
-
const proposalTxParamsBatch = [];
|
|
162
|
-
let firstTxFeePayload = {};
|
|
163
|
-
let firstDataNo0x = "";
|
|
164
|
-
for (let i = 0; i < args.steps.length; i++) {
|
|
165
|
-
const s = args.steps[i];
|
|
97
|
+
// src/chains/evm/buildBatch.ts
|
|
98
|
+
async function buildEvmMultisignBatch(args) {
|
|
99
|
+
const { context, steps } = args;
|
|
100
|
+
const {
|
|
101
|
+
chainId,
|
|
102
|
+
rpcUrl,
|
|
103
|
+
executorAddress,
|
|
104
|
+
chainDetail,
|
|
105
|
+
useCustomGas,
|
|
106
|
+
customGasChainDetails,
|
|
107
|
+
keyGen,
|
|
108
|
+
purposeText
|
|
109
|
+
} = context;
|
|
110
|
+
if (steps.length === 0) throw new Error("buildEvmMultisignBatch requires at least one step");
|
|
111
|
+
const ch = viem.defineChain({
|
|
112
|
+
id: chainId,
|
|
113
|
+
name: "Destination",
|
|
114
|
+
nativeCurrency: { decimals: 18, name: "Ether", symbol: "ETH" },
|
|
115
|
+
rpcUrls: { default: { http: [rpcUrl] } }
|
|
116
|
+
});
|
|
117
|
+
const publicClient = viem.createPublicClient({ chain: ch, transport: viem.http(rpcUrl) });
|
|
118
|
+
const feeParams = await continuumNodeSdk.fetchChainFeeParams(rpcUrl, chainId);
|
|
119
|
+
const legacy = Boolean(chainDetail?.legacy) || !feeParams.isEip1559;
|
|
120
|
+
const latestBaseFeeWei = !legacy ? (await publicClient.getBlock({ blockTag: "latest" })).baseFeePerGas ?? 0n : 0n;
|
|
121
|
+
const gasLimitConfig = useCustomGas && chainDetail?.gasLimit != null ? Number(chainDetail.gasLimit) : void 0;
|
|
122
|
+
const chainGasLimitRouter = chainDetail?.gasLimit != null && Number.isFinite(Number(chainDetail.gasLimit)) && Number(chainDetail.gasLimit) > 0 ? Number(chainDetail.gasLimit) : void 0;
|
|
123
|
+
const gasFeeMultiplier = useCustomGas && chainDetail?.gasMultiplier != null ? Number(chainDetail.gasMultiplier) : void 0;
|
|
124
|
+
const executor = viem.getAddress(executorAddress);
|
|
125
|
+
const baseNonce = await publicClient.getTransactionCount({ address: executor, blockTag: "pending" });
|
|
126
|
+
const legs = [];
|
|
127
|
+
for (let i = 0; i < steps.length; i++) {
|
|
128
|
+
const step = steps[i];
|
|
166
129
|
const currentNonce = baseNonce + i;
|
|
167
130
|
let estimatedGas;
|
|
168
|
-
|
|
169
|
-
estimatedGas = await args.
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
131
|
+
if (args.estimateGasForStep) {
|
|
132
|
+
estimatedGas = await args.estimateGasForStep({ step, index: i, publicClient, executor });
|
|
133
|
+
} else {
|
|
134
|
+
try {
|
|
135
|
+
estimatedGas = await publicClient.estimateGas({
|
|
136
|
+
to: step.to,
|
|
137
|
+
data: step.data,
|
|
138
|
+
value: step.value,
|
|
139
|
+
account: executor
|
|
140
|
+
});
|
|
141
|
+
} catch {
|
|
142
|
+
estimatedGas = step.fallbackGas ?? 100000n;
|
|
143
|
+
}
|
|
144
|
+
}
|
|
145
|
+
let gasLimitI;
|
|
146
|
+
if (args.resolveGasLimit) {
|
|
147
|
+
gasLimitI = await args.resolveGasLimit({ step, index: i, estimatedGas, publicClient });
|
|
148
|
+
} else if (step.routerSwap) {
|
|
149
|
+
gasLimitI = routerSwapGasLimitFromEstimate(estimatedGas, chainGasLimitRouter);
|
|
150
|
+
} else {
|
|
151
|
+
gasLimitI = useCustomGas ? continuumNodeSdk.gasLimitFromEstimateAndChainConfig(estimatedGas, gasLimitConfig) : estimatedGas;
|
|
177
152
|
}
|
|
178
|
-
|
|
153
|
+
let proposalTxParams;
|
|
154
|
+
let feeSnapshot;
|
|
155
|
+
let serialized;
|
|
179
156
|
if (legacy) {
|
|
180
|
-
let gasPriceWei = await
|
|
157
|
+
let gasPriceWei = await publicClient.getGasPrice();
|
|
181
158
|
if (useCustomGas && gasFeeMultiplier != null && gasFeeMultiplier > 0) {
|
|
182
159
|
gasPriceWei = gasPriceWei * BigInt(100 + gasFeeMultiplier) / 100n;
|
|
183
160
|
}
|
|
184
|
-
if (useCustomGas &&
|
|
185
|
-
const configured = viem.parseGwei(gweiToDecimalString(Number(
|
|
161
|
+
if (useCustomGas && chainDetail?.gasPrice != null && chainDetail.gasPrice > 0) {
|
|
162
|
+
const configured = viem.parseGwei(continuumNodeSdk.gweiToDecimalString(Number(chainDetail.gasPrice)));
|
|
186
163
|
if (configured > gasPriceWei) gasPriceWei = configured;
|
|
187
164
|
}
|
|
188
|
-
|
|
165
|
+
serialized = viem.serializeTransaction({
|
|
189
166
|
type: "legacy",
|
|
190
|
-
to:
|
|
191
|
-
data:
|
|
192
|
-
value:
|
|
167
|
+
to: step.to,
|
|
168
|
+
data: step.data,
|
|
169
|
+
value: step.value,
|
|
193
170
|
gas: gasLimitI,
|
|
194
171
|
gasPrice: gasPriceWei,
|
|
195
172
|
nonce: currentNonce,
|
|
196
|
-
chainId
|
|
173
|
+
chainId
|
|
197
174
|
});
|
|
198
|
-
|
|
199
|
-
messageHashes.push(h.startsWith("0x") ? h.slice(2) : h);
|
|
200
|
-
messageRawBatch.push(ser);
|
|
201
|
-
proposalTxParamsBatch.push({
|
|
175
|
+
proposalTxParams = {
|
|
202
176
|
nonce: currentNonce,
|
|
203
177
|
gasLimit: gasLimitI.toString(),
|
|
204
178
|
txType: "legacy",
|
|
205
179
|
gasPrice: gasPriceWei.toString()
|
|
206
|
-
}
|
|
207
|
-
|
|
208
|
-
firstTxFeePayload = { txNonce: currentNonce, txGasLimit: gasLimitI.toString(), txGasPrice: gasPriceWei.toString() };
|
|
209
|
-
firstDataNo0x = s.data.startsWith("0x") ? s.data.slice(2) : s.data;
|
|
210
|
-
}
|
|
180
|
+
};
|
|
181
|
+
feeSnapshot = continuumNodeSdk.proposalTxParamsToFeeSnapshot(proposalTxParams);
|
|
211
182
|
} else {
|
|
212
183
|
const fetchedBase = feeParams.baseFeeGwei ?? 0;
|
|
213
184
|
const fetchedPriority = feeParams.priorityFeeGwei ?? 0;
|
|
214
|
-
const configuredBase = useCustomGas &&
|
|
215
|
-
const configuredPriority = useCustomGas &&
|
|
185
|
+
const configuredBase = useCustomGas && chainDetail?.baseFee != null ? Number(chainDetail.baseFee) : 0;
|
|
186
|
+
const configuredPriority = useCustomGas && chainDetail?.priorityFee != null ? Number(chainDetail.priorityFee) : 0;
|
|
216
187
|
const effectiveBaseFeeGwei = Math.max(fetchedBase, configuredBase);
|
|
217
188
|
const effectivePriorityFeeGwei = Math.max(fetchedPriority, configuredPriority);
|
|
218
|
-
const baseFeeMultiplierPct = useCustomGas &&
|
|
189
|
+
const baseFeeMultiplierPct = useCustomGas && chainDetail?.baseFeeMultiplier != null ? Math.max(100, Number(chainDetail.baseFeeMultiplier)) : 100;
|
|
219
190
|
const baseComponentGwei = effectiveBaseFeeGwei * baseFeeMultiplierPct / 100;
|
|
220
191
|
const maxFeePerGasGwei = baseComponentGwei + effectivePriorityFeeGwei;
|
|
221
|
-
let maxPriorityFeePerGas = effectivePriorityFeeGwei > 0 ? viem.parseGwei(gweiToDecimalString(effectivePriorityFeeGwei)) : viem.parseGwei("1");
|
|
222
|
-
let maxFeePerGas = viem.parseGwei(gweiToDecimalString(maxFeePerGasGwei));
|
|
192
|
+
let maxPriorityFeePerGas = effectivePriorityFeeGwei > 0 ? viem.parseGwei(continuumNodeSdk.gweiToDecimalString(effectivePriorityFeeGwei)) : viem.parseGwei("1");
|
|
193
|
+
let maxFeePerGas = viem.parseGwei(continuumNodeSdk.gweiToDecimalString(maxFeePerGasGwei));
|
|
223
194
|
if (useCustomGas && gasFeeMultiplier != null && gasFeeMultiplier > 0) {
|
|
224
195
|
maxPriorityFeePerGas = maxPriorityFeePerGas * BigInt(100 + gasFeeMultiplier) / 100n;
|
|
225
196
|
maxFeePerGas = maxFeePerGas * BigInt(100 + gasFeeMultiplier) / 100n;
|
|
226
197
|
}
|
|
227
|
-
({ maxFeePerGas, maxPriorityFeePerGas } = alignEip1559FeesWithLatestBase(
|
|
198
|
+
({ maxFeePerGas, maxPriorityFeePerGas } = continuumNodeSdk.alignEip1559FeesWithLatestBase(
|
|
228
199
|
maxFeePerGas,
|
|
229
200
|
maxPriorityFeePerGas,
|
|
230
201
|
latestBaseFeeWei
|
|
231
202
|
));
|
|
232
|
-
|
|
203
|
+
serialized = viem.serializeTransaction({
|
|
233
204
|
type: "eip1559",
|
|
234
|
-
to:
|
|
235
|
-
data:
|
|
236
|
-
value:
|
|
205
|
+
to: step.to,
|
|
206
|
+
data: step.data,
|
|
207
|
+
value: step.value,
|
|
237
208
|
gas: gasLimitI,
|
|
238
209
|
maxFeePerGas,
|
|
239
210
|
maxPriorityFeePerGas,
|
|
240
211
|
nonce: currentNonce,
|
|
241
|
-
chainId
|
|
212
|
+
chainId
|
|
242
213
|
});
|
|
243
|
-
|
|
244
|
-
messageHashes.push(h.startsWith("0x") ? h.slice(2) : h);
|
|
245
|
-
messageRawBatch.push(ser);
|
|
246
|
-
proposalTxParamsBatch.push({
|
|
214
|
+
proposalTxParams = {
|
|
247
215
|
nonce: currentNonce,
|
|
248
216
|
gasLimit: gasLimitI.toString(),
|
|
249
217
|
txType: "eip1559",
|
|
250
218
|
maxFeePerGas: maxFeePerGas.toString(),
|
|
251
219
|
maxPriorityFeePerGas: maxPriorityFeePerGas.toString()
|
|
252
|
-
}
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
220
|
+
};
|
|
221
|
+
feeSnapshot = i === 0 ? continuumNodeSdk.proposalTxParamsToFeeSnapshot(proposalTxParams) : {};
|
|
222
|
+
}
|
|
223
|
+
const h = viem.keccak256(serialized);
|
|
224
|
+
const msgHash = h.startsWith("0x") ? h.slice(2) : h;
|
|
225
|
+
const batchMetaExtra = args.buildBatchMeta({ step, index: i, gasLimit: gasLimitI });
|
|
226
|
+
legs.push({
|
|
227
|
+
msgHash,
|
|
228
|
+
msgRaw: i === 0 && args.firstMsgRawNo0x != null ? args.firstMsgRawNo0x : serialized,
|
|
229
|
+
destinationAddress: step.to,
|
|
230
|
+
signatureText: typeof batchMetaExtra.signatureText === "string" ? batchMetaExtra.signatureText : JSON.stringify(batchMetaExtra.signatureText ?? {}),
|
|
231
|
+
audit: batchMetaExtra,
|
|
232
|
+
feeSnapshot: i === 0 ? feeSnapshot : {},
|
|
233
|
+
proposalTxParams,
|
|
234
|
+
valueWei: i === 0 ? step.value : void 0
|
|
235
|
+
});
|
|
236
|
+
if (i === 0 && args.firstMsgRawNo0x != null) {
|
|
237
|
+
legs[0].msgRaw = args.firstMsgRawNo0x;
|
|
262
238
|
}
|
|
263
239
|
}
|
|
264
|
-
const
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
extraPayload.customGasChainDetails = args.customGasChainDetails;
|
|
240
|
+
const extraJSON = {};
|
|
241
|
+
if (useCustomGas && customGasChainDetails && Object.keys(customGasChainDetails).length > 0) {
|
|
242
|
+
extraJSON.customGasChainDetails = customGasChainDetails;
|
|
268
243
|
}
|
|
269
|
-
const
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
244
|
+
const result = finalizeMultisign({
|
|
245
|
+
keyGen,
|
|
246
|
+
purposeText,
|
|
247
|
+
purposeSuffix: args.purposeSuffix,
|
|
248
|
+
destinationChainID: String(chainId),
|
|
249
|
+
destinationAddress: args.destinationAddress ?? steps[0].to,
|
|
250
|
+
legs,
|
|
251
|
+
extraJSON: Object.keys(extraJSON).length > 0 ? extraJSON : void 0
|
|
252
|
+
});
|
|
253
|
+
const pv = args.payableValueWei;
|
|
254
|
+
if (pv != null && pv > 0n) {
|
|
255
|
+
result.bodyForSign.value = pv.toString();
|
|
256
|
+
}
|
|
257
|
+
return result;
|
|
258
|
+
}
|
|
259
|
+
|
|
260
|
+
// src/protocols/evm/sky/lockstakeMultisign.ts
|
|
261
|
+
var SKY_LOCKSTAKE_MULTICALL_FALLBACK_GAS = 5000000n;
|
|
262
|
+
var erc20AllowanceAbi = viem.parseAbi([
|
|
263
|
+
"function allowance(address owner, address spender) view returns (uint256)",
|
|
264
|
+
"function decimals() view returns (uint8)"
|
|
265
|
+
]);
|
|
266
|
+
var erc20ApproveAbi = viem.parseAbi(["function approve(address spender, uint256 amount) returns (bool)"]);
|
|
267
|
+
var engineAbi = viem.parseAbi([
|
|
268
|
+
"function multicall(bytes[] data) returns (bytes[])",
|
|
269
|
+
"function open(uint256 index) returns (address)",
|
|
270
|
+
"function selectFarm(address owner, uint256 index, address farm, uint16 ref)",
|
|
271
|
+
/** Canonical SKY collateral (pulls ERC-20 `sky()`, then `mkrSky.skyToMkr`). Legacy `lock` pulls MKR only. */
|
|
272
|
+
"function lockSky(address owner, uint256 index, uint256 skyWad, uint16 ref)",
|
|
273
|
+
"function draw(address owner, uint256 index, address to, uint256 wad)",
|
|
274
|
+
"function wipe(address owner, uint256 index, uint256 wad)",
|
|
275
|
+
"function wipeAll(address owner, uint256 index) returns (uint256 wad)",
|
|
276
|
+
/** Returns withdrawn SKY; legacy `free` returns MKR after fee-burn. */
|
|
277
|
+
"function freeSky(address owner, uint256 index, address to, uint256 skyWad) returns (uint256 skyFreed)",
|
|
278
|
+
"function getReward(address owner, uint256 index, address farm, address to) returns (uint256)",
|
|
279
|
+
"function ownerUrnsCount(address usr) view returns (uint256)",
|
|
280
|
+
"function ownerUrns(address owner, uint256 index) view returns (address urn)",
|
|
281
|
+
"function urnFarms(address urn) view returns (address farm)",
|
|
282
|
+
"function farms(address farm) view returns (uint8)"
|
|
283
|
+
]);
|
|
284
|
+
var stakingRewardsFarmReadAbi = viem.parseAbi([
|
|
285
|
+
"function stakingToken() view returns (address)",
|
|
286
|
+
"function rewardsToken() view returns (address)"
|
|
287
|
+
]);
|
|
288
|
+
async function appendSerializedSkyBatch(args) {
|
|
289
|
+
const evmSteps = args.steps.map((s) => ({
|
|
290
|
+
to: s.to,
|
|
291
|
+
data: s.data,
|
|
292
|
+
value: s.value,
|
|
293
|
+
fallbackGas: SKY_LOCKSTAKE_MULTICALL_FALLBACK_GAS
|
|
294
|
+
}));
|
|
295
|
+
const firstDataNo0x = evmSteps[0].data.startsWith("0x") ? evmSteps[0].data.slice(2) : evmSteps[0].data;
|
|
296
|
+
return buildEvmMultisignBatch({
|
|
297
|
+
context: {
|
|
298
|
+
chainCategory: "evm",
|
|
299
|
+
keyGen: args.keyGen,
|
|
300
|
+
purposeText: "",
|
|
301
|
+
chainId: args.chainId,
|
|
302
|
+
rpcUrl: args.rpcUrl,
|
|
303
|
+
executorAddress: args.executor,
|
|
304
|
+
chainDetail: args.chainDetail,
|
|
305
|
+
useCustomGas: args.useCustomGas,
|
|
306
|
+
customGasChainDetails: args.customGasChainDetails
|
|
307
|
+
},
|
|
308
|
+
steps: evmSteps,
|
|
309
|
+
purposeSuffix: args.purposePrefix,
|
|
310
|
+
firstMsgRawNo0x: firstDataNo0x,
|
|
279
311
|
destinationAddress: args.steps[0].to,
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
purpose: args.purposePrefix,
|
|
283
|
-
...firstTxFeePayload,
|
|
284
|
-
proposalTxParams: proposalTxParamsBatch
|
|
285
|
-
};
|
|
286
|
-
if (clientId) bodyForSign.clientId = clientId;
|
|
287
|
-
return { bodyForSign, messageToSign: JSON.stringify(bodyForSign) };
|
|
312
|
+
buildBatchMeta: ({ index }) => args.steps[index].meta
|
|
313
|
+
});
|
|
288
314
|
}
|
|
289
315
|
async function buildSkyLockstakeStakePositionBatch(args) {
|
|
290
316
|
if (args.chainId !== 1) throw new Error("Sky LockStake is only supported on Ethereum mainnet (chain id 1).");
|
|
@@ -523,7 +549,6 @@ async function buildSkyLockstakeStakePositionBatch(args) {
|
|
|
523
549
|
})();
|
|
524
550
|
return appendSerializedSkyBatch({
|
|
525
551
|
steps,
|
|
526
|
-
publicClient,
|
|
527
552
|
executor,
|
|
528
553
|
chainId: 1,
|
|
529
554
|
rpcUrl: rpc,
|
|
@@ -531,9 +556,7 @@ async function buildSkyLockstakeStakePositionBatch(args) {
|
|
|
531
556
|
useCustomGas: args.useCustomGas,
|
|
532
557
|
customGasChainDetails: args.customGasChainDetails,
|
|
533
558
|
purposePrefix,
|
|
534
|
-
keyGen: args.keyGen
|
|
535
|
-
destinationChainID: "1"
|
|
536
|
-
});
|
|
559
|
+
keyGen: args.keyGen});
|
|
537
560
|
}
|
|
538
561
|
async function buildSkyLockstakeDrawBatch(args) {
|
|
539
562
|
if (args.chainId !== 1) throw new Error("Sky LockStake is only supported on Ethereum mainnet (chain id 1).");
|
|
@@ -591,7 +614,6 @@ async function buildSkyLockstakeDrawBatch(args) {
|
|
|
591
614
|
})();
|
|
592
615
|
return appendSerializedSkyBatch({
|
|
593
616
|
steps,
|
|
594
|
-
publicClient,
|
|
595
617
|
executor,
|
|
596
618
|
chainId: 1,
|
|
597
619
|
rpcUrl: rpc,
|
|
@@ -599,9 +621,7 @@ async function buildSkyLockstakeDrawBatch(args) {
|
|
|
599
621
|
useCustomGas: args.useCustomGas,
|
|
600
622
|
customGasChainDetails: args.customGasChainDetails,
|
|
601
623
|
purposePrefix,
|
|
602
|
-
keyGen: args.keyGen
|
|
603
|
-
destinationChainID: "1"
|
|
604
|
-
});
|
|
624
|
+
keyGen: args.keyGen});
|
|
605
625
|
}
|
|
606
626
|
async function buildSkyLockstakeGetRewardBatch(args) {
|
|
607
627
|
if (args.chainId !== 1) throw new Error("Sky LockStake is only supported on Ethereum mainnet (chain id 1).");
|
|
@@ -670,7 +690,6 @@ async function buildSkyLockstakeGetRewardBatch(args) {
|
|
|
670
690
|
})();
|
|
671
691
|
const built = await appendSerializedSkyBatch({
|
|
672
692
|
steps,
|
|
673
|
-
publicClient,
|
|
674
693
|
executor,
|
|
675
694
|
chainId: 1,
|
|
676
695
|
rpcUrl: rpc,
|
|
@@ -678,9 +697,7 @@ async function buildSkyLockstakeGetRewardBatch(args) {
|
|
|
678
697
|
useCustomGas: args.useCustomGas,
|
|
679
698
|
customGasChainDetails: args.customGasChainDetails,
|
|
680
699
|
purposePrefix,
|
|
681
|
-
keyGen: args.keyGen
|
|
682
|
-
destinationChainID: "1"
|
|
683
|
-
});
|
|
700
|
+
keyGen: args.keyGen});
|
|
684
701
|
return { ...built, rewardToken };
|
|
685
702
|
}
|
|
686
703
|
async function buildSkyLockstakeWipeBatch(args) {
|
|
@@ -827,7 +844,6 @@ async function buildSkyLockstakeWipeBatch(args) {
|
|
|
827
844
|
})();
|
|
828
845
|
return appendSerializedSkyBatch({
|
|
829
846
|
steps,
|
|
830
|
-
publicClient,
|
|
831
847
|
executor,
|
|
832
848
|
chainId: 1,
|
|
833
849
|
rpcUrl: rpc,
|
|
@@ -835,9 +851,7 @@ async function buildSkyLockstakeWipeBatch(args) {
|
|
|
835
851
|
useCustomGas: args.useCustomGas,
|
|
836
852
|
customGasChainDetails: args.customGasChainDetails,
|
|
837
853
|
purposePrefix,
|
|
838
|
-
keyGen: args.keyGen
|
|
839
|
-
destinationChainID: "1"
|
|
840
|
-
});
|
|
854
|
+
keyGen: args.keyGen});
|
|
841
855
|
}
|
|
842
856
|
async function buildSkyLockstakeCloseBatch(args) {
|
|
843
857
|
if (args.chainId !== 1) throw new Error("Sky LockStake is only supported on Ethereum mainnet (chain id 1).");
|
|
@@ -849,7 +863,7 @@ async function buildSkyLockstakeCloseBatch(args) {
|
|
|
849
863
|
nativeCurrency: { decimals: 18, name: "Ether", symbol: "ETH" },
|
|
850
864
|
rpcUrls: { default: { http: [rpc] } }
|
|
851
865
|
});
|
|
852
|
-
|
|
866
|
+
viem.createPublicClient({ chain: ch, transport: viem.http(rpc) });
|
|
853
867
|
const executor = viem.getAddress(args.executorAddress);
|
|
854
868
|
const engine = viem.getAddress(SKY_LOCKSTAKE_ENGINE_MAINNET);
|
|
855
869
|
const usds = viem.getAddress(USDS_ETHEREUM_MAINNET);
|
|
@@ -927,7 +941,6 @@ async function buildSkyLockstakeCloseBatch(args) {
|
|
|
927
941
|
})();
|
|
928
942
|
return appendSerializedSkyBatch({
|
|
929
943
|
steps,
|
|
930
|
-
publicClient,
|
|
931
944
|
executor,
|
|
932
945
|
chainId: 1,
|
|
933
946
|
rpcUrl: rpc,
|
|
@@ -935,9 +948,7 @@ async function buildSkyLockstakeCloseBatch(args) {
|
|
|
935
948
|
useCustomGas: args.useCustomGas,
|
|
936
949
|
customGasChainDetails: args.customGasChainDetails,
|
|
937
950
|
purposePrefix,
|
|
938
|
-
keyGen: args.keyGen
|
|
939
|
-
destinationChainID: "1"
|
|
940
|
-
});
|
|
951
|
+
keyGen: args.keyGen});
|
|
941
952
|
}
|
|
942
953
|
var SKY_FRAGILE_ETH_ESTIMATE_GAS_BATCH_EVMS = /* @__PURE__ */ new Set([
|
|
943
954
|
"sky_lockstake_engine_multicall_stake",
|
|
@@ -1066,7 +1077,6 @@ async function buildSkySusdsRedeemToUsdsBatch(args) {
|
|
|
1066
1077
|
})();
|
|
1067
1078
|
return appendSerializedSkyBatch({
|
|
1068
1079
|
steps,
|
|
1069
|
-
publicClient,
|
|
1070
1080
|
executor,
|
|
1071
1081
|
chainId: 1,
|
|
1072
1082
|
rpcUrl: rpc,
|
|
@@ -1074,9 +1084,7 @@ async function buildSkySusdsRedeemToUsdsBatch(args) {
|
|
|
1074
1084
|
useCustomGas: args.useCustomGas,
|
|
1075
1085
|
customGasChainDetails: args.customGasChainDetails,
|
|
1076
1086
|
purposePrefix,
|
|
1077
|
-
keyGen: args.keyGen
|
|
1078
|
-
destinationChainID: "1"
|
|
1079
|
-
});
|
|
1087
|
+
keyGen: args.keyGen});
|
|
1080
1088
|
}
|
|
1081
1089
|
async function buildSkySusdsDepositFromUsdsBatch(args) {
|
|
1082
1090
|
if (args.chainId !== 1) throw new Error("Sky sUSDS deposit is only supported on Ethereum mainnet (chain id 1).");
|
|
@@ -1190,7 +1198,6 @@ async function buildSkySusdsDepositFromUsdsBatch(args) {
|
|
|
1190
1198
|
})();
|
|
1191
1199
|
return appendSerializedSkyBatch({
|
|
1192
1200
|
steps,
|
|
1193
|
-
publicClient,
|
|
1194
1201
|
executor,
|
|
1195
1202
|
chainId: 1,
|
|
1196
1203
|
rpcUrl: rpc,
|
|
@@ -1198,9 +1205,215 @@ async function buildSkySusdsDepositFromUsdsBatch(args) {
|
|
|
1198
1205
|
useCustomGas: args.useCustomGas,
|
|
1199
1206
|
customGasChainDetails: args.customGasChainDetails,
|
|
1200
1207
|
purposePrefix,
|
|
1201
|
-
keyGen: args.keyGen
|
|
1202
|
-
|
|
1208
|
+
keyGen: args.keyGen});
|
|
1209
|
+
}
|
|
1210
|
+
var RAY = 10n ** 27n;
|
|
1211
|
+
var engineAbi2 = viem.parseAbi([
|
|
1212
|
+
"function ownerUrnsCount(address usr) view returns (uint256)",
|
|
1213
|
+
"function ownerUrns(address owner, uint256 index) view returns (address urn)",
|
|
1214
|
+
"function urnFarms(address urn) view returns (address farm)",
|
|
1215
|
+
"function ilk() view returns (bytes32)",
|
|
1216
|
+
"function vat() view returns (address)"
|
|
1217
|
+
]);
|
|
1218
|
+
var vatAbi = viem.parseAbi([
|
|
1219
|
+
"function urns(bytes32 ilk, address urn) view returns (uint256 ink, uint256 art)",
|
|
1220
|
+
"function ilks(bytes32 ilk) view returns (uint256 Art, uint256 rate, uint256 spot, uint256 line, uint256 dust)"
|
|
1221
|
+
]);
|
|
1222
|
+
function skyClient(rpcUrl) {
|
|
1223
|
+
const rpc = rpcUrl.trim();
|
|
1224
|
+
const ch = viem.defineChain({
|
|
1225
|
+
id: 1,
|
|
1226
|
+
name: "Ethereum",
|
|
1227
|
+
nativeCurrency: { decimals: 18, name: "Ether", symbol: "ETH" },
|
|
1228
|
+
rpcUrls: { default: { http: [rpc] } }
|
|
1229
|
+
});
|
|
1230
|
+
return viem.createPublicClient({ chain: ch, transport: viem.http(rpc) });
|
|
1231
|
+
}
|
|
1232
|
+
function skyUsdsDebtWeiFromUrnArt(art, rate) {
|
|
1233
|
+
if (art === 0n || rate === 0n) return 0n;
|
|
1234
|
+
return (art * rate + RAY - 1n) / RAY;
|
|
1235
|
+
}
|
|
1236
|
+
async function loadSkyLockstakePositions(args) {
|
|
1237
|
+
const client = skyClient(args.rpcUrl);
|
|
1238
|
+
const engine = viem.getAddress(SKY_LOCKSTAKE_ENGINE_MAINNET);
|
|
1239
|
+
const ilk = await client.readContract({
|
|
1240
|
+
address: engine,
|
|
1241
|
+
abi: engineAbi2,
|
|
1242
|
+
functionName: "ilk"
|
|
1243
|
+
});
|
|
1244
|
+
const vat = await client.readContract({
|
|
1245
|
+
address: engine,
|
|
1246
|
+
abi: engineAbi2,
|
|
1247
|
+
functionName: "vat"
|
|
1248
|
+
});
|
|
1249
|
+
const count = await client.readContract({
|
|
1250
|
+
address: engine,
|
|
1251
|
+
abi: engineAbi2,
|
|
1252
|
+
functionName: "ownerUrnsCount",
|
|
1253
|
+
args: [args.owner]
|
|
1254
|
+
});
|
|
1255
|
+
const n = Number(count);
|
|
1256
|
+
if (!Number.isFinite(n) || n <= 0) return [];
|
|
1257
|
+
const ilkInfo = await client.readContract({
|
|
1258
|
+
address: vat,
|
|
1259
|
+
abi: vatAbi,
|
|
1260
|
+
functionName: "ilks",
|
|
1261
|
+
args: [ilk]
|
|
1262
|
+
});
|
|
1263
|
+
const rate = ilkInfo[1];
|
|
1264
|
+
const rows = [];
|
|
1265
|
+
for (let index = 0; index < n; index++) {
|
|
1266
|
+
const urn = await client.readContract({
|
|
1267
|
+
address: engine,
|
|
1268
|
+
abi: engineAbi2,
|
|
1269
|
+
functionName: "ownerUrns",
|
|
1270
|
+
args: [args.owner, BigInt(index)]
|
|
1271
|
+
});
|
|
1272
|
+
if (!urn || urn === "0x0000000000000000000000000000000000000000") continue;
|
|
1273
|
+
const u = await client.readContract({
|
|
1274
|
+
address: vat,
|
|
1275
|
+
abi: vatAbi,
|
|
1276
|
+
functionName: "urns",
|
|
1277
|
+
args: [ilk, urn]
|
|
1278
|
+
});
|
|
1279
|
+
const inkWei = u[0];
|
|
1280
|
+
const art = u[1];
|
|
1281
|
+
const debtUsdsWei = skyUsdsDebtWeiFromUrnArt(art, rate);
|
|
1282
|
+
const farm = await client.readContract({
|
|
1283
|
+
address: engine,
|
|
1284
|
+
abi: engineAbi2,
|
|
1285
|
+
functionName: "urnFarms",
|
|
1286
|
+
args: [urn]
|
|
1287
|
+
});
|
|
1288
|
+
const skyHuman = Number(viem.formatUnits(inkWei, SKY_TOKEN_DECIMALS));
|
|
1289
|
+
const debtHuman = Number(viem.formatUnits(debtUsdsWei, USDS_DECIMALS));
|
|
1290
|
+
let borrowLimitUsdApprox = null;
|
|
1291
|
+
if (args.skyUsd != null && Number.isFinite(args.skyUsd) && args.skyUsd > 0) {
|
|
1292
|
+
const collateralUsd = skyHuman * args.skyUsd;
|
|
1293
|
+
const maxDebtUsd = collateralUsd * SKY_LOCKSTAKE_UI_COLLATERAL_FACTOR;
|
|
1294
|
+
borrowLimitUsdApprox = Math.max(0, maxDebtUsd - debtHuman);
|
|
1295
|
+
}
|
|
1296
|
+
rows.push({
|
|
1297
|
+
index,
|
|
1298
|
+
urn,
|
|
1299
|
+
inkWei,
|
|
1300
|
+
art,
|
|
1301
|
+
debtUsdsWei,
|
|
1302
|
+
farm,
|
|
1303
|
+
skyLocked: viem.formatUnits(inkWei, SKY_TOKEN_DECIMALS),
|
|
1304
|
+
debtUsds: viem.formatUnits(debtUsdsWei, USDS_DECIMALS),
|
|
1305
|
+
borrowLimitUsdApprox,
|
|
1306
|
+
skyPriceUsd: args.skyUsd
|
|
1307
|
+
});
|
|
1308
|
+
}
|
|
1309
|
+
return rows;
|
|
1310
|
+
}
|
|
1311
|
+
var farmRewardsTokenAbi = viem.parseAbi(["function rewardsToken() view returns (address)"]);
|
|
1312
|
+
async function readSkyLockstakeFarmRewardsToken(args) {
|
|
1313
|
+
const client = skyClient(args.rpcUrl);
|
|
1314
|
+
const farm = viem.getAddress(args.farm);
|
|
1315
|
+
const zero = "0x0000000000000000000000000000000000000000";
|
|
1316
|
+
if (farm.toLowerCase() === zero.toLowerCase()) {
|
|
1317
|
+
throw new Error("Farm address is zero.");
|
|
1318
|
+
}
|
|
1319
|
+
const tok = await client.readContract({
|
|
1320
|
+
address: farm,
|
|
1321
|
+
abi: farmRewardsTokenAbi,
|
|
1322
|
+
functionName: "rewardsToken"
|
|
1323
|
+
});
|
|
1324
|
+
return viem.getAddress(tok);
|
|
1325
|
+
}
|
|
1326
|
+
var vaultAbi = viem.parseAbi([
|
|
1327
|
+
"function balanceOf(address account) view returns (uint256)",
|
|
1328
|
+
"function decimals() view returns (uint8)",
|
|
1329
|
+
"function previewRedeem(uint256 shares) view returns (uint256 assets)"
|
|
1330
|
+
]);
|
|
1331
|
+
async function readSusdsVaultShareBalanceWei(args) {
|
|
1332
|
+
const rpc = args.rpcUrl.trim();
|
|
1333
|
+
const ch = viem.defineChain({
|
|
1334
|
+
id: 1,
|
|
1335
|
+
name: "Ethereum",
|
|
1336
|
+
nativeCurrency: { decimals: 18, name: "Ether", symbol: "ETH" },
|
|
1337
|
+
rpcUrls: { default: { http: [rpc] } }
|
|
1338
|
+
});
|
|
1339
|
+
const client = viem.createPublicClient({ chain: ch, transport: viem.http(rpc) });
|
|
1340
|
+
const vault = viem.getAddress(SUSDS_VAULT_ERC4626_MAINNET);
|
|
1341
|
+
return client.readContract({
|
|
1342
|
+
address: vault,
|
|
1343
|
+
abi: vaultAbi,
|
|
1344
|
+
functionName: "balanceOf",
|
|
1345
|
+
args: [args.owner]
|
|
1346
|
+
});
|
|
1347
|
+
}
|
|
1348
|
+
async function readSusdsVaultDecimals(args) {
|
|
1349
|
+
const rpc = args.rpcUrl.trim();
|
|
1350
|
+
const ch = viem.defineChain({
|
|
1351
|
+
id: 1,
|
|
1352
|
+
name: "Ethereum",
|
|
1353
|
+
nativeCurrency: { decimals: 18, name: "Ether", symbol: "ETH" },
|
|
1354
|
+
rpcUrls: { default: { http: [rpc] } }
|
|
1355
|
+
});
|
|
1356
|
+
const client = viem.createPublicClient({ chain: ch, transport: viem.http(rpc) });
|
|
1357
|
+
const vault = viem.getAddress(SUSDS_VAULT_ERC4626_MAINNET);
|
|
1358
|
+
const d = await client.readContract({
|
|
1359
|
+
address: vault,
|
|
1360
|
+
abi: vaultAbi,
|
|
1361
|
+
functionName: "decimals"
|
|
1362
|
+
});
|
|
1363
|
+
return Number(d);
|
|
1364
|
+
}
|
|
1365
|
+
async function readSusdsPreviewRedeemAssetsWei(args) {
|
|
1366
|
+
if (args.sharesWei <= 0n) return 0n;
|
|
1367
|
+
const rpc = args.rpcUrl.trim();
|
|
1368
|
+
const ch = viem.defineChain({
|
|
1369
|
+
id: 1,
|
|
1370
|
+
name: "Ethereum",
|
|
1371
|
+
nativeCurrency: { decimals: 18, name: "Ether", symbol: "ETH" },
|
|
1372
|
+
rpcUrls: { default: { http: [rpc] } }
|
|
1203
1373
|
});
|
|
1374
|
+
const client = viem.createPublicClient({ chain: ch, transport: viem.http(rpc) });
|
|
1375
|
+
const vault = viem.getAddress(SUSDS_VAULT_ERC4626_MAINNET);
|
|
1376
|
+
return client.readContract({
|
|
1377
|
+
address: vault,
|
|
1378
|
+
abi: vaultAbi,
|
|
1379
|
+
functionName: "previewRedeem",
|
|
1380
|
+
args: [args.sharesWei]
|
|
1381
|
+
});
|
|
1382
|
+
}
|
|
1383
|
+
function formatSusdsSharesHuman(sharesWei, decimals) {
|
|
1384
|
+
return viem.formatUnits(sharesWei, decimals);
|
|
1385
|
+
}
|
|
1386
|
+
|
|
1387
|
+
// src/core/defiProxy.ts
|
|
1388
|
+
var coingeckoProxyUrl;
|
|
1389
|
+
function getCoingeckoProxyUrl() {
|
|
1390
|
+
return coingeckoProxyUrl;
|
|
1391
|
+
}
|
|
1392
|
+
|
|
1393
|
+
// src/protocols/evm/sky/usdPrice.ts
|
|
1394
|
+
async function fetchSkyUsdFromCoinGecko() {
|
|
1395
|
+
try {
|
|
1396
|
+
const addr = viem.getAddress(SKY_ETHEREUM_MAINNET).toLowerCase();
|
|
1397
|
+
const url = "https://api.coingecko.com/api/v3/simple/token_price/ethereum?contract_addresses=" + encodeURIComponent(addr) + "&vs_currencies=usd";
|
|
1398
|
+
const proxy = getCoingeckoProxyUrl();
|
|
1399
|
+
const res = proxy ? await fetch(proxy, {
|
|
1400
|
+
method: "POST",
|
|
1401
|
+
headers: { "content-type": "application/json" },
|
|
1402
|
+
body: JSON.stringify({ platform: "ethereum", contractAddress: addr })
|
|
1403
|
+
}) : await fetch(url, { cache: "no-store" });
|
|
1404
|
+
if (!res.ok) return null;
|
|
1405
|
+
const raw = await res.json();
|
|
1406
|
+
const row = raw[addr];
|
|
1407
|
+
const n = row?.usd;
|
|
1408
|
+
return typeof n === "number" && Number.isFinite(n) && n > 0 ? n : null;
|
|
1409
|
+
} catch {
|
|
1410
|
+
return null;
|
|
1411
|
+
}
|
|
1412
|
+
}
|
|
1413
|
+
|
|
1414
|
+
// src/protocols/evm/sky/loadLockstakeSupportedChainIds.ts
|
|
1415
|
+
function loadSkyLockstakeSupportedChainIds() {
|
|
1416
|
+
return /* @__PURE__ */ new Set([1]);
|
|
1204
1417
|
}
|
|
1205
1418
|
|
|
1206
1419
|
// src/protocols/evm/sky/index.ts
|
|
@@ -1247,8 +1460,17 @@ exports.buildSkyLockstakeStakePositionBatch = buildSkyLockstakeStakePositionBatc
|
|
|
1247
1460
|
exports.buildSkyLockstakeWipeBatch = buildSkyLockstakeWipeBatch;
|
|
1248
1461
|
exports.buildSkySusdsDepositFromUsdsBatch = buildSkySusdsDepositFromUsdsBatch;
|
|
1249
1462
|
exports.buildSkySusdsRedeemToUsdsBatch = buildSkySusdsRedeemToUsdsBatch;
|
|
1463
|
+
exports.fetchSkyUsdFromCoinGecko = fetchSkyUsdFromCoinGecko;
|
|
1464
|
+
exports.formatSusdsSharesHuman = formatSusdsSharesHuman;
|
|
1250
1465
|
exports.isSkyLockstakeIsolationEstimateGasFragileBatchStep = isSkyLockstakeIsolationEstimateGasFragileBatchStep;
|
|
1466
|
+
exports.loadSkyLockstakePositions = loadSkyLockstakePositions;
|
|
1467
|
+
exports.loadSkyLockstakeSupportedChainIds = loadSkyLockstakeSupportedChainIds;
|
|
1468
|
+
exports.readSkyLockstakeFarmRewardsToken = readSkyLockstakeFarmRewardsToken;
|
|
1469
|
+
exports.readSusdsPreviewRedeemAssetsWei = readSusdsPreviewRedeemAssetsWei;
|
|
1470
|
+
exports.readSusdsVaultDecimals = readSusdsVaultDecimals;
|
|
1471
|
+
exports.readSusdsVaultShareBalanceWei = readSusdsVaultShareBalanceWei;
|
|
1251
1472
|
exports.resolveSkyLockstakeBatchStepGasFromSignRequest = resolveSkyLockstakeBatchStepGasFromSignRequest;
|
|
1252
1473
|
exports.skyProtocolModule = skyProtocolModule;
|
|
1474
|
+
exports.skyUsdsDebtWeiFromUrnArt = skyUsdsDebtWeiFromUrnArt;
|
|
1253
1475
|
//# sourceMappingURL=index.cjs.map
|
|
1254
1476
|
//# sourceMappingURL=index.cjs.map
|