Python愛上區塊鏈[入門篇]

# -*- coding: utf-8 -*-

# @Author  : TerryJay
# @File    : chain.py
# @Software: PyCharm
# @Time    : 2018/8/13 21:54
# I believe that the God rewards the diligent.


import hashlib
import time
import copy



class block_module:
    def __init__(self, **param):
        self._Prev_Hash = None

        self.Temporary_Random = param['Temp_Random']
        self.Block_Index = param['Block_Index']
        self.Block_Data = param['Block_Data']
        self.Block_Hash = None
        self.Block_Generation_Time = param['Block_Generation_Time']

    def calculation_this_block_hash(self):
        """
        :parameter:將初始的5個str合併爲一個str
        :return:計算出一個256位hash值,字節數爲 256/8 = 32 個
        """
        custom_sha256 = hashlib.sha256()
        # ss << _nIndex << _tTime << _sData << _nNonce << sPrevHash;

        content = str(self.Temporary_Random) + str(self.Block_Data) + str(self.Block_Index) + str(
            self.Block_Generation_Time) + str(self._Prev_Hash)
        custom_sha256.update(content.encode("utf8"))

        return custom_sha256.hexdigest()

    # 挖礦函數
    def mine_block(self, difficulty=20):

        terry_str = str(difficulty + 1)
        terry_list = list(terry_str)

        for i in range(len(terry_list)):
            terry_list[i] = "0"

        update_terry_str = ''.join(terry_list)
        while True:
            self.Temporary_Random += 1
            self.Block_Hash = self.calculation_this_block_hash()
            print("temp哈希值爲:", self.Block_Hash)
            print("校驗目標值爲:", update_terry_str[0:difficulty])

            # time.sleep(1)

            if update_terry_str[0:difficulty] in self.Block_Hash:
                break
            else:
                pass

        print("===============================恭喜你挖到一個區塊=================================")
        print("該區塊的hash爲:", self.Block_Hash)
        print("================================================================================")

    # return self.Block_Hash


    def get_this_block_hash(self):
        return self.Block_Hash


class block_chain:
    def __init__(self, **param):
        self.param = param
        self.chain = list()

    # self.other_node = None

    def __get_last_node_block(self):
        if self.chain:
            # 返回末尾節點塊
            return self.chain[len(self.chain)]
        else:
            print("當前區塊鏈中不存在任何節點,請先初始化創世塊後重試~")

    # def __create_new_block(self, block_module_cls):
    #     self.this_block = block_module_cls(self.param)



    def add_seed_block_to_chain(self):

        """將創世塊掛載到區塊鏈頭部"""
        __seed_node = self.param

        block_class = block_module(**self.param)

        """首次的創世塊的Block_Hash直接計算即可,無需調用挖礦函數"""
        __seed_node["Block_Hash"] = block_class.calculation_this_block_hash()

        self.chain.append(__seed_node)
        print("創世塊掛載成功!")
        print("===============================|_創_世_塊_|=================================")
        print("創世塊的hash:", __seed_node["Block_Hash"])
        print("創世塊挖掘難度:", __seed_node["Mine_Difficulty"])
        print("創世塊獎勵幣的總數:", __seed_node["Block_panda_coin_reward"])
        print("================================================================================")

    def add_other_block_to_chain(self):

        """將新區塊連接到主鏈的尾部"""
        if self.chain:
            block_class = block_module(**self.param)

            # b = copy.deepcopy(a)
            next_param = copy.deepcopy(self.param)

            """self.param["Mine_Difficulty"]指的是:挖掘難度 """
            block_class.mine_block(self.param["Mine_Difficulty"])

            # self.chain[len(self.chain)]["Block_Hash"]
            """第二個區塊的prev_hash保存的是創世塊的Block_Hash值, len(self.chain)-1代表主鏈中最後一個塊的下標"""
            block_number = len(self.chain) - 1
            next_param["_Prev_Hash"] = self.chain[block_number]["Block_Hash"]
            next_param["Block_Generation_Time"] = int(time.time())
            next_param["Block_panda_coin_reward"] -= 1
            next_param["Block_Index"] = block_number + 1


            self.chain.append(next_param)
            print("第[%s]個區塊成功接入主鏈!" % len(self.chain))

        else:
            print("提示:您的主鏈中不存在任何節點,請先初始化創世塊後重試~")


# creation_block:創世塊基本配置
class creation_block:
    """
    @block_index:當前區塊的序號
    @user_data:需要用此區塊鏈進行加密傳輸的信息
    @admin_coin_reward:創世塊設置的獎勵,也可以稱爲幣
    """

    def __init__(self, **seed_setting):
        self.Block_Data = seed_setting["user_data"]
        self.Block_Index = seed_setting["block_index"]
        self.Temp_Random = seed_setting["Temp_Random"]
        # self.Block_Generation_Time = None
        self.Block_panda_coin_reward = seed_setting["admin_coin_reward"]
        self.mine_difficulty = seed_setting["diff"]

    def rtn_setting(self):
        now_time = int(time.time())
        print("創世塊的創建時間戳是:", now_time, "北京時間:", time.ctime())

        """8個標準參數"""
        block = {
            "_Prev_Hash": '|_創_世_塊_|',
            "Block_Index": self.Block_Index,
            "Block_Hash": None,
            "Block_Generation_Time": now_time,
            "Block_Data": self.Block_Data,
            "Temp_Random": self.Temp_Random,
            "Mine_Difficulty": self.mine_difficulty,
            "Block_panda_coin_reward": self.Block_panda_coin_reward
        }
        return block


# create_seed_block:創世塊初始化
class create_seed_block:
    def __init__(self):
        self.seed = None

    def rtn_seed_param(self):
        """創世塊的種子配置"""
        panda_setting = {
            "user_data": "這裏是放數據的,它將隨着區塊鏈的延伸而進化成分佈式儲存",
            "block_index": 0,
            "admin_coin_reward": 100,
            "diff": 100000000,
            "Temp_Random": 2056985438
        }

        """設置創世塊,並返回它的全部數據"""
        self.seed = creation_block(**panda_setting).rtn_setting()
        return self.seed


if __name__ == '__main__':

    """初始化創世塊,將它放置在區塊鏈第一個節點"""
    seed = create_seed_block()
    seed_data = seed.rtn_seed_param()
    panda_chain = block_chain(**seed_data)
    panda_chain.add_seed_block_to_chain()

    """創建第二個節點"""
    panda_chain.add_other_block_to_chain()

    """挖掘和創建更多節點"""
    # 後續補充更新···
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章