区块链时代的拜占庭容错:Tendermint(六)

别来无恙 提交于 2020-03-02 13:15:41

原文题目:《Tendermint: Byzantine Fault Tolerance in the Age of Blockchains》

原文作者:Ethan Buchman

本文为节选

 

客户端的考量

这章回顾了客户端的考量(consideration),该客户端直接与一个基于Tendermint的应用进行交互。

 

发现

网络节点发现机制(network discovery)是简单地通过TCP连接向种子节点拨号的方式进行。P2P网络使用了认证加密技术,然而验证者公钥需要通过带外数据验证。确实,在这些系统中,创世状态(genesis state)必须通过带外同步,理想情况下,这也是唯一需要进行通讯的数据,因为其已经包含了验证者在认证加密中使用的公钥,这与共识中用来签名投票的公私钥不同。

对于一个会随时间变化的验证者集合,可以通过DNS来注册所有的验证者,可以在他们真正成为验证者之前注册一个新的验证者,可以将它们作为验证者移出后将其删除。或者,验证者位置可以通过其他的拜占庭容错分布式数据存储来注册,包括可能的其他的Tendermint集群。

 

广播交易

作为一个通用的应用层平台,Tendermint提供了一个简单的接口用来为客户端广播交易。通用的范例是客户端通过代理连接到Tendermint共识网络中,代理既可以是本地的也可以是远端的。代理可以作为一个网络中的非验证者节点,用来同步共识和处理交易,但不签名投票。代理使得客户端交易可以通过gossip协议,快速地广播到网络中。

一个节点只需要通过连接网络中的另外一个节点来广播交易,但是,在默认情况下,它将连接许多节点来最小化交易丢包的可能。交易会被送进内存池(mempool),通过gossip协议借助内存池反应器(mempool reactor)缓存在所有节点的内存池中,所以最终他们之一会被包含在一个区块内。

注意到交易并不会真正地参与到状态的执行直到交易被打包进一个区块中,所以客户端除了被告知该交易已经被包含进内存池中,并且广播到了其他节点之外,并不能马上得到一个预期的结果。客户端应当注册一个代理,这个代理在交易最终被提交的时候会发出相应的通知。

客户端并不需要连接到当前的提议者(proposer),因为最终任何一个验证者都会轮流成为下一个提议者。然而在高负载情况下,客户端优先广播到下一个提议者能够减少交易延迟。否则,交易需要快速地被gosssiped到每一个验证节点。

 

内存池

内存池负责在交易被包含到区块里之前,缓存交易到内存中。其行为比较微妙,对整个系统架构形成了许多挑战。首先,如果内存池缓存所有的交易将很容易受到dos攻击。大多数区块链解决这个问题通过使用原生货币,只允许附带交易费用的交易驻留在内存池里。

在一个更一般化的系统中,像Tendermint,并没有用来作为交易费用的原生代币,系统必须建立更严格的过滤规则,并且依赖更智能的客户端来重新提交之前没有成功提交的交易。这种情形甚至更微妙,因为用来过滤内存池中交易的规则集合一定是应用程序自己的功能。因此,TMSP的CheckTx消息类型可以被内存池根据根据应用程序的当前状态,用来决定是否接受该交易。

处理应用程序的当前状态并不是一件简单的工作,像许多应用程序例子一样,其被留给应用程序的开发者来解决。无论如何,客户端需要监控内存池的状态(即没有确认的交易)来决定他们是否需要重新广播他们的交易,这些交易可能是高度并行的,某个交易的有效性依赖于之前处理的交易。

 

语义学(Semantics)

Tendermint的核心共识算法仅提供了至少一次的语义(at-least-once semantics),也就是说系统会遭受到重放攻击,同样的交易可能被提交多次。然而,许多用户和应用程序希望对数据库的更强的保障(guarantees)。Tendermint系统的灵活性使得应用程序开发者可以实现这些功能。通过利用CheckTx消息类型并且相应地管理应用程序的状态,应用程序开发者能够提供一个适合他们并且满足他们需要的数据库语义。例如,正如在本系列第四篇“构建应用”所讨论的那样,通过使用附加序列号的基于账户的系统能够减轻重放攻击,改变语义从至少一次到仅此一次。

 

客户端发起读请求到之前用来广播交易的代理节点。代理总是可以进行读操作,即使网络停顿下来。然而,当整个网络出现分区,该代理读取的数据可能不是最新的。

为了避免上述情况,读请求可以被作为一个交易发送出去,假设应用程序允许这样的查询。通过使用交易,能够保证读取的一定是最新提交的数据,即当读交易被提交到下一个区块中。当然这样做的成本要比简单的查询本地代理的状态要高。当然可以通过一些启发式的方法来测定读取的数据是否是最新的,比如这个代理是否与网络中的其他节点连接良好,这个代理是否在出块或者其投票是否正常,但是没有方法能够替代实际的交易读取的方法。

 

轻量客户端证明

区块链相对于传统数据库的主要创新在于引入了梅克尔哈希树,其中便用到了轻量级客户端证明(light client proofs)。所谓的轻量客户端证明是梅克尔树上的一条路径,使得客户端可以验证某一个key-value键值对,在已知根哈希的情况下。梅克尔树根哈希(root hash)的状态被包含在区块头中,这样仅通过最新的区块头便可以验证当前状态的任意一部分。当然,为了确保这个区块头是有效的,他们必须要么通过验证整个链,或者与最新的验证者集合保持同步,并且依赖于经济激励来保证状态转换是正确的。

 

结论

尽管在客户端中需要考虑到基于区块的提交特性和内存池的行为,Tendermint网络中的客户端功能还是类似于其他分布式数据库。除此之外,客户端必须被设计成特定的应用程序。尽管这添加了一些复杂度,它却赋予了客户端极大的灵活性。

 

相关阅读:

区块链时代的拜占庭容错:Tendermint(一)

区块链时代的拜占庭容错:Tendermint(二)

区块链时代的拜占庭容错:Tendermint(三)

区块链时代的拜占庭容错:Tendermint (四)

区块链时代的拜占庭容错:Tendermint(五)

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!