def end_block(self, request_end_block): """Calculate block hash using transaction ids and previous block hash to be stored in the next block. Args: height (int): new height of the chain. """ height = request_end_block.height self.new_height = height block_txn_hash = calculate_hash(self.block_txn_ids) block = self.bigchaindb.get_latest_block() if self.block_txn_ids: self.block_txn_hash = calculate_hash( [block['app_hash'], block_txn_hash]) else: self.block_txn_hash = block['app_hash'] # TODO: calculate if an election has concluded # NOTE: ensure the local validator set is updated # validator_updates = self.bigchaindb.get_validator_update() # validator_updates = [encode_validator(v) for v in validator_updates] validator_updates = [] # Store pre-commit state to recover in case there is a crash # during `commit` pre_commit_state = PreCommitState(commit_id=PRE_COMMIT_ID, height=self.new_height, transactions=self.block_txn_ids) logger.debug('Updating PreCommitState: %s', self.new_height) self.bigchaindb.store_pre_commit_state(pre_commit_state._asdict()) return ResponseEndBlock(validator_updates=validator_updates)
def end_block(self, request_end_block): """Calculate block hash using transaction ids and previous block hash to be stored in the next block. Args: height (int): new height of the chain. """ self.abort_if_abci_chain_is_not_synced() chain_shift = 0 if self.chain is None else self.chain['height'] height = request_end_block.height + chain_shift self.new_height = height block_txn_hash = calculate_hash(self.block_txn_ids) block = self.bigchaindb.get_latest_block() if self.block_txn_ids: self.block_txn_hash = calculate_hash( [block['app_hash'], block_txn_hash]) else: self.block_txn_hash = block['app_hash'] validator_update = Election.process_block(self.bigchaindb, self.new_height, self.block_transactions) # Store pre-commit state to recover in case there is a crash during `commit` pre_commit_state = PreCommitState(commit_id=PRE_COMMIT_ID, height=self.new_height, transactions=self.block_txn_ids) logger.debug('Updating PreCommitState: %s', self.new_height) self.bigchaindb.store_pre_commit_state(pre_commit_state._asdict()) return ResponseEndBlock(validator_updates=validator_update)
def end_block(self, request_end_block): """Calculate block hash using transaction ids and previous block hash to be stored in the next block. Args: height (int): new height of the chain. """ height = request_end_block.height self.new_height = height block_txn_hash = calculate_hash(self.block_txn_ids) block = self.bigchaindb.get_latest_block() if self.block_txn_ids: self.block_txn_hash = calculate_hash([block['app_hash'], block_txn_hash]) else: self.block_txn_hash = block['app_hash'] # Check if the current block concluded any validator elections and # update the locally tracked validator set validator_updates = ValidatorElection.get_validator_update(self.bigchaindb, self.new_height, self.block_transactions) # Store pre-commit state to recover in case there is a crash # during `commit` pre_commit_state = PreCommitState(commit_id=PRE_COMMIT_ID, height=self.new_height, transactions=self.block_txn_ids) logger.debug('Updating PreCommitState: %s', self.new_height) self.bigchaindb.store_pre_commit_state(pre_commit_state._asdict()) return ResponseEndBlock(validator_updates=validator_updates)
def test_get_pre_commit_state(db_context): from bigchaindb.backend import query from bigchaindb.lib import PreCommitState state = PreCommitState(commit_id='test2', height=3, transactions=[]) db_context.conn.db.pre_commit.insert(state._asdict()) resp = query.get_pre_commit_state(db_context.conn, 'test2') assert resp == state._asdict()
def test_store_pre_commit_state(db_context): from bigchaindb.backend import query from bigchaindb.lib import PreCommitState state = PreCommitState(commit_id='test', height=3, transactions=[]) query.store_pre_commit_state(db_context.conn, state._asdict()) cursor = db_context.conn.db.pre_commit.find({'commit_id': 'test'}, projection={'_id': False}) assert cursor.count() == 1
def end_block(self, request_end_block): """Calculate block hash using transaction ids and previous block hash to be stored in the next block. Args: height (int): new height of the chain. """ self.abort_if_abci_chain_is_not_synced() chain_shift = 0 if self.chain is None else self.chain['height'] height = request_end_block.height + chain_shift self.new_height = height block_txn_hash = calculate_hash(self.block_txn_ids) block = self.bigchaindb.get_latest_block() if self.block_txn_ids: self.block_txn_hash = calculate_hash([block['app_hash'], block_txn_hash]) else: self.block_txn_hash = block['app_hash'] # Check if the current block concluded any validator elections and # update the locally tracked validator set validator_update = ValidatorElection.approved_update(self.bigchaindb, self.new_height, self.block_transactions) update = [validator_update] if validator_update else [] # Store pre-commit state to recover in case there is a crash # during `commit` pre_commit_state = PreCommitState(commit_id=PRE_COMMIT_ID, height=self.new_height, transactions=self.block_txn_ids) logger.debug('Updating PreCommitState: %s', self.new_height) self.bigchaindb.store_pre_commit_state(pre_commit_state._asdict()) return ResponseEndBlock(validator_updates=update)
def test_run_recover(b, alice, bob): from bigchaindb.commands.bigchaindb import run_recover from bigchaindb.models import Transaction from bigchaindb.lib import Block, PreCommitState from bigchaindb.backend.query import PRE_COMMIT_ID from bigchaindb.backend import query tx1 = Transaction.create([alice.public_key], [([alice.public_key], 1)], asset={'cycle': 'hero'}, metadata={'name': 'hohenheim'}) \ .sign([alice.private_key]) tx2 = Transaction.create([bob.public_key], [([bob.public_key], 1)], asset={'cycle': 'hero'}, metadata={'name': 'hohenheim'}) \ .sign([bob.private_key]) # store the transactions b.store_bulk_transactions([tx1, tx2]) # create a random block block8 = Block(app_hash='random_app_hash1', height=8, transactions=['txid_doesnt_matter'])._asdict() b.store_block(block8) # create the next block block9 = Block(app_hash='random_app_hash1', height=9, transactions=[tx1.id])._asdict() b.store_block(block9) # create a pre_commit state which is ahead of the commit state pre_commit_state = PreCommitState(commit_id=PRE_COMMIT_ID, height=10, transactions=[tx2.id])._asdict() b.store_pre_commit_state(pre_commit_state) run_recover(b) assert not query.get_transaction(b.connection, tx2.id)