原文題目:《Tendermint: Byzantine Fault Tolerance in the Age of Blockchains》react
原文做者:Ethan Buchman算法
本文爲節選數據庫
客戶端的考量緩存
這章回顧了客戶端的考量(consideration),該客戶端直接與一個基於Tendermint的應用進行交互。網絡
發現架構
網絡節點發現機制(network discovery)是簡單地經過TCP鏈接向種子節點撥號的方式進行。P2P網絡使用了認證加密技術,然而驗證者公鑰須要經過帶外數據驗證。確實,在這些系統中,創世狀態(genesis state)必須經過帶外同步,理想狀況下,這也是惟一須要進行通信的數據,由於其已經包含了驗證者在認證加密中使用的公鑰,這與共識中用來簽名投票的公私鑰不一樣。分佈式
對於一個會隨時間變化的驗證者集合,能夠經過DNS來註冊全部的驗證者,能夠在他們真正成爲驗證者以前註冊一個新的驗證者,能夠將它們做爲驗證者移出後將其刪除。或者,驗證者位置能夠經過其餘的拜占庭容錯分佈式數據存儲來註冊,包括可能的其餘的Tendermint集羣。ide
廣播交易區塊鏈
做爲一個通用的應用層平臺,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網絡中的客戶端功能仍是相似於其餘分佈式數據庫。除此以外,客戶端必須被設計成特定的應用程序。儘管這添加了一些複雜度,它卻賦予了客戶端極大的靈活性。
相關閱讀: