Turechain上线解读——如何实现高性能

Turechain上线解读——如何实现高性能

# 介绍:

初链是什么?从白皮书中我们可以看到这样的定义,初恋是商用去中心化应用的无需许可链,基于混合共识机制设计,旨在为社会提供高速点对点通信、价值传输以及智能合约基础设施。初链的使命是——打造一个公平透明的区块链商业世界。初链的愿景是——成为影响百年的区块链基础设施。

优势:

1支持无限节点进入
2安全性
3高性能
4免费使用

关键词

高性能

在truechain众多优势中,我接选择高性能这以方面进行解读。近阶段,公链的矛盾在于公链的性能与当前用户需求不相符,从时常堵塞的eth我们便可知一二。所以公链之间的竞争归根到底是性能的竞争。

那初链是如何实现其高性能呢?

谈到公链的性能,我们往往要去关注其共识算法。我们常见的共识机制都有POW、POS、DPOS、PBFT、VRF,但是每一种共识机制都存在缺陷,如区块链1.0时代的比特币采取的是POW,参与节点广泛但运算性能低下,POS容易引起“巨大的贫富差距”,DPOS目前常饱受“中心化”的诟病,而PBFT和VRF一般使用在许可链中。因此,目前区块链技术发展趋势之一就是在共识方面,从单一共识向混合共识演变。而初链就是其中的一个代表,其在共识方面讲POW和PBFT相结合,而不是使用单一的共识机制。进而衍生出双链接结构:快链(fastchain)和慢链(snailchain),已达到提高性能的目的。

基于pbft对交易进行验证

传统的区块链如btc的每一笔交易需要全节点验证,十分耗时,且麻烦。fastchain基于pbft在选取固定且少量的节点快速验证由快链打包的交易,这便是初链实现高性能的核心所在。
在这里插入图片描述

我的理解和EOS超级节点差不多,只是节点比EOS多,初链目前有11个节点。广播方式不同,从而PBFT在安全性上高一些。

在这里插入图片描述

具体步骤如下:
其中C为发送请求端,0123为服务端,3为宕机的服务端

  1. Request:请求端C发送请求到任意一节点,这里是0
  2. Pre-Prepare:服务端0收到C的请求后进行广播,扩散至123
  3. Prepare:123,收到后记录并再次广播,1->023,2->013,3因为宕机无法广播
  4. Commit:0123节点在Prepare阶段,若收到超过一定数量的相同请求,则进入Commit阶段,广播Commit请求
    5.Reply:0123节点在Commit阶段,若收到超过一定数量的相同请求,则对C进行反馈

由此可以看出,拜占庭容错能够容纳将近1/3的错误节点误差,交易打包成区块后经过拜占庭委员会(PBFT)的共识即被确认慢链区块包含快链区块的内容,通过挖矿完成慢链区块的打包。慢链基于pow,可通过算力保护整个区块链和拜占庭委员会的安全,以达到去中心化。

相关代码
func (state *State) PrePrepare(prePrepareMsg *PrePrepareMsg) (*VoteMsg, error) {
	//获取请求信息,并将其保存
	state.MsgLogs.ReqMsg = prePrepareMsg.RequestMsg

	// 验证msg是否正常,错误则返回一个error
	if !state.verifyMsg(prePrepareMsg.ViewID, prePrepareMsg.SequenceID, prePrepareMsg.Digest) {
		return nil, errors.New("pre-prepare message is corrupted")
	}
	// 节点当前状态
	state.CurrentStage = PrePrepared
    //返回相关信息
	return &VoteMsg{
		ViewID:     state.ViewID,
		SequenceID: prePrepareMsg.SequenceID,
		Digest:     prePrepareMsg.Digest,
		MsgType:    PrepareMsg,
		Height:     prePrepareMsg.Height,
	}, nil
}

func (state *State) Prepare(prepareMsg *VoteMsg, f float64) (*VoteMsg, error) {
	//验证信息
	if !state.verifyMsg(prepareMsg.ViewID, prepareMsg.SequenceID, prepareMsg.Digest) {
		return nil, errors.New("prepare message is corrupted")
	}

	//将信息添加到log
	state.MsgLogs.SetPrepareMsg(prepareMsg.NodeID, prepareMsg)

	//若节点的状态为prepared ,则返回信息
	if state.prepared(f) {
		return &VoteMsg{
			ViewID:     state.ViewID,
			SequenceID: prepareMsg.SequenceID,
			Digest:     prepareMsg.Digest,
			MsgType:    CommitMsg,
			Height:     prepareMsg.Height,
		}, nil
		lock.PSLog("Prepare", "end", f, "Return")
	}

	lock.PSLog("Prepare", "end", f, "notReturn")
	return nil, nil
}

func (state *State) Commit(commitMsg *VoteMsg, f float64) (*ReplyMsg, *RequestMsg, error) {
	//验证信息
	if !state.verifyMsg(commitMsg.ViewID, commitMsg.SequenceID, commitMsg.Digest) {
		return nil, nil, errors.New("commit message is corrupted")
	}

	// 将信息添加到log
	state.MsgLogs.SetCommitMsgs(commitMsg.NodeID, commitMsg)

	
	if state.committed(f) {
		//处理结果
		result := "Executed"

		return &ReplyMsg{
			ViewID:    state.ViewID,
			Timestamp: state.MsgLogs.ReqMsg.Timestamp,
			ClientID:  state.MsgLogs.ReqMsg.ClientID,
			Result:    result,
			Height:    state.MsgLogs.ReqMsg.Height,
		}, state.MsgLogs.ReqMsg, nil
	}
	return nil, nil, nil
}

//上述代码  ,事pbft的共识过程,从getrequest->preprepared->prepared->commit


//下面的resoloveMsg函数则是处理pbft中msg,通过case条件选择指令将其串联起来
func (node *Node) resolveMsg() {
	for {
		// 从调度程序获取缓冲消息
		msgs := <-node.MsgDelivery
		switch msgs.(type) {
		case []*consensus.RequestMsg:   //获取请求
			errs := node.resolveRequestMsg(msgs.([]*consensus.RequestMsg))
			if len(errs) != 0 {
				for _, err := range errs {
					fmt.Println(err)
				}
				// TODO: 发送错误
			}
		case []*consensus.PrePrepareMsg:  //想其他节点发送信息
			errs := node.resolvePrePrepareMsg(msgs.([]*consensus.PrePrepareMsg))
			if len(errs) != 0 {
				for _, err := range errs {
					fmt.Println(err)
				}
				
			}
		case []*consensus.VoteMsg:  
			voteMsgs := msgs.([]*consensus.VoteMsg)
			if len(voteMsgs) == 0 {
				break
			}

			if voteMsgs[0].MsgType == consensus.PrepareMsg {
				errs := node.resolvePrepareMsg(voteMsgs)
				if len(errs) != 0 {
					for _, err := range errs {
						fmt.Println(err)
					}
					
				}
			} else if voteMsgs[0].MsgType == consensus.CommitMsg {
				errs := node.resolveCommitMsg(voteMsgs)
				if len(errs) != 0 {
					for _, err := range errs {
						fmt.Println(err)
					}
					
				}
			}
		}
	}
}
--------------------- 

//以上事pbft的工作流程


所以truechain之所以快,就在于使用了pbft,用较少的节点完成交易的打包。因为节点的选择也是很重要的问题

func (e *Election) elect(candidates []*candidateMember, seed common.Hash) []*types.CommitteeMember {
	//传入参数1 候选节点 candidates  2 随机种子 seed
		var addrs map[common.Address]uint = make(map[common.Address]uint)
		var members []*types.CommitteeMember
	
		log.Debug("elect committee members ..", "count", len(candidates), "seed", seed)
		// 记录候选人数,以及seed
		round := new(big.Int).Set(common.Big1)
		for {
			seedNumber := new(big.Int).Add(seed.Big(), round) // seed + 1
			hash := crypto.Keccak256Hash(seedNumber.Bytes())  
			//prop := new(big.Int).Div(maxUint256, hash.Big())
			prop := hash.Big() 
			//产生随机数
			for _, cm := range candidates {
				if prop.Cmp(cm.lower) < 0 {
					continue
				}
				if prop.Cmp(cm.upper) >= 0 { 
					continue
				}
			//选取规则,通过prop与节点的难度区间进行比较
				log.Trace("get member", "seed", hash, "member", cm.address, "prop", prop)
				if _, ok := addrs[cm.address]; ok { 
					break
				}
				addrs[cm.address] = 1   //标记1  代表入选成功       
				member := &types.CommitteeMember{ 
					Coinbase:  cm.coinbase,
					Publickey: cm.publickey,
				}
				//给改节点分配相关参数  ,公钥 ,地址
				members = append(members, member) 
				//添加改节点

				break
			}

			round = new(big.Int).Add(round, common.Big1) Number = big.NewInt(40)
			if round.Cmp(params.MaximumCommitteeNumber) > 0 {
				break //若人数已满,则停止
			}
		}
	
		log.Debug("get new committee members", "count", len(members))

		return members 
	}





从上面一段代码我们大概可以了解节点的选择过程,先记录候选的地址,并通过hash.Big()产生一个随机数与候选人难度区间进行比较,若在其中,则被选中。这变保证了其公平性,各个候选人都有机会入选。具体的流程图可看下方图片。
在这里插入图片描述

总结

本文从truechain如何实现其高性能,高tps进行了简单的探究,认为truechain在当前公链之林中,既做到了高tps,又保证了其去中心化性,实属不易。在目前已经上线的在无许可(Permissionless)环境中运行的公链中,初链TrueChain主网Beta版的tps的性能已经非常高,在后期正式主网发布和加上Sharding分片技术的融入,TPS将达到更高的性能要求。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值