-
Notifications
You must be signed in to change notification settings - Fork 0
/
block4.py
145 lines (110 loc) · 3.88 KB
/
block4.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
"""
blockchain with tokens and coinbase by Vincent LIU and Samir SAYAH - MAIN - Polytech Sorbonne
Inspired by: https://anders.com/blockchain/public-private-keys/blockchain.html
Usage: python block4.py
Or: mpirun -n 4 python block4.py
"""
from hash import sha256
from block1 import Block, difficulty, pattern
from block2 import Block_v2
from blockchain import Blockchain
from mpi4py import MPI
from signature import generate_keys, sign_message, verify_message, encrypt, key_to_string
from Crypto.PublicKey import RSA
from Crypto import Random
from Crypto.Cipher import PKCS1_OAEP
from Crypto.Hash import SHA256
import sys
import numpy
class Tx(object):
def __init__(self, amount, sender_public_key, recipient_public_key, sender_private_key):
self.amount = amount
self.sender = sender_public_key
self.recipient = recipient_public_key
self.sign, _ = sign_message(str(amount) + key_to_string(sender_public_key) + key_to_string(recipient_public_key), sender_private_key)
@property
def valid(self):
plaintext = str(self.amount) + key_to_string(self.sender) + key_to_string(self.recipient)
Hash = SHA256.new(plaintext.encode()).digest()
return verify_message(self.sign, Hash, self.sender)
def to_string(self):
return str(self.amount) + key_to_string(self.sender) + key_to_string(self.recipient) + str(self.sign)
@property
def sender_str(self):
return key_to_string(self.sender)
@property
def recipient_str(self):
return key_to_string(self.recipient)
class Person(object):
def __init__(self, name):
self.name = name
self.public_key, self.private_key = generate_keys()
@property
def pubkey(self):
return key_to_string(self.public_key)
@property
def privkey(self):
return key_to_string(self.private_key)
class Block_v4(Block_v2):
def __init__(self, block = 0, nonce = 0, data = "", coinbase = None, tx = []):
Block_v2.__init__(self, block, nonce, data)
self.coinbase = coinbase
self.tx = tx
@property
def hash(self):
s = self.coinbase["amount"] + self.coinbase["recipient"] if self.coinbase else ""
for t in self.tx:
s += t.to_string()
if self.previous:
s += self.previous.hash
else:
s += "0" * 64
return sha256(str(self.block) + str(self.nonce) + s )
def text_hash(self, i):
s = self.coinbase["amount"] + self.coinbase["recipient"] if self.coinbase else ""
for t in self.tx:
s += t.to_string()
if self.previous:
s += self.previous.hash
else:
s += "0" * 64
return sha256(str(self.block) + str(i) + s)
def show(self):
# Your result
print("\n=================")
print("=== Block =======")
print("=================\n")
print("Block: #{}".format(self.block))
print("Nonce: {}".format(self.nonce))
if self.coinbase:
print("Coinbase: ${} -> {}".format(self.coinbase["amount"], self.coinbase["recipient"]))
print("\n")
for t in self.tx:
print("$ {} From: {} ---------------------------> {} (Valid : {})\n".format(t.amount, t.recipient_str, t.sender_str,t.valid) )
if self.previous:
print("Previous: {}\n".format(self.previous.hash))
else:
print("Previous: " + "0"*64)
print("Hash: {}\n".format(self.hash))
print("Valid: {}\n".format(self.valid))
## Unit test
if __name__ == "__main__":
# Initialize MPI
comm = MPI.COMM_WORLD
size = comm.Get_size() # Returns the number of tasks in comm
rank = comm.Get_rank() # Returns the rank of the calling task
P1 = Person("Vincent")
P2 = Person("Samir")
bchain = Blockchain()
Coinbase = {"amount": "100.00", "recipient": P1.pubkey}
T = []
bchain.add( Block_v4(block = "1", nonce = "29082", coinbase = Coinbase, tx = T) )
Coinbase = {"amount": "100.00", "recipient": P1.pubkey}
T = [Tx("100", P1.public_key, P2.public_key, P1.private_key)]
bchain.add( Block_v4(block = "2", nonce = "16651", coinbase = Coinbase, tx = T) )
if rank == 0:
bchain.show()
bchain.mine()
if rank == 0:
print("We mine, and get the NEW nonce for every blocks")
bchain.show()