这个过程中需要许许多多「去中心化的银行」,在两条 Rollup 上分别扮演存款机和取款机的角色。

原文标题:《Vitalik 说的跨 Rollup DEX 是啥?》
撰文:Breeze

当人们还在思考用 Rollup 的方式缓解 Layer 1 拥堵的时候,Vitalik 已经在考虑 Rollup 之间怎么做交互。

6 天前,Vitalik 发起了一个叫做「跨 Rollup DEX」的提案,其中提到当一条 Rollup 有智能合约部署,另一条 Rollup 没有完全的智能合约功能的时候,资产可以在两条 Rollup 之间以去中心化的方式转移。有一点「隔空挪物」的感觉。

这个过程到底是怎么实现的呢?哔哔 News 将提案,以及 Vitalik 和社区成员间的精彩讨论内容翻译如下:

假设我们有两条 Rollup,分别是 Rollup A 和 Rollup B。Alice 想要把 Rollup A 上特定数量的代币转移到 Rollup B 上。如果 A 和 B 都有完全的智能合约支持,在这种情况下,已经有关于如何以去中心化的方式解决这个问题的提案。本提案想要为只有 Rollup B 有完全的智能合约支持(Rollup A 只能处理简单的交易)的情况提供思路。

我们假设,Rollup A 上的交易有某种「备注字段」,如果没有的话,我们可以使用值的低阶位作为备注发送。

提案

假设存在一个交易中介 Ivan(在实际实现中,将有许多中介可供选择)。Ivan 在 Rollup A 上有一个账户 IVAN_A(他完全控制该帐户)。Ivan 还将一些资金存入了 RollupB 上的智能合约 IVAN_B 中。

智能合约 IVAN_B 有以下规则:如果任何人发送 TRADE_VALUE 数量的代币到 IVAN_A,其中包含一个地址 DESTINATION 作为备注,那么在 MIN_REDEMPTION_DELAY 块之后, IVAN_B 将收到一笔交易,该交易包含一个代币转移的证明,从而把提取 TRADE_VALUE 数量的代币这样一笔交易排队到 DESTINATION 地址。提币按照交易被包括到 Rollup A 中的批次和索引顺序处理,要经过一些延迟 (比如 1 天)。

当 Ivan 看到他在 IVAN_A 收到资金时,他可以亲自将 TRADE_VALUE *(1 - fee) 数量的代币发送到 DESTINATION 地址。他可以通过 IVAN_B 中的方法发送交易,该方法保存一条记录,防止合约中的自动发送条款触发该交易。

预期的操作很简单:

  • Alice 向 IVAN_A 发送一笔交易,其中包含 N 个代币和备注地址 ALICE_B。

  • Ivan 通过 IVAN_B 发送 TRADE_VALUE * (1 - fee) 数量的代币到 ALICE_B。

第二步可以在第一步之后立即进行。如果 Ivan 证明第二笔交易和第一笔交易之间的时间戳差异非常小,那么合约甚至可以制定规则,允许费用更高。

「最坏的情况」是 Ivan 没有像预期的那样向 ALICE_B 发送代币。在这种情况下,Alice 可以等待 Rollup A 上的交易确认,找到获得 Rollup B 上的代币的其他途径来支付费用,然后她自己就可以索要资金。

资本成本

该方案的主要限制是,IVAN_B 需要持有大量资金,以确保所有发送者都能得到支付。特别是,假设:我们把交易金额上限设置为 TRADE_LIMIT (所以发送到 IVAN_A 的交易中,交易值 > TRADE_LIMIT 的交易都不是有效交易)。

同时,我们设置每个 Rollup 批次最多可包含的交易数量是 TXS_PER_BATCH。Alice 可以自己检查,Rollup A 即将到来的批处理之前有多少未处理交易,用她在 IVAN_B 合约中看到的资金减去这个值,并检查剩余的金额是否足够。由于提币是按顺序处理的 (这是上面顺序机制的目标),Alice 不需要担心在她自己提币之前 IVAN_B 会去处理后面的提币需求。

在一个批次中可以交易的最大金额是 TRADE_LIMIT * TXS_PER_BATCH,因此 IVAN_B 合约需要至少持有这个数量的 ETH,再加上足够的资金来覆盖未处理的交易。

例如,假设 TRADE_LIMIT = 0.1 ETH (上限可以设得比较低,因为一笔较高金额的交易可以通过多笔交易完成),并且 TXS_PER_BATCH = 1000。那么,IVAN_B 需要有 100 ETH 的资金。

注意,在这个设计中还有额外的隐含费用,因为任何交易超过 0.1 枚 ETH 的人都需要消耗区块空间,这与资金要求相权衡:如果你消耗掉一半的区块空间,那么你的资金要求也会翻倍(可能指隐含费用更高),反之亦然。要建立合适的平衡,似乎应该让隐含费用比市场上出现的显性费用少几倍。

如果我们想减少或消除这种消耗,Rollup A 可以被设计成这样,例如,让排序器发送一个签名消息,向 Alice 证明到目前为止,批次中批准的所有消息。然后 Alice 就会知道在她之前没有交易 (尽管恶意的排序器可以欺骗 Alice,但代价很高)。

备注

上面的设计建立在 Rollup A 上的交易有一个备注字段的假设上,Alice 可以使用该字段指定 ALICE_B 作为她接收代币的目的地址。如果 Rollup 没有此特性,那么我们可以使用以下解决方案。

Alice 可以在顺序注册合约的 Rollup B 上注册 ALICE_B,并获得一个按顺序分配的 ID(因此 Alice 的 ID 等于在她之前注册的用户数量)。设置 MAX_USER_COUNT 为用户数的最大值,如果有必要,这个值可以随时间向上调整。Alice 可以简单地确保 TRADE_VALUE % MAX_USER_COUNT 等于 (Alice 的 ID),使用 TRADE_VALUE 的低阶位 (这个数字表示一个不重要的值) 来表示她想交易的代币数量。

从 Rollup B 到 Rollup A 的交易

如果 Alice 把 Rollup B 上的代币转移到 Rollup A,可以使用类似的机制,只是角色颠倒了:

  • Alice 将代币发送给 IVAN_B

  • 经过一段时间的延迟,她将获得收回代币的权利

  • 如果 Ivan 可以向 IVAN_B 证明,他在 Rollup A 上给 Alice 发送了代币,Alice 就失去了这个权利

总结

所以我们可以看到,在这个过程中,许许多多的「Ivan」其实就是去中心化的银行,在两条 Rollup 上分别扮演存款机和取款机的角色,从而赚取手续费。

如果 Ivan 作恶,Rollup A 和 RollupB 间不需要进行过多的交互,Alice 就可以提供打币证明。根据 Vitalik 的表述,在从 Rollup A 向 Rollup B 转账的场景中,提供证明这一步操作可以直接在 Rollup B 上进行,只要 Rollup B 能获取 Rollup A 的区块哈希,就可以计算出 Rollup A 上的交易记录,从而向 Ivan 索赔。

在索赔这个过程中,Vitalik 还给出了更多的可能性。比如,可以在 Ivan B 上增加一个「快速通道」,Alice B 可以把她在 Ivan B 上的提币插槽出售给其他用户。

假设这个用户叫 Bob,那么 Bob 可以把款项先转账给 Alice B,此后,Ivan B 应该转账给 Alice B 的资金将被 Bob 获取。也就是由 Bob 先垫付资金给 Alice,以此来提升 Alice 的用户体验,这个过程或许可以涉及到挖矿之类的玩法。

Github 上有用户提到,如果中间商 Ivan 不是个体,而是去中心化的资金池,这个模型是否会更好。Vitalik 表示,这会涉及到 Rollup A 上资金池的所有权问题(可能池子中的所有资金被一个私钥控制),相比之下,由多个中间商来作为分散的「资金桥」可能更合理。

这就是跨 Rollup DEX 的大致思路。虽然可应用场景可能不多,也有一些影响到资金安全的场景可能没有被考虑进去,但是这让我们又看到了一些 Layer2 上的可能性。区块链解决方案从某些角度来看,或许就是规则设计。