def TElementTest(rpc: RPC) -> None: #BLS key. blsPrivKey: PrivateKey = PrivateKey( blake2b(b'\0', digest_size=32).digest()) blsPubKey: str = blsPrivKey.toPublicKey().serialize().hex() #Blocks. file: IO[Any] = open("PythonTests/Vectors/Merit/BlankBlocks.json", "r") blocks: List[Dict[str, Any]] = json.loads(file.read()) file.close() #Merit. merit: Merit = Merit() #Handshake with the node. rpc.meros.connect(254, 254, merit.blockchain.blocks[0].header.hash) #Send the first Block. block: Block = Block.fromJSON(merit.blockchain.keys, blocks[0]) merit.blockchain.add(block) rpc.meros.blockHeader(block.header) #Handle sync requests. reqHash: bytes = bytes() while True: msg: bytes = rpc.meros.recv() if MessageType(msg[0]) == MessageType.Syncing: rpc.meros.syncingAcknowledged() elif MessageType(msg[0]) == MessageType.BlockBodyRequest: reqHash = msg[1:33] if reqHash != block.header.hash: raise TestError( "Meros asked for a Block Body that didn't belong to the Block we just sent it." ) #Send the BlockBody. rpc.meros.blockBody(merit.state.nicks, block) elif MessageType(msg[0]) == MessageType.SyncingOver: pass elif MessageType(msg[0]) == MessageType.BlockHeader: break else: raise TestError("Unexpected message sent: " + msg.hex().upper()) #Create and transmit a DataDifficulty. dataDiff: SignedDataDifficulty = SignedDataDifficulty( bytes.fromhex("00" * 32), 0, 0) dataDiff.sign(0, blsPrivKey) rpc.meros.signedElement(dataDiff) sleep(0.5) #Verify the block template has the DataDifficulty. template: Dict[str, Any] = rpc.call("merit", "getBlockTemplate", [blsPubKey]) template["header"] = bytes.fromhex(template["header"]) if template["header"][36:68] != BlockHeader.createContents( merit.state.nicks, [], [dataDiff]): raise TestError("Block template doesn't have the Data Difficulty.") #Mine the Block. block = Block( BlockHeader( 0, block.header.hash, BlockHeader.createContents(merit.state.nicks, [], [dataDiff]), 1, template["header"][-43:-39], BlockHeader.createSketchCheck(template["header"][-43:-39], []), 0, int.from_bytes(template["header"][-4:], byteorder="big"), ), BlockBody([], [dataDiff], dataDiff.signature)) if block.header.serializeHash()[:-4] != template["header"]: raise TestError("Failed to recreate the header.") if block.body.serialize(merit.state.nicks, block.header.sketchSalt) != bytes.fromhex( template["body"]): raise TestError("Failed to recreate the body.") block.mine(blsPrivKey, merit.blockchain.difficulty()) merit.blockchain.add(block) #Publish it. rpc.call("merit", "publishBlock", [ template["id"], (template["header"] + block.header.proof.to_bytes(4, byteorder="big") + block.header.signature + block.body.serialize( merit.state.nicks, block.header.sketchSalt)).hex() ]) #Create and transmit a new DataDifficulty. dataDiff = SignedDataDifficulty(bytes.fromhex("AA" * 32), 1, 0) dataDiff.sign(0, blsPrivKey) rpc.meros.signedElement(dataDiff) sleep(0.5) #Verify the block template has the DataDifficulty. template = rpc.call("merit", "getBlockTemplate", [blsPubKey]) template["header"] = bytes.fromhex(template["header"]) if template["header"][36:68] != BlockHeader.createContents( merit.state.nicks, [], [dataDiff]): raise TestError("Block template doesn't have the new Data Difficulty.") #Create and transmit a new DataDifficulty reusing an existing nonce. signatures: List[Signature] = [dataDiff.signature] dataDiff = SignedDataDifficulty(bytes.fromhex("BB" * 32), 1, 0) dataDiff.sign(0, blsPrivKey) signatures.append(dataDiff.signature) rpc.meros.signedElement(dataDiff) sleep(0.5) #Verify the block template has a MeritRemoval. mr: MeritRemoval = MeritRemoval( SignedDataDifficulty(bytes.fromhex("AA" * 32), 1, 0), SignedDataDifficulty(bytes.fromhex("BB" * 32), 1, 0), False) template = rpc.call("merit", "getBlockTemplate", [blsPubKey]) template["header"] = bytes.fromhex(template["header"]) if template["header"][36:68] != BlockHeader.createContents( merit.state.nicks, [], [mr]): raise TestError("Block template doesn't have the Merit Removal.") #Mine the Block. block = Block( BlockHeader( 0, block.header.hash, BlockHeader.createContents(merit.state.nicks, [], [mr]), 1, template["header"][-43:-39], BlockHeader.createSketchCheck(template["header"][-43:-39], []), 0, int.from_bytes(template["header"][-4:], byteorder="big"), ), BlockBody([], [mr], Signature.aggregate(signatures))) if block.header.serializeHash()[:-4] != template["header"]: raise TestError("Failed to recreate the header.") if block.body.serialize(merit.state.nicks, block.header.sketchSalt) != bytes.fromhex( template["body"]): raise TestError("Failed to recreate the body.") block.mine(blsPrivKey, merit.blockchain.difficulty()) merit.blockchain.add(block) #Publish it. rpc.call("merit", "publishBlock", [ template["id"], (template["header"] + block.header.proof.to_bytes(4, byteorder="big") + block.header.signature + block.body.serialize( merit.state.nicks, block.header.sketchSalt)).hex() ]) #Verify the Blockchain. verifyBlockchain(rpc, merit.blockchain)
blsPubKey.serialize(), blockchain.blocks[-1].header.time + 1200), BlockBody()) #Mine it. block.mine(blsPrivKey, blockchain.difficulty()) #Add it. blockchain.add(block) print("Generated Same Nonce Block " + str(len(blockchain.blocks)) + ".") #Create a DataDifficulty. dataDiff: SignedDataDifficulty = SignedDataDifficulty(3, 0) dataDiff.sign(0, blsPrivKey) #Create a conflicting DataDifficulty with the same nonce. dataDiffConflicting = SignedDataDifficulty(1, 0) dataDiffConflicting.sign(0, blsPrivKey) #Create a MeritRemoval out of the two of them. mr: SignedMeritRemoval = SignedMeritRemoval(dataDiff, dataDiffConflicting) #Generate a Block containing the MeritRemoval. block = Block( BlockHeader(0, blockchain.last(), BlockHeader.createContents([], [mr]), 1, bytes(4), bytes(32), 0, blockchain.blocks[-1].header.time + 1200), BlockBody([], [mr], mr.signature)) #Mine it. block.mine(blsPrivKey, blockchain.difficulty()) #Add it. blockchain.add(block)
bytes(32), 0, blockchain.blocks[-1].header.time + 1200 ), BlockBody() ) #Mine it. block.mine(blsPrivKey, blockchain.difficulty()) #Add it. blockchain.add(block) print("Generated DataDifficulty Block " + str(len(blockchain.blocks)) + ".") #Now that we have aa vote, update our vote. dataDiff = SignedDataDifficulty(bytes.fromhex("8888888888888888888888888888888888888888888888888888888888888888"), 1) dataDiff.sign(0, blsPrivKey) #Generate a Block containing the new DataDifficulty. block = Block( BlockHeader( 0, blockchain.last(), BlockHeader.createContents([], [], [dataDiff]), 1, bytes(4), bytes(32), 0, blockchain.blocks[-1].header.time + 1200 ), BlockBody([], [dataDiff], dataDiff.signature) )