Skip to content
IRC-Coding IRC-Coding
Blockchain Grundlagen Kryptographie Dezentrale Netzwerke Smart Contracts Kryptowährungen

Blockchain Grundlagen: Kryptographie, Dezentrale Netzwerke, Smart Contracts & Kryptowährungen

Blockchain Grundlagen mit Kryptographie, dezentralen Netzwerken, Smart Contracts und Kryptowährungen. Distributed Ledger Technology, Konsens-Algorithmen, Mining, Wallets mit praktischen Beispielen.

S

schutzgeist

2 min read

Blockchain Grundlagen: Kryptographie, Dezentrale Netzwerke, Smart Contracts & Kryptowährungen

Dieser Beitrag ist eine umfassende Einführung in die Blockchain Grundlagen – inklusive Kryptographie, dezentralen Netzwerken, Smart Contracts und Kryptowährungen mit praktischen Beispielen.

In a Nutshell

Blockchain ist eine dezentrale, unveränderliche Datenbanktechnologie, die durch kryptographische Verfahren die Integrität und Sicherheit von Transaktionen in verteilten Netzwerken gewährleistet.

Kompakte Fachbeschreibung

Blockchain ist eine verteilte Ledger-Technologie, die Daten in Blöcken organisiert und durch kryptographische Hash-Funktionen miteinander verkettet, um eine unveränderliche Kette von Transaktionen zu erstellen.

Kernkomponenten:

Kryptographische Grundlagen

  • Hash-Funktionen: SHA-256, Keccak-256 für Integrität
  • Digitale Signaturen: ECDSA, Ed25519 für Authentizität
  • Public-Key-Infrastruktur: Asymmetrische Verschlüsselung
  • Merkle Trees: Effiziente Datenverifikation

Dezentrale Netzwerke

  • Peer-to-Peer: Direkte Kommunikation ohne Zentralinstanz
  • Konsens-Algorithmen: Proof of Work, Proof of Stake
  • Distributed Ledger: Replizierte Datenhaltung
  • Network Topology: Mesh-Netzwerke

Smart Contracts

  • Automatisierte Verträge: Selbstausführende Vertragslogik
  • Ethereum Virtual Machine: Ausführungsumgebung
  • Solidity: Programmiersprache für Smart Contracts
  • Gas Fees: Transaktionskostenberechnung

Kryptowährungen

  • Bitcoin: Erste dezentrale Kryptowährung
  • Ethereum: Plattform für Smart Contracts
  • Altcoins: Alternative Kryptowährungen
  • Stablecoins: Preisstabile Token

Prüfungsrelevante Stichpunkte

  • Blockchain: Dezentrale, unveränderliche Datenbanktechnologie
  • Kryptographie: Hash-Funktionen, digitale Signaturen, Public-Key
  • Dezentrale Netzwerke: P2P, Konsens-Algorithmen, Distributed Ledger
  • Smart Contracts: Selbstausführende Verträge, EVM, Solidity
  • Kryptowährungen: Bitcoin, Ethereum, Altcoins, Stablecoins
  • Mining: Proof of Work, Block-Rewards, Difficulty Adjustment
  • Wallets: Private Keys, Public Keys, Address Generation
  • Konsens: Byzantine Fault Tolerance, Network Consensus
  • IHK-relevant: Moderne dezentrale Technologien und Kryptographie

Kernkomponenten

  1. Distributed Ledger: Dezentrale Datenhaltung
  2. Kryptographie: Sicherheitsgrundlagen
  3. Konsens-Algorithmen: Einigung im Netzwerk
  4. Smart Contracts: Automatisierte Verträge
  5. Mining/Validierung: Block-Erstellung
  6. Wallets: Schlüsselverwaltung
  7. Transaktionen: Datenübertragung
  8. Network Layer: Kommunikationsprotokolle

Praxisbeispiele

1. Blockchain Implementation mit JavaScript

// Block structure
class Block {
    constructor(index, timestamp, data, previousHash = '') {
        this.index = index;
        this.timestamp = timestamp;
        this.data = data;
        this.previousHash = previousHash;
        this.hash = this.calculateHash();
        this.nonce = 0;
    }
    
    calculateHash() {
        return SHA256(
            this.index +
            this.previousHash +
            this.timestamp +
            JSON.stringify(this.data) +
            this.nonce
        ).toString();
    }
    
    mineBlock(difficulty) {
        const target = Array(difficulty + 1).join("0");
        
        while (this.hash.substring(0, difficulty) !== target) {
            this.nonce++;
            this.hash = this.calculateHash();
        }
        
        console.log(`Block mined: ${this.hash}`);
    }
}

// Blockchain structure
class Blockchain {
    constructor() {
        this.chain = [this.createGenesisBlock()];
        this.difficulty = 2;
        this.pendingTransactions = [];
        this.miningReward = 100;
    }
    
    createGenesisBlock() {
        return new Block(0, Date.now(), "Genesis Block", "0");
    }
    
    getLatestBlock() {
        return this.chain[this.chain.length - 1];
    }
    
    addBlock(newBlock) {
        newBlock.previousHash = this.getLatestBlock().hash;
        newBlock.mineBlock(this.difficulty);
        this.chain.push(newBlock);
    }
    
    isChainValid() {
        for (let i = 1; i < this.chain.length; i++) {
            const currentBlock = this.chain[i];
            const previousBlock = this.chain[i - 1];
            
            if (currentBlock.hash !== currentBlock.calculateHash()) {
                return false;
            }
            
            if (currentBlock.previousHash !== previousBlock.hash) {
                return false;
            }
        }
        
        return true;
    }
    
    createTransaction(transaction) {
        this.pendingTransactions.push(transaction);
    }
    
    minePendingTransactions(miningRewardAddress) {
        const rewardTx = {
            from: null,
            to: miningRewardAddress,
            amount: this.miningReward
        };
        
        const block = new Block(
            this.chain.length,
            Date.now(),
            this.pendingTransactions,
            this.getLatestBlock().hash
        );
        
        block.mineBlock(this.difficulty);
        
        console.log('Block successfully mined!');
        this.chain.push(block);
        
        this.pendingTransactions = [rewardTx];
    }
    
    getBalance(address) {
        let balance = 0;
        
        for (const block of this.chain) {
            for (const trans of block.data) {
                if (trans.from === address) {
                    balance -= trans.amount;
                }
                
                if (trans.to === address) {
                    balance += trans.amount;
                }
            }
        }
        
        return balance;
    }
}

// SHA256 implementation
function SHA256(msg) {
    // Convert string to bytes
    const msgBuffer = new TextEncoder().encode(msg);
    
    // Hash the message
    return crypto.subtle.digest('SHA-256', msgBuffer);
}

// Transaction structure
class Transaction {
    constructor(fromAddress, toAddress, amount) {
        this.fromAddress = fromAddress;
        this.toAddress = toAddress;
        this.amount = amount;
        this.timestamp = Date.now();
    }
    
    calculateHash() {
        return SHA256(this.fromAddress + this.toAddress + this.amount + this.timestamp);
    }
    
    signTransaction(signingKey) {
        if (signingKey.getPublic('hex') !== this.fromAddress) {
            throw new Error('You cannot sign transactions for other wallets!');
        }
        
        const hashTx = this.calculateHash();
        const sig = signingKey.sign(hashTx, 'base64');
        
        this.signature = sig;
    }
    
    isValid() {
        if (this.fromAddress === null) return true;
        
        if (!this.signature || this.signature.length === 0) {
            throw new Error('No signature in this transaction');
        }
        
        const publicKey = ec.keyFromPublic(this.fromAddress, 'hex');
        const hashTx = this.calculateHash();
        
        return publicKey.verify(hashTx, this.signature);
    }
}

// Wallet implementation
class Wallet {
    constructor() {
        const keyPair = ec.genKeyPair();
        this.privateKey = keyPair.getPrivate('hex');
        this.publicKey = keyPair.getPublic('hex');
    }
    
    getPublicKey() {
        return this.publicKey;
    }
    
    getPrivateKey() {
        return this.privateKey;
    }
    
    getAddress() {
        const hash = SHA256(this.publicKey);
        return hash.toString().substring(0, 40);
    }
    
    sign(data) {
        const key = ec.keyFromPrivate(this.privateKey, 'hex');
        const hash = SHA256(data);
        return key.sign(hash);
    }
    
    verify(data, signature) {
        const key = ec.keyFromPublic(this.publicKey, 'hex');
        const hash = SHA256(data);
        return key.verify(hash, signature);
    }
}

// Usage example
const myCoin = new Blockchain();
const walletA = new Wallet();
const walletB = new Wallet();

console.log('Starting the miner...');
myCoin.minePendingTransactions(walletA.getAddress());

console.log(`Balance of walletA is ${myCoin.getBalance(walletA.getAddress())}`);

// Create transactions
const tx1 = new Transaction(walletA.getAddress(), walletB.getAddress(), 100);
tx1.signTransaction(walletA);
myCoin.createTransaction(tx1);

console.log('Starting the miner again...');
myCoin.minePendingTransactions(walletA.getAddress());

console.log(`Balance of walletA is ${myCoin.getBalance(walletA.getAddress())}`);
console.log(`Balance of walletB is ${myCoin.getBalance(walletB.getAddress())}`);

// Verify chain integrity
console.log(`Is chain valid? ${myCoin.isChainValid()}`);

2. Smart Contract mit Solidity

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;

// Simple Token Contract
contract SimpleToken {
    string public name;
    string public symbol;
    uint8 public decimals;
    uint256 public totalSupply;
    
    mapping(address => uint256) public balanceOf;
    mapping(address => mapping(address => uint256)) public allowance;
    
    event Transfer(address indexed from, address indexed to, uint256 value);
    event Approval(address indexed owner, address indexed spender, uint256 value);
    
    constructor(string memory _name, string memory _symbol, uint256 _totalSupply) {
        name = _name;
        symbol = _symbol;
        decimals = 18;
        totalSupply = _totalSupply * 10**decimals;
        balanceOf[msg.sender] = totalSupply;
        emit Transfer(address(0), msg.sender, totalSupply);
    }
    
    function transfer(address _to, uint256 _value) public returns (bool success) {
        require(_to != address(0), "Invalid address");
        require(balanceOf[msg.sender] >= _value, "Insufficient balance");
        require(balanceOf[_to] + _value >= balanceOf[_to], "Overflow check");
        
        balanceOf[msg.sender] -= _value;
        balanceOf[_to] += _value;
        
        emit Transfer(msg.sender, _to, _value);
        return true;
    }
    
    function approve(address _spender, uint256 _value) public returns (bool success) {
        allowance[msg.sender][_spender] = _value;
        emit Approval(msg.sender, _spender, _value);
        return true;
    }
    
    function transferFrom(address _from, address _to, uint256 _value) public returns (bool success) {
        require(_to != address(0), "Invalid address");
        require(balanceOf[_from] >= _value, "Insufficient balance");
        require(allowance[_from][msg.sender] >= _value, "Insufficient allowance");
        require(balanceOf[_to] + _value >= balanceOf[_to], "Overflow check");
        
        balanceOf[_from] -= _value;
        balanceOf[_to] += _value;
        allowance[_from][msg.sender] -= _value;
        
        emit Transfer(_from, _to, _value);
        return true;
    }
    
    function mint(address _to, uint256 _value) public returns (bool success) {
        require(_to != address(0), "Invalid address");
        require(totalSupply + _value >= totalSupply, "Overflow check");
        
        totalSupply += _value;
        balanceOf[_to] += _value;
        
        emit Transfer(address(0), _to, _value);
        return true;
    }
    
    function burn(uint256 _value) public returns (bool success) {
        require(balanceOf[msg.sender] >= _value, "Insufficient balance");
        require(totalSupply >= _value, "Total supply check");
        
        balanceOf[msg.sender] -= _value;
        totalSupply -= _value;
        
        emit Transfer(msg.sender, address(0), _value);
        return true;
    }
}

// Voting Contract
contract Voting {
    struct Candidate {
        string name;
        uint256 voteCount;
    }
    
    struct Voter {
        bool hasVoted;
        uint256 votedCandidateId;
        uint256 weight;
    }
    
    address public owner;
    string public electionName;
    uint256 public votingDeadline;
    bool public electionEnded;
    
    mapping(address => Voter) public voters;
    Candidate[] public candidates;
    
    event VoteCast(address voter, uint256 candidateId);
    event ElectionEnded(string electionName);
    
    modifier onlyOwner() {
        require(msg.sender == owner, "Only owner can call this function");
        _;
    }
    
    modifier votingOpen() {
        require(!electionEnded, "Election has ended");
        require(block.timestamp < votingDeadline, "Voting deadline passed");
        _;
    }
    
    constructor(string memory _electionName, uint256 _votingDuration) {
        owner = msg.sender;
        electionName = _electionName;
        votingDeadline = block.timestamp + _votingDuration;
        electionEnded = false;
    }
    
    function addCandidate(string memory _name) public onlyOwner {
        candidates.push(Candidate({
            name: _name,
            voteCount: 0
        }));
    }
    
    function giveRightToVote(address _voter) public onlyOwner {
        voters[_voter].weight = 1;
    }
    
    function vote(uint256 _candidateId) public votingOpen {
        require(voters[msg.sender].weight > 0, "No voting rights");
        require(!voters[msg.sender].hasVoted, "Already voted");
        require(_candidateId < candidates.length, "Invalid candidate");
        
        voters[msg.sender].hasVoted = true;
        voters[msg.sender].votedCandidateId = _candidateId;
        
        candidates[_candidateId].voteCount += voters[msg.sender].weight;
        
        emit VoteCast(msg.sender, _candidateId);
    }
    
    function endElection() public onlyOwner {
        require(!electionEnded, "Election already ended");
        electionEnded = true;
        emit ElectionEnded(electionName);
    }
    
    function getWinner() public view returns (string memory winnerName, uint256 winnerVotes) {
        require(electionEnded, "Election not ended yet");
        
        uint256 maxVotes = 0;
        uint256 winnerIndex = 0;
        
        for (uint256 i = 0; i < candidates.length; i++) {
            if (candidates[i].voteCount > maxVotes) {
                maxVotes = candidates[i].voteCount;
                winnerIndex = i;
            }
        }
        
        return (candidates[winnerIndex].name, maxVotes);
    }
    
    function getCandidateCount() public view returns (uint256) {
        return candidates.length;
    }
    
    function getCandidate(uint256 _index) public view returns (string memory, uint256) {
        require(_index < candidates.length, "Invalid candidate index");
        return (candidates[_index].name, candidates[_index].voteCount);
    }
}

// Escrow Contract
contract Escrow {
    enum State { AWAITING_PAYMENT, AWAITING_DELIVERY, COMPLETED, REFUNDED }
    
    address public buyer;
    address public seller;
    address public arbiter;
    
    uint256 public amount;
    uint256 public fee;
    
    State public currentState;
    
    modifier inState(State _state) {
        require(currentState == _state, "Invalid state for this operation");
        _;
    }
    
    modifier onlyBuyer() {
        require(msg.sender == buyer, "Only buyer can call this function");
        _;
    }
    
    modifier onlySeller() {
        require(msg.sender == seller, "Only seller can call this function");
        _;
    }
    
    modifier onlyArbiter() {
        require(msg.sender == arbiter, "Only arbiter can call this function");
        _;
    }
    
    event PaymentReceived(address from, uint256 amount);
    event DeliveryConfirmed();
    escrowCompleted(uint256 amount);
    escrowRefunded(uint256 amount);
    
    constructor(address _seller, address _arbiter, uint256 _fee) {
        buyer = msg.sender;
        seller = _seller;
        arbiter = _arbiter;
        fee = _fee;
        currentState = State.AWAITING_PAYMENT;
    }
    
    function deposit() public payable onlyBuyer inState(State.AWAITING_PAYMENT) {
        require(msg.value == amount, "Incorrect amount");
        currentState = State.AWAITING_DELIVERY;
        emit PaymentReceived(msg.sender, msg.value);
    }
    
    function confirmDelivery() public onlyBuyer inState(State.AWAITING_DELIVERY) {
        currentState = State.COMPLETED;
        
        uint256 sellerAmount = amount - fee;
        payable(seller).transfer(sellerAmount);
        payable(arbiter).transfer(fee);
        
        emit DeliveryConfirmed();
        emit escrowCompleted(amount);
    }
    
    function refundBuyer() public onlyArbiter inState(State.AWAITING_DELIVERY) {
        currentState = State.REFUNDED;
        payable(buyer).transfer(amount);
        emit escrowRefunded(amount);
    }
    
    function getBalance() public view returns (uint256) {
        return address(this).balance;
    }
    
    function getState() public view returns (string memory) {
        if (currentState == State.AWAITING_PAYMENT) return "AWAITING_PAYMENT";
        if (currentState == State.AWAITING_DELIVERY) return "AWAITING_DELIVERY";
        if (currentState == State.COMPLETED) return "COMPLETED";
        if (currentState == State.REFUNDED) return "REFUNDED";
        return "UNKNOWN";
    }
}

// Decentralized Autonomous Organization (DAO)
contract DAO {
    struct Proposal {
        string description;
        uint256 amount;
        address recipient;
        uint256 votesFor;
        uint256 votesAgainst;
        uint256 deadline;
        bool executed;
        mapping(address => bool) hasVoted;
    }
    
    address public owner;
    uint256 public votingPeriod;
    uint256 public quorum;
    
    mapping(uint256 => Proposal) public proposals;
    mapping(address => uint256) public shares;
    uint256 public totalShares;
    
    uint256 public proposalCount;
    
    event ProposalCreated(uint256 proposalId, string description, uint256 amount);
    event VoteCast(address voter, uint256 proposalId, bool inFavor);
    event ProposalExecuted(uint256 proposalId);
    
    modifier onlyShareholder() {
        require(shares[msg.sender] > 0, "Only shareholders can vote");
        _;
    }
    
    constructor(uint256 _votingPeriod, uint256 _quorum) {
        owner = msg.sender;
        votingPeriod = _votingPeriod;
        quorum = _quorum;
    }
    
    function addShareholder(address _shareholder, uint256 _shares) public {
        require(msg.sender == owner, "Only owner can add shareholders");
        require(_shares > 0, "Shares must be greater than 0");
        
        if (shares[_shareholder] == 0) {
            totalShares += _shares;
        } else {
            totalShares += _shares - shares[_shareholder];
        }
        
        shares[_shareholder] = _shares;
    }
    
    function createProposal(string memory _description, uint256 _amount, address _recipient) public onlyShareholder {
        proposalCount++;
        
        proposals[proposalCount] = Proposal({
            description: _description,
            amount: _amount,
            recipient: _recipient,
            votesFor: 0,
            votesAgainst: 0,
            deadline: block.timestamp + votingPeriod,
            executed: false
        });
        
        emit ProposalCreated(proposalCount, _description, _amount);
    }
    
    function vote(uint256 _proposalId, bool _inFavor) public onlyShareholder {
        Proposal storage proposal = proposals[_proposalId];
        
        require(block.timestamp < proposal.deadline, "Voting period ended");
        require(!proposal.hasVoted[msg.sender], "Already voted");
        require(!proposal.executed, "Proposal already executed");
        
        proposal.hasVoted[msg.sender] = true;
        
        if (_inFavor) {
            proposal.votesFor += shares[msg.sender];
        } else {
            proposal.votesAgainst += shares[msg.sender];
        }
        
        emit VoteCast(msg.sender, _proposalId, _inFavor);
    }
    
    function executeProposal(uint256 _proposalId) public {
        Proposal storage proposal = proposals[_proposalId];
        
        require(block.timestamp >= proposal.deadline, "Voting period not ended");
        require(!proposal.executed, "Proposal already executed");
        
        uint256 totalVotes = proposal.votesFor + proposal.votesAgainst;
        require(totalVotes >= quorum, "Quorum not reached");
        require(proposal.votesFor > proposal.votesAgainst, "Proposal not approved");
        
        proposal.executed = true;
        
        if (address(this).balance >= proposal.amount) {
            payable(proposal.recipient).transfer(proposal.amount);
        }
        
        emit ProposalExecuted(_proposalId);
    }
    
    function deposit() public payable {
        // Allow anyone to deposit funds to the DAO
    }
    
    function getProposal(uint256 _proposalId) public view returns (
        string memory description,
        uint256 amount,
        address recipient,
        uint256 votesFor,
        uint256 votesAgainst,
        uint256 deadline,
        bool executed
    ) {
        Proposal storage proposal = proposals[_proposalId];
        return (
            proposal.description,
            proposal.amount,
            proposal.recipient,
            proposal.votesFor,
            proposal.votesAgainst,
            proposal.deadline,
            proposal.executed
        );
    }
    
    function hasVoted(uint256 _proposalId, address _voter) public view returns (bool) {
        return proposals[_proposalId].hasVoted[_voter];
    }
    
    function getBalance() public view returns (uint256) {
        return address(this).balance;
    }
}

3. Python Blockchain mit Mining

import hashlib
import json
from time import time
from uuid import uuid4
from flask import Flask, jsonify, request
from urllib.parse import urlparse
import requests

class Blockchain:
    def __init__(self):
        self.chain = []
        self.current_transactions = []
        self.nodes = set()
        
        # Create the genesis block
        self.new_block(previous_hash='1', proof=100)
    
    def new_block(self, proof, previous_hash=None):
        """
        Create a new Block in the Blockchain
        :param proof: The proof given by the Proof of Work algorithm
        :param previous_hash: Hash of previous Block
        :return: New Block
        """
        
        block = {
            'index': len(self.chain) + 1,
            'timestamp': time(),
            'transactions': self.current_transactions,
            'proof': proof,
            'previous_hash': previous_hash or self.hash(self.chain[-1]),
        }
        
        # Reset the current list of transactions
        self.current_transactions = []
        
        self.chain.append(block)
        return block
    
    def new_transaction(self, sender, recipient, amount):
        """
        Creates a new transaction to go into the next mined Block
        :param sender: Address of the Sender
        :param recipient: Address of the Recipient
        :param amount: Amount
        :return: The index of the Block that will hold this transaction
        """
        
        self.current_transactions.append({
            'sender': sender,
            'recipient': recipient,
            'amount': amount,
        })
        
        return self.last_block['index'] + 1
    
    @property
    def last_block(self):
        return self.chain[-1]
    
    @staticmethod
    def hash(block):
        """
        Creates a SHA-256 hash of a Block
        :param block: Block
        :return: hash
        """
        
        # We must make sure that the Dictionary is Ordered, or we'll have inconsistent hashes
        block_string = json.dumps(block, sort_keys=True).encode()
        return hashlib.sha256(block_string).hexdigest()
    
    def proof_of_work(self, last_proof):
        """
        Simple Proof of Work Algorithm:
         - Find a number 'p' such that hash(pp') contains leading 4 zeroes
         - Where p is the previous Proof, and p' is the new Proof
        :param last_proof: Previous Proof
        :return: proof
        """
        
        proof = 0
        while self.valid_proof(last_proof, proof) is False:
            proof += 1
        
        return proof
    
    @staticmethod
    def valid_proof(last_proof, proof):
        """
        Validates the Proof: Does hash(last_proof, proof) contain 4 leading zeroes?
        :param last_proof: Previous Proof
        :param proof: Current Proof
        :return: True if correct, False if not.
        """
        
        guess = f'{last_proof}{proof}'.encode()
        guess_hash = hashlib.sha256(guess).hexdigest()
        return guess_hash[:4] == "0000"
    
    def register_node(self, address):
        """
        Add a new node to the list of nodes
        :param address: Address of node. Eg. 'http://192.168.0.1:5000'
        :return: None
        """
        
        parsed_url = urlparse(address)
        if parsed_url.netloc:
            self.nodes.add(parsed_url.netloc)
        elif parsed_url.path:
            # Accepts an URL without scheme like '192.168.0.1:5000'.
            self.nodes.add(parsed_url.path)
        else:
            raise ValueError('Invalid URL')
    
    def valid_chain(self, chain):
        """
        Determine if a given blockchain is valid
        :param chain: A blockchain
        :return: True if valid, False if not
        """
        
        last_block = chain[0]
        current_index = 1
        
        while current_index < len(chain):
            block = chain[current_index]
            print(f'{last_block}')
            print(f'{block}')
            print("\n-----------\n")
            
            # Check that the hash of the block is correct
            if block['previous_hash'] != self.hash(last_block):
                return False
            
            # Check that the Proof of Work is correct
            if not self.valid_proof(last_block['proof'], block['proof']):
                return False
            
            last_block = block
            current_index += 1
        
        return True
    
    def resolve_conflicts(self):
        """
        This is our Consensus Algorithm, it resolves conflicts
        by replacing our chain with the longest one in the network.
        :return: True if our chain was replaced, False if not
        """
        
        neighbours = self.nodes
        new_chain = None
        
        # We're only looking for chains longer than ours
        max_length = len(self.chain)
        
        # Grab and verify the chains from all the nodes in our network
        for node in neighbours:
            response = requests.get(f'http://{node}/chain')
            
            if response.status_code == 200:
                length = response.json()['length']
                chain = response.json()['chain']
                
                # Check if the length is longer and the chain is valid
                if length > max_length and self.valid_chain(chain):
                    max_length = length
                    new_chain = chain
        
        # Replace our chain if we discovered a new, valid chain longer than ours
        if new_chain:
            self.chain = new_chain
            return True
        
        return False

# Flask application
app = Flask(__name__)
node_identifier = str(uuid4()).replace('-', '')

# Instantiate the Blockchain
blockchain = Blockchain()

@app.route('/mine', methods=['GET'])
def mine():
    # We run the proof of work algorithm to get the next proof...
    last_block = blockchain.last_block
    last_proof = last_block['proof']
    proof = blockchain.proof_of_work(last_proof)
    
    # We must receive a reward for finding the proof.
    blockchain.new_transaction(
        sender="0",
        recipient=node_identifier,
        amount=1,
    )
    
    # Forge the new Block by adding it to the chain
    previous_hash = blockchain.hash(last_block)
    block = blockchain.new_block(proof, previous_hash)
    
    response = {
        'message': "New Block Forged",
        'index': block['index'],
        'transactions': block['transactions'],
        'proof': block['proof'],
        'previous_hash': block['previous_hash'],
    }
    return jsonify(response), 200

@app.route('/transactions/new', methods=['POST'])
def new_transaction():
    values = request.get_json()
    
    # Check that the required fields are in the POST'ed data
    required = ['sender', 'recipient', 'amount']
    if not all(k in values for k in required):
        return "Missing values", 400
    
    # Create a new Transaction
    index = blockchain.new_transaction(values['sender'], values['recipient'], values['amount'])
    
    response = {'message': f'Transaction will be added to Block {index}'}
    return jsonify(response), 201

@app.route('/chain', methods=['GET'])
def full_chain():
    response = {
        'chain': blockchain.chain,
        'length': len(blockchain.chain),
    }
    return jsonify(response), 200

@app.route('/nodes/register', methods=['POST'])
def register_nodes():
    values = request.get_json()
    
    nodes = values.get('nodes')
    if nodes is None:
        return "Error: Please supply a valid list of nodes", 400
    
    for node in nodes:
        blockchain.register_node(node)
    
    response = {
        'message': 'New nodes have been added',
        'total_nodes': list(blockchain.nodes),
    }
    return jsonify(response), 201

@app.route('/nodes/resolve', methods=['GET'])
def consensus():
    replaced = blockchain.resolve_conflicts()
    
    if replaced:
        response = {
            'message': 'Our chain was replaced',
            'new_chain': blockchain.chain
        }
    else:
        response = {
            'message': 'Our chain is authoritative',
            'chain': blockchain.chain
        }
    
    return jsonify(response), 200

if __name__ == '__main__':
    app.run(host='0.0.0.0', port=5000)

# Cryptographic utilities
import base64
from cryptography.hazmat.primitives import hashes
from cryptography.hazmat.primitives.asymmetric import rsa, padding
from cryptography.hazmat.primitives import serialization
from cryptography.hazmat.backends import default_backend

class CryptoUtils:
    @staticmethod
    def generate_key_pair():
        """Generate RSA key pair for digital signatures"""
        private_key = rsa.generate_private_key(
            public_exponent=65537,
            key_size=2048,
            backend=default_backend()
        )
        
        public_key = private_key.public_key()
        
        return private_key, public_key
    
    @staticmethod
    def sign_message(private_key, message):
        """Sign a message with private key"""
        signature = private_key.sign(
            message.encode('utf-8'),
            padding.PSS(
                mgf=padding.MGF1(hashes.SHA256()),
                salt_length=padding.PSS.MAX_LENGTH
            ),
            hashes.SHA256()
        )
        
        return base64.b64encode(signature).decode('utf-8')
    
    @staticmethod
    def verify_signature(public_key, message, signature):
        """Verify a signature with public key"""
        try:
            public_key.verify(
                base64.b64decode(signature),
                message.encode('utf-8'),
                padding.PSS(
                    mgf=padding.MGF1(hashes.SHA256()),
                    salt_length=padding.PSS.MAX_LENGTH
                ),
                hashes.SHA256()
            )
            return True
        except:
            return False
    
    @staticmethod
    def serialize_public_key(public_key):
        """Serialize public key to PEM format"""
        return public_key.public_bytes(
            encoding=serialization.Encoding.PEM,
            format=serialization.PublicFormat.SubjectPublicKeyInfo
        ).decode('utf-8')
    
    @staticmethod
    def deserialize_public_key(pem_data):
        """Deserialize public key from PEM format"""
        return serialization.load_pem_public_key(
            pem_data.encode('utf-8'),
            backend=default_backend()
        )

# Wallet implementation
class Wallet:
    def __init__(self):
        self.private_key, self.public_key = CryptoUtils.generate_key_pair()
        self.address = self.generate_address()
    
    def generate_address(self):
        """Generate wallet address from public key"""
        public_key_pem = CryptoUtils.serialize_public_key(self.public_key)
        address = hashlib.sha256(public_key_pem.encode('utf-8')).hexdigest()
        return address[:40]  # Use first 40 characters as address
    
    def sign_transaction(self, transaction_data):
        """Sign transaction data"""
        transaction_string = json.dumps(transaction_data, sort_keys=True)
        return CryptoUtils.sign_message(self.private_key, transaction_string)
    
    def get_address(self):
        """Get wallet address"""
        return self.address
    
    def get_public_key(self):
        """Get public key in PEM format"""
        return CryptoUtils.serialize_public_key(self.public_key)

# Usage example
if __name__ == "__main__":
    # Create wallets
    alice_wallet = Wallet()
    bob_wallet = Wallet()
    
    print(f"Alice's address: {alice_wallet.get_address()}")
    print(f"Bob's address: {bob_wallet.get_address()}")
    
    # Create transaction
    transaction = {
        'sender': alice_wallet.get_address(),
        'recipient': bob_wallet.get_address(),
        'amount': 10,
        'timestamp': time()
    }
    
    # Sign transaction
    signature = alice_wallet.sign_transaction(transaction)
    print(f"Transaction signature: {signature}")
    
    # Verify signature
    alice_public_key = CryptoUtils.deserialize_public_key(alice_wallet.get_public_key())
    transaction_string = json.dumps(transaction, sort_keys=True)
    is_valid = CryptoUtils.verify_signature(alice_public_key, transaction_string, signature)
    print(f"Signature valid: {is_valid}")

Blockchain Architektur

Schichtenmodell

graph TD
    A[Application Layer] --> B[Smart Contracts]
    B --> C[Virtual Machine]
    C --> D[Consensus Layer]
    D --> E[Network Layer]
    E --> F[Data Layer]
    
    A1[DApps] --> A
    A2[Wallets] --> A
    A3[Exchanges] --> A
    
    B1[Ethereum] --> B
    B2[Solidity] --> B
    B3[Gas Fees] --> B
    
    C1[EVM] --> C
    C2[WASM] --> C
    C3[Bytecode] --> C
    
    D1[PoW] --> D
    D2[PoS] --> D
    D3[DPoS] --> D
    
    E1[P2P] --> E
    E2[Gossip] --> E
    E3[RPC] --> E
    
    F1[Blocks] --> F
    F2[Merkle Trees] --> F
    F3[Hash Chains] --> F

Konsens-Algorithmen

Proof of Work (PoW)

EigenschaftBeschreibungEnergieverbrauch
SicherheitHoch durch kryptographische BeweiseSehr Hoch
ZentralisierungTendenz zur ZentralisierungHoch
SkalierbarkeitBegrenzt durch BlockzeitNiedrig
AnwendungBitcoin, Ethereum (früher)Mining

Proof of Stake (PoS)

EigenschaftBeschreibungEnergieverbrauch
SicherheitWirtschaftliche AnreizeGering
ZentralisierungWeniger zentralisiertMittel
SkalierbarkeitBesser als PoWHoch
AnwendungEthereum 2.0, CardanoStaking

Kryptographische Grundlagen

Hash-Funktionen

# SHA-256 Implementation
import hashlib

def sha256_hash(data):
    """Calculate SHA-256 hash of data"""
    return hashlib.sha256(data.encode()).hexdigest()

# Merkle Tree Implementation
class MerkleTree:
    def __init__(self, transactions):
        self.transactions = transactions
        self.tree = self.build_tree()
    
    def build_tree(self):
        """Build Merkle tree from transactions"""
        tree = [transactions]
        
        while len(tree[-1]) > 1:
            current_level = tree[-1]
            next_level = []
            
            for i in range(0, len(current_level), 2):
                if i + 1 < len(current_level):
                    combined = current_level[i] + current_level[i + 1]
                    next_level.append(sha256_hash(combined))
                else:
                    next_level.append(current_level[i])
            
            tree.append(next_level)
        
        return tree
    
    def get_root(self):
        """Get Merkle root"""
        return self.tree[-1][0] if self.tree else None
    
    def verify_proof(self, transaction_hash, proof, root):
        """Verify Merkle proof"""
        current_hash = transaction_hash
        
        for proof_element in proof:
            if current_hash < proof_element:
                combined = current_hash + proof_element
            else:
                combined = proof_element + current_hash
            
            current_hash = sha256_hash(combined)
        
        return current_hash == root

Digitale Signaturen

# ECDSA Implementation
from ecdsa import SigningKey, VerifyingKey, NIST256p, SECP256k1

class DigitalSignature:
    def __init__(self):
        self.private_key = SigningKey.generate(SECP256k1)
        self.public_key = self.private_key.get_verifying_key()
    
    def sign_message(self, message):
        """Sign message with private key"""
        return self.private_key.sign(message.encode())
    
    def verify_signature(self, message, signature):
        """Verify signature with public key"""
        try:
            self.public_key.verify(signature, message.encode())
            return True
        except:
            return False
    
    def get_public_key_hex(self):
        """Get public key in hex format"""
        return self.public_key.to_string().hex()
    
    @staticmethod
    def from_public_key_hex(public_key_hex):
        """Create verifier from public key hex"""
        public_key = VerifyingKey.from_string(bytes.fromhex(public_key_hex), curve=SECP256k1)
        return DigitalSignature.from_public_key(public_key)

Smart Contract Entwicklung

Ethereum Virtual Machine (EVM)

KomponenteBeschreibungFunktion
BytecodeKompilierter Smart ContractAusführung
GasTransaktionskostenRessourcenlimit
StoragePersistenter SpeicherDatenhaltung
MemoryTemporärer SpeicherBerechnungen
StackAusführungsstackOperationen

Solidity Best Practices

// Secure contract example
pragma solidity ^0.8.0;

contract SecureContract {
    // Use latest Solidity version
    // Use explicit visibility specifiers
    // Implement proper access control
    // Handle reentrancy attacks
    // Use safe math operations
    
    address private owner;
    mapping(address => uint256) private balances;
    bool private locked;
    
    modifier onlyOwner() {
        require(msg.sender == owner, "Only owner can call this function");
        _;
    }
    
    modifier noReentrant() {
        require(!locked, "No reentrancy");
        locked = true;
        _;
        locked = false;
    }
    
    modifier safeTransfer(address to, uint256 amount) {
        require(to != address(0), "Invalid address");
        require(amount > 0, "Amount must be greater than 0");
        require(balances[msg.sender] >= amount, "Insufficient balance");
        _;
    }
    
    constructor() {
        owner = msg.sender;
    }
    
    function transfer(address to, uint256 amount) 
        public 
        safeTransfer(to, amount) 
        noReentrant 
        returns (bool) 
    {
        balances[msg.sender] -= amount;
        balances[to] += amount;
        return true;
    }
    
    function getBalance(address account) public view returns (uint256) {
        return balances[account];
    }
}

Dezentrale Anwendungen (DApps)

Web3.js Integration

// Web3.js for blockchain interaction
const Web3 = require('web3');
const web3 = new Web3('https://mainnet.infura.io/v3/YOUR_PROJECT_ID');

// Contract ABI and address
const contractABI = [...]; // Contract ABI
const contractAddress = '0x...'; // Contract address

// Create contract instance
const contract = new web3.eth.Contract(contractABI, contractAddress);

// Get account balance
async function getBalance(address) {
    const balance = await web3.eth.getBalance(address);
    return web3.utils.fromWei(balance, 'ether');
}

// Send transaction
async function sendTransaction(from, to, amount, privateKey) {
    const nonce = await web3.eth.getTransactionCount(from);
    const gasPrice = await web3.eth.getGasPrice();
    
    const tx = {
        from: from,
        to: to,
        value: web3.utils.toWei(amount, 'ether'),
        gas: 21000,
        gasPrice: gasPrice,
        nonce: nonce
    };
    
    const signedTx = await web3.eth.accounts.signTransaction(tx, privateKey);
    const receipt = await web3.eth.sendSignedTransaction(signedTx.rawTransaction);
    
    return receipt;
}

// Interact with smart contract
async function callContract(method, ...args) {
    const result = await contract.methods[method](...args).call();
    return result;
}

async function sendContractTransaction(method, from, privateKey, ...args) {
    const nonce = await web3.eth.getTransactionCount(from);
    const gasPrice = await web3.eth.getGasPrice();
    
    const tx = contract.methods[method](...args);
    const gas = await tx.estimateGas({ from: from });
    
    const txData = {
        from: from,
        to: contractAddress,
        gas: gas,
        gasPrice: gasPrice,
        nonce: nonce,
        data: tx.encodeABI()
    };
    
    const signedTx = await web3.eth.accounts.signTransaction(txData, privateKey);
    const receipt = await web3.eth.sendSignedTransaction(signedTx.rawTransaction);
    
    return receipt;
}

Kryptowährungs-Typen

Kategorien

TypBeschreibungBeispieleUse Cases
Payment CoinsDigitales GeldBitcoin, LitecoinZahlungen
Platform CoinsSmart Contract PlattformenEthereum, SolanaDApps
Privacy CoinsAnonyme TransaktionenMonero, ZcashDatenschutz
StablecoinsPreisstabile TokenUSDC, DAIStabilität
Utility TokensPlattform-NutzungBNB, LINKServices
Security TokensRegulierte WertpapiereSTOsInvestment

Mining und Validierung

Mining Prozess

# Mining simulation
import hashlib
import json
import time

class Miner:
    def __init__(self, blockchain):
        self.blockchain = blockchain
        self.mining_reward = 10
    
    def mine_block(self, transactions):
        """Mine a new block"""
        last_block = self.blockchain.get_last_block()
        proof = self.proof_of_work(last_block.proof)
        
        # Create reward transaction
        reward_tx = {
            'sender': '0',
            'recipient': 'miner_address',
            'amount': self.mining_reward
        }
        
        transactions.append(reward_tx)
        
        # Create new block
        new_block = {
            'index': last_block.index + 1,
            'timestamp': time.time(),
            'transactions': transactions,
            'proof': proof,
            'previous_hash': self.hash_block(last_block)
        }
        
        # Add block to blockchain
        self.blockchain.add_block(new_block)
        
        return new_block
    
    def proof_of_work(self, last_proof):
        """Proof of Work algorithm"""
        proof = 0
        difficulty = 4  # Number of leading zeros
        
        while not self.valid_proof(last_proof, proof, difficulty):
            proof += 1
        
        return proof
    
    @staticmethod
    def valid_proof(last_proof, proof, difficulty):
        """Validate proof"""
        guess = f'{last_proof}{proof}'.encode()
        guess_hash = hashlib.sha256(guess).hexdigest()
        return guess_hash[:difficulty] == '0' * difficulty
    
    @staticmethod
    def hash_block(block):
        """Hash a block"""
        block_string = json.dumps(block, sort_keys=True).encode()
        return hashlib.sha256(block_string).hexdigest()

Wallet Management

Hierarchical Deterministic Wallets

# HD Wallet implementation
import hmac
import hashlib
from bip_utils import Bip39MnemonicValidator, Bip39SeedGenerator, Bip44, Bip44Coins, Bip44Changes

class HDWallet:
    def __init__(self, mnemonic=None):
        if mnemonic is None:
            # Generate new mnemonic
            self.mnemonic = self.generate_mnemonic()
        else:
            # Validate existing mnemonic
            if not Bip39MnemonicValidator().Validate(mnemonic):
                raise ValueError("Invalid mnemonic phrase")
            self.mnemonic = mnemonic
        
        # Generate seed from mnemonic
        self.seed_bytes = Bip39SeedGenerator(self.mnemonic).Generate()
        
        # Create master key
        self.master_key = Bip44.FromSeed(self.seed_bytes, Bip44Coins.BITCOIN)
    
    def generate_mnemonic(self, wordlist='english', strength=128):
        """Generate new mnemonic phrase"""
        return Bip39MnemonicValidator().Generate(strength, wordlist)
    
    def get_address(self, account=0, change=0, address_index=0):
        """Generate address from HD path"""
        # Derive key from HD path: m/44'/0'/0'/0/0
        bip44_obj = self.master_key.Purpose().Coin().Account(account).Change(change).AddressIndex(address_index)
        return bip44_obj.Address()
    
    def get_private_key(self, account=0, change=0, address_index=0):
        """Get private key from HD path"""
        bip44_obj = self.master_key.Purpose().Coin().Account(account).Change(change).AddressIndex(address_index)
        return bip44_obj.PrivateKey().Raw().ToHex()
    
    def get_public_key(self, account=0, change=0, address_index=0):
        """Get public key from HD path"""
        bip44_obj = self.master_key.Purpose().Coin().Account(account).Change(change).AddressIndex(address_index)
        return bip44_obj.PublicKey().RawCompressed().ToHex()
    
    def get_extended_public_key(self, account=0):
        """Get extended public key for account"""
        return self.master_key.Purpose().Coin().Account(account).Public()
    
    def get_extended_private_key(self, account=0):
        """Get extended private key for account"""
        return self.master_key.Purpose().Coin().Account(account).Private()

Vorteile und Nachteile

Vorteile von Blockchain

  • Dezentralisierung: Keine zentrale Kontrollinstanz
  • Unveränderlichkeit: Daten können nicht nachträglich geändert werden
  • Transparenz: Alle Transaktionen sind öffentlich einsehbar
  • Sicherheit: Kryptographische Sicherheit
  • Effizienz: Eliminierung von Intermediären

Nachteile

  • Skalierbarkeit: Begrenzte Transaktionsdurchsatz
  • Energieverbrauch: Hoher Energieverbrauch bei PoW
  • Komplexität: Technische Komplexität
  • Regulierung: Unsicherheit bei rechtlicher Behandlung
  • Volatilität: Starke Preisschwankungen

Häufige Prüfungsfragen

  1. Was ist der Unterschied zwischen Proof of Work und Proof of Stake? PoW verwendet rechenintensive Aufgaben zur Block-Erstellung, PoS verwendet wirtschaftliche Anreize durch Staking von Coins.

  2. Erklären Sie die Funktion von Smart Contracts! Smart Contracts sind selbstausführende Verträge, die auf der Blockchain laufen und automatisch Vertragsbedingungen durch Code umsetzen.

  3. Wie funktioniert kryptographische Hashing in Blockchain? Jeder Block enthält den Hash des vorherigen Blocks, was eine unveränderliche Kette erstellt. Änderungen würden alle nachfolgenden Hashes ungültig machen.

  4. Was ist der Zweck von Mining? Mining sichert das Netzwerk durch Proof of Work, validiert Transaktionen und erstellt neue Blöcke mit Belohnungen.

Wichtigste Quellen

  1. https://bitcoin.org/
  2. https://ethereum.org/
  3. https://solidity.readthedocs.io/
  4. https://web3js.readthedocs.io/
Zurück zum Blog
Share:

Ähnliche Beiträge