摘要
Fabric目前的应用情况(目前已有超过400的原型、概念、系统用到了)
Fabric的优势(第一个真正可扩展的区块链系统、第一个可以运行通用程序语言没有内置货币的区块链系统、是准入制的区块链系统)
本文将会介绍Fabric的架构、原理、安全模型及保证、最关键的实现、分布式应用编程模型等
一 引入
介绍区块链(一个保存在分布式不可信任节点之间不可修改的账本)
对比公共区块链(公共的通常内置加密货币、使用pow共识、有一定的经济激励,准入制的通常运行在一批身份已知的节点上)
区块链运行任意可编程的交易(以太坊的智能合约、比特币的脚本)的方式类似于状态机复制,并列出了三个区别(多个智能合约同时运行、任何人都可以随时部署智能合约、智能合约代码不可信)
介绍order-execute架构(先按共识机制给交易排序,然后所有节点按这个顺序执行交易)及其限制(影响性能)
介绍先前permissioned blockchain的一些限制(共识机制硬编码、信任模型由共识机制确定无法由智能合约修改、所有节点顺序执行交易影响性能、在程序层面无法确认交易的确定性)
本论文介绍了Fabric(再次重复的说了Fabric有多好,主要是应用有多广泛)
Fabric是为解决啥问题提出的(支持什么什么,之前摘要里面的优势又提了一遍)
介绍了Fabric中的执行-排序-验证模型,分为3步:
1、执行交易检查正确性然后背书、
2、根据共识协议排序交易、
3、根据应用级的信任模型验证交易
介绍Fabric是积极积极复制和消极复制的结合,然后介绍怎么结合的(只在一部分节点上运行交易「消极」,在运行的节点上达到共识后才会将改变账本状态) 另外还提了一下状态更新的顺序是由模块化的共识组件确定的,这个组件是与运行应用和保存账本的节点是相互隔离的
Fabric的这种新的执行-排序-验证的模型是Fabric最重要的创新
介绍为了实现这种模型,需要的组件
1、排序服务「广播交易,建立对交易顺序的共识」、
2、身份会员、
3、可扩展的散播「对等gossip服务,排序服务的输出」、
4、智能合约的运行「可以是通用编程语言编写的、运行在容器内、不能改变账本状态」、
5、账本保存「每个节点都保存账本」
二 背景
介绍区块链的排序-执行架构
1、每个节点执行交易验证后,将交易打包成一个块
2、尝试解决pow问题
3、解出来之后通过gossip协议广播该区块
4、每个节点收到别的节点的区块之后,验证pow的解是否正确,运行区块上的所有交易
排序-执行架构的限制
1、顺序执行
「影响吞吐量,吞吐量和执行延迟是成反比的,一个带死循坏的智能合约会产生致命的影响,为此,以太坊引入gas的概念,但这不适用于不;含内置货币的区块链系统;为了提高性能,有人提出将无关操作并行运行,但这目前还无法实际运用,因为无法推断智能合约中所有依赖项的要求(因此无法确定智是否可以并行);有的智能合约还是机密的,这也无法解决dos攻击」
2、不确定性的代码
「为解决这个问题以太坊采用专用的编程语言,这需要额外的学习成本;使用通用的程序语言会有很多问题,程序员可以通过隐藏是实现细节产生破坏性的影响」
3、执行的机密性
「准入制的区块链系统需要一定的机密性,目前已有的那些(数据加密、零知识证明、可验证计算)需要相当大的开销」)
先有架构的其他限制
1、固定的信任模型
「信任模型固定,每次都是相同的节点运行交易,这可不合理(有的交易可能只需要更少的节点运行)
2、硬编码的共识机制
「不存在一个通用的共识机制可以适用于所有的情况」
排序-执行架构的经验
1、分歧状态的出现通常是由于不确定性的交易
2、性能往往比预期差)
三 架构
先Fabric架构概述,然后介绍执行步骤,然后排序步骤,然后验证步骤
1、概述
再次一句话介绍Fabric,它是一个可以运行通用编程语言所编写的分布式应用的准入制区块链的操作系统,可以安全的追溯执行历史。
Fabric引入了 执行-排序-验证 区块链架构,为什么要用引入这个架构(论文第二章有写)
Fabric主要由两个部分组成:
1、智能合约(也成为链码)「实现应用逻辑,在执行阶段运行,特殊的链码(系统链码)」
2、背书策略「仅能由链码配置,由指定的系统管理员运行系统管理函数进行修改,在验证阶段被验证」(一个典型的背书策略一般是让链码用一个简单的逻辑表达式来指定一个交易需要的背书节点集)
【在上述架构中,智能合约这种分布式应用包括了两个部分:
chaincode:即原来的smart contract code,在execute阶段可以运行,值得注意的是,还有一种特殊的system chaincodes,这类chaincodes定义了整个链的底层设置,包括validation system chaincode和endorsement system chaincode(和我们的NBRE非常相似)。
endorsement policy:这个概念理解起来就有点绕了,可以理解为独立于共识模块的一种验证或者背书机制。传统consensus包括了验证节点是否作恶以及交易本身是否正确两个任务,而在Fabric中,将后者抽离成为endorsement policy。实际上这个模块也是可以替换的,比如“五个endorser节点中只要有三个执行结果一致则完成验证”这种策略完全可以换成“只需要XXX endorser节点完成执行则通过验证”。】
- 执行阶段(客户端发送交易到由背书策略指定的节点,这些节点运行交易,记录运行结果)
- 排序阶段(使用可拔插的共识协议将背书过的交易排序,组成区块,广播给所有节点)
- 验证阶段(每个节点都验证状态的改变以及背书策略执行的一致性,Fabric是按照交易的输出和状态依赖来排序交易的)
Fabric中的节点分为三类:
1、客户节点「提交交易建议,将背书后的交易广播出去以供排序」、
2、对等点「执行交易建议,验证交易(部分点,由交易自带的链码决定哪些对等点点来验证交易)、保存账本(所有对等点)」、
3、排序服务节点「为所有交易(其产生的状态更新、计算所需依赖、背书阶段产生的加密签名)建立顺序关系,排序节点与应用状态无关,既不参与执行阶段,也不参与验证阶段」
因为可以运行一个物理节点,带多个角色,所以Fabric也可以像其他传统的对等点区块链系统(每个节点都能保存状态信息,验证排序交易)一样运行
Fabric支持多条区块链链接到同一个排序服务,每条区块链被称为一个通道,通道被用于分隔区块链网络的状态,每个区块链的交易顺序都是隔离的,跨区块链的共识机制是无法协调的
2、执行阶段
1、客户端提交交易建议(包括了提交客户端的身份、执行交易所需的有效负载参数、链码标识、随机数、由客户标识符和随机数得到的交易标识、客户的签名)=>
2、背书节点通过执行指定链码(这个链码安装在了区块链上)来模拟提议,链码运行在指定容器内,与背书过程隔离 、
提议的模拟是根据背书节点的本地区块链状态进行的,也不会将模拟结果保存至账本 、
由某个链码产生的状态只能由该链码更改 、
链码应该将通过GetState、PutState、DelState操作本地状态 、
3、通过模拟,每个背书操作会产出writeset(保存模拟产生的状态更新)、readset(保存模拟过程中所需要的key和他们的版本),模拟结束后会产生一个签名(签名 貌似就是根据writeset和readset 产生的)=>
4、背书结束后,将背书后的交易送回给客户,客户收到满足 交易指定链码中的背书策略 的回应之后(所有背书节点要产生相同的结果,即相同的writeset和readset集),将交易转给排序节点
对设计选择的讨论
一个标准的背书策略需要所有的背书节点产生相同的结果,这意味着对某个相同的key的访问会有竞争厉害的时候,这时候可能就无法满足背书策略的要求
应减少或完全消除访问同一状态引起的争用
对存在非确定性交易的情况来说,在排序操作前对交易进行模拟是很重要的一步,因为如果有非确定性的交易是恶意的,客户就不会收到足够的背书回应,那就不会对账本状态产生影响,这还能解决Dos攻击的问题
3、排序阶段
客户收到足够多的对某提议的背书回应之后,会将这些交易收集起来,提交给排序服务,排序服务通过按顺序将交易广播出去来给交易建立顺序,排序服务还会将多笔交易组成一个区块,以散列的有顺序的区块形式输出
排序服务提供两个接口,brodcast(tx)「用于客户广播交易tx,其实就是提交交易给排序服务吧」
deliver(s)「客户使用一个非负数s去检索区块」
排序服务保证:
1、相同编号的区块完全相同
2、后一个区块包含了前一个区块的哈希值
3、如果某正确节点提交了序号为s的区块,那0~s-1的区块都被提交过了
4、正确节点提交的区块上的交易均被某客户广播过
5、如果某个正确的客户广播了tx那么每个正确的对等点最终提交的区块都包含tx(排序服务证明自己还活着的最重属性)
5、每个排序服务都可以根据客户的要求,提供一些证明自己还活着的证明
Fabric的广播服务也是模块化的(可用gossip广播服务)
排序服务还可用于权限控制,控制客户是否能广播交易,或者接受从某通道传来的区块
对设计选择的讨论
排序服务不包括任何区块链的状态也不验证或者执行交易,这种架构让Fabric成为第一个把共识机制完全隔离出去的区块链
4、验证阶段
验证包括三个步骤:
1、背书策略验证「并行验证区块内的交易背书是否符合背书策略,不满足会被记为不合法」
2、读写冲突检查「检查交易的readset是否和本地的状态一致,不一致会被记为不合法」
3、账本更新「将区块添加到本地存储的账本,更新区块链状态,前两个步骤的额结果也会以掩码的形式存储」
Fabric的账本包括了所有合格不合格的交易,因为链条由排序服务给出(排序服务与链码状态无关)而验证在这之后。
Fabric组件
1、会员服务
「保存了系统中所有节点的标示,负责给每个节点发布用于授权和验证的证书」
「MSP在每个节点上都有一个组件」
「MSP可以有不同实现 (目前有个想法,可以依靠匿名证书授权客户端调用事务而不将其连接到身份)」
「Fabric有两种方式建立区块链网络,离线方式(证书由CA提供 )和在线方式(证书由Fabric提供),对等点和排序节点只能离线方式注
册,客户可以在线注册」
「MSP支持标识联合,通过在每个组织和MSP之间创建映射实现多个MSP实例」
2、排序服务
「包括了原子广播、通道的重新配置、准入控制三类服务」
「排序服务由系统通道的创世区块进行引导,这个创世块中定义了排序服务相关的配置」
「在目前的实现中,原子广播由KafKa提供,OSN只是节点与Kafka之间的代理」
「OSN将新接收的交易直接注入到原子广播,另一方面,从原子广播接收的事务进行批处理并形成块。满足三个条件截断块:区块包含了最大数量的交
易数、区块达到了最大的字节数、时间花完了」
「另外两种排序服务:solo 、基于BFT-SMaRt的排序节点」
对等点gossip广播 「由于排序服务和验证服务事隔离的,gossip就致力于有效的将执行过的交易广播以供验证」
「gossip的传输基于gRPC,使用TLS进行相互验证」
「gossip保存了系统中在线的所有对等点的会员信息,所有对等点也都本地的保存了一份其他节点信息」
「gossip的两个操作pull和push都是随机选择一批节点,随机选择节点,减少了节点直接保持链接的开销,还能减少攻击面」
「为了减少排序节点传输块的负载,协议会选出1个leader负责从排序服务中拉块初始化gossip」
「gossip的另一个任务时传输状态到新加入的节点,或者已经断连很久的节点」
3、账本
「账本有账本区块存储和对等点交易管理PTM组成,账本块存储去维护了一些索引用于随机访问块或块中事务,PTM保存了最新的状态」
「模拟期间,PTM提供最新状态的快照」
「PTM按顺序验证交易,检查当前交易是否与之前交易冲突(还是检查readset是否和最新状态一致)」
「当PTM收到一个新区块之后,验证,完了将该块加入区块存储区,写入磁盘,更新索引,随后根据writeset中更新本地状态,然后PTM计算并
保存一个savepoint记录最新加入的区块数」
4、链码执行
「在与其他节点松耦合的环境中运行,支持 添加新语言(用以编写链码) 的插件,每个用户级别的链代码在Docker容器中单独的进程中运
行,隔离了链码和链码,链码和对等点,链码使用gRPc和对等点交流,对等点不知道链码使用的具体语言」
「系统链码事直接在对等点的进程中运行的」
配置和系统链码「通道配置保存在一个配置块中,该配置块不包含任何交易,也叫创世块,通道配置的更改要通过通道配置改变交易」
「部署系统链码时,可以参考背书系统链码(ESCC)和验证系统链码(VSCC),ESCC以交易提议为输入,输出提议模拟的结果,
VSCC以交易为输入,然后输出该交易是否合法(收集背书信息,然后判断是否符合背书策略的要求)」
四 实验
为了测试,Fabric设计了一种UTXO模型的代币,简称Fabcoin。通过一个chaincode不断产生SPEND和MINT transactions,分别模拟Fabcoin的产生和销毁。
实验1:测试block size和Throughput关系,结论是在block size超过2MB之后TPS不再显著提升;不同transaction的size略有差别,比如MINT transaction因为需要带有CB验证所以更大。
实验2:性能测试,结论是validation是主要瓶颈,但随着vCPU增加得到了缓解,但是endorsement由于很难并行因此提升有限。32-vCPU peers可以达到3560 tps(SPEND only)和3420 tps(MINT only);
实验3:RAM disk,tmpfs相比SSD提升了9%;
实验4:Scalability
参考: https://baijiahao.baidu.com/s?id=1626229819150414021&wfr=spider&for=pc