由于区块链的分布式特性,其上的交易天然存在一定延迟。因此,构建于其上的分布式应用就出现了需要对用户在DApp前端所见的状态与区块链上的状态之间进行同步的问题。本文测试分析了一些DApp中的链上、连下同步问题。

文章目录


  1. 背景与简介
  2. 同步问题
    1. 现网检测
    2. 同步错误分类
      1. I 类错误
      2. II类错误
  3. 检测方法
    1. 断言
      1. 断言一
      2. 断言二
    2. DArcher
  4. 实验分析
    1. 数据集
    2. 实验环境
    3. 结果分析
  5. 存在问题
  6. 引用

今天分享的这篇论文介绍了基于区块链的分布式应用程序中,链下(用户在DApp中看到的)与链上(区块链上)状态不一致的问题。

背景与简介

基于区块链的DApp(分布式应用程序)存在线上线下同步的问题。由于区块链的交易天然是有较大延迟的,比如最常见的比特币平均每10分钟生成一个区块。此外区块链可能会出现分叉,因此为了确保交易不被反转,通常交易需要被多个区块确认后,才会被认为最终不会被改变。在比特币区块链上,默认交易被6个区块确认(交易所在区块后又生成了5个新的合法区块)后,该交易会被最终确认(不会再被反转)。因此比特币区块链上确认一笔交易大概需要60分钟。类似的,以太坊区块链确认一笔交易大概需要90秒。

如果DApp开发者在开发DApp时对同步问题处理不当,就会给用户造成困扰,甚至给用户带来大的经济损失。实际上,很多DApp开发者都不会完全同步DApp与区块链上的状态。这可能是由于开发者疏忽或该问题不那么重要,也可能是为了平衡DApp的性能。

典型的DApp由链上智能合约与链下的应用程序构成(如下图所示)。

典型DApp 结构
图 1:典型DApp结构

链下部分负责与用户进行交互以及其它一些程序逻辑,链上部分通过区块链上的智能合约自动管理。链下部分通过rpc请求或者远程 API调用来访问区块链。

同步问题

区块链上一般交易的生命周期如下图所示。

交易生命周期
图 2:交易典型生命周期

各个状态含义如下:

  • 已经创建:用户已创建交易,但尚未广播到区块链网络
  • 等待收入区块:交易已被广播到区块链网络,进入到交易池中,但尚未被已生成区块包含
  • 被区块收入并执行:交易已被某个区块收入,并且此区块已经被广播到了整个区块链网络,但是此状态的交易仍有可能被区块链上出现的分叉反转
  • 被反转:交易虽然被某个区块包含了,但是由于分叉的出现,导致交易所在链最终没有能成为主链(而主链上由于某种原因未包含此交易),导致交易被反转
  • 被最终确认:交易被认为“永久”存在于区块链上

关于状态转移的一些解释:

  • 等待中的交易有可能被丢弃,比如出现了双花问题,导致交易不再有效
  • 被反转的交易可能会被丢弃(原因同上),也有可能被再次加入到区块中,从而进入到被区块收入并执行状态

现网检测

论文中,作者们通过Etherscan对以太坊上的交易进行了长达4个月的监测,发现:以太坊上每秒收到的交易数大概为32.5,而最终被区块链确认的仅有约16.4。可以看出大约有一半的交易都由于某些原因未被包含在区块链中。此外他们还发现,区块链的分叉重组大概每11.06分钟发生一次,其中每次大约有16.69笔交易的状态会变为被反转状态。

根据观测可知,开发DApp时,开发人员有必要考虑DApp的同步问题。

同步错误分类

文中提出了两类不同步类型,分别称之为I 类错误II类错误

I 类错误

I 类错误如下图所示。

I类错误
图 3:I 类错误

该错误发生于交易已经被广播到区块链网络,但是没有被任何区块包含的情况下。在此情况下,如果DApp将应用的链下状态变为交易已经处理完成,此类错误 (I类)就会出现。我们将处于等待收入状态下的交易状态的不一致性定义为 I类错误。

II类错误

II 类错误如下图所示。

II 类错误
图 4:II 类错误

II 类错误发生在交易已经被某个区块包含之后,但是尚未被最终确认的情况下。此时如果DApp将应用的链下状态变为交易已处理完成状态,此类错误就会出现。我们将处于被区块收入并执行状态下的交易状态的不一致性定义为 II类错误。

检测方法

断言

文中使用断言来判断错误是否发生。定义函数$\sigma$为从链上状态到链下状态的映射。那么我们通过以下两个断言来判断是否出错。一旦断言被触发,我们认为错误发生了。

函数$\sigma(tx, status)$表示交易tx 在链上的状态为status状态时,DApp 中显示的状态。即:

$$ 链下状态 = \sigma (交易, 链上状态) $$

断言一

断言一用于判断I类错误。

断言一:对于每笔交易$t$$\sigma (t, 已创建) \ne \sigma(t, 已完成) \wedge \sigma(t, 待收入区块) \ne \sigma(t, 已完成)$

断言一指出:交易在已创建或者待收入区块状态时 DApp 显示的状态不能与 DApp 中指示交易已完成的状态一样。

断言二

断言二用于判断II类错误。

断言二:对于每笔交易$t$$\sigma(t, 等待收入区块) = \sigma(t, 被反转)$

断言二指出如果交易被反转,DApp应当将所显示状态修改为与交易等待收入区块状态一致状态显示。

DArcher

本文提出一个测试框架DArcher用于检测状态不一致错误。DArcher工作流如下图所示。

DArcher 工作流概览
图 5:DArcher 工作流概览

前端浏览器用于通过远程请求触发DApp中的交易事件。状态分析器在交易的链上状态改变时读取交易状态,并同时读取链下状态,最终分析生成报告。

实验分析

数据集

论文选取了11个DApp作为测试对象,这11个DApp均为在github上均获取超过100颗星的智能合约项目。

由于不同的DApp的线下状态的实现、存储方式不一样,所以无法使用统一的方法来获取DApp的链下状态。作者通过人工分析的方式来找到状态对应的存储位置,以供分析器读取。此过程由两个不同的研究人员分别完成以防止出错。

由于测试环境中,区块链是受控的,DApp的链上状态可以直接获取。

所选取的DApp如下表所示。

应用功能
AgroChain农业供应链
Augur预测市场
DemocracyEarthDAOs管理
ETH Hot Wallet钱包
Ethereum Voting Dapp投票
Giveth慈善捐赠
Heiswap匿名转账
MetaMask钱包
Multisender一对多转账
PublicVotes投票
TodoList Dapp代办事项列表

实验环境

文中使用Crawljax作为前端测试工具。此外研究者们在以太坊客户端 Geth 的基础上实现了用于实验的可控区块链。在此区块链中,研究者们可以控制交易的生命周期按照设计好的状态进行。为了测试,研究者们将智能合约部署于本地的区块链中,以方便与DApp进行交互。

结果分析

结果那肯定很好啊,没啥好分析的,文中给出了一张表,不过看不出太多有用信息,直接贴在下面了。对比的baseline-i, baseline-ii 感觉没什么对比价值,感兴趣的可参考原论文。

实验结果数据
图 6:实验结果数据

文中测出的一些Bugs(15个)被反馈给了开发者,其中有6个已经被确认,并且有3个已被修复。

存在问题

  1. 无法确保实验中所用链下状态的准确性,这种不准确性可能由读取的时间间隔(可控变量)引起,也可能由于对DApp分析不够引起
  2. DApp可能不单依赖单个智能合约来判断状态,所以我们前面的断言本身可能并不正确
  3. 应用 DArcher 的另外一个问题是:每测试一个DApp都需要手动去适配获取链下状态的方法,十分麻烦

引用

[1] Zhang, Wuqi, et al. "ÐArcher: detecting on-chain-off-chain synchronization bugs in decentralized applications."Proceedings of the 29th ACM Joint Meeting on European Software Engineering Conference and Symposium on the Foundations of Software Engineering. 2021.


[本]通信工程@河海大学 & [硕]CS@清华大学
这个人很懒,他什么也没有写!

0
919
0

更多推荐


2022年11月30日