From 18e367f6473c60d4960afca79e72b24eae5166f4 Mon Sep 17 00:00:00 2001 From: anurags10 Date: Thu, 3 Oct 2024 09:42:04 +0000 Subject: [PATCH 01/11] updating DIRECTORY.md --- DIRECTORY.md | 1 + 1 file changed, 1 insertion(+) diff --git a/DIRECTORY.md b/DIRECTORY.md index cdbbac684..900bd64d5 100644 --- a/DIRECTORY.md +++ b/DIRECTORY.md @@ -22,6 +22,7 @@ * [Rat In Maze](backtracking/rat_in_maze.py) * [Sudoku](backtracking/sudoku.py) * [Sum Of Subsets](backtracking/sum_of_subsets.py) + * [Word Break](backtracking/word_break.py) * [Word Ladder](backtracking/word_ladder.py) * [Word Search](backtracking/word_search.py) From 37549d5700b92774cc8eb073eaaadf7d0031f02e Mon Sep 17 00:00:00 2001 From: Anurag Singh <54910091+anurags10@users.noreply.github.com> Date: Thu, 3 Oct 2024 15:14:06 +0530 Subject: [PATCH 02/11] Create PoWAlgorithm.py --- blockchain/PoWAlgorithm.py | 129 +++++++++++++++++++++++++++++++++++++ 1 file changed, 129 insertions(+) create mode 100644 blockchain/PoWAlgorithm.py diff --git a/blockchain/PoWAlgorithm.py b/blockchain/PoWAlgorithm.py new file mode 100644 index 000000000..99b74876d --- /dev/null +++ b/blockchain/PoWAlgorithm.py @@ -0,0 +1,129 @@ +""" +# Title: Proof of Work Algorithm for Blockchain + +## Algorithm Statement: +The algorithm implements the Proof of Work (PoW) consensus mechanism used in blockchain to validate blocks. PoW is used to ensure that participants (miners) must perform a computational task to create a valid block and add it to the blockchain. The difficulty of the task is defined by the number of leading zeros required in the hash of the block. + +## Approach: +1. Each block contains a list of transactions, a previous block's hash, a timestamp, and a nonce (random value). +2. The block is hashed using the SHA-256 cryptographic hash function. +3. The miner's goal is to find a nonce such that the resulting hash has a certain number of leading zeros, which defines the difficulty level. +4. The difficulty is adjustable. The more leading zeros required, the harder it is to find a valid nonce. +5. This process is repeated until a valid hash is found, which demonstrates that computational work has been done (Proof of Work). + +## Steps: +1. Create a `Block` class to hold block details (transactions, previous hash, timestamp, and nonce). +2. Implement a `Blockchain` class that adds new blocks to the chain by solving the PoW problem. +3. Implement the hashing function using SHA-256. +4. Adjust the difficulty by varying the number of leading zeros required in the hash. +5. Use test cases to validate the PoW algorithm. +""" + +import hashlib +import time + +class Block: + def __init__(self, index, previous_hash, transactions, timestamp, difficulty): + self.index = index + self.previous_hash = previous_hash + self.transactions = transactions + self.timestamp = timestamp + self.nonce = 0 # Start with nonce 0 + self.difficulty = difficulty + self.hash = self.compute_hash() + + def compute_hash(self): + """ + Generates the hash of the block content. + Combines index, previous hash, transactions, timestamp, and nonce into a string, + which is then hashed using SHA-256. + """ + block_string = f"{self.index}{self.previous_hash}{self.transactions}{self.timestamp}{self.nonce}" + return hashlib.sha256(block_string.encode()).hexdigest() + + def mine_block(self): + """ + Performs Proof of Work by adjusting the nonce until a valid hash is found. + A valid hash has the required number of leading zeros based on the difficulty level. + """ + target = '0' * self.difficulty # Target hash should start with 'difficulty' number of zeros + while self.hash[:self.difficulty] != target: + self.nonce += 1 + self.hash = self.compute_hash() + + print(f"Block mined with nonce {self.nonce}, hash: {self.hash}") + +class Blockchain: + def __init__(self, difficulty): + self.chain = [] + self.difficulty = difficulty + self.create_genesis_block() + + def create_genesis_block(self): + """ + Creates the first block in the blockchain (the Genesis block). + """ + genesis_block = Block(0, "0", "Genesis Block", time.time(), self.difficulty) + genesis_block.mine_block() + self.chain.append(genesis_block) + + def add_block(self, transactions): + """ + Adds a new block to the blockchain after performing Proof of Work. + """ + previous_block = self.chain[-1] + new_block = Block(len(self.chain), previous_block.hash, transactions, time.time(), self.difficulty) + new_block.mine_block() + self.chain.append(new_block) + + def is_chain_valid(self): + """ + Verifies the integrity of the blockchain by ensuring each block's previous hash matches + and that all blocks meet the Proof of Work requirement. + """ + for i in range(1, len(self.chain)): + current_block = self.chain[i] + previous_block = self.chain[i - 1] + + if current_block.hash != current_block.compute_hash(): + print(f"Invalid block at index {i}. Hash mismatch.") + return False + + if current_block.previous_hash != previous_block.hash: + print(f"Invalid chain at index {i}. Previous hash mismatch.") + return False + + return True + +# Test cases + +def test_blockchain(): + """ + Test cases for the Blockchain proof of work algorithm. + """ + # Create blockchain with difficulty level of 4 (hash should start with 4 zeros) + blockchain = Blockchain(difficulty=4) + + # Add new blocks + blockchain.add_block("Transaction 1: Alice pays Bob 5 BTC") + blockchain.add_block("Transaction 2: Bob pays Charlie 3 BTC") + + # Verify the integrity of the blockchain + assert blockchain.is_chain_valid() == True, "Blockchain should be valid" + + # Tamper with the blockchain and check validation + blockchain.chain[1].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering the transaction + assert blockchain.is_chain_valid() == False, "Blockchain should be invalid due to tampering" + + print("All test cases passed.") + +if __name__ == "__main__": + test_blockchain() + +""" +# Output: +- Block mined with nonce X, hash: 0000abcd... +- Block mined with nonce Y, hash: 0000xyz... +- Block mined with nonce Z, hash: 0000pqrs... +- All test cases passed. +""" From f5459b80836909ca5361b37a46ffab48263904db Mon Sep 17 00:00:00 2001 From: anurags10 Date: Thu, 3 Oct 2024 09:44:19 +0000 Subject: [PATCH 03/11] updating DIRECTORY.md --- DIRECTORY.md | 1 + 1 file changed, 1 insertion(+) diff --git a/DIRECTORY.md b/DIRECTORY.md index 900bd64d5..eff19be15 100644 --- a/DIRECTORY.md +++ b/DIRECTORY.md @@ -54,6 +54,7 @@ * [Swap All Odd And Even Bits](bit_manipulation/swap_all_odd_and_even_bits.py) ## Blockchain + * [Powalgorithm](blockchain/PoWAlgorithm.py) * [Diophantine Equation](blockchain/diophantine_equation.py) ## Boolean Algebra From 95732058fbbab279f7484202915a3ddfd95a4a11 Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Thu, 3 Oct 2024 09:49:33 +0000 Subject: [PATCH 04/11] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- blockchain/PoWAlgorithm.py | 31 ++++++++++++++++++++++++------- 1 file changed, 24 insertions(+), 7 deletions(-) diff --git a/blockchain/PoWAlgorithm.py b/blockchain/PoWAlgorithm.py index 99b74876d..c85ee1eba 100644 --- a/blockchain/PoWAlgorithm.py +++ b/blockchain/PoWAlgorithm.py @@ -22,6 +22,7 @@ The algorithm implements the Proof of Work (PoW) consensus mechanism used in blo import hashlib import time + class Block: def __init__(self, index, previous_hash, transactions, timestamp, difficulty): self.index = index @@ -35,7 +36,7 @@ class Block: def compute_hash(self): """ Generates the hash of the block content. - Combines index, previous hash, transactions, timestamp, and nonce into a string, + Combines index, previous hash, transactions, timestamp, and nonce into a string, which is then hashed using SHA-256. """ block_string = f"{self.index}{self.previous_hash}{self.transactions}{self.timestamp}{self.nonce}" @@ -46,13 +47,16 @@ class Block: Performs Proof of Work by adjusting the nonce until a valid hash is found. A valid hash has the required number of leading zeros based on the difficulty level. """ - target = '0' * self.difficulty # Target hash should start with 'difficulty' number of zeros - while self.hash[:self.difficulty] != target: + target = ( + "0" * self.difficulty + ) # Target hash should start with 'difficulty' number of zeros + while self.hash[: self.difficulty] != target: self.nonce += 1 self.hash = self.compute_hash() print(f"Block mined with nonce {self.nonce}, hash: {self.hash}") + class Blockchain: def __init__(self, difficulty): self.chain = [] @@ -72,13 +76,19 @@ class Blockchain: Adds a new block to the blockchain after performing Proof of Work. """ previous_block = self.chain[-1] - new_block = Block(len(self.chain), previous_block.hash, transactions, time.time(), self.difficulty) + new_block = Block( + len(self.chain), + previous_block.hash, + transactions, + time.time(), + self.difficulty, + ) new_block.mine_block() self.chain.append(new_block) def is_chain_valid(self): """ - Verifies the integrity of the blockchain by ensuring each block's previous hash matches + Verifies the integrity of the blockchain by ensuring each block's previous hash matches and that all blocks meet the Proof of Work requirement. """ for i in range(1, len(self.chain)): @@ -95,8 +105,10 @@ class Blockchain: return True + # Test cases + def test_blockchain(): """ Test cases for the Blockchain proof of work algorithm. @@ -112,11 +124,16 @@ def test_blockchain(): assert blockchain.is_chain_valid() == True, "Blockchain should be valid" # Tamper with the blockchain and check validation - blockchain.chain[1].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering the transaction - assert blockchain.is_chain_valid() == False, "Blockchain should be invalid due to tampering" + blockchain.chain[ + 1 + ].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering the transaction + assert ( + blockchain.is_chain_valid() == False + ), "Blockchain should be invalid due to tampering" print("All test cases passed.") + if __name__ == "__main__": test_blockchain() From 5ebea50f6f8932fb1bfdb7ca3838915a4530346a Mon Sep 17 00:00:00 2001 From: Anurag Singh <54910091+anurags10@users.noreply.github.com> Date: Thu, 3 Oct 2024 15:25:02 +0530 Subject: [PATCH 05/11] Update and rename PoWAlgorithm.py to pow_algorithm.py --- .../{PoWAlgorithm.py => pow_algorithm.py} | 61 ++++++------------- 1 file changed, 19 insertions(+), 42 deletions(-) rename blockchain/{PoWAlgorithm.py => pow_algorithm.py} (60%) diff --git a/blockchain/PoWAlgorithm.py b/blockchain/pow_algorithm.py similarity index 60% rename from blockchain/PoWAlgorithm.py rename to blockchain/pow_algorithm.py index c85ee1eba..7d4000227 100644 --- a/blockchain/PoWAlgorithm.py +++ b/blockchain/pow_algorithm.py @@ -2,27 +2,15 @@ # Title: Proof of Work Algorithm for Blockchain ## Algorithm Statement: -The algorithm implements the Proof of Work (PoW) consensus mechanism used in blockchain to validate blocks. PoW is used to ensure that participants (miners) must perform a computational task to create a valid block and add it to the blockchain. The difficulty of the task is defined by the number of leading zeros required in the hash of the block. - -## Approach: -1. Each block contains a list of transactions, a previous block's hash, a timestamp, and a nonce (random value). -2. The block is hashed using the SHA-256 cryptographic hash function. -3. The miner's goal is to find a nonce such that the resulting hash has a certain number of leading zeros, which defines the difficulty level. -4. The difficulty is adjustable. The more leading zeros required, the harder it is to find a valid nonce. -5. This process is repeated until a valid hash is found, which demonstrates that computational work has been done (Proof of Work). - -## Steps: -1. Create a `Block` class to hold block details (transactions, previous hash, timestamp, and nonce). -2. Implement a `Blockchain` class that adds new blocks to the chain by solving the PoW problem. -3. Implement the hashing function using SHA-256. -4. Adjust the difficulty by varying the number of leading zeros required in the hash. -5. Use test cases to validate the PoW algorithm. +The algorithm implements the Proof of Work (PoW) consensus mechanism used in +blockchain to validate blocks. PoW ensures participants (miners) perform a +computational task to create a valid block and add it to the blockchain. The +difficulty is defined by the number of leading zeros required in the block hash. """ import hashlib import time - class Block: def __init__(self, index, previous_hash, transactions, timestamp, difficulty): self.index = index @@ -39,24 +27,25 @@ class Block: Combines index, previous hash, transactions, timestamp, and nonce into a string, which is then hashed using SHA-256. """ - block_string = f"{self.index}{self.previous_hash}{self.transactions}{self.timestamp}{self.nonce}" + block_string = ( + f"{self.index}{self.previous_hash}{self.transactions}{self.timestamp}" + f"{self.nonce}" + ) return hashlib.sha256(block_string.encode()).hexdigest() def mine_block(self): """ Performs Proof of Work by adjusting the nonce until a valid hash is found. - A valid hash has the required number of leading zeros based on the difficulty level. + A valid hash has the required number of leading zeros based on the difficulty + level. """ - target = ( - "0" * self.difficulty - ) # Target hash should start with 'difficulty' number of zeros - while self.hash[: self.difficulty] != target: + target = '0' * self.difficulty # Target hash should start with 'difficulty' zeros + while self.hash[:self.difficulty] != target: self.nonce += 1 self.hash = self.compute_hash() print(f"Block mined with nonce {self.nonce}, hash: {self.hash}") - class Blockchain: def __init__(self, difficulty): self.chain = [] @@ -76,20 +65,15 @@ class Blockchain: Adds a new block to the blockchain after performing Proof of Work. """ previous_block = self.chain[-1] - new_block = Block( - len(self.chain), - previous_block.hash, - transactions, - time.time(), - self.difficulty, - ) + new_block = Block(len(self.chain), previous_block.hash, transactions, time.time(), + self.difficulty) new_block.mine_block() self.chain.append(new_block) def is_chain_valid(self): """ - Verifies the integrity of the blockchain by ensuring each block's previous hash matches - and that all blocks meet the Proof of Work requirement. + Verifies the integrity of the blockchain by ensuring each block's previous + hash matches and that all blocks meet the Proof of Work requirement. """ for i in range(1, len(self.chain)): current_block = self.chain[i] @@ -105,10 +89,8 @@ class Blockchain: return True - # Test cases - def test_blockchain(): """ Test cases for the Blockchain proof of work algorithm. @@ -121,19 +103,14 @@ def test_blockchain(): blockchain.add_block("Transaction 2: Bob pays Charlie 3 BTC") # Verify the integrity of the blockchain - assert blockchain.is_chain_valid() == True, "Blockchain should be valid" + assert blockchain.is_chain_valid(), "Blockchain should be valid" # Tamper with the blockchain and check validation - blockchain.chain[ - 1 - ].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering the transaction - assert ( - blockchain.is_chain_valid() == False - ), "Blockchain should be invalid due to tampering" + blockchain.chain[1].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering + assert not blockchain.is_chain_valid(), "Blockchain should be invalid due to tampering" print("All test cases passed.") - if __name__ == "__main__": test_blockchain() From 91a43251d8e1367fbef9267b321d544cde5b87f2 Mon Sep 17 00:00:00 2001 From: anurags10 Date: Thu, 3 Oct 2024 09:55:15 +0000 Subject: [PATCH 06/11] updating DIRECTORY.md --- DIRECTORY.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/DIRECTORY.md b/DIRECTORY.md index eff19be15..9a48214bf 100644 --- a/DIRECTORY.md +++ b/DIRECTORY.md @@ -54,8 +54,8 @@ * [Swap All Odd And Even Bits](bit_manipulation/swap_all_odd_and_even_bits.py) ## Blockchain - * [Powalgorithm](blockchain/PoWAlgorithm.py) * [Diophantine Equation](blockchain/diophantine_equation.py) + * [Pow Algorithm](blockchain/pow_algorithm.py) ## Boolean Algebra * [And Gate](boolean_algebra/and_gate.py) From 66cd40e387b2a062c6390a32d48e0caa4fddb0fe Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Thu, 3 Oct 2024 09:55:24 +0000 Subject: [PATCH 07/11] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- blockchain/pow_algorithm.py | 38 ++++++++++++++++++++++++++----------- 1 file changed, 27 insertions(+), 11 deletions(-) diff --git a/blockchain/pow_algorithm.py b/blockchain/pow_algorithm.py index 7d4000227..69fa58948 100644 --- a/blockchain/pow_algorithm.py +++ b/blockchain/pow_algorithm.py @@ -2,15 +2,16 @@ # Title: Proof of Work Algorithm for Blockchain ## Algorithm Statement: -The algorithm implements the Proof of Work (PoW) consensus mechanism used in -blockchain to validate blocks. PoW ensures participants (miners) perform a -computational task to create a valid block and add it to the blockchain. The +The algorithm implements the Proof of Work (PoW) consensus mechanism used in +blockchain to validate blocks. PoW ensures participants (miners) perform a +computational task to create a valid block and add it to the blockchain. The difficulty is defined by the number of leading zeros required in the block hash. """ import hashlib import time + class Block: def __init__(self, index, previous_hash, transactions, timestamp, difficulty): self.index = index @@ -36,16 +37,19 @@ class Block: def mine_block(self): """ Performs Proof of Work by adjusting the nonce until a valid hash is found. - A valid hash has the required number of leading zeros based on the difficulty + A valid hash has the required number of leading zeros based on the difficulty level. """ - target = '0' * self.difficulty # Target hash should start with 'difficulty' zeros - while self.hash[:self.difficulty] != target: + target = ( + "0" * self.difficulty + ) # Target hash should start with 'difficulty' zeros + while self.hash[: self.difficulty] != target: self.nonce += 1 self.hash = self.compute_hash() print(f"Block mined with nonce {self.nonce}, hash: {self.hash}") + class Blockchain: def __init__(self, difficulty): self.chain = [] @@ -65,14 +69,19 @@ class Blockchain: Adds a new block to the blockchain after performing Proof of Work. """ previous_block = self.chain[-1] - new_block = Block(len(self.chain), previous_block.hash, transactions, time.time(), - self.difficulty) + new_block = Block( + len(self.chain), + previous_block.hash, + transactions, + time.time(), + self.difficulty, + ) new_block.mine_block() self.chain.append(new_block) def is_chain_valid(self): """ - Verifies the integrity of the blockchain by ensuring each block's previous + Verifies the integrity of the blockchain by ensuring each block's previous hash matches and that all blocks meet the Proof of Work requirement. """ for i in range(1, len(self.chain)): @@ -89,8 +98,10 @@ class Blockchain: return True + # Test cases + def test_blockchain(): """ Test cases for the Blockchain proof of work algorithm. @@ -106,11 +117,16 @@ def test_blockchain(): assert blockchain.is_chain_valid(), "Blockchain should be valid" # Tamper with the blockchain and check validation - blockchain.chain[1].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering - assert not blockchain.is_chain_valid(), "Blockchain should be invalid due to tampering" + blockchain.chain[ + 1 + ].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering + assert ( + not blockchain.is_chain_valid() + ), "Blockchain should be invalid due to tampering" print("All test cases passed.") + if __name__ == "__main__": test_blockchain() From c051734d9c9f44412510c033396c509343ae5929 Mon Sep 17 00:00:00 2001 From: Anurag Singh <54910091+anurags10@users.noreply.github.com> Date: Thu, 3 Oct 2024 15:33:48 +0530 Subject: [PATCH 08/11] Update pow_algorithm.py with return type --- blockchain/pow_algorithm.py | 108 ++++++++++++++++++++++-------------- 1 file changed, 66 insertions(+), 42 deletions(-) diff --git a/blockchain/pow_algorithm.py b/blockchain/pow_algorithm.py index 69fa58948..44e35baec 100644 --- a/blockchain/pow_algorithm.py +++ b/blockchain/pow_algorithm.py @@ -2,18 +2,34 @@ # Title: Proof of Work Algorithm for Blockchain ## Algorithm Statement: -The algorithm implements the Proof of Work (PoW) consensus mechanism used in -blockchain to validate blocks. PoW ensures participants (miners) perform a -computational task to create a valid block and add it to the blockchain. The +The algorithm implements the Proof of Work (PoW) consensus mechanism used in +blockchain to validate blocks. PoW ensures participants (miners) perform a +computational task to create a valid block and add it to the blockchain. The difficulty is defined by the number of leading zeros required in the block hash. """ import hashlib import time - class Block: - def __init__(self, index, previous_hash, transactions, timestamp, difficulty): + def __init__( + self, + index: int, + previous_hash: str, + transactions: str, + timestamp: float, + difficulty: int + ) -> None: + """ + Initializes a Block object with the specified parameters. + + Parameters: + - index (int): The index of the block in the blockchain. + - previous_hash (str): The hash of the previous block. + - transactions (str): The list of transactions in the block. + - timestamp (float): The time when the block was created (in Unix timestamp format). + - difficulty (int): The difficulty level for mining this block. + """ self.index = index self.previous_hash = previous_hash self.transactions = transactions @@ -22,11 +38,14 @@ class Block: self.difficulty = difficulty self.hash = self.compute_hash() - def compute_hash(self): + def compute_hash(self) -> str: """ Generates the hash of the block content. Combines index, previous hash, transactions, timestamp, and nonce into a string, which is then hashed using SHA-256. + + Returns: + - str: The hash of the block. """ block_string = ( f"{self.index}{self.previous_hash}{self.transactions}{self.timestamp}" @@ -34,55 +53,72 @@ class Block: ) return hashlib.sha256(block_string.encode()).hexdigest() - def mine_block(self): + def mine_block(self) -> None: """ Performs Proof of Work by adjusting the nonce until a valid hash is found. - A valid hash has the required number of leading zeros based on the difficulty - level. + A valid hash has the required number of leading zeros based on the difficulty level. + + Returns: + - None """ - target = ( - "0" * self.difficulty - ) # Target hash should start with 'difficulty' zeros - while self.hash[: self.difficulty] != target: + target = '0' * self.difficulty # Target hash should start with 'difficulty' zeros + while self.hash[:self.difficulty] != target: self.nonce += 1 self.hash = self.compute_hash() print(f"Block mined with nonce {self.nonce}, hash: {self.hash}") - class Blockchain: - def __init__(self, difficulty): + def __init__(self, difficulty: int) -> None: + """ + Initializes the blockchain with a given difficulty level. + + Parameters: + - difficulty (int): The difficulty level for mining blocks in this blockchain. + + Returns: + - None + """ self.chain = [] self.difficulty = difficulty self.create_genesis_block() - def create_genesis_block(self): + def create_genesis_block(self) -> None: """ Creates the first block in the blockchain (the Genesis block). + + Returns: + - None """ genesis_block = Block(0, "0", "Genesis Block", time.time(), self.difficulty) genesis_block.mine_block() self.chain.append(genesis_block) - def add_block(self, transactions): + def add_block(self, transactions: str) -> None: """ Adds a new block to the blockchain after performing Proof of Work. + + Parameters: + - transactions (str): The list of transactions to be added in the new block. + + Returns: + - None """ previous_block = self.chain[-1] new_block = Block( - len(self.chain), - previous_block.hash, - transactions, - time.time(), - self.difficulty, + len(self.chain), previous_block.hash, transactions, time.time(), + self.difficulty ) new_block.mine_block() self.chain.append(new_block) - def is_chain_valid(self): + def is_chain_valid(self) -> bool: """ - Verifies the integrity of the blockchain by ensuring each block's previous + Verifies the integrity of the blockchain by ensuring each block's previous hash matches and that all blocks meet the Proof of Work requirement. + + Returns: + - bool: True if the blockchain is valid, False otherwise. """ for i in range(1, len(self.chain)): current_block = self.chain[i] @@ -98,13 +134,14 @@ class Blockchain: return True - # Test cases - -def test_blockchain(): +def test_blockchain() -> None: """ Test cases for the Blockchain proof of work algorithm. + + Returns: + - None """ # Create blockchain with difficulty level of 4 (hash should start with 4 zeros) blockchain = Blockchain(difficulty=4) @@ -117,23 +154,10 @@ def test_blockchain(): assert blockchain.is_chain_valid(), "Blockchain should be valid" # Tamper with the blockchain and check validation - blockchain.chain[ - 1 - ].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering - assert ( - not blockchain.is_chain_valid() - ), "Blockchain should be invalid due to tampering" + blockchain.chain[1].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering + assert not blockchain.is_chain_valid(), "Blockchain should be invalid due to tampering" print("All test cases passed.") - if __name__ == "__main__": test_blockchain() - -""" -# Output: -- Block mined with nonce X, hash: 0000abcd... -- Block mined with nonce Y, hash: 0000xyz... -- Block mined with nonce Z, hash: 0000pqrs... -- All test cases passed. -""" From 3d91445a577aeb92b2266a9f42ab893a6f5b3481 Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Thu, 3 Oct 2024 10:04:15 +0000 Subject: [PATCH 09/11] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- blockchain/pow_algorithm.py | 58 +++++++++++++++++++++++-------------- 1 file changed, 36 insertions(+), 22 deletions(-) diff --git a/blockchain/pow_algorithm.py b/blockchain/pow_algorithm.py index 44e35baec..139cb3648 100644 --- a/blockchain/pow_algorithm.py +++ b/blockchain/pow_algorithm.py @@ -2,23 +2,24 @@ # Title: Proof of Work Algorithm for Blockchain ## Algorithm Statement: -The algorithm implements the Proof of Work (PoW) consensus mechanism used in -blockchain to validate blocks. PoW ensures participants (miners) perform a -computational task to create a valid block and add it to the blockchain. The +The algorithm implements the Proof of Work (PoW) consensus mechanism used in +blockchain to validate blocks. PoW ensures participants (miners) perform a +computational task to create a valid block and add it to the blockchain. The difficulty is defined by the number of leading zeros required in the block hash. """ import hashlib import time + class Block: def __init__( - self, - index: int, - previous_hash: str, - transactions: str, - timestamp: float, - difficulty: int + self, + index: int, + previous_hash: str, + transactions: str, + timestamp: float, + difficulty: int, ) -> None: """ Initializes a Block object with the specified parameters. @@ -43,7 +44,7 @@ class Block: Generates the hash of the block content. Combines index, previous hash, transactions, timestamp, and nonce into a string, which is then hashed using SHA-256. - + Returns: - str: The hash of the block. """ @@ -57,17 +58,20 @@ class Block: """ Performs Proof of Work by adjusting the nonce until a valid hash is found. A valid hash has the required number of leading zeros based on the difficulty level. - + Returns: - None """ - target = '0' * self.difficulty # Target hash should start with 'difficulty' zeros - while self.hash[:self.difficulty] != target: + target = ( + "0" * self.difficulty + ) # Target hash should start with 'difficulty' zeros + while self.hash[: self.difficulty] != target: self.nonce += 1 self.hash = self.compute_hash() print(f"Block mined with nonce {self.nonce}, hash: {self.hash}") + class Blockchain: def __init__(self, difficulty: int) -> None: """ @@ -75,7 +79,7 @@ class Blockchain: Parameters: - difficulty (int): The difficulty level for mining blocks in this blockchain. - + Returns: - None """ @@ -86,7 +90,7 @@ class Blockchain: def create_genesis_block(self) -> None: """ Creates the first block in the blockchain (the Genesis block). - + Returns: - None """ @@ -100,21 +104,24 @@ class Blockchain: Parameters: - transactions (str): The list of transactions to be added in the new block. - + Returns: - None """ previous_block = self.chain[-1] new_block = Block( - len(self.chain), previous_block.hash, transactions, time.time(), - self.difficulty + len(self.chain), + previous_block.hash, + transactions, + time.time(), + self.difficulty, ) new_block.mine_block() self.chain.append(new_block) def is_chain_valid(self) -> bool: """ - Verifies the integrity of the blockchain by ensuring each block's previous + Verifies the integrity of the blockchain by ensuring each block's previous hash matches and that all blocks meet the Proof of Work requirement. Returns: @@ -134,12 +141,14 @@ class Blockchain: return True + # Test cases + def test_blockchain() -> None: """ Test cases for the Blockchain proof of work algorithm. - + Returns: - None """ @@ -154,10 +163,15 @@ def test_blockchain() -> None: assert blockchain.is_chain_valid(), "Blockchain should be valid" # Tamper with the blockchain and check validation - blockchain.chain[1].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering - assert not blockchain.is_chain_valid(), "Blockchain should be invalid due to tampering" + blockchain.chain[ + 1 + ].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering + assert ( + not blockchain.is_chain_valid() + ), "Blockchain should be invalid due to tampering" print("All test cases passed.") + if __name__ == "__main__": test_blockchain() From 9a6fcd541789228206cf068664ccda8a122efbf1 Mon Sep 17 00:00:00 2001 From: Anurag Singh <54910091+anurags10@users.noreply.github.com> Date: Thu, 3 Oct 2024 15:39:44 +0530 Subject: [PATCH 10/11] Update pow_algorithm.py --- blockchain/pow_algorithm.py | 82 ++++++++++++++++++------------------- 1 file changed, 40 insertions(+), 42 deletions(-) diff --git a/blockchain/pow_algorithm.py b/blockchain/pow_algorithm.py index 139cb3648..65e2f59b6 100644 --- a/blockchain/pow_algorithm.py +++ b/blockchain/pow_algorithm.py @@ -1,17 +1,14 @@ -""" # Title: Proof of Work Algorithm for Blockchain ## Algorithm Statement: -The algorithm implements the Proof of Work (PoW) consensus mechanism used in -blockchain to validate blocks. PoW ensures participants (miners) perform a -computational task to create a valid block and add it to the blockchain. The -difficulty is defined by the number of leading zeros required in the block hash. -""" +# The algorithm implements the Proof of Work (PoW) consensus mechanism used in +# blockchain to validate blocks. PoW ensures participants (miners) perform a +# computational task to create a valid block and add it to the blockchain. The +# difficulty is defined by the number of leading zeros required in the block hash. import hashlib import time - class Block: def __init__( self, @@ -19,7 +16,7 @@ class Block: previous_hash: str, transactions: str, timestamp: float, - difficulty: int, + difficulty: int ) -> None: """ Initializes a Block object with the specified parameters. @@ -28,7 +25,8 @@ class Block: - index (int): The index of the block in the blockchain. - previous_hash (str): The hash of the previous block. - transactions (str): The list of transactions in the block. - - timestamp (float): The time when the block was created (in Unix timestamp format). + - timestamp (float): The time when the block was created + (in Unix timestamp format). - difficulty (int): The difficulty level for mining this block. """ self.index = index @@ -42,9 +40,9 @@ class Block: def compute_hash(self) -> str: """ Generates the hash of the block content. - Combines index, previous hash, transactions, timestamp, and nonce into a string, - which is then hashed using SHA-256. - + Combines index, previous hash, transactions, timestamp, and nonce into + a string, which is then hashed using SHA-256. + Returns: - str: The hash of the block. """ @@ -57,21 +55,19 @@ class Block: def mine_block(self) -> None: """ Performs Proof of Work by adjusting the nonce until a valid hash is found. - A valid hash has the required number of leading zeros based on the difficulty level. - + A valid hash has the required number of leading zeros based on the + difficulty level. + Returns: - None """ - target = ( - "0" * self.difficulty - ) # Target hash should start with 'difficulty' zeros - while self.hash[: self.difficulty] != target: + target = '0' * self.difficulty # Target hash should start with 'difficulty' zeros + while self.hash[:self.difficulty] != target: self.nonce += 1 self.hash = self.compute_hash() print(f"Block mined with nonce {self.nonce}, hash: {self.hash}") - class Blockchain: def __init__(self, difficulty: int) -> None: """ @@ -79,18 +75,18 @@ class Blockchain: Parameters: - difficulty (int): The difficulty level for mining blocks in this blockchain. - + Returns: - None """ - self.chain = [] + self.chain: list[Block] = [] # Adding type hint for the list of blocks self.difficulty = difficulty self.create_genesis_block() def create_genesis_block(self) -> None: """ Creates the first block in the blockchain (the Genesis block). - + Returns: - None """ @@ -104,24 +100,21 @@ class Blockchain: Parameters: - transactions (str): The list of transactions to be added in the new block. - + Returns: - None """ previous_block = self.chain[-1] new_block = Block( - len(self.chain), - previous_block.hash, - transactions, - time.time(), - self.difficulty, + len(self.chain), previous_block.hash, transactions, time.time(), + self.difficulty ) new_block.mine_block() self.chain.append(new_block) def is_chain_valid(self) -> bool: """ - Verifies the integrity of the blockchain by ensuring each block's previous + Verifies the integrity of the blockchain by ensuring each block's previous hash matches and that all blocks meet the Proof of Work requirement. Returns: @@ -141,37 +134,42 @@ class Blockchain: return True - # Test cases - +## Test Case 1: Blockchain Initialization and Genesis Block +# This test verifies if the blockchain is correctly initialized with a Genesis block +# and if the block is successfully mined. def test_blockchain() -> None: """ Test cases for the Blockchain proof of work algorithm. - + Returns: - None """ # Create blockchain with difficulty level of 4 (hash should start with 4 zeros) blockchain = Blockchain(difficulty=4) - # Add new blocks + ## Test Case 2: Add a block and verify the block is mined + # This test adds a new block with transactions and ensures it's mined according + # to the proof of work mechanism. blockchain.add_block("Transaction 1: Alice pays Bob 5 BTC") blockchain.add_block("Transaction 2: Bob pays Charlie 3 BTC") - # Verify the integrity of the blockchain + ## Test Case 3: Verify blockchain integrity + # This test checks that the blockchain remains valid after adding new blocks assert blockchain.is_chain_valid(), "Blockchain should be valid" - # Tamper with the blockchain and check validation - blockchain.chain[ - 1 - ].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering - assert ( - not blockchain.is_chain_valid() - ), "Blockchain should be invalid due to tampering" + ## Test Case 4: Tampering with the blockchain + # This test simulates tampering with the blockchain and checks that the validation + # correctly detects the tampering. + blockchain.chain[1].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering + assert not blockchain.is_chain_valid(), "Blockchain should be invalid due to tampering" + ## Test Case 5: Correct blockchain validation + # This test checks if the blockchain becomes invalid after tampering and verifies + # if the PoW still holds after tampering is done. + print("All test cases passed.") - if __name__ == "__main__": test_blockchain() From 6a7b49d95ee66a6d10473da24ec68c656d7417f0 Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Thu, 3 Oct 2024 10:10:05 +0000 Subject: [PATCH 11/11] [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci --- blockchain/pow_algorithm.py | 44 ++++++++++++++++++++++++------------- 1 file changed, 29 insertions(+), 15 deletions(-) diff --git a/blockchain/pow_algorithm.py b/blockchain/pow_algorithm.py index 65e2f59b6..cd4213e92 100644 --- a/blockchain/pow_algorithm.py +++ b/blockchain/pow_algorithm.py @@ -9,6 +9,7 @@ import hashlib import time + class Block: def __init__( self, @@ -16,7 +17,7 @@ class Block: previous_hash: str, transactions: str, timestamp: float, - difficulty: int + difficulty: int, ) -> None: """ Initializes a Block object with the specified parameters. @@ -42,7 +43,7 @@ class Block: Generates the hash of the block content. Combines index, previous hash, transactions, timestamp, and nonce into a string, which is then hashed using SHA-256. - + Returns: - str: The hash of the block. """ @@ -57,17 +58,20 @@ class Block: Performs Proof of Work by adjusting the nonce until a valid hash is found. A valid hash has the required number of leading zeros based on the difficulty level. - + Returns: - None """ - target = '0' * self.difficulty # Target hash should start with 'difficulty' zeros - while self.hash[:self.difficulty] != target: + target = ( + "0" * self.difficulty + ) # Target hash should start with 'difficulty' zeros + while self.hash[: self.difficulty] != target: self.nonce += 1 self.hash = self.compute_hash() print(f"Block mined with nonce {self.nonce}, hash: {self.hash}") + class Blockchain: def __init__(self, difficulty: int) -> None: """ @@ -75,7 +79,7 @@ class Blockchain: Parameters: - difficulty (int): The difficulty level for mining blocks in this blockchain. - + Returns: - None """ @@ -86,7 +90,7 @@ class Blockchain: def create_genesis_block(self) -> None: """ Creates the first block in the blockchain (the Genesis block). - + Returns: - None """ @@ -100,21 +104,24 @@ class Blockchain: Parameters: - transactions (str): The list of transactions to be added in the new block. - + Returns: - None """ previous_block = self.chain[-1] new_block = Block( - len(self.chain), previous_block.hash, transactions, time.time(), - self.difficulty + len(self.chain), + previous_block.hash, + transactions, + time.time(), + self.difficulty, ) new_block.mine_block() self.chain.append(new_block) def is_chain_valid(self) -> bool: """ - Verifies the integrity of the blockchain by ensuring each block's previous + Verifies the integrity of the blockchain by ensuring each block's previous hash matches and that all blocks meet the Proof of Work requirement. Returns: @@ -134,15 +141,17 @@ class Blockchain: return True + # Test cases + ## Test Case 1: Blockchain Initialization and Genesis Block # This test verifies if the blockchain is correctly initialized with a Genesis block # and if the block is successfully mined. def test_blockchain() -> None: """ Test cases for the Blockchain proof of work algorithm. - + Returns: - None """ @@ -162,14 +171,19 @@ def test_blockchain() -> None: ## Test Case 4: Tampering with the blockchain # This test simulates tampering with the blockchain and checks that the validation # correctly detects the tampering. - blockchain.chain[1].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering - assert not blockchain.is_chain_valid(), "Blockchain should be invalid due to tampering" + blockchain.chain[ + 1 + ].transactions = "Transaction 1: Alice pays Bob 50 BTC" # Tampering + assert ( + not blockchain.is_chain_valid() + ), "Blockchain should be invalid due to tampering" ## Test Case 5: Correct blockchain validation # This test checks if the blockchain becomes invalid after tampering and verifies # if the PoW still holds after tampering is done. - + print("All test cases passed.") + if __name__ == "__main__": test_blockchain()