用Java 實現區塊鏈:基本原型(第一章)


參考網站:

https://jeiwan.cc/posts/building-blockchain-in-go-part-1/

https://github.com/liuchengxu/blockchain-tutorial/blob/master/content/part-1/basic-prototype.md#%E5%8C%BA%E5%9D%97%E9%93%BE

  前言:

  區塊鏈是 21 世紀最具革命性的技術之一,它仍然處於不斷成長的階段,而且還有很多潛力尚未顯現。 本質上,區塊鏈只是一個分布式數據庫而已。 不過,使它獨一無二的是,區塊鏈是一個公開的數據庫,而不是一個私人數據庫,也就是說,每個使用它的人都有一個完整或部分的副本。 只有經過其他“數據庫管理員”的同意,才能向數據庫中添加新的記錄。 此外,也正是由於區塊鏈,才使得加密貨幣和智能合約成為現實。

  區塊:

  首先從 “區塊” 談起。在區塊鏈中,真正存儲有效信息的是區塊(block)。而在比特幣中,真正有價值的信息就是交易(transaction)。實際上,交易信息是所有加密貨幣的價值所在。除此以外,區塊還包含了一些技術實現的相關信息,比如版本,當前時間戳和前一個區塊的哈希。

  不過,我們要實現的是一個簡化版的區塊鏈,而不是一個像比特幣技術規范所描述那樣成熟完備的區塊鏈。所以在我們目前的實現中,區塊僅包含了部分關鍵信息,它的數據結構如下:

@Getter
public class Block {
    private long timestamp; // 區塊創建的時間
    private byte[] data; //區塊儲存的有效信息
    private byte[] prevBlockHash; //上一個區塊的哈希值
    private byte[] hash; //當前塊的Hash塊
}
Block.java

  在比特幣中,有兩部分數據,一種是Header數據(timestamp、preBlockHash、hash等)和交易數據 (data),這里簡化模型,將兩部分數據合並在一起。

  下面創建Block的構造函數和hash處理函數,我們這里將timestamp、preBlockHash和data拼接起來使用SHA-256計算得到一個哈希。

public void setHash() {
    byte[] time = (timestamp + "").getBytes();
    byte[] target = new byte[time.length + data.length + prevBlockHash.length];
    int index = 0;
    System.arraycopy(time, 0, target, index, time.length);
    index += time.length;
    System.arraycopy(prevBlockHash, 0, target, index, prevBlockHash.length);
    index += prevBlockHash.length;
    System.arraycopy(data, 0, target, index, data.length);
    hash = SHA256Util.getSHA256Bytes(target);
}
public Block(byte[] data, byte[] prevBlockHash) {
    if (data == null || prevBlockHash == null || data.length == 0) {
        throw new RuntimeException("error block!");
    }
    this.data = data;
    this.prevBlockHash = prevBlockHash;
    this.timestamp = new Date().getTime();
    setHash();
}
View Code

  區塊鏈:

  有了區塊,下面讓我們來實現區塊。本質上,區塊鏈就是一個有着特定結構的數據庫,是一個有序,每一個塊都連接到前一個塊的鏈表。也就是說,區塊按照插入的順序進行存儲,每個塊都與前一個塊相連。這樣的結構,能夠讓我們快速地獲取鏈上的最新塊,並且高效地通過哈希來檢索一個塊。

public class BlockChain {

    //這里暫時只用一個List就OK
    private List<Block> blocks;

    public BlockChain() {
        blocks = new ArrayList<>();
//添加初始塊
        blocks.add(new Block("Genesis Block".getBytes(), new byte[]{}));
    }
    public void addBlock(byte[] data) {
        if (data == null || data.length == 0) {
            throw new RuntimeException("data can't be empty");
        }
        Block preBlock = blocks.get(blocks.size() - 1);
        blocks.add(new Block(data, preBlock.getHash()));
    }
    @Override
    public String toString() {
        StringBuilder sb = new StringBuilder();
        for (Block block : blocks) {
            sb.append("================\n");
            sb.append("data : ").append(new String(block.getData())).append("\n");
            sb.append("preHash : ").append(ByteUtils.byte2Hex(block.getPrevBlockHash())).append("\n");
            sb.append("hash : ").append(ByteUtils.byte2Hex(block.getHash())).append("\n");
        }
        sb.append("length : ").append(blocks.size());
        return sb.toString();
    }
}
BlockChain.java

  測試效果

public static void main(String[] args) {
    BlockChain blockChain = new BlockChain();
    blockChain.addBlock("Block1".getBytes());
    blockChain.addBlock("Block2".getBytes());
    System.out.println(blockChain.toString());
}
結果
================
data : Genesis Block
preHash : 
hash : cde7c1538c6b384fa7af18e6ce6f7cde3440028c5d599ffd8bb61121e6b46681
================
data : Block1
preHash : cde7c1538c6b384fa7af18e6ce6f7cde3440028c5d599ffd8bb61121e6b46681
hash : 074d9d9f9bba1d6d2471e2f97e95564841107368f773112df5e1d05d7381ee58
================
data : Block2
preHash : 074d9d9f9bba1d6d2471e2f97e95564841107368f773112df5e1d05d7381ee58
hash : c6079e03785a5093ce0caa4116e78ada790d227425337f65668d6ed8fb9a3baa
length : 3

  總結:

  我們創建了一個非常簡單的區塊鏈原型:它僅僅是一個數組構成的一系列區塊,每個塊都與前一個塊相關聯。真實的區塊鏈要比這復雜得多。在我們的區塊鏈中,加入新的塊非常簡單,也很快,但是在真實的區塊鏈中,加入新的塊需要很多工作:你必須要經過十分繁重的計算(這個機制叫做工作量證明),來獲得添加一個新塊的權力。並且,區塊鏈是一個分布式數據庫,並且沒有單一決策者。因此,要加入一個新塊,必須要被網絡的其他參與者確認和同意(這個機制叫做共識(consensus))。還有一點,我們的區塊鏈還沒有任何的交易!


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM