Skip to content

Commit 5eb7068

Browse files
committed
feat: add populateApprove
1 parent f939831 commit 5eb7068

File tree

4 files changed

+56
-1
lines changed

4 files changed

+56
-1
lines changed

README.md

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -181,6 +181,15 @@ import curve from "@curvefi/api";
181181
// '0xb0cada2a2983dc0ed85a26916d32b9caefe45fecde47640bd7d0e214ff22aed3',
182182
// '0x00ea7d827b3ad50ce933e96c579810cd7e70d66a034a86ec4e1e10005634d041'
183183
// ]
184+
185+
// Get populated approve transactions (without executing)
186+
const approveTxs = await curve.populateApprove(["DAI", "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48"], ['1000', '1000'], spender);
187+
// Returns array of TransactionLike objects (may include reset to 0 if needed for some tokens)
188+
console.log(approveTxs);
189+
// [
190+
// { to: '0x6B17...', data: '0x095ea7b3...', from: '0x...', ... },
191+
// { to: '0xA0b8...', data: '0x095ea7b3...', from: '0x...', ... }
192+
// ]
184193
})()
185194
```
186195
@@ -1191,6 +1200,14 @@ import curve from "@curvefi/api";
11911200
// [
11921201
// '0xc111e471715ae6f5437e12d3b94868a5b6542cd7304efca18b5782d315760ae5'
11931202
// ]
1203+
1204+
// Get populated transactions for approve (without executing)
1205+
const approveTxs = await curve.router.populateApprove('DAI', 1000);
1206+
// OR const approveTxs = await curve.router.populateApprove('0x6B175474E89094C44Da98b954EedeAC495271d0F', 1000);
1207+
// OR with custom spender: await curve.router.populateApprove('DAI', 1000, '0x...customSpender');
1208+
console.log(approveTxs);
1209+
// [{ to: '0x6B17...', data: '0x...', ... }]
1210+
// Returns array of TransactionLike objects
11941211
const swapTx = await curve.router.swap('DAI', 'CRV', '1000');
11951212
// OR const swapTx = await curve.router.swap('0x6B175474E89094C44Da98b954EedeAC495271d0F', '0xD533a949740bb3306d119CC777fa900bA034cd52', '1000');
11961213
console.log(swapTx.hash);

src/index.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ import {
1616
swapIsApproved,
1717
swapApproveEstimateGas,
1818
swapApprove,
19+
swapPopulateApprove,
1920
swapEstimateGas,
2021
swap,
2122
populateSwap,
@@ -63,6 +64,7 @@ import {
6364
hasAllowance,
6465
ensureAllowanceEstimateGas,
6566
ensureAllowance,
67+
populateApprove,
6668
getUsdRate,
6769
getGasPriceFromL1,
6870
getGasPriceFromL2,
@@ -176,6 +178,7 @@ export const createCurve = () => {
176178
getAllowance: getAllowance.bind(_curve),
177179
hasAllowance: hasAllowance.bind(_curve),
178180
ensureAllowance: ensureAllowance.bind(_curve),
181+
populateApprove: populateApprove.bind(_curve),
179182
getCoinsData: getCoinsData.bind(_curve),
180183
getVolume: getVolume.bind(_curve),
181184
hasDepositAndStake: hasDepositAndStake.bind(_curve),
@@ -353,6 +356,7 @@ export const createCurve = () => {
353356
priceImpact: swapPriceImpact.bind(_curve),
354357
isApproved: swapIsApproved.bind(_curve),
355358
approve: swapApprove.bind(_curve),
359+
populateApprove: swapPopulateApprove.bind(_curve),
356360
swap: swap.bind(_curve),
357361
populateSwap: populateSwap.bind(_curve),
358362
getSwappedAmount: getSwappedAmount.bind(_curve),

src/router.ts

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import {
88
_get_small_x,
99
_getCoinAddresses,
1010
_getCoinDecimals,
11+
_getAllowance,
1112
_getUsdRate,
1213
BN,
1314
DIGas,
@@ -19,7 +20,9 @@ import {
1920
getTxCostsUsd,
2021
hasAllowance,
2122
isEth,
23+
MAX_ALLOWANCE,
2224
parseUnits,
25+
populateApprove,
2326
runWorker,
2427
smartNumber,
2528
toBN,
@@ -406,6 +409,11 @@ export async function swapApprove(this: Curve, inputCoin: string, amount: number
406409
return await ensureAllowance.call(this, [inputCoin], [amount], this.constants.ALIASES.router);
407410
}
408411

412+
export async function swapPopulateApprove(this: Curve, inputCoin: string, amount: number | string, spender?: string, isMax = true): Promise<TransactionLike[]> {
413+
const routerAddress = this.contracts[this.constants.ALIASES.router].contract.target as string;
414+
return await populateApprove.call(this, [inputCoin], [amount], spender || routerAddress, isMax);
415+
}
416+
409417
export async function swapEstimateGas(this: Curve, inputCoin: string, outputCoin: string, amount: number | string): Promise<number | number[]> {
410418
const [inputCoinAddress, outputCoinAddress] = _getCoinAddresses.call(this, inputCoin, outputCoin);
411419
const [inputCoinDecimals] = _getCoinDecimals.call(this, inputCoinAddress, outputCoinAddress);

src/utils.ts

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import {Contract, ethers} from 'ethers';
1+
import {Contract, ethers, TransactionLike} from 'ethers';
22
import {Contract as MulticallContract} from "@curvefi/ethcall";
33
import BigNumber from 'bignumber.js';
44
import {
@@ -310,6 +310,32 @@ export async function ensureAllowance(this: Curve, coins: string[], amounts: (nu
310310
return await _ensureAllowance.call(this, coinAddresses, _amounts, spender, isMax)
311311
}
312312

313+
export async function populateApprove(this: Curve, coins: string[], amounts: (number | string)[], spender: string, isMax = true): Promise<TransactionLike[]> {
314+
const coinAddresses = _getCoinAddresses.call(this, coins);
315+
const decimals = _getCoinDecimals.call(this, coinAddresses);
316+
const _amounts = amounts.map((a, i) => parseUnits(a, decimals[i]));
317+
318+
const address = this.signerAddress;
319+
const allowance = await _getAllowance.call(this, coinAddresses, address, spender);
320+
321+
const transactions: TransactionLike[] = [];
322+
323+
for (let i = 0; i < allowance.length; i++) {
324+
if (allowance[i] < _amounts[i]) {
325+
const contract = this.contracts[coinAddresses[i]].contract;
326+
const _approveAmount = isMax ? MAX_ALLOWANCE : _amounts[i];
327+
328+
if (allowance[i] > parseUnits("0")) {
329+
transactions.push(await contract.approve.populateTransaction(spender, parseUnits("0")));
330+
}
331+
332+
transactions.push(await contract.approve.populateTransaction(spender, _approveAmount));
333+
}
334+
}
335+
336+
return transactions;
337+
}
338+
313339
export function getPoolIdBySwapAddress(this: Curve, swapAddress: string): string {
314340
const poolsData = this.getPoolsData();
315341
const poolIds = Object.entries(poolsData).filter(([, poolData]) => poolData.swap_address.toLowerCase() === swapAddress.toLowerCase());

0 commit comments

Comments
 (0)