0% found this document useful (0 votes)
51 views4 pages

Code Source Java

The document describes code for implementing a basic blockchain with cryptocurrency functionality in Java. It includes classes for wallets, transactions, blocks, and the overall blockchain data structure. Key points include: - The Wallet class stores a public/private key pair to manage funds and allow signing of transactions. - Transactions contain inputs (referencing previous transaction outputs), outputs, and a signature and transfer funds between wallets. - Blocks contain a list of transactions, hash/nonce fields for proof of work mining, and methods for adding/verifying transactions. - The Blockchain class manages the full chain of blocks and unspent transaction outputs (UTXOs).

Uploaded by

mohsen gharbi
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
51 views4 pages

Code Source Java

The document describes code for implementing a basic blockchain with cryptocurrency functionality in Java. It includes classes for wallets, transactions, blocks, and the overall blockchain data structure. Key points include: - The Wallet class stores a public/private key pair to manage funds and allow signing of transactions. - Transactions contain inputs (referencing previous transaction outputs), outputs, and a signature and transfer funds between wallets. - Blocks contain a list of transactions, hash/nonce fields for proof of work mining, and methods for adding/verifying transactions. - The Blockchain class manages the full chain of blocks and unspent transaction outputs (UTXOs).

Uploaded by

mohsen gharbi
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 4

import java.security.PrivateKey;import java.security.

PublicKey;public class Wallet { public PrivateKey


privateKey; public PublicKey publicKey;
}

public void generateKeyPair() { try { KeyPairGenerator keyGen =


KeyPairGenerator.getInstance("ECDSA", "BC"); SecureRandom random =
SecureRandom.getInstance("SHA1PRNG"); ECGenParameterSpec ecSpec = new
ECGenParameterSpec("prime192v1"); keyGen.initialize(ecSpec, random); KeyPair keyPair =
keyGen.generateKeyPair(); // on récupère les clés générées pour notre Wallet privateKey =
keyPair.getPrivate(); publicKey = keyPair.getPublic(); } catch (Exception e) { throw new
RuntimeException(e); }
}

import java.security.PrivateKey;import java.security.PublicKey;import java.util.ArrayList;public class


Transaction { public String transactionId; public PublicKey sender; public PublicKey recipient;
public float value; public byte[] signature; public ArrayList<TransactionInput> inputs = new
ArrayList<TransactionInput>(); public ArrayList<TransactionOutput> outputs = new
ArrayList<TransactionOutput>(); // Nombre de transactions générées private static int sequence = 0;
public Transaction(PublicKey from, PublicKey to, float value, ArrayList<TransactionInput> inputs) {
this.sender = from; this.recipient = to; this.value = value; this.inputs = inputs; } // ...
}

import java.security.PrivateKey;import java.security.PublicKey;import java.security.Signature;public


class Utils { // Application d'une signature avec les courbes elliptiques (ECDSA) public static byte[]
applyECDSASig(PrivateKey privateKey, String input) { Signature dsa; byte[] output = new byte[0];
try { dsa = Signature.getInstance("ECDSA", "BC"); dsa.initSign(privateKey); byte[] strByte =
input.getBytes(); dsa.update(strByte); byte[] realSig = dsa.sign(); output = realSig; } catch
(Exception e) { throw new RuntimeException(e); } return output; } // Vérification de la signature
pour les données d'entrée public static boolean verifyECDSASig(PublicKey publicKey, String data,
byte[] signature) { try { Signature ecdsaVerify = Signature.getInstance("ECDSA", "BC");
ecdsaVerify.initVerify(publicKey); ecdsaVerify.update(data.getBytes()); return
ecdsaVerify.verify(signature); } catch (Exception e) { throw new RuntimeException(e); } } // ...
}

public class Transaction { // ... private String calculateHash() { sequence++; return


Utils.applySha256(Utils.getStringFromKey(sender) + Utils.getStringFromKey(recipient) +
Float.toString(value) + sequence); } public void generateSignature(PrivateKey privateKey) {
String data = Utils.getStringFromKey(sender) + Utils.getStringFromKey(recipient)
+ Float.toString(value); signature = Utils.applyECDSASig(privateKey, data); } public
boolean verifiySignature() { String data = Utils.getStringFromKey(sender) +
Utils.getStringFromKey(recipient) + Float.toString(value); return
Utils.verifyECDSASig(sender, data, signature); } // ...
}

public class TransactionInput { public String transactionOutputId; public TransactionOutput UTXO;


public TransactionInput(String transactionOutputId) { this.transactionOutputId = transactionOutputId;
}
}

import java.security.PublicKey;public class TransactionOutput { public String id; public PublicKey


recipient; public float value; public String parentTransactionId; public TransactionOutput(PublicKey
recipient, float value, String parentTransactionId) { this.recipient = recipient; this.value = value;
this.parentTransactionId = parentTransactionId; this.id =
Utils.applySha256(Utils.getStringFromKey(recipient) + Float.toString(value) +
parentTransactionId); } public boolean isMine(PublicKey publicKey) { return (publicKey ==
recipient); }
}

public class Transaction { // ... public boolean processTransaction() { if (verifiySignature() == false) {


System.out.println("Echec de vérification de la signature de la Transaction"); return false; } // On
associe les données des transactions entrantes for (TransactionInput i : inputs) { i.UTXO =
Blockchain.UTXOs.get(i.transactionOutputId); } // On vérifie que la transaction est valide if
(getInputsValue() < Blockchain.minimumTransaction) { System.out.println("Somme montant des
transactions entrantes trop faible : " + getInputsValue()); System.out.println("Le montant doit être
plus grand que : " + Blockchain.minimumTransaction); return false; } // Génération des
transactions sortantes // Calcul montant restant float leftOver = getInputsValue() - value;
transactionId = calulateHash(); // prise en compte envoi du montant au destinataire outputs.add(new
TransactionOutput(this.recipient, value, transactionId)); // prise en compte montant restant pour
l'expéditeur outputs.add(new TransactionOutput(this.sender, leftOver, transactionId)); // Ajout aux
transactions non dépensées de la Blockchain for (TransactionOutput o : outputs) {
Blockchain.UTXOs.put(o.id, o); } // Suppression de ces transactions de la liste UTXOs de la
Blockchain for (TransactionInput i : inputs) { if (i.UTXO == null) continue;
Blockchain.UTXOs.remove(i.UTXO.id); } return true; } public float getInputsValue() { float total =
0; for (TransactionInput i : inputs) { if (i.UTXO == null) continue; total += i.UTXO.value;
} return total; } // ...
}
public class Wallet { // ... // Retourne le montant disponible dans le Wallet public float getBalance() {
float total = 0; for (Map.Entry<String, TransactionOutput> item : Blockchain.UTXOs.entrySet()) {
TransactionOutput UTXO = item.getValue(); if (UTXO.isMine(publicKey)) { // on ajoute
uniquement le montant des transactions appartenant à ce wallet UTXOs.put(UTXO.id, UTXO);
total += UTXO.value; } } return total; } public Transaction sendFunds(PublicKey recipient, float
value) { if (getBalance() < value) { System.out.println("Manque de fonds pour créer la
transaction"); return null; } ArrayList<TransactionInput> inputs = new
ArrayList<TransactionInput>(); float total = 0; for (Map.Entry<String, TransactionOutput> item :
UTXOs.entrySet()) { TransactionOutput UTXO = item.getValue(); total += UTXO.value;
inputs.add(new TransactionInput(UTXO.id)); if (total > value) break; } Transaction
newTransaction = new Transaction(publicKey, recipient, value, inputs);
newTransaction.generateSignature(privateKey); for (TransactionInput input : inputs) {
UTXOs.remove(input.transactionOutputId); } return newTransaction; }
}

public static String getMerkleRoot(ArrayList<Transaction> transactions) { int count =


transactions.size(); ArrayList<String> previousTreeLayer = new ArrayList<String>(); for (Transaction
transaction : transactions) { previousTreeLayer.add(transaction.transactionId); } ArrayList<String>
treeLayer = previousTreeLayer; while (count > 1) { treeLayer = new ArrayList<String>(); for (int i
= 1; i < previousTreeLayer.size(); i++) { treeLayer.add(applySha256(previousTreeLayer.get(i - 1) +
previousTreeLayer.get(i))); } count = treeLayer.size(); previousTreeLayer = treeLayer; } String
merkleRoot = (treeLayer.size() == 1) ? treeLayer.get(0) : ""; return merkleRoot;
}

public class Block { // ... public ArrayList<Transaction> transactions = new ArrayList<Transaction>();


// ... public void mineBlock(int difficulty) { String merkleRoot = Utils.getMerkleRoot(transactions);
data = (!"".equals(merkleRoot)) ? merkleRoot : data; nonce = 0; while (!getHash().substring(0,
difficulty).equals(Utils.zeros(difficulty))) { nonce++; hash = Block.calculateHash(this); } }
public boolean addTransaction(Transaction transaction) { if (transaction == null) return false; if
(previousHash != null) { if (!transaction.processTransaction()) { System.out.println("Transaction
non valide. Ajout annulé"); return false; } } transactions.add(transaction);
System.out.println("Transaction ajoutée avec succès au bloc"); return true; }
}

import java.security.Security;import java.util.ArrayList;import java.util.HashMap;import


java.util.List;public class Blockchain { public static float minimumTransaction = 0.1f; private int
difficulty; private List<Block> blocks;
public static HashMap<String, TransactionOutput> UTXOs = new HashMap<String,
TransactionOutput>();
public Wallet walletA; public Wallet walletB; public Transaction genesisTransaction; public
Blockchain(int difficulty) { Security.addProvider(new
org.bouncycastle.jce.provider.BouncyCastleProvider()); // Création des Wallets walletA = new
Wallet(); walletB = new Wallet(); Wallet baseWallet = new Wallet(); // Transaction genèse
genesisTransaction = new Transaction(baseWallet.publicKey, walletA.publicKey, 100f, null); //
Signature de de la transaction genesisTransaction.generateSignature(baseWallet.privateKey);
genesisTransaction.transactionId = "0";
genesisTransaction.outputs.add(new TransactionOutput(genesisTransaction.recipient,
genesisTransaction.value, genesisTransaction.transactionId));
// Ajout à la liste UTXOs des transactions non dépensées
UTXOs.put(genesisTransaction.outputs.get(0).id, genesisTransaction.outputs.get(0)); this.difficulty =
difficulty; blocks = new ArrayList<>(); // Création du bloc genèse Block b = new Block(0,
System.currentTimeMillis(), null, "Genesis Block"); b.transactions.add(genesisTransaction);
b.mineBlock(difficulty); // Ajout du Bloc addBlock(b); } // ...
}

public static void main(String[] args) { Blockchain blockchain = new Blockchain(4);


System.out.println("\nWallet A montant : " + blockchain.walletA.getBalance());
System.out.println("Wallet A essaie d'envoyer 40 au Wallet B ..."); Block b =
blockchain.newBlock("Block 2");
b.addTransaction(blockchain.walletA.sendFunds(blockchain.walletB.publicKey, 40f));
blockchain.addBlock(b); System.out.println("Wallet A montant : " + blockchain.walletA.getBalance());
System.out.println("Wallet B montant : " + blockchain.walletB.getBalance());
System.out.println("\nWallet A essaie d'envoyer plus (100) que ce qu'il possède ..."); b =
blockchain.newBlock("Block 3");
b.addTransaction(blockchain.walletA.sendFunds(blockchain.walletB.publicKey, 1000f));
blockchain.addBlock(b); System.out.println("Wallet A montant : " + blockchain.walletA.getBalance());
System.out.println("Wallet B montant : " + blockchain.walletB.getBalance());
System.out.println("\nWallet B essaie d'envoyer 20 au Wallet A ..."); System.out.println("Wallet A essaie
d'envoyer 10 au Wallet B ..."); b = blockchain.newBlock("Block 4");
b.addTransaction(blockchain.walletB.sendFunds(blockchain.walletA.publicKey, 20f));
b.addTransaction(blockchain.walletA.sendFunds(blockchain.walletB.publicKey, 10f));
blockchain.addBlock(b); System.out.println("Wallet A montant : " + blockchain.walletA.getBalance());
System.out.println("Wallet B montant : " + blockchain.walletB.getBalance()); System.out.println();
System.out.println(blockchain); System.out.println("Blockchain valide : " +
(blockchain.isBlockChainValid() ? "Oui" : "Non"));
}

You might also like