如同在以太坊中一样,Arbitrum 客户端提交想要的交易,系统(通常来说)稍后执行这些交易。在Arbitrum rollup中,客户端直接或通过聚合器或在排序器链上(通过定序器)将消息发布到以太坊链上提交交易,这些消息被放入链的收件箱。
Arbitrum 链收件箱中的消息将按顺序处理。通常,从将消息放入收件箱(并带有时间戳)到合约处理消息并执行交易都需要耗费一些时间。
Arbitrum 会直接指定他们的区块号,区分与以太坊的区块编号。
一个以太坊区块可能包含多个Arbitrum区块(有可能Arbitrum链上的活动很多);不过,一个Arbitrum区块不可能跨越多个以太坊区块。因此,对于给定的 Arbitrum 交易来说只能与一个以太坊区块和一个 Arbitrum 区块相关联。
在排序器链上(如 Arbitrum One
主网上), 在 Arbitrum 智能合约中获取区块编号(即在 solidity 中通过
block.number
代码获取), 会在接收到该交易排序器返回一个接近 L1
的区块编号(不一定精确)
// some Arbitrum contract:
block.number // => returns L1 block number ("ish")
原则上,合约对区块编号和时间戳所做的任何时间假设长期上是可靠的,在短期内(分钟)是不可靠的(直接在以太坊上使用区块号来操作时这些假设是一样的!)。
Arbitrum 区块有自己的区块编号,从 Arbitrum 创世区块的 0 开始并按顺序更新。
ArbOS 和 Sequencer 负责规划一个 Arbitrum 块何时结束以及下一个何时开始,人们应该看到 Arbitrum 以相对稳定的速度出块。
查询 Arbitrum 节点的 RPC 接口(例如,交易收据)的客户端将收到已经交易的 Arbitrum
区号作为标准的字段并返回,当然 L1 块编号作为新增的字段 l1BlockNumber
也包含其中。
const txnReceipt = await arbitrumProvider.getTransactionReceipt('0x...')
/**
txnReceipt.blockNumber => Arbitrum block number
txnReceipt.l1BlockNumber => L1 block number ("ish")
*/
Arbitrum 区块号也可以通过ArbSys在 Arbitrum 合约中检索:
ArbSys(100).arbBlockNumber() // returns Arbitrum block number
挂钟时间 | 上午12:00 | 上午12:00:15 | 上午12:00:30 | 上午12:00:45 | 上午12:01 | 上午12:01:15 |
---|---|---|---|---|---|---|
L1 区块编号 |
1000 | 1001 | 1002 | 1003 | 1004 | 1005 |
L2 区块编号 |
1000 | 1000 | 1000 | 1000 | 1004 | 1004 |
Arbitrum 区块编号(来自 RPCs) | 370000 | 370005 | 370006 | 370008 | 370012 | 370015 |
L2 区块编号
: L2 区块每分钟跟 L1 区块同步一次,因此,随着时间的推移,它会像
L1 一样平均每15秒更新一次区块。来自 RPC 的 Arbitrum区块编号:
需要注意的是,它可以在每个 L1 块中多次更新(这让定序器提供子 L1 块时间的 tx
收据。)
Multicall 合约为 L1 和 L2 区块号之间的差异提供了一个很好的案例研究。
Multicall的规范实现返回区块编号(block.number) 的值 。如果尝试使用开箱即用,某些应用程序可能会面临意外行为。
您可以在 0x842eC2c7D803033Edf55E478F461FC547Bc54EB2 找到改编后的 Multicall2 的部署版本。
默认情况下 getBlockNumber
、tryBlockAndAggregate
、 和 aggregate
函数返回 L2 区块编号。这允许你使用该值将你的状态与链的末端(最新区块)进行比较。
如果应用程序需要显示 L1 区块号,可以通过 getL1BlockNumber
函数查询。
→ 排序器和抗审查性