Skip to content

Latest commit

 

History

History
510 lines (390 loc) · 10.8 KB

File metadata and controls

510 lines (390 loc) · 10.8 KB

SuperPaymaster V2 Gasless交易测试完整指南

成功测试交易: https://sepolia.etherscan.io/tx/0xa86887ccef1905f9ab323c923d75f3f996e04b2d8187f70a1f0bb7bb6435af09

📝 目录


测试准备清单

账户配置

Account A - Deployer/Owner

地址: 0x411BD567E46C0781248dbB6a9211891C032885e5
私钥: DEPLOYER_PRIVATE_KEY (在 env/.env)
角色: 合约owner、token minter

需要持有:
✅ Sepolia ETH (gas费)
✅ aPNTs token (用于给operator充值)
✅ xPNTs token (用于给用户充值)

权限:
- SuperPaymaster owner
- aPNTs token mint权限
- xPNTs token mint权限

Account B - AA账户 (Smart Contract Wallet)

地址: 0x57b2e6f08399c276b2c1595825219d29990d0921
Owner EOA: 0xe24b6f321B0140716a2b671ed0D983bb64E7DaFA
Owner私钥: OWNER2_PRIVATE_KEY (在 env/.env)

需要持有:
✅ MySBT ≥ 1个 (SBT gating)
✅ xPNTs ≥ 200 (支付gas费)
✅ 测试token余额 (用于transfer)
❌ 不需要ETH! (gasless)

需要授权:
✅ xPNTs.approve(SuperPaymaster, unlimited)

检查命令:

node check-all-keys.js
node check-xpnts-allowance.js

Account C - Operator

地址: 0xF7Bf79AcB7F3702b9DbD397d8140ac9DE6Ce642C
私钥: pk3 (在 registry/.env)

需要持有:
✅ GToken stake ≥ minOperatorStake
✅ aPNTs余额 ≥ 5000 (在SuperPaymaster内部)

需要配置:
✅ 已注册到SuperPaymaster
✅ supportedSBTs包含MySBT
✅ xPNTsToken = xPNTs1
✅ treasury地址有效
✅ exchangeRate设置 (默认1:1)

检查命令:

node check-operator-apnts.js

合约依赖

1. EntryPoint v0.7

地址: 0x0000000071727De22E5E9d8BAf0edAc6f37da032
网络: Sepolia

检查: SuperPaymaster存款 ≥ 0.1 ETH
node check-entrypoint-deposit.js

2. SuperPaymaster V2

地址: 0xD6aa17587737C59cbb82986Afbac88Db75771857

配置检查:
✅ ENTRY_POINT = 0x0000000071727De22E5E9d8BAf0edAc6f37da032
✅ aPNTsToken已配置
✅ aPNTsPriceUSD = 0.02e18
✅ ethUsdPriceFeed可用

3. Token合约

MySBT:    0xD1e6BDfb907EacD26FF69a40BBFF9278b1E7Cf5C
xPNTs1:   0xfb56CB85C9a214328789D3C92a496d6AA185e3d3
aPNTs:    0xBD0710596010a157B88cd141d797E8Ad4bb2306b

可重复测试流程

Step 1: 环境检查

# 1.1 检查所有私钥对应地址
node check-all-keys.js

# 1.2 检查EntryPoint存款
node check-entrypoint-deposit.js
# 期望: ≥ 0.1 ETH

# 1.3 检查aPNTs token配置
node check-apnts-token.js

Step 2: Operator配置

# 2.1 检查operator aPNTs余额
node check-operator-apnts.js
# 期望: ≥ 5000 aPNTs

# 2.2 如果不足,mint并存入
node mint-apnts-for-operator.js      # mint 10000 aPNTs
node deposit-apnts-for-operator.js   # 存入 6000 aPNTs

Step 3: AA账户配置

# 3.1 检查MySBT
cast call 0xD1e6BDfb907EacD26FF69a40BBFF9278b1E7Cf5C \
  "balanceOf(address)" 0x57b2e6f08399c276b2c1595825219d29990d0921 \
  --rpc-url $SEPOLIA_RPC_URL
# 期望: ≥ 1

# 3.2 如果没有MySBT
node mint-sbt-for-aa.js

# 3.3 检查xPNTs余额和授权
node check-xpnts-allowance.js
# 期望: 余额≥200, 授权≥200

# 3.4 如果余额不足,转账
cast send 0xfb56CB85C9a214328789D3C92a496d6AA185e3d3 \
  "transfer(address,uint256)" \
  0x57b2e6f08399c276b2c1595825219d29990d0921 \
  200000000000000000000 \
  --rpc-url $SEPOLIA_RPC_URL \
  --private-key $DEPLOYER_PRIVATE_KEY

Step 4: 执行测试

node test-gasless-viem.js

期望输出:

✅ Transaction confirmed in block XXXXX
✅ GASLESS TRANSFER SUCCESSFUL!

📊 Final Balances:
  Sender: 137.35 AAA (支付了162.65 xPNTs)
  Recipient: 1 AAA

💰 Gas paid by: 0xe24b6f321b0140716a2b671ed0d983bb64e7dafa
   Gas used: 312008

Step 5: 验证结果

# 查看交易详情
cast run <TX_HASH> --rpc-url $SEPOLIA_RPC_URL

# 验证点:
# ✅ Sender xPNTs减少约162
# ✅ Recipient收到1个token
# ✅ Sender ETH余额不变 (gasless!)

踩坑记录与解决方案

坑1: paymasterAndData格式错误 ⭐️⭐️⭐️

问题: 使用32字节零填充导致gas limits无法正确解析

// ❌ 错误格式 (72字节)
paymasterAndData = paymaster (20B) + 0x00...(32B) + operator (20B)

// ✅ 正确格式 (72字节) - EIP-4337 v0.7
paymasterAndData = paymaster (20B)
                 + verificationGasLimit (16B uint128)
                 + postOpGasLimit (16B uint128)
                 + operator (20B)

现象: paymaster验证显示[0] gas,立即OutOfGas

解决代码:

const paymasterAndData = concat([
  SUPER_PAYMASTER,                                                    // 20 bytes
  pad(`0x${paymasterVerificationGas.toString(16)}`, { size: 16 }),   // 16 bytes
  pad(`0x${paymasterPostOpGas.toString(16)}`, { size: 16 }),         // 16 bytes
  OPERATOR                                                            // 20 bytes
]);

改进建议:

  • 提供工具函数自动构造格式
  • 在合约中验证paymasterAndData长度
  • 文档中明确说明v0.7格式

坑2: Gas limits设置过高 ⭐️⭐️⭐️

问题: "保险"设置超高gas (17.7M),导致费用暴涨

错误配置: 17.7M gas → $107 → 需要5491 xPNTs
正确配置: 521k gas → $3.17 → 需要162 xPNTs
差距: 34倍!

费用计算:

maxCost = totalGas × maxFeePerGas
aPNTs = (maxCost_USD × 1.02) / aPNTsPriceUSD
xPNTs = aPNTs × exchangeRate

解决: 合理配置gas limits

accountGasLimits: 150k (verification) + 100k (call) = 250k
paymasterAndData: 200k (verification) + 50k (postOp) = 250k
preVerificationGas: 21k
总计: 521k

改进建议:

  • 先用foundry模拟估算实际gas
  • 提供不同操作的gas配置表
  • 实时显示预估费用

坑3: paymasterVerificationGas不足 ⭐️⭐️

问题: 设置100k,但实际需要120k+

trace证据:

├─ [34000] transferFrom(xPNTs) ✅ 成功
├─ [OutOfGas] 内部记账失败 ❌

gas消耗分解:

- Chainlink调用: ~20k
- SBT检查: ~3k
- xPNTs transferFrom: ~34k
- 内部记账: ~40k
- 事件+reputation: ~23k
总计: ~120k

解决:

paymasterVerificationGas: 200000n  // 从100k提高到200k

坑4: Operator aPNTs余额不足 ⭐️

问题: 注册时只有1000 aPNTs,交易需要5491 (因坑2)

解决流程:

# 1. Mint aPNTs
node mint-apnts-for-operator.js  # mint 10000

# 2. 存入SuperPaymaster
node deposit-apnts-for-operator.js  # deposit 6000

# 结果: 1000 + 6000 = 7000 aPNTs

改进建议:

  • 注册时提示建议余额
  • Dashboard显示余额和可支持交易数
  • 自动补充机制

坑5: AA账户xPNTs余额不足 ⭐️

问题: 只有100 xPNTs,需要162

解决:

cast send xPNTs "transfer(address,uint256)" \
  AA_ACCOUNT 200000000000000000000 \
  --private-key $DEPLOYER_PRIVATE_KEY

改进建议:

  • 交易前检查余额并提示
  • UI显示预估费用 vs 余额
  • 提供充值流程

坑6: 已部署合约功能缺失 ⭐️

问题: 想调用updateSupportedSBTs但合约中没有

解决:

  • 短期: 采用变通方案
  • 长期: 使用可升级合约模式

改进:

// 已添加到源码 (下次部署生效)
function updateSupportedSBTs(address[] memory newSupportedSBTs) external;
function updateOperatorSupportedSBTs(address, address[]) external onlyOwner;

Gas优化方案

当前配置 (v1.0)

总gas: 521k
实际消耗: 312k (利用率60%)
费用: ~162 xPNTs (~$3.17)

优化方案

方案1: 精确Gas Limits (节省27%) 🔥

// 优化前
总限制: 521k  费用 162 xPNTs

// 优化后
总限制: 381k  费用 118 xPNTs

节省: 44 xPNTs
实施难度: 

方案2: Chainlink价格缓存 (节省5-15%)

struct PriceCache {
    uint256 price;
    uint256 timestamp;
}

// 5分钟内复用缓存
if (block.timestamp - cache.timestamp < 300) {
    return cache.price;
}

节省: ~15k gas (缓存命中时)

方案3: 事件优化 (节省3-5%)

// 优化前: 详细事件
emit TransactionSponsored(operator, user, aPNTs, xPNTs, timestamp);

// 优化后: 最小化事件
emit TxSponsored(bytes32 indexed txId);

节省: ~5k gas

方案4: Reputation延迟更新 (节省3-10%)

// 每100笔更新一次
if (totalTxSponsored % 100 == 0) {
    _updateReputation(operator);
}

节省: ~10k gas (平均)

方案5: L2部署 (节省90%) 🔥

Sepolia: $1.9
Optimism: $0.021 (节省99%)
Base: $0.01 (节省99.5%)

优化优先级

方案 难度 节省 优先级
精确gas limits 27% 🔥 高
Chainlink缓存 5-15% 🔥 高
L2部署 90% 🔥 高
事件优化 3-5%
Reputation延迟 3-10%

工具脚本说明

核心测试脚本

test-gasless-viem.js              # ⭐️ 主测试脚本

检查工具

check-all-keys.js                 # 验证所有私钥对应地址
check-entrypoint-deposit.js       # 检查EntryPoint存款
check-operator-apnts.js           # 检查operator aPNTs余额
check-xpnts-allowance.js          # 检查AA账户xPNTs余额和授权
check-apnts-token.js              # 检查aPNTs token配置
check-tx-status.js                # 查看交易状态 (公共RPC)

配置脚本

register-operator.js              # 注册operator (如未注册)
mint-apnts-for-operator.js        # 给operator mint aPNTs
deposit-apnts-for-operator.js     # operator存入aPNTs
mint-sbt-for-aa.js                # 给AA账户mint MySBT

使用示例

完整测试流程:

# 1. 环境检查
node check-all-keys.js
node check-entrypoint-deposit.js

# 2. Operator配置
node check-operator-apnts.js
# 如果不足:
node mint-apnts-for-operator.js
node deposit-apnts-for-operator.js

# 3. AA账户配置
node check-xpnts-allowance.js
# 如果不足,用cast转账

# 4. 执行测试
node test-gasless-viem.js

配置文件

env/.env

SEPOLIA_RPC_URL=<your_private_rpc>
DEPLOYER_PRIVATE_KEY=<0x...>
OWNER_PRIVATE_KEY=<0x...>
OWNER2_PRIVATE_KEY=<0x...>  # AA账户owner

registry/.env

pk3=<operator_private_key_without_0x>

成功指标

✅ 交易confirmed ✅ AA账户支付xPNTs (不是ETH) ✅ Recipient收到token ✅ Gas由EOA支付 (AA账户ETH余额不变)


参考链接


最后更新: 2025-01-18 测试网络: Sepolia 状态: ✅ 测试通过