mirror of
https://github.com/bigchaindb/bigchaindb.git
synced 2024-10-13 13:34:05 +00:00
generalise get_txids_by_asset_id into get_txids_filtered and remove get_transactions_by_asset_id
This commit is contained in:
parent
d899d4c8b6
commit
dbb3414fd0
@ -82,21 +82,6 @@ def get_blocks_status_from_transaction(conn, transaction_id):
|
||||
projection=['id', 'block.voters'])
|
||||
|
||||
|
||||
@register_query(MongoDBConnection)
|
||||
def get_txids_by_asset_id(conn, asset_id):
|
||||
cursor = conn.db['bigchain'].aggregate([
|
||||
{'$match': {
|
||||
'block.transactions.asset.id': asset_id
|
||||
}},
|
||||
{'$unwind': '$block.transactions'},
|
||||
{'$match': {
|
||||
'block.transactions.asset.id': asset_id
|
||||
}},
|
||||
{'$project': {'block.transactions.id': True}}
|
||||
])
|
||||
return (elem['block']['transactions']['id'] for elem in cursor)
|
||||
|
||||
|
||||
@register_query(MongoDBConnection)
|
||||
def get_asset_by_id(conn, asset_id):
|
||||
cursor = conn.db['bigchain'].aggregate([
|
||||
@ -249,3 +234,19 @@ def get_unvoted_blocks(conn, node_pubkey):
|
||||
'votes': False, '_id': False
|
||||
}}
|
||||
])
|
||||
|
||||
|
||||
@register_query(MongoDBConnection)
|
||||
def get_txids_filtered(conn, asset_id, operation=None):
|
||||
match = {'block.transactions.asset.id': asset_id}
|
||||
|
||||
if operation:
|
||||
match['block.transactions.operation'] = operation
|
||||
|
||||
cursor = conn.db['bigchain'].aggregate([
|
||||
{'$match': match},
|
||||
{'$unwind': '$block.transactions'},
|
||||
{'$match': match},
|
||||
{'$project': {'block.transactions.id': True}}
|
||||
])
|
||||
return (r['block']['transactions']['id'] for r in cursor)
|
||||
|
@ -318,3 +318,16 @@ def get_unvoted_blocks(connection, node_pubkey):
|
||||
"""
|
||||
|
||||
raise NotImplementedError
|
||||
|
||||
|
||||
@singledispatch
|
||||
def get_txids_filtered(connection, asset_id, operation=None):
|
||||
"""
|
||||
Return all transactions for a particular asset id and optional operation.
|
||||
|
||||
Args:
|
||||
asset_id (str): ID of transaction that defined the asset
|
||||
operation (str) (optional): Operation to filter on
|
||||
"""
|
||||
|
||||
raise NotImplementedError
|
||||
|
@ -71,22 +71,6 @@ def get_blocks_status_from_transaction(connection, transaction_id):
|
||||
.pluck('votes', 'id', {'block': ['voters']}))
|
||||
|
||||
|
||||
@register_query(RethinkDBConnection)
|
||||
def get_txids_by_asset_id(connection, asset_id):
|
||||
# here we only want to return the transaction ids since later on when
|
||||
# we are going to retrieve the transaction with status validation
|
||||
|
||||
# Then find any TRANSFER transactions related to the asset
|
||||
tx_cursor = connection.run(
|
||||
r.table('bigchain')
|
||||
.get_all(asset_id, index='asset_id')
|
||||
.concat_map(lambda block: block['block']['transactions'])
|
||||
.filter(lambda transaction: transaction['asset']['id'] == asset_id)
|
||||
.get_field('id'))
|
||||
|
||||
return tx_cursor
|
||||
|
||||
|
||||
@register_query(RethinkDBConnection)
|
||||
def get_asset_by_id(connection, asset_id):
|
||||
return connection.run(_get_asset_create_tx_query(asset_id).pluck('asset'))
|
||||
@ -249,3 +233,20 @@ def get_unvoted_blocks(connection, node_pubkey):
|
||||
# database level. Solving issue #444 can help untangling the situation
|
||||
unvoted_blocks = filter(lambda block: not utils.is_genesis_block(block), unvoted)
|
||||
return unvoted_blocks
|
||||
|
||||
|
||||
@register_query(RethinkDBConnection)
|
||||
def get_txids_filtered(connection, asset_id, operation=None):
|
||||
# here we only want to return the transaction ids since later on when
|
||||
# we are going to retrieve the transaction with status validation
|
||||
|
||||
tx_filter = r.row['asset']['id'] == asset_id
|
||||
if operation:
|
||||
tx_filter &= r.row['operation'] == operation
|
||||
|
||||
return connection.run(
|
||||
r.table('bigchain')
|
||||
.get_all(asset_id, index='asset_id')
|
||||
.concat_map(lambda block: block['block']['transactions'])
|
||||
.filter(tx_filter)
|
||||
.get_field('id'))
|
||||
|
@ -317,30 +317,6 @@ class Bigchain(object):
|
||||
else:
|
||||
return None
|
||||
|
||||
def get_transactions_by_asset_id(self, asset_id):
|
||||
"""Retrieves valid or undecided transactions related to a particular
|
||||
asset.
|
||||
|
||||
A digital asset in bigchaindb is identified by an uuid. This allows us
|
||||
to query all the transactions related to a particular digital asset,
|
||||
knowing the id.
|
||||
|
||||
Args:
|
||||
asset_id (str): the id for this particular asset.
|
||||
|
||||
Returns:
|
||||
A list of valid or undecided transactions related to the asset.
|
||||
If no transaction exists for that asset it returns an empty list
|
||||
`[]`
|
||||
"""
|
||||
txids = backend.query.get_txids_by_asset_id(self.connection, asset_id)
|
||||
transactions = []
|
||||
for txid in txids:
|
||||
tx = self.get_transaction(txid)
|
||||
if tx:
|
||||
transactions.append(tx)
|
||||
return transactions
|
||||
|
||||
def get_asset_by_id(self, asset_id):
|
||||
"""Returns the asset associated with an asset_id.
|
||||
|
||||
|
@ -90,95 +90,6 @@ def test_asset_id_mismatch(b, user_pk):
|
||||
Transaction.get_asset_id([tx1, tx2])
|
||||
|
||||
|
||||
@pytest.mark.bdb
|
||||
@pytest.mark.usefixtures('inputs')
|
||||
def test_get_transactions_by_asset_id(b, user_pk, user_sk):
|
||||
from bigchaindb.models import Transaction
|
||||
|
||||
tx_create = b.get_owned_ids(user_pk).pop()
|
||||
tx_create = b.get_transaction(tx_create.txid)
|
||||
asset_id = tx_create.id
|
||||
txs = b.get_transactions_by_asset_id(asset_id)
|
||||
|
||||
assert len(txs) == 1
|
||||
assert txs[0].id == tx_create.id
|
||||
assert txs[0].id == asset_id
|
||||
|
||||
# create a transfer transaction
|
||||
tx_transfer = Transaction.transfer(tx_create.to_inputs(), [([user_pk], 1)],
|
||||
tx_create.id)
|
||||
tx_transfer_signed = tx_transfer.sign([user_sk])
|
||||
# create the block
|
||||
block = b.create_block([tx_transfer_signed])
|
||||
b.write_block(block)
|
||||
# vote the block valid
|
||||
vote = b.vote(block.id, b.get_last_voted_block().id, True)
|
||||
b.write_vote(vote)
|
||||
|
||||
txs = b.get_transactions_by_asset_id(asset_id)
|
||||
|
||||
assert len(txs) == 2
|
||||
assert {tx_create.id, tx_transfer.id} == set(tx.id for tx in txs)
|
||||
assert asset_id == Transaction.get_asset_id(txs)
|
||||
|
||||
|
||||
@pytest.mark.bdb
|
||||
@pytest.mark.usefixtures('inputs')
|
||||
def test_get_transactions_by_asset_id_with_invalid_block(b, user_pk, user_sk):
|
||||
from bigchaindb.models import Transaction
|
||||
|
||||
tx_create = b.get_owned_ids(user_pk).pop()
|
||||
tx_create = b.get_transaction(tx_create.txid)
|
||||
asset_id = tx_create.id
|
||||
txs = b.get_transactions_by_asset_id(asset_id)
|
||||
|
||||
assert len(txs) == 1
|
||||
assert txs[0].id == tx_create.id
|
||||
assert txs[0].id == asset_id
|
||||
|
||||
# create a transfer transaction
|
||||
tx_transfer = Transaction.transfer(tx_create.to_inputs(), [([user_pk], 1)],
|
||||
tx_create.id)
|
||||
tx_transfer_signed = tx_transfer.sign([user_sk])
|
||||
# create the block
|
||||
block = b.create_block([tx_transfer_signed])
|
||||
b.write_block(block)
|
||||
# vote the block invalid
|
||||
vote = b.vote(block.id, b.get_last_voted_block().id, False)
|
||||
b.write_vote(vote)
|
||||
|
||||
txs = b.get_transactions_by_asset_id(asset_id)
|
||||
|
||||
assert len(txs) == 1
|
||||
|
||||
|
||||
@pytest.mark.bdb
|
||||
@pytest.mark.usefixtures('inputs')
|
||||
def test_get_asset_by_id(b, user_pk, user_sk):
|
||||
from bigchaindb.models import Transaction
|
||||
|
||||
tx_create = b.get_owned_ids(user_pk).pop()
|
||||
tx_create = b.get_transaction(tx_create.txid)
|
||||
|
||||
# create a transfer transaction
|
||||
tx_transfer = Transaction.transfer(tx_create.to_inputs(), [([user_pk], 1)],
|
||||
tx_create.id)
|
||||
tx_transfer_signed = tx_transfer.sign([user_sk])
|
||||
# create the block
|
||||
block = b.create_block([tx_transfer_signed])
|
||||
b.write_block(block)
|
||||
# vote the block valid
|
||||
vote = b.vote(block.id, b.get_last_voted_block().id, True)
|
||||
b.write_vote(vote)
|
||||
|
||||
asset_id = Transaction.get_asset_id([tx_create, tx_transfer])
|
||||
txs = b.get_transactions_by_asset_id(asset_id)
|
||||
assert len(txs) == 2
|
||||
|
||||
asset = b.get_asset_by_id(asset_id)
|
||||
assert asset == tx_create.asset
|
||||
|
||||
|
||||
def test_create_invalid_divisible_asset(b, user_pk, user_sk):
|
||||
from bigchaindb.models import Transaction
|
||||
from bigchaindb.common.exceptions import AmountError
|
||||
|
@ -125,24 +125,6 @@ def test_get_block_status_from_transaction(create_tx):
|
||||
assert block_db['block']['voters'] == block.voters
|
||||
|
||||
|
||||
def test_get_txids_by_asset_id(signed_create_tx, signed_transfer_tx):
|
||||
from bigchaindb.backend import connect, query
|
||||
from bigchaindb.models import Block
|
||||
conn = connect()
|
||||
|
||||
# create and insert two blocks, one for the create and one for the
|
||||
# transfer transaction
|
||||
block = Block(transactions=[signed_create_tx])
|
||||
conn.db.bigchain.insert_one(block.to_dict())
|
||||
block = Block(transactions=[signed_transfer_tx])
|
||||
conn.db.bigchain.insert_one(block.to_dict())
|
||||
|
||||
txids = list(query.get_txids_by_asset_id(conn, signed_create_tx.id))
|
||||
|
||||
assert len(txids) == 2
|
||||
assert txids == [signed_create_tx.id, signed_transfer_tx.id]
|
||||
|
||||
|
||||
def test_get_asset_by_id(create_tx):
|
||||
from bigchaindb.backend import connect, query
|
||||
from bigchaindb.models import Block
|
||||
@ -366,3 +348,30 @@ def test_get_unvoted_blocks(signed_create_tx):
|
||||
|
||||
assert len(unvoted_blocks) == 1
|
||||
assert unvoted_blocks[0] == block.to_dict()
|
||||
|
||||
|
||||
def test_get_txids_filtered(signed_create_tx, signed_transfer_tx):
|
||||
from bigchaindb.backend import connect, query
|
||||
from bigchaindb.models import Block, Transaction
|
||||
conn = connect()
|
||||
|
||||
# create and insert two blocks, one for the create and one for the
|
||||
# transfer transaction
|
||||
block = Block(transactions=[signed_create_tx])
|
||||
conn.db.bigchain.insert_one(block.to_dict())
|
||||
block = Block(transactions=[signed_transfer_tx])
|
||||
conn.db.bigchain.insert_one(block.to_dict())
|
||||
|
||||
asset_id = Transaction.get_asset_id([signed_create_tx, signed_transfer_tx])
|
||||
|
||||
# Test get by just asset id
|
||||
txids = set(query.get_txids_filtered(conn, asset_id))
|
||||
assert txids == {signed_create_tx.id, signed_transfer_tx.id}
|
||||
|
||||
# Test get by asset and CREATE
|
||||
txids = set(query.get_txids_filtered(conn, asset_id, Transaction.CREATE))
|
||||
assert txids == {signed_create_tx.id}
|
||||
|
||||
# Test get by asset and TRANSFER
|
||||
txids = set(query.get_txids_filtered(conn, asset_id, Transaction.TRANSFER))
|
||||
assert txids == {signed_transfer_tx.id}
|
||||
|
@ -26,7 +26,7 @@ def test_schema(schema_func_name, args_qty):
|
||||
('get_stale_transactions', 1),
|
||||
('get_blocks_status_from_transaction', 1),
|
||||
('get_transaction_from_backlog', 1),
|
||||
('get_txids_by_asset_id', 1),
|
||||
('get_txids_filtered', 1),
|
||||
('get_asset_by_id', 1),
|
||||
('get_owned_ids', 1),
|
||||
('get_votes_by_block_id', 1),
|
||||
|
Loading…
x
Reference in New Issue
Block a user