四个项目带你了解 Layer2 互操作性方案设计
引子
随着二层扩容方案如 Polygon、Arbitrum 等纷纷上线,以太坊二层生态呈现百花齐放的格局。与此同时,越来越多的 DeFi 协议宣布与 L2 方案进行合作,将其协议部署或迁移到 L2 上。不同 DeFi 协议对于扩容的需求不同,亦可能选择不同的 L2 方案。在这种趋势下,如何在 L1 和 L2 之间进行交互,或是在不同的 L2 之间高效地转移资金成为一个不小的问题。
例如,如果用户需要在 L2 的 dYdX 和 L2 的 DeversiFi 之间转移资金,他需要先将资金从 L2 的 dYdX 提取到 L1,再将资金从 L1 存入 L2 的 DeversiFi。这样,用户将不得不支付两次 gas 费,并耗费大量的等待时间。对于采用欺诈证明的 L2 方案,提现到 L1 的时间甚至可能长达数天。
为此,实现 L2 之间的互操作性是很有必要的。StarkWare 提出了 L2 互操作性 (Interoperability) 的概念,即在 L2 之间转移资金,且使得转移过程中在 L1 上的摩擦尽可能小。不同 L2 方案对于互操作性的设计思路各有不同,以下对 StarkEx、Loopring、Hermez 和 Connext 的互操作方案作简要的叙述。
StarkEx
StarkEx 定义了一个称为条件交易 (Conditional Transaction) 的原语,即一笔交易的生效与否,取决于其该交易的前置条件是否得到满足。
延伸阅读:
《The Road to L2 Interoperability》
《Conditional Transfers - The Key to Interoperability》
条件交易使用 Fact Registry 合约来监听链上事件。某个事件在使用条件交易之前必须首先在 Fact Registry 合约中「登记」。例如,如果 Alice 不经过 Fact Registry 合约,而是直接在以太坊链上给 Bob 转账了 1 ETH,则无法满足用于条件交易的事件。
Fact Registry 合约中有 transfer() 和 isValid() 两个函数。
如果 Alice 需要给 Bob 转账 1 ETH,则将 Bob 的地址作为参数传给 transfer() 函数,这时 transfer() 函数做两件事。首先把 1 ETH 转账给 Bob;其次,保存这笔转账的记录到合约的存储项中,例如保存发送方、收款方、转账金额的哈希值等信息。
isValid() 函数接受哈希值作为参数,如果输入哈希值等于 Fact Registry 合约中先前记录的某哈希值,则返回 True。这样一来,记录在合约中的哈希值可以当成是一个「Fact」,代表着某个事件已经发生。这个过程通常称为「Fact Registration」(本文译作事实登记)。
条件交易中一笔签过名的链上事件包含两个字段 (哈希值):Fact Registry 合约的地址以及在执行这笔条件交易前应该登记的「Fact」。
上图展示了条件交易在 Fact Registry 合约的工作流程。在 StarkEx 的 zkRollup 中,如果某批次的交易中包含条件交易,将确保其相关的 Fact 是做过登记的,否则整批次的交易都将被回滚。
在 L1/L2 的互操作性中,条件交易有两个用例:
(1)从 L2 提现到 L1(快速取款)
该用例中有两位角色,其中 Alice 需要把 1 ETH 从 L2 提现到 L1,流动性提供者 (Liquidity Provider, LP) 在 L1 上有一定的资金。首先,Alice 向 LP 发起一笔条件交易,承诺在 L2 上支付 1 ETH 给 LP 的地址,条件是 LP 在 L1 上支付 1 ETH 给 Alice 的地址。接着,Alice 在 L1 收到 1 ETH 后,这笔条件交易的条件就得到满足了。此时,LP 把这笔条件交易发送给 L2 的 Operator,等待它被打包到下一证明的交易批次中。当条件交易的证明被提交到 L1 验证通过之后,LP 在 L2 的地址将增加 1 ETH,即从 Alice 处获得的资金。(通过这种方式进行快速取款,Alice 需要给 LP 支付一定的手续费)
因为在提供提现服务的时候,LP 在 L1 的资金持续减少,在 L2 的资金持续增加,所以 LP 需要定期地从 L2 提现到 L1,进行资金的再平衡。
(2) L2_1 与 L2_2 之间转账
用例 2 的解决思路与用例 1 类似,即:Alice 向 LP 发起一笔已签名的条件交易,承诺在 L2_1 上支付 1 ETH 给 LP 的地址,条件是 LP 在 L2_2 上支付 1 ETH 给 Alice 的地址。(Alice 和 LP 同样需要分别支付手续费和进行资金再平衡)
在用例 2 的基础上进行延申,无论是使用有效性证明的系统 (zkRollup),还是使用欺诈证明的系统 (Optimistic Rollup) 都可采用条件交易。当然相较提现确认快的 zkRollup 而言,Optimistic Rollup 上 LP 的资金效率会存在劣势。
在任一 L2 方案中从 L2 提现资金到 L1,需要最终确定 L2 的状态更新 (在这次更新中包含提现的那笔交易)。在有效性证明的 L2 方案中,一般至少需要等待 10 分钟。在欺诈证明的系统中可能需要等待数天。而采用基于条件交易的快速取款则可以使提现摆脱对 L2 状态更新的依赖,实现在「区块链时间」级别 (blockchain-time) 完成资金的转移。
StarkEx 提出条件交易来实现 L2 的互操作性,思路跟 Rollup 很类似。即每个用户提现的多笔费用,转化为 LP 在进行资金再平衡时从 L2 提现到 L1 的单笔费用。对比高昂的 gas 费,用户支付给 LP 的少量手续费显然更加划算。
Loopring
路印融合了其现有工具包的组件,提出了跨 L1、L2 和 CEX 的网桥产品 Ethport。
延伸阅读:
《Ethport: Loopring L1/L2/CEX》
关于 L1 和 L2 之间的交互,路印的方案是将多笔 L1 的交易进行批处理,以此来分摊 L1 的 gas 成本。与上述思路近似,路印在 L2 上同样设置了流动性提供者的角色。但考虑到流动性提供者的资金效率问题,路印提出了单相转换器 (Single Phase Converter)。
单相转换器使用了 L2 上 token 的闪电铸造 (Flash Minting) 功能。即调用闪电铸造出用户们想要购买的 token 总量,使得所有交易可以在 L2 上完成 (按照预期的 token 汇率)。之后再提取用户出售的所有 token,在 L1 上执行这些 token 交易并获得用户真正要购买的 token(先前已经通过闪电铸造分发给用户了)。最后再把这些 token 偿还给闪电铸造。
延伸阅读:
《Flash-Mintable Asset-Backed Tokens. OpenZeppelin》
这是一种理想化的情况,在现实情况下,token 汇率可能产生变化,并且在 L1 上的交易也存在失败的可能性。这时产生了无法偿还闪电铸造的风险,意味着先前 L2 上的所有交易将被回退。
鉴于该问题,路印接着提出了二相转换器 (Double Phase Converter)。
二相转换器将交易分为两个阶段。第一阶段首先将所有用户的资金收集到 Vault 中 (针对特定 token 兑换),给用户一个表示其资产 Vault 中所占份额的 token,而不是直接把 token 兑换给用户。之后再进行 L1 上的交易,以此确定好兑换的汇率。在第二阶段则可将兑换完毕的 token 按比例分配给所有的用户,以此解决汇率变化的问题。
此外,桥 (Bridge) 机制使得多个用户能够通过 L1 的智能合约,将资金批量地存入路印中,而不是逐一地单独加入 L2 网络。这种设计将多笔存款交易汇集成一笔交易,降低了 gas 花费。借助桥,中心化交易所也可以使用标准的 L1 基础设施来支持路印的 L2 网络。
基于以上组件的 Ethport,在实际应用时首先尽可能地使用 L2 上的流动性;如果转换器可供使用,则用它来将 L1 交易汇集起来,降低交易费用;如果以上条件不满足则使用桥机制。
Hermez
Hermez 由 iden3 团队推出,提出的 L2 间交互解决方案是大规模迁移 (Massive Migrations)。
延伸阅读:
《Introducing the First L2 Interoperability Mechanism with Hermez Massive Migrations》
其思路是:首先,负责进行 L1 资金转移的智能合约有一个 L2_1 上的地址。在需要跨 L2 转账时,用户将把资金转入到该地址。之后,Hermez 协议将对有着相同 L2_2 地址的一批 L2 转账进行分组和提取,调用标准的 Hermez 函数将这批 L2 转账的资金总额提现到 L1,再存入到 L2_2。
Hermez 协议在执行上述聚合提款交易时,包含了在 L2_2 上重构 L2_1 原始转账所需的信息和对应的账户信息。在 L2_2 上有一个调度员的角色,负责处理 L1 的取款交易,并从交易信息中分解出资金的流向,再转入到与用户的 L2_1 地址对应的 L2_2 地址上。
Connext
Connext 是基于状态通道的 L2 扩容方案,支持兼容 EVM 的公链和 L2 系统之间的快速交易。在今年年初发布了即时跨 L2 转账产品「Vector」的 0.1.0 版本,旨在连通各 L2 方案之间的流动性,实现资产的跨 L2 转移,并在三月份推出 xDai-Polygon Bridge 测试版,允许用户使用状态通道将 xDai 转至 Polygon 上的 Dai,或是将 Polygon 上的 Dai 转至 xDai。
Connext 通过路由器 (Router) 实现跨 L2 的资金转移。Connext 路由器实际上是一个状态通道节点,它会自动地转发在状态通道内发送给它的交易。对于跨链交易来说,路由器相当于流动性提供者,通过在 chainB 上的状态通道内向用户转移资金,来换取用户在 chainA 上的资金 (这个思路跟 StarkEx 和路印类似)。
延伸阅读:
《Solving the Liquidity Problem》
例如,如果 Alice 想把 100 USDC 从 Polygon 发送到 Arbitrum,她需要使用路由器把 100 USDC 存入 Polygon 上的状态通道中。然后,Alice 向该路由器发送一笔状态通道内转账,条件是 Alice 在 Arbitrum 上的对应的状态通道内收到转账。目前这种条件性的实现依赖于哈希锁定 (Hashlock)。这些转账以原子方式解锁,可实现免信任。路由器在跨 L2 过程中能够赚取 Alice 支付的手续费。
然而,借助流动性提供者的跨 L2 方案不可避免地会有资金效率的问题。Connext 提出了虚拟 AMMs(Virtual AMMs) 来解决这个问题。
在 Uniswap 中,资金池的兑换比例越不平衡,价格差异就越大。这也创造了一个持续增长的套利机会。虚拟 AMMs 借鉴了 Uniswap 的核心概念来为 L2 间资产转移做定价。
考虑一种情况:某个时刻 LP 在 Arbitrum 池的 ETH 数量大于其在 Optimism 池的 ETH 数量,系统希望能平衡两个池子的 ETH 数量。根据上图公式的比例兑换关系,假设 0.99 个 Optimism 上的 ETH 可以换到 1 个 Arbitrum 上的 ETH,此时产生套利机会。则套利者会用其在 Optimism 的 ETH 去兑换 Arbitrum 的 ETH。这样一来,对于 LP 来说,其在 Optimism 池的 ETH 数量变多,在 Arbitrum 池的 ETH 数量变少,以此达到通过套利活动平衡流动性的目的。
另外,在 Connext 上任何人都可以启动自己的路由器来提供流动性。这样导致流动性不会被聚合——一些路由器可能超负荷,一些路由器可能无人问津。于是,Connext 又提出了流动性拍卖的概念 (Liquidity Auctions),即动态地寻找提供最低成本的路由器。
在进行转账时,用户向网络广播想要的发送或接收流动性。路由器会直接向用户提交密封式的报价 (Sealed Bids),以最低价格完成转账。这有点类似于 Uber 将用户与价格最低的司机匹配。
小结
关于 L1、L2 的互操作性问题,上述四个 L2 方案都采用了近似的思路,即引入流动性提供者,将多笔交易聚合为一笔交易进行处理。面对流动性提供者的资金效率问题,各个项目采用的解决方法有所不同、各有优劣。
总体来看,由于各 L2 方案的采用率有限,上述互操作性的方案实际应用效率如何,仍要经历实用性的检验。
微信扫描关注公众号,及时掌握新动向
2.本文版权归属原作所有,仅代表作者本人观点,不代表比特范的观点或立场
2.本文版权归属原作所有,仅代表作者本人观点,不代表比特范的观点或立场