You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何通过HTTP/WSS获取特定ERC20合约全量交易?遇事件差异问题

解决ERC20合约非Transfer事件日志获取问题

问题根源

你的代码硬编码了ERC20标准Transfer事件的topic(0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef),只会返回触发了Transfer事件的日志。而部分合约(比如关联DEX的ERC20)会触发Swap、Mint、Burn等其他事件,这些事件的topic不在你的过滤列表里,自然拿不到结果。

解决方案

方案1:批量获取合约所有事件的topic

如果需要抓取该合约的多类事件日志,先通过合约ABI提取所有事件的topic,再加入过滤列表:

# 替换为目标合约的ABI(可从区块浏览器导出,或通过链上解析获取)
erc20_abi = [...]
checksum_address = web3.toChecksumAddress(erc_20_contract)

# 从ABI生成所有事件的topic
contract_instance = web3.eth.contract(address=checksum_address, abi=erc20_abi)
event_topics = [event.build_filter().topics[0] for event in contract_instance.events]

# 构建包含所有事件的过滤器
filter_params = {
    'fromBlock': int(start_block),
    'toBlock': int(end_block),
    'address': checksum_address,
    'topics': [event_topics]  # 数组包裹表示匹配任意一个topic
}

raw_logs = web3.eth.get_logs(filter_params)

方案2:获取合约所有日志后再筛选

如果需要该合约在指定区块内的全部事件日志,可以直接移除topics参数,拿到所有日志后再根据topic区分事件类型:

checksum_address = web3.toChecksumAddress(erc_20_contract)

filter_params = {
    'fromBlock': int(start_block),
    'toBlock': int(end_block),
    'address': checksum_address
}

raw_logs = web3.eth.get_logs(filter_params)

# 遍历日志区分事件
for log in raw_logs:
    event_topic = log['topics'][0].hex()
    if event_topic == '0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef':
        # 处理Transfer事件
        pass
    elif event_topic == '0xd78ad95fa46c994b6551d0da85fc275fe613ce37657fb8d5e3d130840159d822':
        # 处理Uniswap V2 Swap事件示例
        pass

方案3:指定特定非Transfer事件的topic

如果只需要抓取某类特定事件(比如Swap),直接添加对应事件的topic到过滤列表即可:

checksum_address = web3.toChecksumAddress(erc_20_contract)
logs_topics = [
    '0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef',  # Transfer事件
    '0xd78ad95fa46c994b6551d0da85fc275fe613ce37657fb8d5e3d130840159d822'   # Swap事件示例
]

filter_params = {
    'fromBlock': int(start_block),
    'toBlock': int(end_block),
    'address': checksum_address,
    'topics': [logs_topics]
}

raw_logs = web3.eth.get_logs(filter_params)

注意事项

  • 若没有合约ABI,可通过web3.eth.getCode(checksum_address)获取字节码,再用本地解析工具生成ABI。
  • 不同合约的同类型事件topic可能因实现差异不同,需以合约实际ABI生成的topic为准。

内容的提问来源于stack exchange,提问作者LEGENDRYzZzZ

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.23 19:12:38