bigchaindb整体架构
根据源码可知,bigchaindb整体架构为tendermint、mongo、bigchaindb,目前,mongo和tendermint没有必要去替换,所以只需重新用go写bigchaindb即可。
了解tendermint
tendermint简介
Tendermint包括两个主要技术组件:区块链共识引擎和通用应用程序接口。
共识引擎,被称作Tendermint Core,保证所有的机器按照相同的顺序记录相同的交易。
应用程序接口,被称为应用程序区块链接口ABCI,实现任意编程语言处理交易的功能。
其他区块链和共识解决方案通常预置内部状态机,比如使用键值存储不常见的脚本语言来完成功能, 而Tendermint支持开发者用任意编程语言实现拜占庭容错的状态机复制功能,并且开发环境也非常友好。
ABCI的消息流
Tendermint通过在应用程序进程和共识进程之间提供非常简单的API(即ABCI)来分解区块链设计。
ABCI由3种主要消息类型组成,它们从Tendermint核心传递到应用程序,应用程序用相应的响应消息进行回复。消息规范可查看:ABCI消息类型。
- DeliverTx消息是应用程序的核心部分。 区块链中的每笔交易都会随此消息一起发送。用于应用程序验证和执行交易的消息。Tendermint节点将交易发送给应用程序执行,并期望应用程序返回交易执行结果。
- Info消息:用于在应用程序启动时向Tendermint节点发送应用程序的基本信息,例如版本、特性和支持的选项。
- InitChain消息:在区块链网络启动时,用于初始化应用程序的区块链状态。Tendermint节点会发送InitChain消息并包含初始的验证人列表、初始的验证参数和初始的应用程序状态。
- BeginBlock消息:每当一个新区块开始时,Tendermint节点会发送BeginBlock消息给应用程序,其中包含区块的头信息和交易列表。
- EndBlock消息:每当一个区块结束时,Tendermint节点会发送EndBlock消息给应用程序,其中包含区块的高度和区块上下文相关的信息。
- Commit消息:当Tendermint节点达到共识并将一个区块提交到区块链时,会发送Commit消息给应用程序,该消息包含将被应用程序持久化的应用状态的哈希值。用于计算当前应用状态的加密承诺,并将其放入下一个区块头中。 这有一些方便的特性。 更新状态过程中如果出现不一致问题时会被认为区块链产生了分叉,这样就能捕获一整类的编程错误。
- Query消息:用于应用程序处理Tendermint节点和其他应用程序的查询请求。当Tendermint节点、其他应用程序或用户发起查询时,会向应用程序发送Query消息,并期望应用程序返回查询结果。
- CheckTx消息类似于DeliverTx,但它仅用于验证交易。 Tendermint Core的内存池首先使用CheckTx检查交易的有效性,然后只将有效交易转发给其他节点。 比如,应用程序可以检查交易中递增的序号,如果序号不是最新的,CheckTx就会返回错误。 或者,他们可以使用基于容量的系统,该系统要求对每笔交易都更新容量。
一个应用程序可以有多个ABCI socket连接。 Tendermint Core创建三个到应用程序的ABCI连接: 一个用于内存池广播时验证交易, 一个用于共识引擎运行区块提案, 最后一个用于查询应用状态。
共识概述
Tendermint是一个易于理解的、主要是异步操作的BFT共识协议。协议遵循一个简单的状态机,如下所示:
协议的参与者称为validators(验证者);他们轮流提出区块并对其进行投票。在链中提交的每一个区块都有一个height(高度)。 当一个区块提交失败时,协议将进入到下一round(轮),新的验证者将为该高度提出一个新的区块。在链中提交的每一个区块都有一个height(高度)。 当一个区块提交失败时,协议将进入到下一round(轮),新的验证者将为该高度提出一个新的区块。当超过2/3的验证者在同一轮中预提交同一个区块时,区块就会被提交到区块链中。
也就是说,可以将其流程分为四个阶段:
- 提议阶段:一个验证者被选为该轮的提议者,该提议者负责生成一个新的区块提案,并将其发送给其他验证者节点。
- 投票阶段:在收到区块提案后,其他验证者节点对该提案进行投票。节点会对提案进行验证和检查,然后根据一定的规则进行投票。
- 确认阶段:当超过两三分之两的验证者节点(即超过2/3的节点)接受了同一个区块提案时,该区块被确认为有效的。
- 提交阶段:一旦区块被确认为有效,验证者节点将在链上将该区块提交为新的区块。此后,系统进入下一个共识轮。
tendermint简单使用
安装tendermint
方法1:
git clone https://github.com/tendermint/tendermint.git- make install
- make build
二进制文件在build目录
方法2:
git clone https://github.com/tendermint/tendermint.gitcd tendermint/cmd/tendermintgo build
输入
tendermint version,查看版本,成功显示即成功然后安装ABCI
cd tendermint/abci/cmd/abci-cligo build
然后输入
abci-cli version,查看版本启动tendermimnt
./tendermint init./tendermint node --proxy_app=kvstore
这只是其中一种方法,
tendermint node --proxy_app=kvstore中的--proxy_app=kvstore实际上是代理应用程序地址,或用于本地测试的,命令原文:proxy app address, or one of: 'kvstore', 'persistent_kvstore', 'counter', 'e2e' or 'noop' for local testing. (default "tcp://127.0.0.1:26658"),第二种启动方法:
将abci和tendermint core 分别启动,还记得上面我们编译的文件,查看help可以看到
kvstore,这是一个内置的简单例子。abci-cli kvstore tendermint node执行上述命令与
tendermint node --proxy_app=kvstore是一样的,此时访问url:localhost:26657/status,可以看到区块链状态。现在可以通过访问
localhost:26657/broadcast_tx_commit?tx="abcdee",将交易abcd发送到 kvstore,注意 url 周围的单引号('),这确保 bash 不会转义双引号(")。这个命令发送了一个带有字节abcdee的交易,因此abcdee将作为键和值存储在默克尔树中。此时的响应应该是这样的{ "jsonrpc": "2.0", "id": -1, "result": { "check_tx": { "code": 0, "data": null, "log": "", "info": "", "gas_wanted": "1", "gas_used": "0", "events": [], "codespace": "", "sender": "", "priority": "0", "mempoolError": "" }, "deliver_tx": { "code": 0, "data": null, "log": "", "info": "", "gas_wanted": "0", "gas_used": "0", "events": [ { "type": "app", "attributes": [ { "key": "Y3JlYXRvcg==", "value": "Q29zbW9zaGkgTmV0b3dva28=", "index": true }, { "key": "a2V5", "value": "YWJjZGVl", "index": true }, { "key": "aW5kZXhfa2V5", "value": "aW5kZXggaXMgd29ya2luZw==", "index": true }, { "key": "bm9pbmRleF9rZXk=", "value": "aW5kZXggaXMgd29ya2luZw==", "index": false } ] } ], "codespace": "" }, "hash": "96DD75D85ABD5C6973A2567FAA35D2DD2A9508194891381F974A7AF020D25B80", "height": "725" } }成功发送交易后,可以通过访问
localhost:26657/abci_query?data="abcdee"来查询交易是否正常工作,以及是否储存了值,result:{ "jsonrpc": "2.0", "id": -1, "result": { "response": { "code": 0, "log": "exists", "info": "", "index": "0", "key": "YWJjZGVl", "value": "YWJjZGVl", "proofOps": null, "height": "829", "codespace": "" } } }注意结果中的
value(YWJjZGVl);这是abcdASCII 的 base64 编码。您可以在 python2 shell 中运行"YWJjZGVl".decode('base64')来验证这一点,或者在 python3 shell 中运行import codecs; codecs.decode("YWJjZGVl".encode('utf-8'), 'base64').decode('ascii')。
小结
作为一个通用的区块链引擎,Tendermint 与想要运行的应用程序无关。因此,要运行一个完整的区块链来做一些有用的事情,您必须启动两个程序:一个是 Tenderint Core,另一个是您的应用程序,它可以用任何编程语言编写。回想一下ABCI, Tendermint Core 处理所有的 p2p 和协商一致的东西,当它们需要验证时,或者当它们准备提交到一个块时,就会将交易转发给应用程序。
2. 了解mongo
3. 底层架构
扩展
- Post link: https://skyle.fun/bigchaindb-rewrite/
- Copyright Notice: All articles in this blog are licensed under unless otherwise stated.