• wooyoozoosa
  • Python
  • 3KB
  • zip
  • 0
  • 10 积分
  • 1
  • 2020-10-25 12:24
simple blockchain written in python language
  • blockchain.py
from functools import reduce import hashlib as hl from collections import OrderedDict import json # Import two functions from our hash_util.py file. Omit the ".py" in the import from hash_util import hash_string_256, hash_block # The reward we give to miners (for creating a new block) MINING_REWARD = 10 # Our starting block for the blockchain genesis_block = { 'previous_hash': '', 'index': 0, 'transactions': [], 'proof': 100 } # Initializing our (empty) blockchain list blockchain = [genesis_block] # Unhandled transactions open_transactions = [] # We are the owner of this blockchain node, hence this is our identifier (e.g. for sending coins) owner = 'Max' # Registered participants: Ourself + other people sending/ receiving coins participants = {'Max'} def load_data(): with open('blockchain.txt', mode='r') as f: file_content = f.readlines() global blockchain global open_transactions blockchain = json.loads(file_content[0][:-1]) open_transactions = json.loads(file_content[1]) load_data() def save_data(): with open('blockchain.txt', mode='w') as f: f.write(json.dumps(blockchain)) f.write('\n') f.write(json.dumps(open_transactions)) def valid_proof(transactions, last_hash, proof): """Validate a proof of work number and see if it solves the puzzle algorithm (two leading 0s) Arguments: :transactions: The transactions of the block for which the proof is created. :last_hash: The previous block's hash which will be stored in the current block. :proof: The proof number we're testing. """ # Create a string with all the hash inputs guess = (str(transactions) + str(last_hash) + str(proof)).encode() # Hash the string # IMPORTANT: This is NOT the same hash as will be stored in the previous_hash. It's a not a block's hash. It's only used for the proof-of-work algorithm. guess_hash = hash_string_256(guess) print(guess_hash) # Only a hash (which is based on the above inputs) which starts with two 0s is treated as valid # This condition is of course defined by you. You could also require 10 leading 0s - this would take significantly longer (and this allows you to control the speed at which new blocks can be added) return guess_hash[0:2] == '00' def proof_of_work(): """Generate a proof of work for the open transactions, the hash of the previous block and a random number (which is guessed until it fits).""" last_block = blockchain[-1] last_hash = hash_block(last_block) proof = 0 # Try different PoW numbers and return the first valid one while not valid_proof(open_transactions, last_hash, proof): proof += 1 return proof def get_balance(participant): """Calculate and return the balance for a participant. Arguments: :participant: The person for whom to calculate the balance. """ # Fetch a list of all sent coin amounts for the given person (empty lists are returned if the person was NOT the sender) # This fetches sent amounts of transactions that were already included in blocks of the blockchain tx_sender = [[tx['amount'] for tx in block['transactions'] if tx['sender'] == participant] for block in blockchain] # Fetch a list of all sent coin amounts for the given person (empty lists are returned if the person was NOT the sender) # This fetches sent amounts of open transactions (to avoid double spending) open_tx_sender = [tx['amount'] for tx in open_transactions if tx['sender'] == participant] tx_sender.append(open_tx_sender) print(tx_sender) amount_sent = reduce(lambda tx_sum, tx_amt: tx_sum + sum(tx_amt) if len(tx_amt) > 0 else tx_sum + 0, tx_sender, 0) # This fetches received coin amounts of transactions that were already included in blocks of the blockchain # We ignore open transactions here because you shouldn't be able to spend coins before the transaction was confirmed + included in a block tx_recipient = [[tx['amount'] for tx in block['transactions'] if tx['recipient'] == participant] for block in blockchain] amount_received = reduce(lambda tx_sum, tx_amt: tx_sum + sum(tx_amt) if len(tx_amt) > 0 else tx_sum + 0, tx_recipient, 0) # Return the total balance return amount_received - amount_sent def get_last_blockchain_value(): """ Returns the last value of the current blockchain. """ if len(blockchain) < 1: return None return blockchain[-1] def verify_transaction(transaction): """Verify a transaction by checking whether the sender has sufficient coins. Arguments: :transaction: The transaction that should be verified. """ sender_balance = get_balance(transaction['sender']) return sender_balance >= transaction['amount'] # This function accepts two arguments. # One required one (transaction_amount) and one optional one (last_transaction) # The optional one is optional because it has a default value => [1] def add_transaction(recipient, sender=owner, amount=1.0): """ Append a new value as well as the last blockchain value to the blockchain. Arguments: :sender: The sender of the coins. :recipient: The recipient of the coins. :amount: The amount of coins sent with the transaction (default = 1.0) """ # transaction = { # 'sender': sender, # 'recipient': recipient, # 'amount': amount # } transaction = OrderedDict( [('sender', sender), ('recipient', recipient), ('amount', amount)]) if verify_transaction(transaction): open_transactions.append(transaction) participants.add(sender) participants.add(recipient) save_data() return True return False def mine_block(): """Create a new block and add open transactions to it.""" # Fetch the currently last block of the blockchain last_block = blockchain[-1] # Hash the last block (=> to be able to compare it to the stored hash value) hashed_block = hash_block(last_block) proof = proof_of_work() # Miners should be rewarded, so let's create a reward transaction # reward_transaction = { # 'sender': 'MINING', # 'recipient': owner, # 'amount': MINING_REWARD # } reward_transaction = OrderedDict( [('sender', 'MINING'), ('recipient', owner), ('amount', MINING_REWARD)]) # Copy transaction instead of manipulating the original open_transactions list # This ensures that if for some reason the mining should fail, we don't have the reward transaction stored in the open transactions copied_transactions = open_transactions[:] copied_transactions.append(reward_transaction) block = { 'previous_hash': hashed_block, 'index': len(blockchain), 'transactions': copied_transactions, 'proof': proof } blockchain.append(block) save_data() return True def get_transaction_value(): """ Returns the input of the user (a new transaction amount) as a float. """ # Get the user input, transform it from a string to a float and store it in user_input tx_recipient = input('Enter the recipient of the transaction: ') tx_amount = float(input('Your transaction amount please: ')) return tx_recipient, tx_amount def get_user_choice(): """Prompts the user for its choice and return it.""" user_input = input('Your choice: ') return user_input def print_blockchain_elements(): """ Output all blocks of the blockchain. """ # Output the blockchain list to the console for block in blockchain: print('Outputting Block') print(block) else: print('-' * 20) def verify_chain(): """ Verify the current blockchain and return True if it's valid, False otherwise.""" for (index, block) in enumerate(blockch
    • python-blockchain
      激活虚拟环境 source blockchain-env/bin/activate 安装所有软件包 pip3 install -r requirements.txt 运行测试 确保激活虚拟环境 python3 -m pytest backend/tests
    • Blockchain_Python
    • python_blockchain_flow
      python_blockchain_flow 受到Antonopoulus的“精通比特币”一书的启发,一些区块链交易的基本流程 以及Michael Chrupcala专门针对Python区块链的文章
    • python_blockchain
      python_blockchain 创建虚拟环境 python3 -m venv blockchain-env 激活虚拟环境 source blockchain-env/bin/activate 安装所有软件包 pip3 install -r requirements.txt 运行测试 确保激活虚拟环境。 python3 -m ...
    • BlockChain:Blockhain Python
      区块链 Blockhain Python
    • Blockchain-Python:区块链Python作业
      区块链Python HD(分层确定性)钱包可以允许从单个种子短语生成许多crpyto钱包。这是一个从根节点开始的公共/私有密钥树,该根节点是主节点。任何节点都可以有多个子代。主私钥的唯一目的是重新生成钱包树,并且...
    • Blockchain-Python:Exemplo2区块链Usando Python
      区块链Python Exemplo2区块链Usando Python
    • Python-Blockchain和Crytocurrency资源
      Blockchain和Crytocurrency 资源
    • Blockchain-and-Python-Wallet
    • SIM800C_MQTT.rar