基础数据抓取:获取最新区块、解析交易详情、提取交易哈希列表
说实话,链上数据分析的第一步,就是得知道怎么跟区块链节点「对话」。很多新手一上来就想着跑复杂的策略,结果连最基础的区块数据都拿不到——我当年也踩过这个坑。
今天咱们就手把手搞定三件事:获取最新区块、解析交易详情、提取交易哈希列表。这三板斧练熟了,后面分析聪明钱才有底气。
1. 准备工作:选对工具链
我个人习惯用 Web3.py 这个库。为什么?因为它是对以太坊最友好的 Python 库,文档全,社区活跃。你想想看,如果连文档都查不到,遇到 bug 得多痛苦。
先装好依赖:
pip install web3 requests
然后连接节点。这里有两个选择:
- 公共节点(比如 Infura、Alchemy)—— 免费但有速率限制,适合学习和测试
- 自建节点(比如 Geth、Erigon)—— 稳定、无限制,但需要服务器资源
我的建议:刚开始用 Infura 就够了。注册一个免费账号,拿到项目 ID 就能用。等你要跑生产环境了,再考虑自建节点。
连接代码很简单:
from web3 import Web3
# 用 Infura 举例
infura_url = "https://mainnet.infura.io/v3/YOUR_PROJECT_ID"
w3 = Web3(Web3.HTTPProvider(infura_url))
# 检查是否连接成功
print(w3.is_connected()) # 返回 True 就对了
2. 获取最新区块:别只盯着高度
获取最新区块,最直接的方法是:
latest_block = w3.eth.get_block('latest')
print(latest_block)
但这里有个坑——get_block('latest') 返回的是 完整的区块对象,里面包含所有交易详情。如果你只想要区块头信息,用 get_block('latest', full_transactions=False) 会更高效。
注意:如果区块里交易很多(比如 200 笔以上),拉取完整数据会非常慢。我曾经在分析某个热门 NFT 项目时,一个区块就卡了 10 秒——后来才发现是忘了设 full_transactions=False。
区块对象里有哪些关键字段?我整理了一张表:
| 字段 | 含义 | 用途 |
|---|---|---|
| number | 区块高度 | 定位区块位置 |
| timestamp | 出块时间戳 | 计算时间间隔 |
| transactions | 交易列表 | 提取交易哈希 |
| gas_used | 已用 Gas | 评估网络拥堵 |
| base_fee_per_gas | 基础费用 | EIP-1559 后的 Gas 计算 |
3. 解析交易详情:从哈希到完整信息
拿到区块后,下一步就是解析交易。交易哈希(tx hash)是交易的唯一标识,就像人的身份证号。
提取交易哈希列表:
block = w3.eth.get_block('latest', full_transactions=False)
tx_hashes = block['transactions']
print(f"最新区块包含 {len(tx_hashes)} 笔交易")
print(tx_hashes[:5]) # 只看前 5 笔
然后根据哈希获取交易详情:
for tx_hash in tx_hashes[:3]: # 先看 3 笔
tx = w3.eth.get_transaction(tx_hash)
print(f"交易哈希: {tx_hash.hex()}")
print(f"发送方: {tx['from']}")
print(f"接收方: {tx['to']}")
print(f"金额: {w3.from_wei(tx['value'], 'ether')} ETH")
print("---")
核心知识点:交易对象里的
value 单位是 Wei,一定要用 w3.from_wei() 转换成 ETH 或 Gwei,否则你会看到一串天文数字。
交易对象还有几个重要字段:
- gas:发送方愿意支付的最大 Gas 量
- gas_price:Gas 单价(EIP-1559 前)或 max_fee_per_gas(EIP-1559 后)
- input:交易携带的数据,合约调用时就是 calldata
- nonce:发送方的交易序号,防止重放攻击
4. 实战:批量抓取并保存
光看单个区块不过瘾,咱们写个函数批量抓取:
def fetch_blocks_and_txs(start_block, end_block):
for block_num in range(start_block, end_block + 1):
block = w3.eth.get_block(block_num, full_transactions=True)
print(f"区块 {block_num} 时间: {block['timestamp']}")
for tx in block['transactions']:
# 提取关键信息
tx_info = {
'hash': tx['hash'].hex(),
'from': tx['from'],
'to': tx['to'],
'value': w3.from_wei(tx['value'], 'ether'),
'gas_price': tx.get('gas_price', 0),
}
# 这里可以存到数据库或 CSV
print(tx_info)
# 抓取最近 5 个区块
fetch_blocks_and_txs(19000000, 19000004)
避坑指南:我曾经一次性抓取 1000 个区块,结果被 Infura 限流了半小时。建议每次请求间隔 0.2 秒,或者用
time.sleep(0.2) 控制频率。
5. 知识体系总览
下面这张图帮你理清本章的核心逻辑:
6. 常见问题与调试技巧
抓数据时难免遇到问题,我分享几个经验:
- 连接超时:检查网络,或者换一个节点。公共节点偶尔会挂。
- 数据格式不对:记得用
hex()转换哈希,用from_wei()转换金额。 - 速率限制:加
time.sleep(),或者升级到付费计划。 - 区块不存在:确认区块高度是否在链上,比如以太坊主网目前约 1900 万+。
一句话总结:抓数据就像搭积木——先连节点,再拿区块,最后拆交易。每一步都稳了,后面分析聪明钱才能跑起来。
好了,今天就到这儿。代码都跑通了吗?有问题随时调试,链上数据的世界才刚刚打开。