04.04 將到來的數字革命?用Python實現一個區塊鏈

將到來的數字革命?用Python實現一個區塊鏈

Python具有豐富和強大的庫。它常被暱稱為膠水語言,能夠把用其他語言製作的各種模塊(尤其是C/C++)很輕鬆地聯結在一起。Python是一種面向對象的解釋型計算機程序設計語言,下面我們用區塊鏈的實現。

python實現一個基礎的區塊鏈

我們實現的區塊鏈有如下幾個特性:

可以向區塊鏈中添加多個節點。

工作量證明(PoW)。

簡單的節點間衝突解決機制。

使用RSA 加密進行交易。

我們的區塊鏈客戶端有如下幾個功能:

使用公鑰/私鑰加密技術生成錢包。(基於RSA算法)。

使用RSA 加密算法生成交易。

我們還實現了2個展示界面:

挖礦者使用的“區塊鏈前端”

用戶生成錢包和發幣的“區塊鏈客戶端”

我在原始代碼的基礎上進行了一些改動,向交易中加入了RSA加密,並實現了錢包生成和交易加密,兩個界面使用HTML/CSS/JS 實現。

用python實現區塊鏈:

將到來的數字革命?用Python實現一個區塊鏈

首選: 打造一個 Blockchain

新建一個文件 blockchain.py,本文所有的代碼都寫在這一個文件中。首先創建一個 Blockchain 類,在構造函數中我們創建了兩個列表,一個用於儲存區塊鏈,一個用於儲存交易。

將到來的數字革命?用Python實現一個區塊鏈

一個區塊有五個基本屬性:index,timestamp(in Unix time),transaction 列表,工作量證明(稍後解釋)以及前一個區塊的 Hash 值。

將到來的數字革命?用Python實現一個區塊鏈

將到來的數字革命?用Python實現一個區塊鏈

到這裡,區塊鏈的概念應該比較清楚了:每個新的區塊都會包含上一個區塊的 Hash 值。這一點非常關鍵,它是區塊鏈不可變性的根本保障。如果攻擊者破壞了前面的某個區塊,那麼後面所有區塊的 Hash 都會變得不正確。不理解?慢慢消化~

將到來的數字革命?用Python實現一個區塊鏈

我們需要一個向區塊添加交易的方法:

將到來的數字革命?用Python實現一個區塊鏈

new_transaction() 方法向列表中添加一個交易記錄,並返回該記錄將被添加到的區塊——下一個待挖掘的區塊——的索引,稍後在用戶提交交易時會有用。

當 Blockchain 實例化後,我們需要創建一個初始的區塊(創世塊),並且給它預設一個工作量證明。

除了添加創世塊的代碼,我們還需要補充 new_block(), new_transaction() 和 hash() 方法:

將到來的數字革命?用Python實現一個區塊鏈

上面的代碼應該很直觀,我們基本上有了區塊鏈的雛形。但此時你肯定很想知道一個區塊究竟是怎樣被創建或挖掘出來的。

新的區塊來自工作量證明(PoW)算法。PoW 的目標是計算出一個符合特定條件的數字,這個數字對於所有人而言必須在計算上非常困難,但易於驗證。這就是工作量證明的核心思想。

舉個例子:

假設一個整數 x 乘以另一個整數 y 的積的 Hash 值必須以 0 結尾,即 hash(x * y) = ac23dc...0。設 x = 5,求 y?

將到來的數字革命?用Python實現一個區塊鏈

結果是 y = 21 // hash(5 * 21) = 1253e9373e...5e3600155e860

在比特幣中,工作量證明算法被稱為 Hashcash,它和上面的問題很相似,只不過計算難度非常大。這就是礦工們為了爭奪創建區塊的權利而爭相計算的問題。通常,計算難度與目標字符串需要滿足的特定字符的數量成正比,礦工算出結果後,就會獲得一定數量的比特幣獎勵(通過交易)。

網絡要驗證結果,當然非常容易。

讓我們來實現一個 PoW 算法,和上面的例子非常相似,規則是:尋找一個數 p,使得它與前一個區塊的 proof 拼接成的字符串的 Hash 值以 4 個零開頭。

將到來的數字革命?用Python實現一個區塊鏈

區塊鏈的實現

你可以從終端啟動區塊鏈節點,通過進入blockchain文件夾,並輸入命令:python blockchain_client.py或python blockchain_client.py -p <port> 。如果你未指定端口號,則會默認端口號為5000。在瀏覽器中打開http://localhost:<port>可以看到區塊鏈前端展示界面。/<port>/<port>

將到來的數字革命?用Python實現一個區塊鏈

展示界面導航欄有兩個標籤:

挖掘:用於查看交易和區塊鏈數據,以及挖掘新的交易區塊。

配置:用於配置不同區塊鏈節點之間的連接。

下面是blockchain.py文件代碼中一些重要部分的說明。

我們首先定義一個具有以下屬性的Blockchain類:

transactions:將被添加到下一區塊的交易列表。

chain::實際的區塊鏈,也就是一個區塊數組。

nodes:一個包含節點URL的集合。區塊鏈使用這些節點從其他節點中檢索區塊鏈數據並且在檢查到它們沒有同步時更新其區塊鏈。

node_id:一個標識blockchain節點的隨機字符串。

這個Blockchain類還實現了以下方法:

register_node(node_url): 將新的區塊鏈節點添加到節點列表中。

verify_transaction_signature(sender_address, signature, transaction): 檢查提供的簽名是否與通過公鑰(sender_address)簽署的交易相符。

submit_transaction(sender_address, recipient_address, value, signature): 如果簽名通過驗證,則將交易添加到交易列表中。

create_block(nonce, previous_hash):向區塊鏈添加一個交易塊。

hash(block): 創建一個區塊的SHA-256散列。

proof_of_work():工作算法的證明。尋找滿足挖掘條件的隨機數。

valid_proof(transactions, last_hash, nonce, difficulty=MINING_DIFFICULTY):檢查散列值是否滿足挖掘條件。該函數在proof_of_work函數中使用。

將到來的數字革命?用Python實現一個區塊鏈

valid_chain(chain): 檢查區塊鏈是否有效。

resolve_conflicts():通過用網絡中最長鏈代替鏈的方法解決區塊鏈節點之間的衝突。

class Blockchain: def __init__(self): self.transactions = [] self.chain = [] self.nodes = set() #Generate random number to be used as node_id self.node_id = str(uuid4()).replace('-', '') #Create genesis block self.create_block(0, '00') def register_node(self, node_url):""" Add a new node to the list of nodes """ ... def verify_transaction_signature(self, sender_address, signature, transaction):""" Check that the provided signature corresponds to transaction signed by the public key (sender_address) """ ... def submit_transaction(self, sender_address, recipient_address, value, signature):""" Add a transaction to transactions array if the signature verified """ ... def create_block(self, nonce, previous_hash):""" Add a block of transactions to the blockchain """ ... def hash(self, block):""" Create a SHA-256 hash of a block """ ... def proof_of_work(self):""" Proof of work algorithm """ ... def valid_proof(self, transactions, last_hash, nonce, difficulty=MINING_DIFFICULTY):""" Check if a hash value satisfies the mining conditions. This function is used within the proof_of_work function. """ ... def valid_chain(self, chain):""" check if a bockchain is valid """ ... def resolve_conflicts(self):""" Resolve conflicts between blockchain's nodes by replacing our chain with the longest one in the network. """ ...

下面這一行,我們初始化了一個Python Flask 應用,用於創建和區塊鏈交互的API。

app = Flask(__name__)CORS(app)

下面,我們初始化一個區塊鏈對象。

blockchain = Blockchain()

下面我們定義了2種返回我們區塊鏈前端展示界面html頁面的Flask路線。

@app.route('/')def index():returnrender_template('./index.html')@app.route('/configure')def configure():returnrender_template('./configure.html')

下面我們定義了Flask API來管理交易和挖掘區塊鏈。

此API將'sender_address', 'recipient_address', 'amount' 和 'signature' 作為輸入,並且如果簽名有效,則將交易添加到將添加到下一個塊的交易列表中。

'/transactions/get':此API返回所有將會添加到下一個塊的交易。

'/chain':此API返回所有區塊鏈數據。

'/mine': 此API運行工作算法的證明,同時添加新的交易塊到區塊鏈。

好了,今天的知識就分享到這裡,歡迎關注愛編程的南風,私信關鍵詞:學習資料,獲取更多學習資源,如果文章對你有有幫助,請收藏關注,在今後與你分享更多學習python的文章。同時歡迎在下面評論區留言如何學習python。


分享到:


相關文章: