four-flap-meme-sdk 1.9.43 → 1.9.45
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/chains/eni/batch-router/bundle-buy.d.ts +11 -8
- package/dist/chains/eni/batch-router/bundle-buy.js +31 -23
- package/dist/chains/eni/batch-router/bundle-sell.d.ts +11 -7
- package/dist/chains/eni/batch-router/bundle-sell.js +26 -12
- package/dist/chains/eni/batch-router/bundle-swap.d.ts +8 -21
- package/dist/chains/eni/batch-router/bundle-swap.js +46 -27
- package/dist/chains/eni/batch-router/constants.d.ts +12 -7
- package/dist/chains/eni/batch-router/constants.js +28 -12
- package/dist/chains/eni/batch-router/index.d.ts +8 -8
- package/dist/chains/eni/batch-router/index.js +25 -19
- package/dist/chains/eni/batch-router/transfer.js +3 -3
- package/dist/chains/eni/batch-router/utils.d.ts +10 -2
- package/dist/chains/eni/batch-router/utils.js +64 -41
- package/dist/chains/eni/batch-router/volume.d.ts +17 -15
- package/dist/chains/eni/batch-router/volume.js +32 -16
- package/dist/utils/holders-maker.d.ts +2 -0
- package/dist/utils/holders-maker.js +39 -2
- package/package.json +1 -1
|
@@ -1,19 +1,22 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* ENI BatchRouter — 批量买入
|
|
3
|
-
*
|
|
4
|
-
* Phase 2: 部署 BatchRouter 合约后启用
|
|
5
|
-
* 参考 xlayer/eip7702/bundle-buy.ts 的接口风格
|
|
2
|
+
* ENI BatchRouter — 批量买入 (内盘 + V2 + V3)
|
|
6
3
|
*/
|
|
7
4
|
import type { BatchBuyParams, BatchBuyResult } from './types.js';
|
|
8
5
|
/**
|
|
9
|
-
* 内盘批量买入
|
|
10
|
-
* 主钱包出 EGAS,代币直接到各 EOA
|
|
6
|
+
* 内盘批量买入 (DAOaaS Portal)
|
|
11
7
|
*/
|
|
12
8
|
export declare function batchBuyPortal(params: BatchBuyParams): Promise<BatchBuyResult>;
|
|
13
9
|
/**
|
|
14
|
-
* 外盘 V2 批量买入
|
|
15
|
-
* 通过 DSWAP V2 Router 买入
|
|
10
|
+
* 外盘 V2 批量买入 (DSWAP V2 / IROSwap V2)
|
|
16
11
|
*/
|
|
17
12
|
export declare function batchBuyV2(params: BatchBuyParams & {
|
|
18
13
|
path?: string[];
|
|
14
|
+
router?: string;
|
|
15
|
+
}): Promise<BatchBuyResult>;
|
|
16
|
+
/**
|
|
17
|
+
* 外盘 V3 批量买入 (DSWAP V3 Router02)
|
|
18
|
+
*/
|
|
19
|
+
export declare function batchBuyV3(params: BatchBuyParams & {
|
|
20
|
+
fee: number;
|
|
21
|
+
router: string;
|
|
19
22
|
}): Promise<BatchBuyResult>;
|
|
@@ -1,15 +1,11 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* ENI BatchRouter — 批量买入
|
|
3
|
-
*
|
|
4
|
-
* Phase 2: 部署 BatchRouter 合约后启用
|
|
5
|
-
* 参考 xlayer/eip7702/bundle-buy.ts 的接口风格
|
|
2
|
+
* ENI BatchRouter — 批量买入 (内盘 + V2 + V3)
|
|
6
3
|
*/
|
|
7
4
|
import { DAOAAS_PORTAL, DSWAP_V2_ROUTER, WEGAS } from '../constants.js';
|
|
8
5
|
import { estimateGas } from './constants.js';
|
|
9
|
-
import { validateBatchParams, encodeBatchBuy, encodeBatchBuyV2, buildBatchRouterTx } from './utils.js';
|
|
6
|
+
import { validateBatchParams, encodeBatchBuy, encodeBatchBuyV2, encodeBatchBuyV3, buildBatchRouterTx } from './utils.js';
|
|
10
7
|
/**
|
|
11
|
-
* 内盘批量买入
|
|
12
|
-
* 主钱包出 EGAS,代币直接到各 EOA
|
|
8
|
+
* 内盘批量买入 (DAOaaS Portal)
|
|
13
9
|
*/
|
|
14
10
|
export async function batchBuyPortal(params) {
|
|
15
11
|
const { buyers, amounts, target = DAOAAS_PORTAL, token, profitAmount = 0n } = params;
|
|
@@ -17,7 +13,7 @@ export async function batchBuyPortal(params) {
|
|
|
17
13
|
const totalBuyAmount = amounts.reduce((a, b) => a + b, 0n);
|
|
18
14
|
const totalValue = totalBuyAmount + profitAmount;
|
|
19
15
|
const calldata = encodeBatchBuy(target, token, buyers, amounts);
|
|
20
|
-
const gasLimit = estimateGas(buyers.length,
|
|
16
|
+
const gasLimit = estimateGas(buyers.length, 'portal');
|
|
21
17
|
const result = await buildBatchRouterTx({
|
|
22
18
|
rpcUrl: params.rpcUrl,
|
|
23
19
|
mainPrivateKey: params.mainPrivateKey,
|
|
@@ -27,24 +23,19 @@ export async function batchBuyPortal(params) {
|
|
|
27
23
|
gasLimit,
|
|
28
24
|
gasPrice: params.gasPrice,
|
|
29
25
|
});
|
|
30
|
-
return {
|
|
31
|
-
...result,
|
|
32
|
-
totalValue,
|
|
33
|
-
estimatedGas: gasLimit,
|
|
34
|
-
};
|
|
26
|
+
return { ...result, totalValue, estimatedGas: gasLimit };
|
|
35
27
|
}
|
|
36
28
|
/**
|
|
37
|
-
* 外盘 V2 批量买入
|
|
38
|
-
* 通过 DSWAP V2 Router 买入
|
|
29
|
+
* 外盘 V2 批量买入 (DSWAP V2 / IROSwap V2)
|
|
39
30
|
*/
|
|
40
31
|
export async function batchBuyV2(params) {
|
|
41
|
-
const { buyers, amounts, token, profitAmount = 0n, path } = params;
|
|
32
|
+
const { buyers, amounts, token, profitAmount = 0n, path, router = DSWAP_V2_ROUTER } = params;
|
|
42
33
|
validateBatchParams(buyers, amounts, 'batchBuyV2');
|
|
43
34
|
const totalBuyAmount = amounts.reduce((a, b) => a + b, 0n);
|
|
44
35
|
const totalValue = totalBuyAmount + profitAmount;
|
|
45
36
|
const buyPath = path ?? [WEGAS, token];
|
|
46
|
-
const calldata = encodeBatchBuyV2(
|
|
47
|
-
const gasLimit = estimateGas(buyers.length,
|
|
37
|
+
const calldata = encodeBatchBuyV2(router, buyPath, buyers, amounts);
|
|
38
|
+
const gasLimit = estimateGas(buyers.length, 'v2');
|
|
48
39
|
const result = await buildBatchRouterTx({
|
|
49
40
|
rpcUrl: params.rpcUrl,
|
|
50
41
|
mainPrivateKey: params.mainPrivateKey,
|
|
@@ -54,9 +45,26 @@ export async function batchBuyV2(params) {
|
|
|
54
45
|
gasLimit,
|
|
55
46
|
gasPrice: params.gasPrice,
|
|
56
47
|
});
|
|
57
|
-
return {
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
48
|
+
return { ...result, totalValue, estimatedGas: gasLimit };
|
|
49
|
+
}
|
|
50
|
+
/**
|
|
51
|
+
* 外盘 V3 批量买入 (DSWAP V3 Router02)
|
|
52
|
+
*/
|
|
53
|
+
export async function batchBuyV3(params) {
|
|
54
|
+
const { buyers, amounts, token, profitAmount = 0n, fee, router } = params;
|
|
55
|
+
validateBatchParams(buyers, amounts, 'batchBuyV3');
|
|
56
|
+
const totalBuyAmount = amounts.reduce((a, b) => a + b, 0n);
|
|
57
|
+
const totalValue = totalBuyAmount + profitAmount;
|
|
58
|
+
const calldata = encodeBatchBuyV3(router, token, fee, buyers, amounts);
|
|
59
|
+
const gasLimit = estimateGas(buyers.length, 'v3');
|
|
60
|
+
const result = await buildBatchRouterTx({
|
|
61
|
+
rpcUrl: params.rpcUrl,
|
|
62
|
+
mainPrivateKey: params.mainPrivateKey,
|
|
63
|
+
batchRouterAddress: params.batchRouterAddress,
|
|
64
|
+
calldata,
|
|
65
|
+
value: totalValue,
|
|
66
|
+
gasLimit,
|
|
67
|
+
gasPrice: params.gasPrice,
|
|
68
|
+
});
|
|
69
|
+
return { ...result, totalValue, estimatedGas: gasLimit };
|
|
62
70
|
}
|
|
@@ -1,18 +1,22 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* ENI BatchRouter — 批量卖出
|
|
3
|
-
*
|
|
4
|
-
* Phase 2: 部署 BatchRouter 合约后启用
|
|
5
|
-
* 各钱包需提前 approve(BatchRouter, amount)
|
|
2
|
+
* ENI BatchRouter — 批量卖出 (内盘 + V2 + V3)
|
|
6
3
|
*/
|
|
7
4
|
import type { BatchSellParams, BatchSellResult } from './types.js';
|
|
8
5
|
/**
|
|
9
|
-
* 内盘批量卖出
|
|
10
|
-
* BatchRouter 从各钱包 transferFrom 代币后执行 saleToken
|
|
6
|
+
* 内盘批量卖出 (DAOaaS Portal)
|
|
11
7
|
*/
|
|
12
8
|
export declare function batchSellPortal(params: BatchSellParams): Promise<BatchSellResult>;
|
|
13
9
|
/**
|
|
14
|
-
* 外盘 V2 批量卖出
|
|
10
|
+
* 外盘 V2 批量卖出 (DSWAP V2 / IROSwap V2)
|
|
15
11
|
*/
|
|
16
12
|
export declare function batchSellV2(params: BatchSellParams & {
|
|
17
13
|
path?: string[];
|
|
14
|
+
router?: string;
|
|
15
|
+
}): Promise<BatchSellResult>;
|
|
16
|
+
/**
|
|
17
|
+
* 外盘 V3 批量卖出 (DSWAP V3 Router02)
|
|
18
|
+
*/
|
|
19
|
+
export declare function batchSellV3(params: BatchSellParams & {
|
|
20
|
+
fee: number;
|
|
21
|
+
router: string;
|
|
18
22
|
}): Promise<BatchSellResult>;
|
|
@@ -1,21 +1,17 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* ENI BatchRouter — 批量卖出
|
|
3
|
-
*
|
|
4
|
-
* Phase 2: 部署 BatchRouter 合约后启用
|
|
5
|
-
* 各钱包需提前 approve(BatchRouter, amount)
|
|
2
|
+
* ENI BatchRouter — 批量卖出 (内盘 + V2 + V3)
|
|
6
3
|
*/
|
|
7
4
|
import { DAOAAS_PORTAL, DSWAP_V2_ROUTER, WEGAS } from '../constants.js';
|
|
8
5
|
import { estimateGas } from './constants.js';
|
|
9
|
-
import { validateBatchParams, encodeBatchSell, encodeBatchSellV2, buildBatchRouterTx } from './utils.js';
|
|
6
|
+
import { validateBatchParams, encodeBatchSell, encodeBatchSellV2, encodeBatchSellV3, buildBatchRouterTx } from './utils.js';
|
|
10
7
|
/**
|
|
11
|
-
* 内盘批量卖出
|
|
12
|
-
* BatchRouter 从各钱包 transferFrom 代币后执行 saleToken
|
|
8
|
+
* 内盘批量卖出 (DAOaaS Portal)
|
|
13
9
|
*/
|
|
14
10
|
export async function batchSellPortal(params) {
|
|
15
11
|
const { sellers, amounts, target = DAOAAS_PORTAL, token } = params;
|
|
16
12
|
validateBatchParams(sellers, amounts, 'batchSellPortal');
|
|
17
13
|
const calldata = encodeBatchSell(target, token, sellers, amounts);
|
|
18
|
-
const gasLimit = estimateGas(sellers.length,
|
|
14
|
+
const gasLimit = estimateGas(sellers.length, 'portal');
|
|
19
15
|
const result = await buildBatchRouterTx({
|
|
20
16
|
rpcUrl: params.rpcUrl,
|
|
21
17
|
mainPrivateKey: params.mainPrivateKey,
|
|
@@ -27,14 +23,32 @@ export async function batchSellPortal(params) {
|
|
|
27
23
|
return { ...result, estimatedGas: gasLimit };
|
|
28
24
|
}
|
|
29
25
|
/**
|
|
30
|
-
* 外盘 V2 批量卖出
|
|
26
|
+
* 外盘 V2 批量卖出 (DSWAP V2 / IROSwap V2)
|
|
31
27
|
*/
|
|
32
28
|
export async function batchSellV2(params) {
|
|
33
|
-
const { sellers, amounts, token, path } = params;
|
|
29
|
+
const { sellers, amounts, token, path, router = DSWAP_V2_ROUTER } = params;
|
|
34
30
|
validateBatchParams(sellers, amounts, 'batchSellV2');
|
|
35
31
|
const sellPath = path ?? [token, WEGAS];
|
|
36
|
-
const calldata = encodeBatchSellV2(
|
|
37
|
-
const gasLimit = estimateGas(sellers.length,
|
|
32
|
+
const calldata = encodeBatchSellV2(router, sellPath, sellers, amounts);
|
|
33
|
+
const gasLimit = estimateGas(sellers.length, 'v2');
|
|
34
|
+
const result = await buildBatchRouterTx({
|
|
35
|
+
rpcUrl: params.rpcUrl,
|
|
36
|
+
mainPrivateKey: params.mainPrivateKey,
|
|
37
|
+
batchRouterAddress: params.batchRouterAddress,
|
|
38
|
+
calldata,
|
|
39
|
+
gasLimit,
|
|
40
|
+
gasPrice: params.gasPrice,
|
|
41
|
+
});
|
|
42
|
+
return { ...result, estimatedGas: gasLimit };
|
|
43
|
+
}
|
|
44
|
+
/**
|
|
45
|
+
* 外盘 V3 批量卖出 (DSWAP V3 Router02)
|
|
46
|
+
*/
|
|
47
|
+
export async function batchSellV3(params) {
|
|
48
|
+
const { sellers, amounts, token, fee, router } = params;
|
|
49
|
+
validateBatchParams(sellers, amounts, 'batchSellV3');
|
|
50
|
+
const calldata = encodeBatchSellV3(router, token, fee, sellers, amounts);
|
|
51
|
+
const gasLimit = estimateGas(sellers.length, 'v3');
|
|
38
52
|
const result = await buildBatchRouterTx({
|
|
39
53
|
rpcUrl: params.rpcUrl,
|
|
40
54
|
mainPrivateKey: params.mainPrivateKey,
|
|
@@ -1,29 +1,16 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* ENI BatchRouter —
|
|
2
|
+
* ENI BatchRouter — 原子换手 (内盘 + V2 + V3)
|
|
3
3
|
*
|
|
4
|
-
*
|
|
5
|
-
* 对标 BSC: fourBundleSwapMerkle / pancakeBundleSwapMerkle
|
|
6
|
-
*
|
|
7
|
-
* 内盘: atomicSwapPortal / batchSwapPortal
|
|
8
|
-
* 外盘: atomicSwapV2 / batchSwapV2
|
|
4
|
+
* 支持 1→N (atomicSwap) 和 M→N (batchSwap)
|
|
9
5
|
*/
|
|
10
6
|
import type { AtomicSwapParams, AtomicSwapResult } from './types.js';
|
|
11
|
-
/**
|
|
12
|
-
* 内盘 1 卖 N 买 原子换手
|
|
13
|
-
* 卖出钱包卖出代币 → EGAS 留在合约 → 用于买入到各钱包
|
|
14
|
-
*/
|
|
15
7
|
export declare function atomicSwapPortal(params: AtomicSwapParams): Promise<AtomicSwapResult>;
|
|
16
|
-
/**
|
|
17
|
-
* 内盘 M 卖 N 买 批量换手
|
|
18
|
-
*/
|
|
19
8
|
export declare function batchSwapPortal(params: AtomicSwapParams): Promise<AtomicSwapResult>;
|
|
20
|
-
/**
|
|
21
|
-
* V2 外盘 1 卖 N 买 原子换手
|
|
22
|
-
* token → WEGAS (卖出) → WEGAS → token (买入),同一笔 tx
|
|
23
|
-
*/
|
|
24
9
|
export declare function atomicSwapV2(params: AtomicSwapParams): Promise<AtomicSwapResult>;
|
|
25
|
-
/**
|
|
26
|
-
* V2 外盘 M 卖 N 买 批量换手
|
|
27
|
-
* 对标 BSC pancakeBatchSwapMerkle
|
|
28
|
-
*/
|
|
29
10
|
export declare function batchSwapV2(params: AtomicSwapParams): Promise<AtomicSwapResult>;
|
|
11
|
+
export interface V3SwapParams extends AtomicSwapParams {
|
|
12
|
+
fee: number;
|
|
13
|
+
router: string;
|
|
14
|
+
}
|
|
15
|
+
export declare function atomicSwapV3(params: V3SwapParams): Promise<AtomicSwapResult>;
|
|
16
|
+
export declare function batchSwapV3(params: V3SwapParams): Promise<AtomicSwapResult>;
|
|
@@ -1,29 +1,21 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* ENI BatchRouter —
|
|
2
|
+
* ENI BatchRouter — 原子换手 (内盘 + V2 + V3)
|
|
3
3
|
*
|
|
4
|
-
*
|
|
5
|
-
* 对标 BSC: fourBundleSwapMerkle / pancakeBundleSwapMerkle
|
|
6
|
-
*
|
|
7
|
-
* 内盘: atomicSwapPortal / batchSwapPortal
|
|
8
|
-
* 外盘: atomicSwapV2 / batchSwapV2
|
|
4
|
+
* 支持 1→N (atomicSwap) 和 M→N (batchSwap)
|
|
9
5
|
*/
|
|
10
6
|
import { DAOAAS_PORTAL, DSWAP_V2_ROUTER } from '../constants.js';
|
|
11
7
|
import { estimateGas } from './constants.js';
|
|
12
|
-
import { validateBatchParams, encodeAtomicSwap, encodeBatchSwap, encodeAtomicSwapV2, encodeBatchSwapV2, buildBatchRouterTx, } from './utils.js';
|
|
8
|
+
import { validateBatchParams, encodeAtomicSwap, encodeBatchSwap, encodeAtomicSwapV2, encodeBatchSwapV2, encodeAtomicSwapV3, encodeBatchSwapV3, buildBatchRouterTx, } from './utils.js';
|
|
13
9
|
// ============================================================================
|
|
14
10
|
// 内盘换手 (DAOaaS Portal)
|
|
15
11
|
// ============================================================================
|
|
16
|
-
/**
|
|
17
|
-
* 内盘 1 卖 N 买 原子换手
|
|
18
|
-
* 卖出钱包卖出代币 → EGAS 留在合约 → 用于买入到各钱包
|
|
19
|
-
*/
|
|
20
12
|
export async function atomicSwapPortal(params) {
|
|
21
13
|
const { sellers, sellAmounts, buyers, buyAmounts, target = DAOAAS_PORTAL, token, extraValue = 0n } = params;
|
|
22
14
|
if (sellers.length === 1) {
|
|
23
15
|
validateBatchParams(buyers, buyAmounts, 'atomicSwapPortal.buyers');
|
|
24
16
|
const calldata = encodeAtomicSwap(target, token, sellers[0], sellAmounts[0], buyers, buyAmounts);
|
|
25
17
|
const totalWallets = 1 + buyers.length;
|
|
26
|
-
const gasLimit = estimateGas(totalWallets,
|
|
18
|
+
const gasLimit = estimateGas(totalWallets, 'portal');
|
|
27
19
|
const result = await buildBatchRouterTx({
|
|
28
20
|
rpcUrl: params.rpcUrl,
|
|
29
21
|
mainPrivateKey: params.mainPrivateKey,
|
|
@@ -37,16 +29,13 @@ export async function atomicSwapPortal(params) {
|
|
|
37
29
|
}
|
|
38
30
|
return batchSwapPortal(params);
|
|
39
31
|
}
|
|
40
|
-
/**
|
|
41
|
-
* 内盘 M 卖 N 买 批量换手
|
|
42
|
-
*/
|
|
43
32
|
export async function batchSwapPortal(params) {
|
|
44
33
|
const { sellers, sellAmounts, buyers, buyAmounts, target = DAOAAS_PORTAL, token, extraValue = 0n } = params;
|
|
45
34
|
validateBatchParams(sellers, sellAmounts, 'batchSwap.sellers');
|
|
46
35
|
validateBatchParams(buyers, buyAmounts, 'batchSwap.buyers');
|
|
47
36
|
const calldata = encodeBatchSwap(target, token, sellers, sellAmounts, buyers, buyAmounts);
|
|
48
37
|
const totalWallets = sellers.length + buyers.length;
|
|
49
|
-
const gasLimit = estimateGas(totalWallets,
|
|
38
|
+
const gasLimit = estimateGas(totalWallets, 'portal');
|
|
50
39
|
const result = await buildBatchRouterTx({
|
|
51
40
|
rpcUrl: params.rpcUrl,
|
|
52
41
|
mainPrivateKey: params.mainPrivateKey,
|
|
@@ -59,19 +48,15 @@ export async function batchSwapPortal(params) {
|
|
|
59
48
|
return { ...result, totalValue: extraValue, estimatedGas: gasLimit };
|
|
60
49
|
}
|
|
61
50
|
// ============================================================================
|
|
62
|
-
// V2 外盘换手 (DSWAP V2
|
|
51
|
+
// V2 外盘换手 (DSWAP V2 / IROSwap V2)
|
|
63
52
|
// ============================================================================
|
|
64
|
-
/**
|
|
65
|
-
* V2 外盘 1 卖 N 买 原子换手
|
|
66
|
-
* token → WEGAS (卖出) → WEGAS → token (买入),同一笔 tx
|
|
67
|
-
*/
|
|
68
53
|
export async function atomicSwapV2(params) {
|
|
69
54
|
const { sellers, sellAmounts, buyers, buyAmounts, target = DSWAP_V2_ROUTER, token, extraValue = 0n } = params;
|
|
70
55
|
if (sellers.length === 1) {
|
|
71
56
|
validateBatchParams(buyers, buyAmounts, 'atomicSwapV2.buyers');
|
|
72
57
|
const calldata = encodeAtomicSwapV2(target, token, sellers[0], sellAmounts[0], buyers, buyAmounts);
|
|
73
58
|
const totalWallets = 1 + buyers.length;
|
|
74
|
-
const gasLimit = estimateGas(totalWallets,
|
|
59
|
+
const gasLimit = estimateGas(totalWallets, 'v2');
|
|
75
60
|
const result = await buildBatchRouterTx({
|
|
76
61
|
rpcUrl: params.rpcUrl,
|
|
77
62
|
mainPrivateKey: params.mainPrivateKey,
|
|
@@ -85,17 +70,51 @@ export async function atomicSwapV2(params) {
|
|
|
85
70
|
}
|
|
86
71
|
return batchSwapV2(params);
|
|
87
72
|
}
|
|
88
|
-
/**
|
|
89
|
-
* V2 外盘 M 卖 N 买 批量换手
|
|
90
|
-
* 对标 BSC pancakeBatchSwapMerkle
|
|
91
|
-
*/
|
|
92
73
|
export async function batchSwapV2(params) {
|
|
93
74
|
const { sellers, sellAmounts, buyers, buyAmounts, target = DSWAP_V2_ROUTER, token, extraValue = 0n } = params;
|
|
94
75
|
validateBatchParams(sellers, sellAmounts, 'batchSwapV2.sellers');
|
|
95
76
|
validateBatchParams(buyers, buyAmounts, 'batchSwapV2.buyers');
|
|
96
77
|
const calldata = encodeBatchSwapV2(target, token, sellers, sellAmounts, buyers, buyAmounts);
|
|
97
78
|
const totalWallets = sellers.length + buyers.length;
|
|
98
|
-
const gasLimit = estimateGas(totalWallets,
|
|
79
|
+
const gasLimit = estimateGas(totalWallets, 'v2');
|
|
80
|
+
const result = await buildBatchRouterTx({
|
|
81
|
+
rpcUrl: params.rpcUrl,
|
|
82
|
+
mainPrivateKey: params.mainPrivateKey,
|
|
83
|
+
batchRouterAddress: params.batchRouterAddress,
|
|
84
|
+
calldata,
|
|
85
|
+
value: extraValue,
|
|
86
|
+
gasLimit,
|
|
87
|
+
gasPrice: params.gasPrice,
|
|
88
|
+
});
|
|
89
|
+
return { ...result, totalValue: extraValue, estimatedGas: gasLimit };
|
|
90
|
+
}
|
|
91
|
+
export async function atomicSwapV3(params) {
|
|
92
|
+
const { sellers, sellAmounts, buyers, buyAmounts, token, extraValue = 0n, fee, router } = params;
|
|
93
|
+
if (sellers.length === 1) {
|
|
94
|
+
validateBatchParams(buyers, buyAmounts, 'atomicSwapV3.buyers');
|
|
95
|
+
const calldata = encodeAtomicSwapV3(router, token, fee, sellers[0], sellAmounts[0], buyers, buyAmounts);
|
|
96
|
+
const totalWallets = 1 + buyers.length;
|
|
97
|
+
const gasLimit = estimateGas(totalWallets, 'v3');
|
|
98
|
+
const result = await buildBatchRouterTx({
|
|
99
|
+
rpcUrl: params.rpcUrl,
|
|
100
|
+
mainPrivateKey: params.mainPrivateKey,
|
|
101
|
+
batchRouterAddress: params.batchRouterAddress,
|
|
102
|
+
calldata,
|
|
103
|
+
value: extraValue,
|
|
104
|
+
gasLimit,
|
|
105
|
+
gasPrice: params.gasPrice,
|
|
106
|
+
});
|
|
107
|
+
return { ...result, totalValue: extraValue, estimatedGas: gasLimit };
|
|
108
|
+
}
|
|
109
|
+
return batchSwapV3(params);
|
|
110
|
+
}
|
|
111
|
+
export async function batchSwapV3(params) {
|
|
112
|
+
const { sellers, sellAmounts, buyers, buyAmounts, token, extraValue = 0n, fee, router } = params;
|
|
113
|
+
validateBatchParams(sellers, sellAmounts, 'batchSwapV3.sellers');
|
|
114
|
+
validateBatchParams(buyers, buyAmounts, 'batchSwapV3.buyers');
|
|
115
|
+
const calldata = encodeBatchSwapV3(router, token, fee, sellers, sellAmounts, buyers, buyAmounts);
|
|
116
|
+
const totalWallets = sellers.length + buyers.length;
|
|
117
|
+
const gasLimit = estimateGas(totalWallets, 'v3');
|
|
99
118
|
const result = await buildBatchRouterTx({
|
|
100
119
|
rpcUrl: params.rpcUrl,
|
|
101
120
|
mainPrivateKey: params.mainPrivateKey,
|
|
@@ -1,23 +1,28 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* ENI BatchRouter 合约常量
|
|
2
|
+
* ENI BatchRouter V2 合约常量
|
|
3
3
|
*
|
|
4
|
-
*
|
|
4
|
+
* V2 变更:
|
|
5
|
+
* - V2 swap 改用 SupportingFeeOnTransferTokens
|
|
6
|
+
* - 新增 V3 (DSWAP V3 Router02) 全套批量操作
|
|
7
|
+
* - buyAmounts[i]==0 自动均分 (原子刷量)
|
|
5
8
|
*/
|
|
6
|
-
/** BatchRouter 合约地址 (
|
|
9
|
+
/** BatchRouter V2 合约地址 (部署后更新) */
|
|
7
10
|
export declare const BATCH_ROUTER_ADDRESS = "0xDe44dC76cE29f743FbC250930a92a847Bf1662F2";
|
|
8
11
|
/** 每个钱包操作的预估 Gas (内盘) */
|
|
9
12
|
export declare const GAS_PER_WALLET_PORTAL = 250000n;
|
|
10
13
|
/** 每个钱包操作的预估 Gas (V2 外盘) */
|
|
11
14
|
export declare const GAS_PER_WALLET_V2 = 200000n;
|
|
15
|
+
/** 每个钱包操作的预估 Gas (V3 外盘) */
|
|
16
|
+
export declare const GAS_PER_WALLET_V3 = 280000n;
|
|
12
17
|
/** 基础 Gas (合约开销) */
|
|
13
18
|
export declare const BASE_GAS = 100000n;
|
|
14
19
|
/** 最大钱包数 (受 10M gas 限制) */
|
|
15
20
|
export declare const MAX_BATCH_SIZE = 35;
|
|
16
|
-
/** BatchRouter ABI —
|
|
17
|
-
export declare const BATCH_ROUTER_ABI: readonly ["function batchBuy(address portal, address token, address[] buyers, uint256[] amounts) payable", "function batchSell(address portal, address token, address[] sellers, uint256[] amounts)", "function batchBuyV2(address router, address[] path, address[] buyers, uint256[] amounts) payable", "function batchSellV2(address router, address[] path, address[] sellers, uint256[] amounts)", "function atomicSwap(address portal, address token, address seller, uint256 sellAmount, address[] buyers, uint256[] buyAmounts) payable", "function batchSwap(address portal, address token, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable", "function atomicSwapV2(address router, address token, address seller, uint256 sellAmount, address[] buyers, uint256[] buyAmounts) payable", "function batchSwapV2(address router, address token, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable", "function buyFirstSwap(address portal, address token, address[] buyers, uint256[] buyAmounts, address[] sellers, uint256[] sellAmounts) payable", "function buyFirstSwapV2(address router, address token, address[] buyers, uint256[] buyAmounts, address[] sellers, uint256[] sellAmounts) payable", "function createAndBatchBuy(address portal, string name, string symbol, uint256 salt, uint256 createValue, address token, address[] buyers, uint256[] buyAmounts) payable", "function fairLaunchAndBatchBuyV2(address launcher, tuple(string name, string symbol, string logo, string metadata, address quoteTokenAddr, uint256 initialLp, uint256 initialQuote, uint256 lpAddRate, uint256 lpAddMin, uint256 buybackRate, uint256 buybackMin, address[] buybackPath, uint256[] marketingRates, address[] marketingAddrs, uint256 vestingAmount, uint256 vestingLockEndTime, uint256 vestingReleaseEndTime, address[] vestingRecipients, uint256[] vestingRatios, uint256 tradeStartTime, uint256 claimStartTime, uint256 claimEndTime, uint256 lockTime, uint256 releasePeriod, uint256 maxCount, uint256 minAmount, uint256 maxAmount, bool whitelistEnabled, address[] whitelistAddrs, bool inviteCodeEnabled, bytes32[] inviteCodes) launchParams, uint256 launchValue, address router, address token, address[] buyers, uint256[] buyAmounts) payable", "function crossSwapPortalToV2(address portal, address router, address token, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable", "function crossSwapV2ToPortal(address portal, address router, address token, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable", "function batchTransfer(address[] recipients, uint256[] amounts) payable", "function batchTransferToken(address token, address[] recipients, uint256[] amounts)", "function batchSweepToken(address token, address[] sources, address target)", "function owner() view returns (address)", "function transferOwnership(address o)", "function withdrawETH()", "function withdrawToken(address t)"];
|
|
21
|
+
/** BatchRouter V2 ABI — 25 个业务函数 */
|
|
22
|
+
export declare const BATCH_ROUTER_ABI: readonly ["function batchBuy(address portal, address token, address[] buyers, uint256[] amounts) payable", "function batchSell(address portal, address token, address[] sellers, uint256[] amounts)", "function batchBuyV2(address router, address[] path, address[] buyers, uint256[] amounts) payable", "function batchSellV2(address router, address[] path, address[] sellers, uint256[] amounts)", "function batchBuyV3(address router, address token, uint24 fee, address[] buyers, uint256[] amounts) payable", "function batchSellV3(address router, address token, uint24 fee, address[] sellers, uint256[] amounts)", "function atomicSwap(address portal, address token, address seller, uint256 sellAmount, address[] buyers, uint256[] buyAmounts) payable", "function batchSwap(address portal, address token, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable", "function atomicSwapV2(address router, address token, address seller, uint256 sellAmount, address[] buyers, uint256[] buyAmounts) payable", "function batchSwapV2(address router, address token, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable", "function atomicSwapV3(address router, address token, uint24 fee, address seller, uint256 sellAmount, address[] buyers, uint256[] buyAmounts) payable", "function batchSwapV3(address router, address token, uint24 fee, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable", "function buyFirstSwap(address portal, address token, address[] buyers, uint256[] buyAmounts, address[] sellers, uint256[] sellAmounts) payable", "function buyFirstSwapV2(address router, address token, address[] buyers, uint256[] buyAmounts, address[] sellers, uint256[] sellAmounts) payable", "function buyFirstSwapV3(address router, address token, uint24 fee, address[] buyers, uint256[] buyAmounts, address[] sellers, uint256[] sellAmounts) payable", "function createAndBatchBuy(address portal, string name, string symbol, uint256 salt, uint256 createValue, address token, address[] buyers, uint256[] buyAmounts) payable", "function fairLaunchAndBatchBuyV2(address launcher, tuple(string name, string symbol, string logo, string metadata, address quoteTokenAddr, uint256 initialLp, uint256 initialQuote, uint256 lpAddRate, uint256 lpAddMin, uint256 buybackRate, uint256 buybackMin, address[] buybackPath, uint256[] marketingRates, address[] marketingAddrs, uint256 vestingAmount, uint256 vestingLockEndTime, uint256 vestingReleaseEndTime, address[] vestingRecipients, uint256[] vestingRatios, uint256 tradeStartTime, uint256 claimStartTime, uint256 claimEndTime, uint256 lockTime, uint256 releasePeriod, uint256 maxCount, uint256 minAmount, uint256 maxAmount, bool whitelistEnabled, address[] whitelistAddrs, bool inviteCodeEnabled, bytes32[] inviteCodes) launchParams, uint256 launchValue, address router, address token, address[] buyers, uint256[] buyAmounts) payable", "function fairLaunchAndBatchBuyV3(address launcher, tuple(string name, string symbol, string logo, string metadata, address quoteTokenAddr, uint256 initialLp, uint256 initialQuote, uint256 lpAddRate, uint256 lpAddMin, uint256 buybackRate, uint256 buybackMin, address[] buybackPath, uint256[] marketingRates, address[] marketingAddrs, uint256 vestingAmount, uint256 vestingLockEndTime, uint256 vestingReleaseEndTime, address[] vestingRecipients, uint256[] vestingRatios, uint256 tradeStartTime, uint256 claimStartTime, uint256 claimEndTime, uint256 lockTime, uint256 releasePeriod, uint256 maxCount, uint256 minAmount, uint256 maxAmount, bool whitelistEnabled, address[] whitelistAddrs, bool inviteCodeEnabled, bytes32[] inviteCodes) launchParams, uint256 launchValue, address router, address token, uint24 fee, address[] buyers, uint256[] buyAmounts) payable", "function crossSwapPortalToV2(address portal, address router, address token, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable", "function crossSwapV2ToPortal(address portal, address router, address token, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable", "function crossSwapPortalToV3(address portal, address router, address token, uint24 fee, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable", "function crossSwapV3ToPortal(address portal, address router, address token, uint24 fee, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable", "function batchTransfer(address[] recipients, uint256[] amounts) payable", "function batchTransferToken(address token, address[] recipients, uint256[] amounts)", "function batchSweepToken(address token, address[] sources, address target)", "function owner() view returns (address)", "function transferOwnership(address o)", "function withdrawETH()", "function withdrawToken(address t)"];
|
|
18
23
|
/**
|
|
19
24
|
* 估算 Gas
|
|
20
25
|
* @param walletCount 钱包数量
|
|
21
|
-
* @param
|
|
26
|
+
* @param mode 操作类型: 'portal' | 'v2' | 'v3'
|
|
22
27
|
*/
|
|
23
|
-
export declare function estimateGas(walletCount: number,
|
|
28
|
+
export declare function estimateGas(walletCount: number, mode?: 'portal' | 'v2' | 'v3'): bigint;
|
|
@@ -1,42 +1,56 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* ENI BatchRouter 合约常量
|
|
2
|
+
* ENI BatchRouter V2 合约常量
|
|
3
3
|
*
|
|
4
|
-
*
|
|
4
|
+
* V2 变更:
|
|
5
|
+
* - V2 swap 改用 SupportingFeeOnTransferTokens
|
|
6
|
+
* - 新增 V3 (DSWAP V3 Router02) 全套批量操作
|
|
7
|
+
* - buyAmounts[i]==0 自动均分 (原子刷量)
|
|
5
8
|
*/
|
|
6
|
-
/** BatchRouter 合约地址 (
|
|
9
|
+
/** BatchRouter V2 合约地址 (部署后更新) */
|
|
7
10
|
export const BATCH_ROUTER_ADDRESS = '0xDe44dC76cE29f743FbC250930a92a847Bf1662F2';
|
|
8
11
|
/** 每个钱包操作的预估 Gas (内盘) */
|
|
9
12
|
export const GAS_PER_WALLET_PORTAL = 250000n;
|
|
10
13
|
/** 每个钱包操作的预估 Gas (V2 外盘) */
|
|
11
14
|
export const GAS_PER_WALLET_V2 = 200000n;
|
|
15
|
+
/** 每个钱包操作的预估 Gas (V3 外盘) */
|
|
16
|
+
export const GAS_PER_WALLET_V3 = 280000n;
|
|
12
17
|
/** 基础 Gas (合约开销) */
|
|
13
18
|
export const BASE_GAS = 100000n;
|
|
14
19
|
/** 最大钱包数 (受 10M gas 限制) */
|
|
15
20
|
export const MAX_BATCH_SIZE = 35;
|
|
16
|
-
/** BatchRouter ABI —
|
|
21
|
+
/** BatchRouter V2 ABI — 25 个业务函数 */
|
|
17
22
|
export const BATCH_ROUTER_ABI = [
|
|
18
23
|
// ── 内盘批量操作 (DAOaaS Portal) ──
|
|
19
24
|
'function batchBuy(address portal, address token, address[] buyers, uint256[] amounts) payable',
|
|
20
25
|
'function batchSell(address portal, address token, address[] sellers, uint256[] amounts)',
|
|
21
|
-
// ── 外盘批量操作 (
|
|
26
|
+
// ── V2 外盘批量操作 (SupportingFeeOnTransfer + balanceOf) ──
|
|
22
27
|
'function batchBuyV2(address router, address[] path, address[] buyers, uint256[] amounts) payable',
|
|
23
28
|
'function batchSellV2(address router, address[] path, address[] sellers, uint256[] amounts)',
|
|
29
|
+
// ── V3 外盘批量操作 (DSWAP V3 Router02) ──
|
|
30
|
+
'function batchBuyV3(address router, address token, uint24 fee, address[] buyers, uint256[] amounts) payable',
|
|
31
|
+
'function batchSellV3(address router, address token, uint24 fee, address[] sellers, uint256[] amounts)',
|
|
24
32
|
// ── 内盘换手 (先卖后买) ──
|
|
25
33
|
'function atomicSwap(address portal, address token, address seller, uint256 sellAmount, address[] buyers, uint256[] buyAmounts) payable',
|
|
26
34
|
'function batchSwap(address portal, address token, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable',
|
|
27
35
|
// ── V2 外盘换手 (先卖后买) ──
|
|
28
36
|
'function atomicSwapV2(address router, address token, address seller, uint256 sellAmount, address[] buyers, uint256[] buyAmounts) payable',
|
|
29
37
|
'function batchSwapV2(address router, address token, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable',
|
|
30
|
-
// ──
|
|
38
|
+
// ── V3 外盘换手 (先卖后买) ──
|
|
39
|
+
'function atomicSwapV3(address router, address token, uint24 fee, address seller, uint256 sellAmount, address[] buyers, uint256[] buyAmounts) payable',
|
|
40
|
+
'function batchSwapV3(address router, address token, uint24 fee, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable',
|
|
41
|
+
// ── 先买后卖 ──
|
|
31
42
|
'function buyFirstSwap(address portal, address token, address[] buyers, uint256[] buyAmounts, address[] sellers, uint256[] sellAmounts) payable',
|
|
32
43
|
'function buyFirstSwapV2(address router, address token, address[] buyers, uint256[] buyAmounts, address[] sellers, uint256[] sellAmounts) payable',
|
|
33
|
-
|
|
44
|
+
'function buyFirstSwapV3(address router, address token, uint24 fee, address[] buyers, uint256[] buyAmounts, address[] sellers, uint256[] sellAmounts) payable',
|
|
45
|
+
// ── 发币+首买 ──
|
|
34
46
|
'function createAndBatchBuy(address portal, string name, string symbol, uint256 salt, uint256 createValue, address token, address[] buyers, uint256[] buyAmounts) payable',
|
|
35
|
-
// ── ⭐ 发币+首买: FairLaunch 5种模式 → V2 ──
|
|
36
47
|
'function fairLaunchAndBatchBuyV2(address launcher, tuple(string name, string symbol, string logo, string metadata, address quoteTokenAddr, uint256 initialLp, uint256 initialQuote, uint256 lpAddRate, uint256 lpAddMin, uint256 buybackRate, uint256 buybackMin, address[] buybackPath, uint256[] marketingRates, address[] marketingAddrs, uint256 vestingAmount, uint256 vestingLockEndTime, uint256 vestingReleaseEndTime, address[] vestingRecipients, uint256[] vestingRatios, uint256 tradeStartTime, uint256 claimStartTime, uint256 claimEndTime, uint256 lockTime, uint256 releasePeriod, uint256 maxCount, uint256 minAmount, uint256 maxAmount, bool whitelistEnabled, address[] whitelistAddrs, bool inviteCodeEnabled, bytes32[] inviteCodes) launchParams, uint256 launchValue, address router, address token, address[] buyers, uint256[] buyAmounts) payable',
|
|
37
|
-
|
|
48
|
+
'function fairLaunchAndBatchBuyV3(address launcher, tuple(string name, string symbol, string logo, string metadata, address quoteTokenAddr, uint256 initialLp, uint256 initialQuote, uint256 lpAddRate, uint256 lpAddMin, uint256 buybackRate, uint256 buybackMin, address[] buybackPath, uint256[] marketingRates, address[] marketingAddrs, uint256 vestingAmount, uint256 vestingLockEndTime, uint256 vestingReleaseEndTime, address[] vestingRecipients, uint256[] vestingRatios, uint256 tradeStartTime, uint256 claimStartTime, uint256 claimEndTime, uint256 lockTime, uint256 releasePeriod, uint256 maxCount, uint256 minAmount, uint256 maxAmount, bool whitelistEnabled, address[] whitelistAddrs, bool inviteCodeEnabled, bytes32[] inviteCodes) launchParams, uint256 launchValue, address router, address token, uint24 fee, address[] buyers, uint256[] buyAmounts) payable',
|
|
49
|
+
// ── 跨盘换手 ──
|
|
38
50
|
'function crossSwapPortalToV2(address portal, address router, address token, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable',
|
|
39
51
|
'function crossSwapV2ToPortal(address portal, address router, address token, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable',
|
|
52
|
+
'function crossSwapPortalToV3(address portal, address router, address token, uint24 fee, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable',
|
|
53
|
+
'function crossSwapV3ToPortal(address portal, address router, address token, uint24 fee, address[] sellers, uint256[] sellAmounts, address[] buyers, uint256[] buyAmounts) payable',
|
|
40
54
|
// ── 分发 / 归集 ──
|
|
41
55
|
'function batchTransfer(address[] recipients, uint256[] amounts) payable',
|
|
42
56
|
'function batchTransferToken(address token, address[] recipients, uint256[] amounts)',
|
|
@@ -50,9 +64,11 @@ export const BATCH_ROUTER_ABI = [
|
|
|
50
64
|
/**
|
|
51
65
|
* 估算 Gas
|
|
52
66
|
* @param walletCount 钱包数量
|
|
53
|
-
* @param
|
|
67
|
+
* @param mode 操作类型: 'portal' | 'v2' | 'v3'
|
|
54
68
|
*/
|
|
55
|
-
export function estimateGas(walletCount,
|
|
56
|
-
const perWallet =
|
|
69
|
+
export function estimateGas(walletCount, mode = 'portal') {
|
|
70
|
+
const perWallet = mode === 'portal' ? GAS_PER_WALLET_PORTAL
|
|
71
|
+
: mode === 'v3' ? GAS_PER_WALLET_V3
|
|
72
|
+
: GAS_PER_WALLET_V2;
|
|
57
73
|
return BASE_GAS + perWallet * BigInt(walletCount);
|
|
58
74
|
}
|
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* ENI BatchRouter 模块入口
|
|
2
|
+
* ENI BatchRouter V2 模块入口
|
|
3
3
|
*
|
|
4
|
-
*
|
|
4
|
+
* 支持内盘 (Portal) / V2 (DSWAP/IROSwap) / V3 (DSWAP V3) 全部操作
|
|
5
5
|
*/
|
|
6
6
|
export type { BatchRouterConfig, BatchBuyParams, BatchBuyResult, BatchSellParams, BatchSellResult, AtomicSwapParams, AtomicSwapResult, BatchApproveParams, BatchApproveResult, BatchTransferParams, BatchTransferResult, } from './types.js';
|
|
7
|
-
export { BATCH_ROUTER_ADDRESS, BATCH_ROUTER_ABI, GAS_PER_WALLET_PORTAL, GAS_PER_WALLET_V2, BASE_GAS, MAX_BATCH_SIZE, estimateGas, } from './constants.js';
|
|
8
|
-
export { validateBatchParams, encodeBatchBuy, encodeBatchSell, encodeBatchBuyV2, encodeBatchSellV2, encodeAtomicSwap, encodeBatchSwap, encodeAtomicSwapV2, encodeBatchSwapV2, encodeBuyFirstSwap, encodeBuyFirstSwapV2, encodeCreateAndBatchBuy, encodeFairLaunchAndBatchBuyV2, type FairLaunchParamsForRouter, encodeCrossSwapPortalToV2, encodeCrossSwapV2ToPortal, encodeBatchTransfer, encodeBatchTransferToken, encodeBatchSweepToken, buildBatchRouterTx, } from './utils.js';
|
|
9
|
-
export { batchBuyPortal, batchBuyV2 } from './bundle-buy.js';
|
|
10
|
-
export { batchSellPortal, batchSellV2 } from './bundle-sell.js';
|
|
11
|
-
export { atomicSwapPortal, batchSwapPortal, atomicSwapV2, batchSwapV2 } from './bundle-swap.js';
|
|
7
|
+
export { BATCH_ROUTER_ADDRESS, BATCH_ROUTER_ABI, GAS_PER_WALLET_PORTAL, GAS_PER_WALLET_V2, GAS_PER_WALLET_V3, BASE_GAS, MAX_BATCH_SIZE, estimateGas, } from './constants.js';
|
|
8
|
+
export { validateBatchParams, encodeBatchBuy, encodeBatchSell, encodeBatchBuyV2, encodeBatchSellV2, encodeBatchBuyV3, encodeBatchSellV3, encodeAtomicSwap, encodeBatchSwap, encodeAtomicSwapV2, encodeBatchSwapV2, encodeAtomicSwapV3, encodeBatchSwapV3, encodeBuyFirstSwap, encodeBuyFirstSwapV2, encodeBuyFirstSwapV3, encodeCreateAndBatchBuy, encodeFairLaunchAndBatchBuyV2, encodeFairLaunchAndBatchBuyV3, type FairLaunchParamsForRouter, encodeCrossSwapPortalToV2, encodeCrossSwapV2ToPortal, encodeCrossSwapPortalToV3, encodeCrossSwapV3ToPortal, encodeBatchTransfer, encodeBatchTransferToken, encodeBatchSweepToken, buildBatchRouterTx, } from './utils.js';
|
|
9
|
+
export { batchBuyPortal, batchBuyV2, batchBuyV3 } from './bundle-buy.js';
|
|
10
|
+
export { batchSellPortal, batchSellV2, batchSellV3 } from './bundle-sell.js';
|
|
11
|
+
export { atomicSwapPortal, batchSwapPortal, atomicSwapV2, batchSwapV2, atomicSwapV3, batchSwapV3, type V3SwapParams, } from './bundle-swap.js';
|
|
12
12
|
export { batchApprove } from './bundle-approve.js';
|
|
13
|
-
export { washVolume, washVolumeV2, type WashVolumeParams, type WashVolumeResult } from './volume.js';
|
|
13
|
+
export { washVolume, washVolumeV2, washVolumeV3, type WashVolumeParams, type WashVolumeResult, } from './volume.js';
|
|
14
14
|
export { batchTransferEgas, batchTransferToken, batchSweepToken, batchSweepEgas, eniDisperseForSubmit, eniSweepForSubmit, type BatchTransferTokenParams, type BatchSweepTokenParams, type BatchSweepTokenResult, type BatchSweepEgasParams, type EniDisperseParams, type EniDisperseResult, type EniSweepParams, type EniSweepResult, } from './transfer.js';
|
|
@@ -1,28 +1,34 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* ENI BatchRouter 模块入口
|
|
2
|
+
* ENI BatchRouter V2 模块入口
|
|
3
3
|
*
|
|
4
|
-
*
|
|
4
|
+
* 支持内盘 (Portal) / V2 (DSWAP/IROSwap) / V3 (DSWAP V3) 全部操作
|
|
5
5
|
*/
|
|
6
6
|
// ============================================================================
|
|
7
7
|
// 常量
|
|
8
8
|
// ============================================================================
|
|
9
|
-
export { BATCH_ROUTER_ADDRESS, BATCH_ROUTER_ABI, GAS_PER_WALLET_PORTAL, GAS_PER_WALLET_V2, BASE_GAS, MAX_BATCH_SIZE, estimateGas, } from './constants.js';
|
|
9
|
+
export { BATCH_ROUTER_ADDRESS, BATCH_ROUTER_ABI, GAS_PER_WALLET_PORTAL, GAS_PER_WALLET_V2, GAS_PER_WALLET_V3, BASE_GAS, MAX_BATCH_SIZE, estimateGas, } from './constants.js';
|
|
10
10
|
// ============================================================================
|
|
11
11
|
// calldata 编码工具 (全部操作)
|
|
12
12
|
// ============================================================================
|
|
13
13
|
export { validateBatchParams,
|
|
14
|
-
//
|
|
15
|
-
encodeBatchBuy, encodeBatchSell,
|
|
16
|
-
//
|
|
17
|
-
|
|
18
|
-
//
|
|
19
|
-
|
|
20
|
-
//
|
|
21
|
-
|
|
22
|
-
//
|
|
23
|
-
|
|
24
|
-
//
|
|
25
|
-
|
|
14
|
+
// 内盘
|
|
15
|
+
encodeBatchBuy, encodeBatchSell,
|
|
16
|
+
// V2
|
|
17
|
+
encodeBatchBuyV2, encodeBatchSellV2,
|
|
18
|
+
// V3
|
|
19
|
+
encodeBatchBuyV3, encodeBatchSellV3,
|
|
20
|
+
// 内盘换手
|
|
21
|
+
encodeAtomicSwap, encodeBatchSwap,
|
|
22
|
+
// V2 换手
|
|
23
|
+
encodeAtomicSwapV2, encodeBatchSwapV2,
|
|
24
|
+
// V3 换手
|
|
25
|
+
encodeAtomicSwapV3, encodeBatchSwapV3,
|
|
26
|
+
// 先买后卖
|
|
27
|
+
encodeBuyFirstSwap, encodeBuyFirstSwapV2, encodeBuyFirstSwapV3,
|
|
28
|
+
// 发币+首买
|
|
29
|
+
encodeCreateAndBatchBuy, encodeFairLaunchAndBatchBuyV2, encodeFairLaunchAndBatchBuyV3,
|
|
30
|
+
// 跨盘换手
|
|
31
|
+
encodeCrossSwapPortalToV2, encodeCrossSwapV2ToPortal, encodeCrossSwapPortalToV3, encodeCrossSwapV3ToPortal,
|
|
26
32
|
// 分发 / 归集
|
|
27
33
|
encodeBatchTransfer, encodeBatchTransferToken, encodeBatchSweepToken,
|
|
28
34
|
// 交易构建
|
|
@@ -30,9 +36,9 @@ buildBatchRouterTx, } from './utils.js';
|
|
|
30
36
|
// ============================================================================
|
|
31
37
|
// 高层操作
|
|
32
38
|
// ============================================================================
|
|
33
|
-
export { batchBuyPortal, batchBuyV2 } from './bundle-buy.js';
|
|
34
|
-
export { batchSellPortal, batchSellV2 } from './bundle-sell.js';
|
|
35
|
-
export { atomicSwapPortal, batchSwapPortal, atomicSwapV2, batchSwapV2 } from './bundle-swap.js';
|
|
39
|
+
export { batchBuyPortal, batchBuyV2, batchBuyV3 } from './bundle-buy.js';
|
|
40
|
+
export { batchSellPortal, batchSellV2, batchSellV3 } from './bundle-sell.js';
|
|
41
|
+
export { atomicSwapPortal, batchSwapPortal, atomicSwapV2, batchSwapV2, atomicSwapV3, batchSwapV3, } from './bundle-swap.js';
|
|
36
42
|
export { batchApprove } from './bundle-approve.js';
|
|
37
|
-
export { washVolume, washVolumeV2 } from './volume.js';
|
|
43
|
+
export { washVolume, washVolumeV2, washVolumeV3, } from './volume.js';
|
|
38
44
|
export { batchTransferEgas, batchTransferToken, batchSweepToken, batchSweepEgas, eniDisperseForSubmit, eniSweepForSubmit, } from './transfer.js';
|
|
@@ -26,7 +26,7 @@ export async function batchTransferEgas(params) {
|
|
|
26
26
|
validateBatchParams(recipients, amounts, 'batchTransferEgas');
|
|
27
27
|
const totalValue = amounts.reduce((a, b) => a + b, 0n);
|
|
28
28
|
const calldata = encodeBatchTransfer(recipients, amounts);
|
|
29
|
-
const gasLimit = estimateGas(recipients.length,
|
|
29
|
+
const gasLimit = estimateGas(recipients.length, 'v2');
|
|
30
30
|
const result = await buildBatchRouterTx({
|
|
31
31
|
rpcUrl: params.rpcUrl,
|
|
32
32
|
mainPrivateKey: params.mainPrivateKey,
|
|
@@ -43,7 +43,7 @@ export async function batchTransferToken(params) {
|
|
|
43
43
|
validateBatchParams(recipients, amounts, 'batchTransferToken');
|
|
44
44
|
const routerAddr = params.batchRouterAddress || BATCH_ROUTER_ADDRESS;
|
|
45
45
|
const calldata = encodeBatchTransferToken(token, recipients, amounts);
|
|
46
|
-
const gasLimit = estimateGas(recipients.length,
|
|
46
|
+
const gasLimit = estimateGas(recipients.length, 'v2');
|
|
47
47
|
const result = await buildBatchRouterTx({
|
|
48
48
|
rpcUrl: params.rpcUrl,
|
|
49
49
|
mainPrivateKey: params.mainPrivateKey,
|
|
@@ -156,7 +156,7 @@ export async function eniDisperseForSubmit(params) {
|
|
|
156
156
|
const totalNeeded = amountsWei.reduce((a, b) => a + b, 0n);
|
|
157
157
|
const signedTxs = [];
|
|
158
158
|
let currentNonce = await mainWallet.getNonce();
|
|
159
|
-
const gasLimit = estimateGas(recipients.length,
|
|
159
|
+
const gasLimit = estimateGas(recipients.length, 'v2');
|
|
160
160
|
if (allowance < totalNeeded) {
|
|
161
161
|
const approveTx = await mainWallet.signTransaction({
|
|
162
162
|
to: tokenAddress,
|
|
@@ -1,19 +1,24 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* ENI BatchRouter 编码工具
|
|
2
|
+
* ENI BatchRouter V2 编码工具
|
|
3
3
|
*
|
|
4
|
-
*
|
|
4
|
+
* 支持内盘 (Portal) / V2 / V3 全部操作的 calldata 编码
|
|
5
5
|
*/
|
|
6
6
|
export declare function validateBatchParams(addresses: string[], amounts: bigint[], label?: string): void;
|
|
7
7
|
export declare function encodeBatchBuy(portal: string, token: string, buyers: string[], amounts: bigint[]): string;
|
|
8
8
|
export declare function encodeBatchSell(portal: string, token: string, sellers: string[], amounts: bigint[]): string;
|
|
9
9
|
export declare function encodeBatchBuyV2(router: string, path: string[], buyers: string[], amounts: bigint[]): string;
|
|
10
10
|
export declare function encodeBatchSellV2(router: string, path: string[], sellers: string[], amounts: bigint[]): string;
|
|
11
|
+
export declare function encodeBatchBuyV3(router: string, token: string, fee: number, buyers: string[], amounts: bigint[]): string;
|
|
12
|
+
export declare function encodeBatchSellV3(router: string, token: string, fee: number, sellers: string[], amounts: bigint[]): string;
|
|
11
13
|
export declare function encodeAtomicSwap(portal: string, token: string, seller: string, sellAmount: bigint, buyers: string[], buyAmounts: bigint[]): string;
|
|
12
14
|
export declare function encodeBatchSwap(portal: string, token: string, sellers: string[], sellAmounts: bigint[], buyers: string[], buyAmounts: bigint[]): string;
|
|
13
15
|
export declare function encodeAtomicSwapV2(router: string, token: string, seller: string, sellAmount: bigint, buyers: string[], buyAmounts: bigint[]): string;
|
|
14
16
|
export declare function encodeBatchSwapV2(router: string, token: string, sellers: string[], sellAmounts: bigint[], buyers: string[], buyAmounts: bigint[]): string;
|
|
17
|
+
export declare function encodeAtomicSwapV3(router: string, token: string, fee: number, seller: string, sellAmount: bigint, buyers: string[], buyAmounts: bigint[]): string;
|
|
18
|
+
export declare function encodeBatchSwapV3(router: string, token: string, fee: number, sellers: string[], sellAmounts: bigint[], buyers: string[], buyAmounts: bigint[]): string;
|
|
15
19
|
export declare function encodeBuyFirstSwap(portal: string, token: string, buyers: string[], buyAmounts: bigint[], sellers: string[], sellAmounts: bigint[]): string;
|
|
16
20
|
export declare function encodeBuyFirstSwapV2(router: string, token: string, buyers: string[], buyAmounts: bigint[], sellers: string[], sellAmounts: bigint[]): string;
|
|
21
|
+
export declare function encodeBuyFirstSwapV3(router: string, token: string, fee: number, buyers: string[], buyAmounts: bigint[], sellers: string[], sellAmounts: bigint[]): string;
|
|
17
22
|
export declare function encodeCreateAndBatchBuy(portal: string, name: string, symbol: string, salt: string, createValue: bigint, token: string, buyers: string[], buyAmounts: bigint[]): string;
|
|
18
23
|
export interface FairLaunchParamsForRouter {
|
|
19
24
|
name: string;
|
|
@@ -49,8 +54,11 @@ export interface FairLaunchParamsForRouter {
|
|
|
49
54
|
inviteCodes: string[];
|
|
50
55
|
}
|
|
51
56
|
export declare function encodeFairLaunchAndBatchBuyV2(launcher: string, launchParams: FairLaunchParamsForRouter, launchValue: bigint, router: string, token: string, buyers: string[], buyAmounts: bigint[]): string;
|
|
57
|
+
export declare function encodeFairLaunchAndBatchBuyV3(launcher: string, launchParams: FairLaunchParamsForRouter, launchValue: bigint, router: string, token: string, fee: number, buyers: string[], buyAmounts: bigint[]): string;
|
|
52
58
|
export declare function encodeCrossSwapPortalToV2(portal: string, router: string, token: string, sellers: string[], sellAmounts: bigint[], buyers: string[], buyAmounts: bigint[]): string;
|
|
53
59
|
export declare function encodeCrossSwapV2ToPortal(portal: string, router: string, token: string, sellers: string[], sellAmounts: bigint[], buyers: string[], buyAmounts: bigint[]): string;
|
|
60
|
+
export declare function encodeCrossSwapPortalToV3(portal: string, router: string, token: string, fee: number, sellers: string[], sellAmounts: bigint[], buyers: string[], buyAmounts: bigint[]): string;
|
|
61
|
+
export declare function encodeCrossSwapV3ToPortal(portal: string, router: string, token: string, fee: number, sellers: string[], sellAmounts: bigint[], buyers: string[], buyAmounts: bigint[]): string;
|
|
54
62
|
export declare function encodeBatchTransfer(recipients: string[], amounts: bigint[]): string;
|
|
55
63
|
export declare function encodeBatchTransferToken(token: string, recipients: string[], amounts: bigint[]): string;
|
|
56
64
|
export declare function encodeBatchSweepToken(token: string, sources: string[], target: string): string;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* ENI BatchRouter 编码工具
|
|
2
|
+
* ENI BatchRouter V2 编码工具
|
|
3
3
|
*
|
|
4
|
-
*
|
|
4
|
+
* 支持内盘 (Portal) / V2 / V3 全部操作的 calldata 编码
|
|
5
5
|
*/
|
|
6
6
|
import { Interface, Wallet, JsonRpcProvider } from 'ethers';
|
|
7
7
|
import { ENI_CHAIN_ID, ENI_RPC_URL } from '../constants.js';
|
|
@@ -22,7 +22,7 @@ export function validateBatchParams(addresses, amounts, label = 'batch') {
|
|
|
22
22
|
}
|
|
23
23
|
}
|
|
24
24
|
// ============================================================================
|
|
25
|
-
// calldata 编码 —
|
|
25
|
+
// calldata 编码 — 内盘 (Portal)
|
|
26
26
|
// ============================================================================
|
|
27
27
|
export function encodeBatchBuy(portal, token, buyers, amounts) {
|
|
28
28
|
return routerIface.encodeFunctionData('batchBuy', [portal, token, buyers, amounts]);
|
|
@@ -30,6 +30,9 @@ export function encodeBatchBuy(portal, token, buyers, amounts) {
|
|
|
30
30
|
export function encodeBatchSell(portal, token, sellers, amounts) {
|
|
31
31
|
return routerIface.encodeFunctionData('batchSell', [portal, token, sellers, amounts]);
|
|
32
32
|
}
|
|
33
|
+
// ============================================================================
|
|
34
|
+
// calldata 编码 — V2 外盘
|
|
35
|
+
// ============================================================================
|
|
33
36
|
export function encodeBatchBuyV2(router, path, buyers, amounts) {
|
|
34
37
|
return routerIface.encodeFunctionData('batchBuyV2', [router, path, buyers, amounts]);
|
|
35
38
|
}
|
|
@@ -37,7 +40,16 @@ export function encodeBatchSellV2(router, path, sellers, amounts) {
|
|
|
37
40
|
return routerIface.encodeFunctionData('batchSellV2', [router, path, sellers, amounts]);
|
|
38
41
|
}
|
|
39
42
|
// ============================================================================
|
|
40
|
-
// calldata 编码 —
|
|
43
|
+
// calldata 编码 — V3 外盘
|
|
44
|
+
// ============================================================================
|
|
45
|
+
export function encodeBatchBuyV3(router, token, fee, buyers, amounts) {
|
|
46
|
+
return routerIface.encodeFunctionData('batchBuyV3', [router, token, fee, buyers, amounts]);
|
|
47
|
+
}
|
|
48
|
+
export function encodeBatchSellV3(router, token, fee, sellers, amounts) {
|
|
49
|
+
return routerIface.encodeFunctionData('batchSellV3', [router, token, fee, sellers, amounts]);
|
|
50
|
+
}
|
|
51
|
+
// ============================================================================
|
|
52
|
+
// calldata 编码 — 内盘换手 (先卖后买)
|
|
41
53
|
// ============================================================================
|
|
42
54
|
export function encodeAtomicSwap(portal, token, seller, sellAmount, buyers, buyAmounts) {
|
|
43
55
|
return routerIface.encodeFunctionData('atomicSwap', [portal, token, seller, sellAmount, buyers, buyAmounts]);
|
|
@@ -45,6 +57,9 @@ export function encodeAtomicSwap(portal, token, seller, sellAmount, buyers, buyA
|
|
|
45
57
|
export function encodeBatchSwap(portal, token, sellers, sellAmounts, buyers, buyAmounts) {
|
|
46
58
|
return routerIface.encodeFunctionData('batchSwap', [portal, token, sellers, sellAmounts, buyers, buyAmounts]);
|
|
47
59
|
}
|
|
60
|
+
// ============================================================================
|
|
61
|
+
// calldata 编码 — V2 外盘换手
|
|
62
|
+
// ============================================================================
|
|
48
63
|
export function encodeAtomicSwapV2(router, token, seller, sellAmount, buyers, buyAmounts) {
|
|
49
64
|
return routerIface.encodeFunctionData('atomicSwapV2', [router, token, seller, sellAmount, buyers, buyAmounts]);
|
|
50
65
|
}
|
|
@@ -52,7 +67,16 @@ export function encodeBatchSwapV2(router, token, sellers, sellAmounts, buyers, b
|
|
|
52
67
|
return routerIface.encodeFunctionData('batchSwapV2', [router, token, sellers, sellAmounts, buyers, buyAmounts]);
|
|
53
68
|
}
|
|
54
69
|
// ============================================================================
|
|
55
|
-
// calldata 编码 —
|
|
70
|
+
// calldata 编码 — V3 外盘换手
|
|
71
|
+
// ============================================================================
|
|
72
|
+
export function encodeAtomicSwapV3(router, token, fee, seller, sellAmount, buyers, buyAmounts) {
|
|
73
|
+
return routerIface.encodeFunctionData('atomicSwapV3', [router, token, fee, seller, sellAmount, buyers, buyAmounts]);
|
|
74
|
+
}
|
|
75
|
+
export function encodeBatchSwapV3(router, token, fee, sellers, sellAmounts, buyers, buyAmounts) {
|
|
76
|
+
return routerIface.encodeFunctionData('batchSwapV3', [router, token, fee, sellers, sellAmounts, buyers, buyAmounts]);
|
|
77
|
+
}
|
|
78
|
+
// ============================================================================
|
|
79
|
+
// calldata 编码 — 先买后卖 (Buy-First)
|
|
56
80
|
// ============================================================================
|
|
57
81
|
export function encodeBuyFirstSwap(portal, token, buyers, buyAmounts, sellers, sellAmounts) {
|
|
58
82
|
return routerIface.encodeFunctionData('buyFirstSwap', [portal, token, buyers, buyAmounts, sellers, sellAmounts]);
|
|
@@ -60,54 +84,43 @@ export function encodeBuyFirstSwap(portal, token, buyers, buyAmounts, sellers, s
|
|
|
60
84
|
export function encodeBuyFirstSwapV2(router, token, buyers, buyAmounts, sellers, sellAmounts) {
|
|
61
85
|
return routerIface.encodeFunctionData('buyFirstSwapV2', [router, token, buyers, buyAmounts, sellers, sellAmounts]);
|
|
62
86
|
}
|
|
87
|
+
export function encodeBuyFirstSwapV3(router, token, fee, buyers, buyAmounts, sellers, sellAmounts) {
|
|
88
|
+
return routerIface.encodeFunctionData('buyFirstSwapV3', [router, token, fee, buyers, buyAmounts, sellers, sellAmounts]);
|
|
89
|
+
}
|
|
63
90
|
// ============================================================================
|
|
64
|
-
// calldata 编码 —
|
|
91
|
+
// calldata 编码 — 发币+首买
|
|
65
92
|
// ============================================================================
|
|
66
93
|
export function encodeCreateAndBatchBuy(portal, name, symbol, salt, createValue, token, buyers, buyAmounts) {
|
|
67
94
|
return routerIface.encodeFunctionData('createAndBatchBuy', [
|
|
68
95
|
portal, name, symbol, salt, createValue, token, buyers, buyAmounts,
|
|
69
96
|
]);
|
|
70
97
|
}
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
launchParams.buybackMin,
|
|
84
|
-
launchParams.buybackPath,
|
|
85
|
-
launchParams.marketingRates,
|
|
86
|
-
launchParams.marketingAddrs,
|
|
87
|
-
launchParams.vestingAmount,
|
|
88
|
-
launchParams.vestingLockEndTime,
|
|
89
|
-
launchParams.vestingReleaseEndTime,
|
|
90
|
-
launchParams.vestingRecipients,
|
|
91
|
-
launchParams.vestingRatios,
|
|
92
|
-
launchParams.tradeStartTime,
|
|
93
|
-
launchParams.claimStartTime,
|
|
94
|
-
launchParams.claimEndTime,
|
|
95
|
-
launchParams.lockTime,
|
|
96
|
-
launchParams.releasePeriod,
|
|
97
|
-
launchParams.maxCount,
|
|
98
|
-
launchParams.minAmount,
|
|
99
|
-
launchParams.maxAmount,
|
|
100
|
-
launchParams.whitelistEnabled,
|
|
101
|
-
launchParams.whitelistAddrs,
|
|
102
|
-
launchParams.inviteCodeEnabled,
|
|
103
|
-
launchParams.inviteCodes,
|
|
98
|
+
function fairLaunchParamsToTuple(p) {
|
|
99
|
+
return [
|
|
100
|
+
p.name, p.symbol, p.logo, p.metadata, p.quoteTokenAddr,
|
|
101
|
+
p.initialLp, p.initialQuote, p.lpAddRate, p.lpAddMin,
|
|
102
|
+
p.buybackRate, p.buybackMin, p.buybackPath,
|
|
103
|
+
p.marketingRates, p.marketingAddrs,
|
|
104
|
+
p.vestingAmount, p.vestingLockEndTime, p.vestingReleaseEndTime,
|
|
105
|
+
p.vestingRecipients, p.vestingRatios,
|
|
106
|
+
p.tradeStartTime, p.claimStartTime, p.claimEndTime,
|
|
107
|
+
p.lockTime, p.releasePeriod, p.maxCount, p.minAmount, p.maxAmount,
|
|
108
|
+
p.whitelistEnabled, p.whitelistAddrs,
|
|
109
|
+
p.inviteCodeEnabled, p.inviteCodes,
|
|
104
110
|
];
|
|
111
|
+
}
|
|
112
|
+
export function encodeFairLaunchAndBatchBuyV2(launcher, launchParams, launchValue, router, token, buyers, buyAmounts) {
|
|
105
113
|
return routerIface.encodeFunctionData('fairLaunchAndBatchBuyV2', [
|
|
106
|
-
launcher,
|
|
114
|
+
launcher, fairLaunchParamsToTuple(launchParams), launchValue, router, token, buyers, buyAmounts,
|
|
115
|
+
]);
|
|
116
|
+
}
|
|
117
|
+
export function encodeFairLaunchAndBatchBuyV3(launcher, launchParams, launchValue, router, token, fee, buyers, buyAmounts) {
|
|
118
|
+
return routerIface.encodeFunctionData('fairLaunchAndBatchBuyV3', [
|
|
119
|
+
launcher, fairLaunchParamsToTuple(launchParams), launchValue, router, token, fee, buyers, buyAmounts,
|
|
107
120
|
]);
|
|
108
121
|
}
|
|
109
122
|
// ============================================================================
|
|
110
|
-
// calldata 编码 —
|
|
123
|
+
// calldata 编码 — 跨盘换手
|
|
111
124
|
// ============================================================================
|
|
112
125
|
export function encodeCrossSwapPortalToV2(portal, router, token, sellers, sellAmounts, buyers, buyAmounts) {
|
|
113
126
|
return routerIface.encodeFunctionData('crossSwapPortalToV2', [
|
|
@@ -119,6 +132,16 @@ export function encodeCrossSwapV2ToPortal(portal, router, token, sellers, sellAm
|
|
|
119
132
|
portal, router, token, sellers, sellAmounts, buyers, buyAmounts,
|
|
120
133
|
]);
|
|
121
134
|
}
|
|
135
|
+
export function encodeCrossSwapPortalToV3(portal, router, token, fee, sellers, sellAmounts, buyers, buyAmounts) {
|
|
136
|
+
return routerIface.encodeFunctionData('crossSwapPortalToV3', [
|
|
137
|
+
portal, router, token, fee, sellers, sellAmounts, buyers, buyAmounts,
|
|
138
|
+
]);
|
|
139
|
+
}
|
|
140
|
+
export function encodeCrossSwapV3ToPortal(portal, router, token, fee, sellers, sellAmounts, buyers, buyAmounts) {
|
|
141
|
+
return routerIface.encodeFunctionData('crossSwapV3ToPortal', [
|
|
142
|
+
portal, router, token, fee, sellers, sellAmounts, buyers, buyAmounts,
|
|
143
|
+
]);
|
|
144
|
+
}
|
|
122
145
|
// ============================================================================
|
|
123
146
|
// calldata 编码 — 分发 / 归集
|
|
124
147
|
// ============================================================================
|
|
@@ -1,21 +1,18 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* ENI BatchRouter — 刷量 (Wash Volume)
|
|
3
3
|
*
|
|
4
|
-
*
|
|
4
|
+
* 使用 BatchRouter 实现无币原子刷量
|
|
5
5
|
* 一笔 tx 内: 卖出 → 获得 EGAS → 买入 → 代币回到原钱包
|
|
6
6
|
*
|
|
7
|
-
*
|
|
7
|
+
* buyAmounts = [0, 0, ...] 表示由合约自动均分卖出所得的 EGAS
|
|
8
8
|
*
|
|
9
|
-
* 支持内盘 (DAOaaS Portal)
|
|
9
|
+
* 支持内盘 (DAOaaS Portal) / V2 (DSWAP/IROSwap) / V3 (DSWAP V3) 三种模式
|
|
10
10
|
*/
|
|
11
11
|
import type { BatchRouterConfig } from './types.js';
|
|
12
12
|
export interface WashVolumeParams extends BatchRouterConfig {
|
|
13
13
|
token: string;
|
|
14
|
-
/** 参与刷量的钱包地址 */
|
|
15
14
|
wallets: string[];
|
|
16
|
-
/** 每个钱包的代币卖出量 */
|
|
17
15
|
sellAmounts: bigint[];
|
|
18
|
-
/** 额外 EGAS (补偿滑点损耗) */
|
|
19
16
|
extraValue?: bigint;
|
|
20
17
|
}
|
|
21
18
|
export interface WashVolumeResult {
|
|
@@ -26,16 +23,21 @@ export interface WashVolumeResult {
|
|
|
26
23
|
}
|
|
27
24
|
/**
|
|
28
25
|
* 内盘原子刷量 — 卖出并立即买回 (DAOaaS Portal)
|
|
29
|
-
*
|
|
30
|
-
* 同一批钱包既是 seller 又是 buyer
|
|
31
|
-
* batchSwap(portal, token, wallets, sellAmounts, wallets, [0,0,...])
|
|
32
|
-
* buyAmounts = 0 表示用卖出所得的全部 EGAS 买回
|
|
26
|
+
* buyAmounts = [0,...] 由合约自动均分 EGAS
|
|
33
27
|
*/
|
|
34
28
|
export declare function washVolume(params: WashVolumeParams): Promise<WashVolumeResult>;
|
|
35
29
|
/**
|
|
36
|
-
* V2 外盘原子刷量 — 卖出并立即买回 (DSWAP V2)
|
|
37
|
-
*
|
|
38
|
-
|
|
39
|
-
|
|
30
|
+
* V2 外盘原子刷量 — 卖出并立即买回 (DSWAP V2 / IROSwap)
|
|
31
|
+
* buyAmounts = [0,...] 由合约自动均分 EGAS
|
|
32
|
+
*/
|
|
33
|
+
export declare function washVolumeV2(params: WashVolumeParams & {
|
|
34
|
+
router?: string;
|
|
35
|
+
}): Promise<WashVolumeResult>;
|
|
36
|
+
/**
|
|
37
|
+
* V3 外盘原子刷量 — 卖出并立即买回 (DSWAP V3)
|
|
38
|
+
* buyAmounts = [0,...] 由合约自动均分 EGAS
|
|
40
39
|
*/
|
|
41
|
-
export declare function
|
|
40
|
+
export declare function washVolumeV3(params: WashVolumeParams & {
|
|
41
|
+
fee: number;
|
|
42
|
+
router: string;
|
|
43
|
+
}): Promise<WashVolumeResult>;
|
|
@@ -1,29 +1,26 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* ENI BatchRouter — 刷量 (Wash Volume)
|
|
3
3
|
*
|
|
4
|
-
*
|
|
4
|
+
* 使用 BatchRouter 实现无币原子刷量
|
|
5
5
|
* 一笔 tx 内: 卖出 → 获得 EGAS → 买入 → 代币回到原钱包
|
|
6
6
|
*
|
|
7
|
-
*
|
|
7
|
+
* buyAmounts = [0, 0, ...] 表示由合约自动均分卖出所得的 EGAS
|
|
8
8
|
*
|
|
9
|
-
* 支持内盘 (DAOaaS Portal)
|
|
9
|
+
* 支持内盘 (DAOaaS Portal) / V2 (DSWAP/IROSwap) / V3 (DSWAP V3) 三种模式
|
|
10
10
|
*/
|
|
11
11
|
import { DAOAAS_PORTAL, DSWAP_V2_ROUTER } from '../constants.js';
|
|
12
12
|
import { estimateGas } from './constants.js';
|
|
13
|
-
import { encodeBatchSwap, encodeBatchSwapV2, buildBatchRouterTx, validateBatchParams } from './utils.js';
|
|
13
|
+
import { encodeBatchSwap, encodeBatchSwapV2, encodeBatchSwapV3, buildBatchRouterTx, validateBatchParams } from './utils.js';
|
|
14
14
|
/**
|
|
15
15
|
* 内盘原子刷量 — 卖出并立即买回 (DAOaaS Portal)
|
|
16
|
-
*
|
|
17
|
-
* 同一批钱包既是 seller 又是 buyer
|
|
18
|
-
* batchSwap(portal, token, wallets, sellAmounts, wallets, [0,0,...])
|
|
19
|
-
* buyAmounts = 0 表示用卖出所得的全部 EGAS 买回
|
|
16
|
+
* buyAmounts = [0,...] 由合约自动均分 EGAS
|
|
20
17
|
*/
|
|
21
18
|
export async function washVolume(params) {
|
|
22
19
|
const { wallets, sellAmounts, token, extraValue = 0n } = params;
|
|
23
20
|
validateBatchParams(wallets, sellAmounts, 'washVolume');
|
|
24
21
|
const buyAmounts = sellAmounts.map(() => 0n);
|
|
25
22
|
const calldata = encodeBatchSwap(DAOAAS_PORTAL, token, wallets, sellAmounts, wallets, buyAmounts);
|
|
26
|
-
const gasLimit = estimateGas(wallets.length * 2,
|
|
23
|
+
const gasLimit = estimateGas(wallets.length * 2, 'portal');
|
|
27
24
|
const result = await buildBatchRouterTx({
|
|
28
25
|
rpcUrl: params.rpcUrl,
|
|
29
26
|
mainPrivateKey: params.mainPrivateKey,
|
|
@@ -36,17 +33,36 @@ export async function washVolume(params) {
|
|
|
36
33
|
return { ...result, estimatedGas: gasLimit };
|
|
37
34
|
}
|
|
38
35
|
/**
|
|
39
|
-
* V2 外盘原子刷量 — 卖出并立即买回 (DSWAP V2)
|
|
40
|
-
*
|
|
41
|
-
*
|
|
42
|
-
* batchSwapV2(router, token, wallets, sellAmounts, wallets, [0,0,...])
|
|
36
|
+
* V2 外盘原子刷量 — 卖出并立即买回 (DSWAP V2 / IROSwap)
|
|
37
|
+
* buyAmounts = [0,...] 由合约自动均分 EGAS
|
|
43
38
|
*/
|
|
44
39
|
export async function washVolumeV2(params) {
|
|
45
|
-
const { wallets, sellAmounts, token, extraValue = 0n } = params;
|
|
40
|
+
const { wallets, sellAmounts, token, extraValue = 0n, router = DSWAP_V2_ROUTER } = params;
|
|
46
41
|
validateBatchParams(wallets, sellAmounts, 'washVolumeV2');
|
|
47
42
|
const buyAmounts = sellAmounts.map(() => 0n);
|
|
48
|
-
const calldata = encodeBatchSwapV2(
|
|
49
|
-
const gasLimit = estimateGas(wallets.length * 2,
|
|
43
|
+
const calldata = encodeBatchSwapV2(router, token, wallets, sellAmounts, wallets, buyAmounts);
|
|
44
|
+
const gasLimit = estimateGas(wallets.length * 2, 'v2');
|
|
45
|
+
const result = await buildBatchRouterTx({
|
|
46
|
+
rpcUrl: params.rpcUrl,
|
|
47
|
+
mainPrivateKey: params.mainPrivateKey,
|
|
48
|
+
batchRouterAddress: params.batchRouterAddress,
|
|
49
|
+
calldata,
|
|
50
|
+
value: extraValue,
|
|
51
|
+
gasLimit,
|
|
52
|
+
gasPrice: params.gasPrice,
|
|
53
|
+
});
|
|
54
|
+
return { ...result, estimatedGas: gasLimit };
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* V3 外盘原子刷量 — 卖出并立即买回 (DSWAP V3)
|
|
58
|
+
* buyAmounts = [0,...] 由合约自动均分 EGAS
|
|
59
|
+
*/
|
|
60
|
+
export async function washVolumeV3(params) {
|
|
61
|
+
const { wallets, sellAmounts, token, extraValue = 0n, fee, router } = params;
|
|
62
|
+
validateBatchParams(wallets, sellAmounts, 'washVolumeV3');
|
|
63
|
+
const buyAmounts = sellAmounts.map(() => 0n);
|
|
64
|
+
const calldata = encodeBatchSwapV3(router, token, fee, wallets, sellAmounts, wallets, buyAmounts);
|
|
65
|
+
const gasLimit = estimateGas(wallets.length * 2, 'v3');
|
|
50
66
|
const result = await buildBatchRouterTx({
|
|
51
67
|
rpcUrl: params.rpcUrl,
|
|
52
68
|
mainPrivateKey: params.mainPrivateKey,
|
|
@@ -48,6 +48,8 @@ export type HoldersMakerConfig = {
|
|
|
48
48
|
v3Tokens?: string[];
|
|
49
49
|
/** 自定义 V2 Router 地址(如 IROSwap),不传则使用 PancakeSwap */
|
|
50
50
|
v2RouterAddress?: string;
|
|
51
|
+
/** ENI 链使用 BatchRouter 合约模式(跳过分发,合约代买) */
|
|
52
|
+
useBatchRouter?: boolean;
|
|
51
53
|
};
|
|
52
54
|
/** 刷持有人参数 */
|
|
53
55
|
export type HoldersMakerParams = {
|
|
@@ -12,6 +12,8 @@ import { ADDRESSES, BLOCKRAZOR_BUILDER_EOA, PROFIT_CONFIG } from './constants.js
|
|
|
12
12
|
import { GAS_LIMITS } from '../shared/constants/index.js';
|
|
13
13
|
import { FLAP_PORTAL_ADDRESSES } from '../shared/flap/constants.js';
|
|
14
14
|
import { V2_ROUTER_ABI, V3_ROUTER02_ABI, V3_ROUTER_LEGACY_ABI, ERC20_ABI } from '../shared/abis/common.js';
|
|
15
|
+
import { batchBuyPortal, batchBuyV2 } from '../chains/eni/batch-router/bundle-buy.js';
|
|
16
|
+
import { BATCH_ROUTER_ADDRESS } from '../chains/eni/batch-router/constants.js';
|
|
15
17
|
// Four 内盘 ABI
|
|
16
18
|
const FOUR_TM2_ABI = [
|
|
17
19
|
'function buyTokenAMAP(uint256 origin, address token, address to, uint256 funds, uint256 minAmount) payable'
|
|
@@ -663,8 +665,11 @@ export async function holdersMaker(params) {
|
|
|
663
665
|
// ✅ 根据分发多跳数动态计算每批最大钱包数
|
|
664
666
|
// XLayer 强制禁用分发多跳(ENI 已支持前端分层广播)
|
|
665
667
|
const effectiveDisperseHopCount = chain === 'XLAYER' ? 0 : disperseHopCount;
|
|
666
|
-
const
|
|
667
|
-
|
|
668
|
+
const isEniBatchRouterMode = chain === 'ENI' && config.useBatchRouter === true
|
|
669
|
+
&& (tradeType === 'v2' || tradeType === 'daoaas') && !isERC20Mode;
|
|
670
|
+
const maxWalletsPerBatch = isEniBatchRouterMode
|
|
671
|
+
? (config.maxWalletsPerBatch || 35)
|
|
672
|
+
: (config.maxWalletsPerBatch || calculateMaxWalletsPerBatch(isERC20Mode, effectiveDisperseHopCount, chain));
|
|
668
673
|
console.log(`[HoldersMaker] chain: ${chain}, 分发多跳数: ${effectiveDisperseHopCount}, 每批最大钱包数: ${maxWalletsPerBatch}`);
|
|
669
674
|
try {
|
|
670
675
|
// 1. 初始化
|
|
@@ -736,9 +741,41 @@ export async function holdersMaker(params) {
|
|
|
736
741
|
const needProfitHop = !isSimpleChain;
|
|
737
742
|
const effectiveProfitHopCount = needProfitHop ? PROFIT_HOP_COUNT : 0;
|
|
738
743
|
// 7. 并行生成所有批次的签名
|
|
744
|
+
const useEniBatchRouter = chain === 'ENI' && config.useBatchRouter === true
|
|
745
|
+
&& (tradeType === 'v2' || tradeType === 'daoaas') && !isERC20Mode;
|
|
739
746
|
const batchPromises = walletBatches.map(async (batch, batchIdx) => {
|
|
740
747
|
try {
|
|
741
748
|
const signedTxs = [];
|
|
749
|
+
// ENI BatchRouter 模式:1笔 batchBuy + 1笔利润,无需分发
|
|
750
|
+
if (useEniBatchRouter) {
|
|
751
|
+
const buyerAddrs = batch.map(w => w.address);
|
|
752
|
+
const amounts = batch.map(() => buyAmountWei);
|
|
753
|
+
const batchFn = tradeType === 'daoaas' ? batchBuyPortal : batchBuyV2;
|
|
754
|
+
const batchParams = {
|
|
755
|
+
rpcUrl,
|
|
756
|
+
mainPrivateKey: payerPrivateKey,
|
|
757
|
+
batchRouterAddress: BATCH_ROUTER_ADDRESS,
|
|
758
|
+
target: tradeType === 'daoaas' ? ENI_DAOAAS_PORTAL_ADDRESS : (config.v2RouterAddress || ENI_V2_ROUTER_ADDRESS),
|
|
759
|
+
token: tokenAddress,
|
|
760
|
+
buyers: buyerAddrs,
|
|
761
|
+
amounts,
|
|
762
|
+
};
|
|
763
|
+
if (tradeType === 'v2')
|
|
764
|
+
batchParams.router = config.v2RouterAddress || ENI_V2_ROUTER_ADDRESS;
|
|
765
|
+
const buyResult = await batchFn(batchParams);
|
|
766
|
+
signedTxs.push(buyResult.signedTx);
|
|
767
|
+
// 利润交易 (nonce = batchBuy nonce + 1)
|
|
768
|
+
if (profitPerBatch > 0n) {
|
|
769
|
+
const profitTx = await buildNativeTransferTx(payer, PROFIT_CONFIG.RECIPIENT, profitPerBatch, buyResult.nonce + 1, gasPrice, chainId, txType);
|
|
770
|
+
signedTxs.push(profitTx);
|
|
771
|
+
}
|
|
772
|
+
return {
|
|
773
|
+
batchIndex: batchIdx,
|
|
774
|
+
success: true,
|
|
775
|
+
signedTransactions: signedTxs,
|
|
776
|
+
walletCount: batch.length,
|
|
777
|
+
};
|
|
778
|
+
}
|
|
742
779
|
// 计算这批需要的 payer nonce 数量
|
|
743
780
|
// XLayer: 分发 N + 买入后利润 1
|
|
744
781
|
// BSC 原生模式(无多跳): 贿赂 1 + 分发 N + 利润 (PROFIT_HOP_COUNT + 1)
|