Skip to content
This repository was archived by the owner on Jan 13, 2023. It is now read-only.

Commit 69ac8bb

Browse files
committed
Fixed some issues with getTransfers.
1 parent 6909515 commit 69ac8bb

File tree

5 files changed

+139
-14
lines changed

5 files changed

+139
-14
lines changed

iota/api.py

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -489,7 +489,7 @@ def get_new_addresses(self, index=None, count=1):
489489
return self.getNewAddresses(seed=self.seed, index=index, count=count)
490490

491491
def get_transfers(self, start=0, end=None, inclusion_states=False):
492-
# type: (int, Optional[int], bool) -> List[Bundle]
492+
# type: (int, Optional[int], bool) -> dict
493493
"""
494494
Returns all transfers associated with the seed.
495495
@@ -512,7 +512,12 @@ def get_transfers(self, start=0, end=None, inclusion_states=False):
512512
disabled by default.
513513
514514
:return:
515-
List of bundles.
515+
Dict containing the following values::
516+
517+
{
518+
'bundles': List[Bundle]
519+
Matching bundles, sorted by tail transaction timestamp.
520+
}
516521
517522
References:
518523
- https://github.com/iotaledger/wiki/blob/master/api-proposal.md#gettransfers

iota/commands/extended/get_transfers.py

Lines changed: 13 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,11 @@ def _execute(self, request):
7171
tails = set()
7272
non_tails = set()
7373

74-
transactions = self._find_transactions(hashes=hashes)
74+
gt_response = GetTrytesCommand(self.adapter)(hashes=hashes)
75+
transactions = list(map(
76+
Transaction.from_tryte_string,
77+
gt_response['trytes'],
78+
))
7579

7680
for txn in transactions:
7781
if txn.is_tail:
@@ -100,7 +104,7 @@ def _execute(self, request):
100104

101105
# Find the bundles for each transaction.
102106
for txn in transactions:
103-
gb_response = GetBundlesCommand(self.adapter)(transactions=txn.hash)
107+
gb_response = GetBundlesCommand(self.adapter)(transaction=txn.hash)
104108
txn_bundles = gb_response['bundles'] # type: List[Bundle]
105109

106110
if inclusion_states:
@@ -109,11 +113,13 @@ def _execute(self, request):
109113

110114
all_bundles.extend(txn_bundles)
111115

112-
# Sort bundles by tail transaction timestamp.
113-
return list(sorted(
114-
all_bundles,
115-
key = lambda bundle_: bundle_.tail_transaction.timestamp,
116-
))
116+
return {
117+
# Sort bundles by tail transaction timestamp.
118+
'bundles': list(sorted(
119+
all_bundles,
120+
key = lambda bundle_: bundle_.tail_transaction.timestamp,
121+
)),
122+
}
117123

118124

119125
def _find_transactions(self, **kwargs):

iota/types.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -235,6 +235,10 @@ def __init__(self, trytes, pad=None):
235235

236236
self._trytes = trytes # type: bytearray
237237

238+
def __hash__(self):
239+
# type: () -> int
240+
return hash(binary_type(self._trytes))
241+
238242
def __repr__(self):
239243
# type: () -> Text
240244
return '{cls}({trytes!r})'.format(

test/__init__.py

Lines changed: 15 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -61,15 +61,28 @@ def send_request(self, payload, **kwargs):
6161

6262
try:
6363
response = self.responses[command].pop(0)
64-
except (KeyError, IndexError):
64+
except KeyError:
6565
raise with_context(
6666
exc = BadApiResponse(
67-
'Unknown request {command!r} (expected one of: {seeds!r}).'.format(
67+
'No seeded response for {command!r} '
68+
'(expected one of: {seeds!r}).'.format(
6869
command = command,
6970
seeds = list(sorted(self.responses.keys())),
7071
),
7172
),
7273

74+
context = {
75+
'request': payload,
76+
},
77+
)
78+
except IndexError:
79+
raise with_context(
80+
exc = BadApiResponse(
81+
'{command} called too many times; no seeded responses left.'.format(
82+
command = command,
83+
),
84+
),
85+
7386
context = {
7487
'request': payload,
7588
},

test/commands/extended/get_transfers_test.py

Lines changed: 100 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,10 @@
66

77
import filters as f
88
from filters.test import BaseFilterTestCase
9+
from mock import Mock, patch
910
from six import binary_type, text_type
1011

11-
from iota import Iota
12+
from iota import Address, Iota, Bundle, Tag, Transaction
1213
from iota.commands.extended.get_transfers import GetTransfersCommand, \
1314
GetTransfersRequestFilter
1415
from iota.crypto.types import Seed
@@ -336,8 +337,104 @@ def test_full_scan(self):
336337
"""
337338
Scanning the Tangle for all transfers.
338339
"""
339-
# :todo: Implement test.
340-
self.skipTest('Not implemented yet.')
340+
addy1 =\
341+
Address(
342+
b'TESTVALUEONE9DONTUSEINPRODUCTION99999YDZ'
343+
b'E9TAFAJGJA9CECKDAEPHBICDR9LHFCOFRBQDHC9IG'
344+
)
345+
346+
addy2 =\
347+
Address(
348+
b'TESTVALUETWO9DONTUSEINPRODUCTION99999TES'
349+
b'GINEIDLEEHRAOGEBMDLENFDAFCHEIHZ9EBZDD9YHL'
350+
)
351+
352+
# To speed up the test, we will mock the address generator.
353+
# :py:class:`iota.crypto.addresses.AddressGenerator` already has
354+
# its own test case, so this does not impact the stability of the
355+
# codebase.
356+
# noinspection PyUnusedLocal
357+
def create_generator(ag, start, step=1):
358+
for addy in [addy1, addy2][start::step]:
359+
yield addy
360+
361+
# The first address received IOTA.
362+
self.adapter.seed_response(
363+
'findTransactions',
364+
365+
{
366+
'duration': 42,
367+
368+
'hashes': [
369+
'TESTVALUEFIVE9DONTUSEINPRODUCTION99999VH'
370+
'YHRHJETGYCAFZGABTEUBWCWAS9WF99UHBHRHLIOFJ',
371+
],
372+
},
373+
)
374+
375+
# The second address is unused.
376+
self.adapter.seed_response(
377+
'findTransactions',
378+
379+
{
380+
'duration': 1,
381+
'hashes': [],
382+
},
383+
)
384+
385+
self.adapter.seed_response(
386+
'getTrytes',
387+
388+
{
389+
'duration': 99,
390+
391+
# Thankfully, we do not have to seed a realistic response for
392+
# ``getTrytes``, as we will be mocking the ``getBundles``
393+
# command that uses on it.
394+
'trytes': [''],
395+
},
396+
)
397+
398+
bundle = Bundle([
399+
Transaction(
400+
address = addy1,
401+
timestamp = 1483033814,
402+
403+
# These values are not relevant to the test.
404+
hash_ = None,
405+
signature_message_fragment = None,
406+
value = 42,
407+
tag = Tag(b''),
408+
current_index = 0,
409+
last_index = 0,
410+
bundle_hash = None,
411+
trunk_transaction_hash = None,
412+
branch_transaction_hash = None,
413+
nonce = None,
414+
)
415+
])
416+
417+
mock_get_bundles = Mock(return_value={
418+
'bundles': [bundle],
419+
})
420+
421+
with patch(
422+
'iota.crypto.addresses.AddressGenerator.create_generator',
423+
create_generator,
424+
):
425+
with patch(
426+
'iota.commands.extended.get_bundles.GetBundlesCommand._execute',
427+
mock_get_bundles,
428+
):
429+
response = self.command(seed=Seed.random())
430+
431+
self.assertDictEqual(
432+
response,
433+
434+
{
435+
'bundles': [bundle],
436+
},
437+
)
341438

342439
def test_start(self):
343440
"""

0 commit comments

Comments
 (0)