def sign_input_at( self, start_index: int, private_key: PrivateKey ) -> None: """ Signs the input at the specified index. :param int start_index: The index of the first input transaction. If necessary, the resulting signature will be split across multiple transactions automatically (i.e., if an input has ``security_level=2``, you still only need to call :py:meth:`sign_input_at` once). :param PrivateKey private_key: The private key that will be used to generate the signature. .. important:: Be sure that the private key was generated using the correct seed, or the resulting signature will be invalid! :raises RuntimeError: if bundle is not yet finalized. """ if not self.hash: raise RuntimeError('Cannot sign inputs until bundle is finalized.') private_key.sign_input_transactions(self, start_index)
def setUp(self): super(GetDigestsCommandTestCase, self).setUp() self.adapter = MockAdapter() self.command = GetDigestsCommand(self.adapter) # Define some tryte sequences that we can reuse between tests. self.key1 = PrivateKey(TryteString(b'KEYONE', pad=FRAGMENT_LENGTH), 0) self.key2 = PrivateKey(TryteString(b'KEYTWO', pad=FRAGMENT_LENGTH), 1) self.digest1 = Digest(TryteString(b'DIGESTONE', pad=Hash.LEN), 0) self.digest2 = Digest(TryteString(b'DIGESTTWO', pad=Hash.LEN), 1)
def test_get_digest_single_fragment(self): """ Generating digest from a PrivateKey 1 fragment long. """ key =\ PrivateKey( b'YYKM9AOPBSOSKZJRE9LIUNGFEBPWAK9JQD9LNKVLLOBVYTDQ9QMRNWJHWGTBFLCCYPQ9B9YMJMORDVGDCCVYAQOYFVGZKYUKXTLLUVWNRKIBYZEQFLYRWYRZNWKJAGVWO9VDRSYCAOARINNIL9EQKBREAGEZMBIXSZKVWRRNRLUYAYYUZUYHW9DUJJKJQVMJCPZFBLAURYJGZLT9ZHBLNUQWE9YVJFMWWZNJRHFSPVCQKJMWUCYPYUBHA9QEPCFAYWMGQOFDLZXDQSPYSSDL9MKJAPUGQWGAIRJC9MEYNTMABQTKVIHLSYSNSWAZGJL9YLIZWIO9G9LNRNENQHVZK9YXNQTJSFIJQPLVWWCJ9UTEEYGVFJVUVBJPHKBZACPVQFQCQAVDV9BUTXLFQSHIXZTEONSVKECHCVICRRUZGIPGEFMGUK9QQOPKMYHTDPIIKKDELF9DGSBBEHESJETZSPYTXSAPYA9ZSRKHECXXT9TTKSRIMRFKBBHFKQIYIJGJNSTZRGORHZLVEVLGGXTUHBEDGFIEVFZBQDCNJPQQ9DXMPP9KJD9PBZWKUT9ZPYW9FHBSSNSVTTGHSEVIHYFSUCIRDXSHWCOOGPTTJCCFNHYLRQHRQOBVNUNROWRSYQATJCSSYUGZ9YWFNJHIQNZMIGYKPDFR9JXMAJHQIR9PEWZRHYMOVJNQUXHKNRZEIJMQOZIQVOUSNEQRCYEIAVMHHUA9XIG9CQSBYCDQGEHHZPGSQCHY9OIBBSHSGTORMXIUAXERVPBZ9OGHBCDRXOUFNFJDKALLQOQFMWHHIPJSOAQTHUUFJWCTCROCFSYLOBHIYWCFJQHGWSGGKJRSKZGNUBDMGQZZM9SEZQXABXYFROYUYOHJEPPGCLCWOTZZGYVTBZH9AWPCVGILCDUWRQVLPDEJLVUKNNKBFFXSMVTAIZGBBJMMOAHGLMASBICFUQKWAKHEVNDQPNHDXSJFYGQOVWOKTWDSRGWCWNF9KP9VFOCTED9LIDRIPBLBMWUGRUIPENOFHSATAKHBRHQFDDEOZOZSDZKZWYNWDXVEMRASWCVMFNESLVUIFQNXXDABDGBBUICOZRAADRKQHRYRD9PVTWAETJCAOQIRNZGSULUWMZIVQZR9WDZVBAQXWBFPQRINPKDHGIMWMEOHOKODFSO9DSEZOPAWFLIYBUZWP9OYSTWFNKEFWYGPUTEZOGDKMZCQOYNTEONUSNSBNBMMPFGFTCUID9AELBVGZHYTJ9VSUQLFZDYYOCBMFYHFNFPOLUHGTLFXRWD9JUHFTU9DMSALSARRPYVHDEQTGY9TYTRUHD9YWCZFUTNNJPPRSZPPARMVKWVRMFIEGVJYXEMQTCDGZPAFHNIJTNPZYVGT9RQWKBZZ9CKRKAFMKGDKXGJUZHMDNWUPZYLDDVSORPMCCDLPGIIIYAVDLJODEVRPQIA9JLSEYQTIGDTNGYRNVIQBFBFLYVHDUORTCFFIWOBQJXQ9NUXAHI9TUVR9SJKTST9MGJIIBGDIFRELOHDW9MXPARDLG9WQWLIC9TTHVOSQ9FCAFDCSUHHISCWVJNYWHKVMPYBKVORHRGVY9PDHXPNDXIMJMYECYQZGDT9DANTQBJPXHN9MG9MDKJ9EJIDQZFLJX9VPACAHZUXMBMPRUGNHBXFCGBDYUWAIPFVAMQZYMLESKEEIKFWQVPJRBQBCDOYVSUFTONAIHMIUEVPXTWUYADPQLMBLKWCYXETFVLTZZATEHYDTHSDXAJMQDLKYNQNUAZBVYRLCVKAOUWA9QHXK9AXYFZGBUAZLVZGLVRKSHVRLXTYKMPDCZURJOSTHVJFCKIXHXXQQNCBTAEXUVMKMKEQVUPOEEY9LSTKT9XNJVJPRK9ZDUFQWTMJHWNMTTDRCRMFRXUEZMYXLQEAQMEV9MBIORUONCARJVMCDIR9PIOUJUXIDFY9NHCENUCVPJDIKHIRVRFPGKDZSIGZSBZGTRWAXLRFQLESYXKUISYBTWGZPAVNIKVXLYGINAUMZSJAMDRM9LVAXXCBSOBXUAKFAPMVAXDPFZTKWQCEOKBKAJWELYR9ZEWOTTNFOLHCNUPNMJO9CBH9HXTKFCSXMGBVHY9QFLDFNYMGQUEOXMEPBZWTOKHUMFIJKLUMYPZJHNKIBTRCDSNRBFOSPMDMYCRTBQJZZASRRNIOZTAZ', ) self.assertEqual( key.get_digest(), TryteString( b'TIBCVWNGKLYX9UDSNQK9FWFODLGWOZREMZYWYRPILH9LYLOSRJSZQKKXBBEGVRJYTFHWQXRAMPMRJJT99', ), )
def __init__(self, private_key: PrivateKey, hash_: Hash) -> None: super(SignatureFragmentGenerator, self).__init__() self._key_chunks = private_key.iter_chunks(FRAGMENT_LENGTH) self._iteration = -1 self._normalized_hash = normalize(hash_) self._sponge = Kerl()
def __next__(self) -> PrivateKey: while self.current >= 0: sponge = self._create_sponge(self.current) key = [0] * (self.fragment_length * self.security_level) buffer = [0] * len(self.seed_as_trits) for fragment_seq in range(self.security_level): # Squeeze trits from the buffer and append them to the # key, one hash at a time. for hash_seq in range(self.hashes_per_fragment): sponge.squeeze(buffer) key_start = ( (fragment_seq * self.fragment_length) + (hash_seq * HASH_LENGTH) ) key_stop = key_start + HASH_LENGTH # Ensure we only capture one hash from the buffer, # in case it is longer than that (i.e., if the seed # is longer than 81 trytes). key[key_start:key_stop] = buffer[0:HASH_LENGTH] private_key = PrivateKey.from_trits( key_index=self.current, security_level=self.security_level, trits=key, ) self.advance() return private_key
def __next__(self): # type: () -> PrivateKey while self.current >= 0: sponge = self._create_sponge(self.current) key = [0] * (self.fragment_length * self.security_level) buffer = [0] * len(self.seed_as_trits) for fragment_seq in range(self.security_level): # Squeeze trits from the buffer and append them to the key, one # hash at a time. for hash_seq in range(self.hashes_per_fragment): sponge.squeeze(buffer) key_start =\ (fragment_seq * self.fragment_length) + (hash_seq * HASH_LENGTH) key_stop = key_start + HASH_LENGTH # Ensure we only capture one hash from the buffer, in case # it is longer than that (i.e., if the seed is longer than 81 # trytes). key[key_start:key_stop] = buffer[0:HASH_LENGTH] private_key =\ PrivateKey.from_trits( key_index = self.current, security_level = self.security_level, trits = key, ) # type: PrivateKey self.advance() return private_key
def __next__(self): # type: () -> PrivateKey while self.current >= 0: sponge = self._create_sponge(self.current) key = [0] * (self.fragment_length * self.iterations) buffer = [0] * HASH_LENGTH # type: MutableSequence[int] for fragment_seq in range(self.iterations): # Squeeze trits from the buffer and append them to the key, one # hash at a time. for hash_seq in range(self.hashes_per_fragment): sponge.squeeze(buffer) key_start =\ (fragment_seq * self.fragment_length) + (hash_seq * HASH_LENGTH) key_stop = key_start + HASH_LENGTH key[key_start:key_stop] = buffer private_key = PrivateKey.from_trits(key) private_key.key_index = self.current self.current += self.step return private_key
def test_get_digest_single_fragment(self): """ Generating digest from a PrivateKey 1 fragment long. """ key =\ PrivateKey( b'BWFTZWBZVFOSQYHQFXOPYTZ9SWB9RYYHBOUA9NOYSWGALF9MSVNEDW9A9FLGBRWKED' b'MPEIPRKBMRXRLLFJCAGVIMXPISRGXIJQ9BOBHKJEUKDEUUWYXJGCGAWHYBQHBPMRTZ' b'FPBGNLMKPZYXZPXFSPFUWZNRWYXUEWMP9URKVVJOSWEPJKSMPLWZPIZGOTVAA9QQOC' b'YISMGHSBU9YCXZCMSTPJVASDKEVZCSPNSPYOUUWWFTNWZTTZBKGZ9PDNAKNSGNODSB' b'IRKUGFYCZXIFHQCDTXQNLMKRVKIFJS9XARBNMJQOTDL9CAOKEXQTMWCKWRNHLLMLYP' b'QGTDFNTDBHNAFRBEUWTKPKPECAADKRPEAFDHABMYYXQPQYDSGFRSRFNHFHHHTAH9YF' b'OXKRZOTKAHZPRISHZRR9YBVSOZUSKKU9HTCXPTPZFAHFMOQJBKZIACZB9ZRXFPPPMY' b'RBCWPBAPRFXLQZOTGXJGMZUUEZIAVWXUEN9UIFLEESVCCGNKDISMEPYWTXDQHOSUWZ' b'OEHOCZQJKDCJJNRZVODVNNUOV9FZQEXFGAMDKMV9PVUYMWTFNISYGYKQG9OKNOQUEK' b'YDEJ9EGHUXQFCPHTTVBCRTZJLOAWHGDEQHLPLHWTWVOBCCQTCWCNLYDGUV9FKFZENU' b'NOCOYNU9CYQDSAQDSMZGRQYB9YOCFSOHQXANMSPYFVCTPTZKUGIGUZMPJIJRZVN9VX' b'ADLIVJYJGQWXBOBBAROGNIOIJVRUHWMFLVCGTMZISADLTXVEZLQDYAVQ9OCYQDPCYL' b'DD9SUPNTUMUESC9VRSCAYBPXAPTYXZODUUMBNCSLOWJYJA9JBITZLZNHPZFGSPRURJ' b'HYFLSFTMEPAEG9DWRFOTFWWPGGDGZWFVEPOHDGNMOXUSR9AVQLNDUMGPYWVN9LKEIZ' b'Q9MNIUPJXPTRYMSXRA9GTSZFMNZZT9Z9HJOKVBCHRRIZZN9UYTVRDNHOXYSFRO9FRK' b'HWNNZ9DXTLV9D9PNJLGWJXAFUOJZTRVJOLYGSPNVCXYWMTOEEUBLNRGAJPK9HIWGZM' b'HMBTHLABTACRYLQIDPOYEFNSYQ9YAQPOYYDCJAAAVDUWCHSS9OKQYH9CQNUPYRTCWK' b'CXYDKTAIJKWOQIHSGBZMFJXGOQDODBDZNBOPFYCBLSU9RJYVGXINUDODGHNAGFDAEG' b'LPDVSCJPCIZHOFNHCZUTRLQXEZUFDZVROFXVHUNWMYRSZHBZAFCWIY9ULTBTEDSKEC' b'CLDGAU9MZXYRAXVY9NIQUYHATJCZXDSAELMCXQMALHNFMEAWHIQAZMQOO9QPEPDOYC' b'OJXTUWEJHMPXGZBXFPNXUPOSDINZJNIREYDFZMESFQUPBKSDGTAJHEZSCOVSLYUAUK' b'DIWNNLQJTPYYTPRGGN9IXIORWXHJBPYINQZIUXKLKXCTQZYJIRH9MHYBQIFQZCFAKZ' b'DUUZTYIMTNNVNKVMFIW9UYRTVRQHMYR9Y9VYFTPBJGSB9VINGTMBKVZJEZUE9RMBDZ' b'CQGDHNPW9YIJHLGFOG9YAPXZECSFVXAMPILBIHC9DBGMIE99YEPGTAALOHBUKXSGFZ' b'YHHWFOIHMEDXFHIYSUHADOCKFNGHKTNPZHINAWG9YGRJBQGECRCVPXXOG9CNVJNFLC' b'LMGC9I9HAGTAGGVRKCXDJWDNHYZBFNQSKH99MFAMLGRSBMIBBMHBDJTVSQ99ZHYPSS' b'XLUNFCNOJXITUETNBHIGXFLLEHUKEXGJLO9BBALXMNGJKTETFIZHSSKLOQXPXOSZRW' b'QP9A9RIHWEHATMSVMZEQPGAUQBCIAQXZSUUFSU9HYK9RAVASYCVNALKJJXAJF9RLTD' b'ZEIIYCFLQVMHBPBFHHQNXVEKPHOOFTQEIVB9IXZMTOFBHTGLPWDYVPO9HHBPVWZYEG' b'IDMK9UPWEJDLIPJSIGFKKCZFRJVDN9ENWADNOTFWZGUDJRRUMFPVXHNAJBBCI9WEDK' b'RKCQUHRQTCFYFHXPOFBC9BCENMI9HRSIUAKLWEAOUXRBWMHWLGEOCP9NWIJAXODJDS' b'P9SKEXEDVUGHZAFPNMR9PXD9THOWNWWTDTWTYMDINGC9EBBVUYZRUQDVSIOXAEVGFP' b'XS9CLTHUESMTDWUJNCZSOIOEJG9WKNAZMDJGMRBXGVMLUAN9IGDVFAESJMXNTMNFND' b'CAXEBRAU9' ) self.assertEqual( key.get_digest(), TryteString(b'ABQXVJNER9MPMXMBPNMFBMDGTXRWSYHNZKGAGUOI' b'JKOJGZVGHCUXXGFZEMMGDSGWDCKJXO9ILLFAKGGZE'), )
def test_generate_multiple_keys(self): """ Generating multiple keys. """ keys = [PrivateKey(self.trytes1, 0), PrivateKey(self.trytes2, 1)] mock_get_keys = mock.Mock(return_value=keys) with mock.patch('iota.crypto.signing.KeyGenerator.get_keys', mock_get_keys): result = \ self.command( count=2, index=0, securityLevel=1, seed=Seed.random(), ) self.assertDictEqual(result, {'keys': keys}) mock_get_keys.assert_called_once_with( count=2, iterations=1, start=0, )
def test_get_digest_multiple_fragments(self): """ Generating digest from a PrivateKey longer than 1 fragment. """ key =\ PrivateKey( # This key is 3 fragments long (split into separate lines to # improve IDE performance). b'KDCFNMNMIFDAX9ACOQMUKGHSXEFHDPHBXBKVCGNENDGZGUAFVZGLPPUASMOWVOYUT9BNGXJ9HHLXHFBGWQCNXMCDXMYTVNWRCDLTCAOORGEPRGHYGHUPVEGCOILRPXMOTMDLYVYSUXTBRZDERVNBLFSVPLXQIHPCP9CRKHPJDIWXTEDZTODIKJBVC9LOO9NZLUDNPKPXUZJXNWQRYCKYYGDAGDTSVBN9LDLHJFVEAZYYYJHUVHDIDNOUHKXOTPZAXIRX999YGKIBZFCKEOGA9HVRSTPQPBS9GS9THHILCTUATKQVKOJHOT9OAVKRBPIROLSZADVRGWKH9MSYWIXEYECSIZJCJDSESQTTW9EADQTOUWAXOXXZGYFBGSPIJLTEUOZFYMFODMIWFFYMPIJN9QZNYSSRGELQJAWPHXKIFFEVDIGYUSXMALQNJCCP9SJCOFWHTVVDLPWDEYDY9UIGRJYEANTXZXJGVGGMLXYTPQMELTXXDHKGZSODPGGXKQQYX9HSWSRLUJENERYZJLCEEAMDADYAAYAOAYEROJQPWAJWIHRZQWXFRXDYZP9AHFVGFBJWGZOUFFWECNLXVIDMCRTKGCMWL9RMMEPSFHJQYOFCFNVZTYSJVTDBSXBTAPQWNKBEOZRWYBYMZQWRPGSBAGDEONBSCPFUZWQTLDYFMWKVNCYLKBUUEKBCNTFVZSWWWWDPRLTBBMMNFELSCNCMICTKXGMNBIHFA9YIJYPOMVKAY9CLXFQN9AIXIHHOXJXQIFESXKKOAKHMAJXQWNPLRFWW9BZF9CFMKQMAMNSKDCBJVUHTMOKWNFNQOSRJTCOXJSEZENVRPNOOARXUV9RMVK9EOCLSJCTRALFDPNNIQH9BGR9VLIIAKABZVUDBXJX9XTWTXJVVF9ZJPQWVOENOWGDMSKAPHMLMQGXXH9LTWHL99HGXTRDFR9ARYLBNEHTXJJOHRUAADM9CLDENRBWHBQEKH9JMVONHRZDSWW9IBNMYEZUSJAUWKSYPTCLISOBTEDNZAM9ISQYFMQENIEMDS9TIXGRQ9XZZSXPNISOFYVDQFVLNJVZYWZTMSLKTGJ9KIWSQCRBKZCDNMOLVPRGSOWGCLCUTAFMXQFQUTVNGHYYITAVABDINXWPKJQPODUKOMHEVBYPYPFJXPTDOLMAKPPUYJFQNQCAHOVPJK9UQTITMBHHUKWIEC9HYLGCZIADKQLV9GQHSGHMUEDJYDAEVJZA9BHSTMWVIVMJOYPLWEAOLRHRSXIJYTTQEFWRSXOGYSCFXOCXQJFVGJSNAUIRNBVWK9QDCGYQQWPKFAMBNXGTIHDJNSNZXRQSDJAIUF9UQY9HWYJGDHAH9UWUSAPEQADUCPHOVOCJGWFGDVFOUYOQXVWPVQCLJWYM9NHJQYCPTLGFXQOSJNHBKLTKHHGFPYXZEIOIAHWMQ9ZZZVBCBE9MIKJPOB9GOMWVSASBCFREOVIP9OHDQGVPBDJJPJHKECVOWKEXGWIGLZNFAFWFVJNXDWQKCWLPBQDZHLSKKC9QDNNDSOGMFDW9PUYEQEXRPJTO9XQNUFCFZBLNYJAGFLJSZKLA9DSQOOHDUDVKXDBNOKVNDXJEYCKYGOSYKAADXK9MRQMZJTKZESBRFINQXTQNEDYXBPVUQHCKELFZRVQFAYT9RHNXFLIPAVVOAPXSVHOZMFKRLMSLUOKZ9WOAIIXOGREMQNJEDIEAXNRMYJVWMPTDHUDCNYXWOONDKQPNNYPVXLXEDZKMJIVHKLCLMHVOMVOOLKNCOM9TRNQNVCGPIAP9LMOUEIUMK9XAHNKIYRVTMLIKTZMURVCNHKVQYPFGDFP9BGGTEGSIJPWBA99WCRIGOKTXHZIWPRCHRINBLRQMGZBLXXFNMKHSOYZBPJBBALUCARASVGUSWDOPAEONUVXC9NCKWKVCCUDBB9PNRQXGAK9DSQDIMBWVERXTCHMSSMHJTSCLJJB9CSSANZDQQFRRGLNUKTQIHIYHDVBNQRYBAJIDOYSMYYOJYUAZCWDZIPOFFE9AHICXMTQELNBWKPBXQUOXBFHYIMMLSGBATONCY9IAIKPGEG9KHCBUVGXJLSDGVJSUI9GBR9WDMFJNZWXLLPVNXFYFPTWRBNKWVHGJKKUBWYWAYWBZUEJEDDGLXHVRXRBMFWQVGBNALNNHGPGGIWLJHSOX' b'YYKM9AOPBSOSKZJRE9LIUNGFEBPWAK9JQD9LNKVLLOBVYTDQ9QMRNWJHWGTBFLCCYPQ9B9YMJMORDVGDCCVYAQOYFVGZKYUKXTLLUVWNRKIBYZEQFLYRWYRZNWKJAGVWO9VDRSYCAOARINNIL9EQKBREAGEZMBIXSZKVWRRNRLUYAYYUZUYHW9DUJJKJQVMJCPZFBLAURYJGZLT9ZHBLNUQWE9YVJFMWWZNJRHFSPVCQKJMWUCYPYUBHA9QEPCFAYWMGQOFDLZXDQSPYSSDL9MKJAPUGQWGAIRJC9MEYNTMABQTKVIHLSYSNSWAZGJL9YLIZWIO9G9LNRNENQHVZK9YXNQTJSFIJQPLVWWCJ9UTEEYGVFJVUVBJPHKBZACPVQFQCQAVDV9BUTXLFQSHIXZTEONSVKECHCVICRRUZGIPGEFMGUK9QQOPKMYHTDPIIKKDELF9DGSBBEHESJETZSPYTXSAPYA9ZSRKHECXXT9TTKSRIMRFKBBHFKQIYIJGJNSTZRGORHZLVEVLGGXTUHBEDGFIEVFZBQDCNJPQQ9DXMPP9KJD9PBZWKUT9ZPYW9FHBSSNSVTTGHSEVIHYFSUCIRDXSHWCOOGPTTJCCFNHYLRQHRQOBVNUNROWRSYQATJCSSYUGZ9YWFNJHIQNZMIGYKPDFR9JXMAJHQIR9PEWZRHYMOVJNQUXHKNRZEIJMQOZIQVOUSNEQRCYEIAVMHHUA9XIG9CQSBYCDQGEHHZPGSQCHY9OIBBSHSGTORMXIUAXERVPBZ9OGHBCDRXOUFNFJDKALLQOQFMWHHIPJSOAQTHUUFJWCTCROCFSYLOBHIYWCFJQHGWSGGKJRSKZGNUBDMGQZZM9SEZQXABXYFROYUYOHJEPPGCLCWOTZZGYVTBZH9AWPCVGILCDUWRQVLPDEJLVUKNNKBFFXSMVTAIZGBBJMMOAHGLMASBICFUQKWAKHEVNDQPNHDXSJFYGQOVWOKTWDSRGWCWNF9KP9VFOCTED9LIDRIPBLBMWUGRUIPENOFHSATAKHBRHQFDDEOZOZSDZKZWYNWDXVEMRASWCVMFNESLVUIFQNXXDABDGBBUICOZRAADRKQHRYRD9PVTWAETJCAOQIRNZGSULUWMZIVQZR9WDZVBAQXWBFPQRINPKDHGIMWMEOHOKODFSO9DSEZOPAWFLIYBUZWP9OYSTWFNKEFWYGPUTEZOGDKMZCQOYNTEONUSNSBNBMMPFGFTCUID9AELBVGZHYTJ9VSUQLFZDYYOCBMFYHFNFPOLUHGTLFXRWD9JUHFTU9DMSALSARRPYVHDEQTGY9TYTRUHD9YWCZFUTNNJPPRSZPPARMVKWVRMFIEGVJYXEMQTCDGZPAFHNIJTNPZYVGT9RQWKBZZ9CKRKAFMKGDKXGJUZHMDNWUPZYLDDVSORPMCCDLPGIIIYAVDLJODEVRPQIA9JLSEYQTIGDTNGYRNVIQBFBFLYVHDUORTCFFIWOBQJXQ9NUXAHI9TUVR9SJKTST9MGJIIBGDIFRELOHDW9MXPARDLG9WQWLIC9TTHVOSQ9FCAFDCSUHHISCWVJNYWHKVMPYBKVORHRGVY9PDHXPNDXIMJMYECYQZGDT9DANTQBJPXHN9MG9MDKJ9EJIDQZFLJX9VPACAHZUXMBMPRUGNHBXFCGBDYUWAIPFVAMQZYMLESKEEIKFWQVPJRBQBCDOYVSUFTONAIHMIUEVPXTWUYADPQLMBLKWCYXETFVLTZZATEHYDTHSDXAJMQDLKYNQNUAZBVYRLCVKAOUWA9QHXK9AXYFZGBUAZLVZGLVRKSHVRLXTYKMPDCZURJOSTHVJFCKIXHXXQQNCBTAEXUVMKMKEQVUPOEEY9LSTKT9XNJVJPRK9ZDUFQWTMJHWNMTTDRCRMFRXUEZMYXLQEAQMEV9MBIORUONCARJVMCDIR9PIOUJUXIDFY9NHCENUCVPJDIKHIRVRFPGKDZSIGZSBZGTRWAXLRFQLESYXKUISYBTWGZPAVNIKVXLYGINAUMZSJAMDRM9LVAXXCBSOBXUAKFAPMVAXDPFZTKWQCEOKBKAJWELYR9ZEWOTTNFOLHCNUPNMJO9CBH9HXTKFCSXMGBVHY9QFLDFNYMGQUEOXMEPBZWTOKHUMFIJKLUMYPZJHNKIBTRCDSNRBFOSPMDMYCRTBQJZZASRRNIOZTAZ' b'JZXMMJLJOODDZHQLMRVW9FNQHWGIXOWXW9CDZMZESYXSN9DGTHFGFOMZERPNHVE9VLYJRSSGLYMPTXAS9WWJWIUVCTU9GWQBL9WLXWNWXMDLSSXATMFRS9KNNJIGIJNSGYUMPNUHQTWNPCGISJWXTKSVKTCWKR9PCCYQUL9HCOFMHMVFYIPH9BENPKVLDU9RIDXTEWSVPMCXPCQ9ULMYFLHNOZVXGJZPIMQJPXAGXSOIOPYYVGDRVSGEBZJGTYTBLRKMQ9DANLRBLLWFKXCIELBTHYFTJTYEWVIEIQKIXMJAEFWRYXYDE9CCVGQCQUUOKZJ9BYNGIBOYY9CVGGIBIUPLMMFCFEPDTHBKVPNNJBKZJWDDQVZFXREWVNLDEZMUJCOXP9SZDFLVWJDHOKGIWGUXXIAMYUOVDGKWQGFEIHFQAWVELDWKCG9FCKVQ9WGLSHERYCPORNXISPGAYBNKXXN9LSGMU9J9NUMMXARUBKBBTFBJMCUWGNOQCGOMLKYUPTKJHMRZCZC9PBHJEBPQJMSJUSWZVTGPYSR9GTASEIHLDPSPQOQJ9LZOQRPUHNJYCFRMVURJEXQSLKHQECVJ9J9ORFVB9QVBGSRCJTDKJJZWHDDDERTYFHDSJYAQEIIQKJT9MJOYXJHANHPJD9ZBEJHPGHVHTBLRQWQSBNLHUDQUHDBH9UP9LURGHMINB9YHIQTACNDCNXDDURRDJMYUSMFMYX9XWD9DCRCKFEYIWPESUPKRNVKPTORTHHZUILKBYRCSADDFNEJ9HQEZPHHYWDJLDXMEMMDEEHUJU9AGF9USJLKWRZPBYIICMPSJXNMVPFEDILRMANTUULXXHU9L9FNVTIB9ZUGXTLICOQUNIWTGFHNMNNUMOBMKLIWLVHBYKMKSSCIDO9TMAYERDGMUSQTNPUJLLAYYQT9HZTNWOXG9WYUNMFHXGXVAQHFHDXEEEXAASFOSARACI9HCWYTKJJFDLQUJ9WBJCWQUJCCHAWANLTZWZBDSIPLOAGNPPHJMONDSZ9AFQTPYZSKCZEBXRGUKPEMVXU9CIIWIQVTKSNBTOFWLDEPFFQCANZ9JCXXWXIWNCWQZRQQQLPYSWKL9YGNEQUXYOXYLZVRIQ99BQJJUOWPPHGKSXMRAZMOMSMKOXOFODLQAPHJPFY9VWNMFGWODDMWCBFRUMFCNSAGVNGIODRFVWYDWSOYXCMCCKIWXJZIL9TFPBOWEW9ORIZOYKDWZHVEKXZURPOUHLYSOIEKKXMIRCLXJSHALHZO9ZPFID9GBODDJZPPMWCMWPIWYTMAPDM9JUNJCJMVHDPBCCRWJHA9IQBTZHQKUUROLCSRTIAROZQPJXBCLYEP9H9PGSVGJVHKIAWRZDVCZIXUGHONGJ9LEHVNXHZNAIPJJZVEWJOMOUFJZSHEBXIZVEMKLK9IFJKDHUXTZD9DIYVPYPTVGBIGINYJVH9KQOWWCEOQBQIMKOC9FTAUMEHYMQEYKZFBGHZYLCDJCGXV9DTKXPZDHIFONHSDSRCMVXSRIIWFXLFB9VFUOEYYKEKGAZJVJHHNYEJCMQOGRIBKJVAHRPTTUALKBETUYDWSNT9IYEVMDYR9SJGMLG9EIKZYDIUXWRXJSZCOMODCRZJTRWTSUHSPNJUASRTDQBEJBONIPKHUSHVVZ9TWZNCVMJVJASSBMX9VAEQJTCW9DBEQSDBUMQOYWIYTKFFBEWHGUAWAGMPMGYUFUQDCNORFBFUJZPSJQLM9ORMRBFZUZGVZTNJHC9FZPICGT9WOHJANEPPM9SNZBEJRDKENYYVLDCLCZIAHWVNAJIGP9MQAQLVHEJKQGSOAGFPYOKPNEBQYVVVQCBTDZXIIXZDCSFHWWTOUTWKSBVMUMWCSSQWHCMWKJGTREMSMBP9ADHFLKAHNFQSWUOMOYARDBPUDZDPGIGRAGBZQJAMHDNU9GDXUGQHDBWXKGZAAVXSZXUWHEKSSRRBXTGHUKUZPVCBSKQNDCOTWVXOKBFWKULVXRLUTNPRULDQJNZKAEFAOX9EUZSRJPPRFO9PDQUKXUNLILADQDGMMYJACOUZCKEK9PDEIMNBDIBGMTABALXJBHQTPXRVXUQDJBLUA9QF9AEQHA9LMUFUQQQOUSMQUGGPSLBWTKGXGVHPAX9SI9ITDCMYWHRONTXMBRUOGGPUYLDZFOGZC', ) self.assertEqual( key.get_digest(), # Note that the digest is 3 hashes long, because the key # is 3 fragments long. TryteString( b'DMQBKFFAGMHSOGLQDYOGTZ9G9NZYSE9JPEAHV9WGAKENOWLVGZJLBIRIKLKQINKKUQ9JDJYGPJYYDTTMW' b'TIBCVWNGKLYX9UDSNQK9FWFODLGWOZREMZYWYRPILH9LYLOSRJSZQKKXBBEGVRJYTFHWQXRAMPMRJJT99' b'KXGAKZZZVNRPQ9ELDPAMOMJOIGOKCRWHLBIURDRVSWLEQLFVFXKCSNSTWQJDDV9YZFHBWDEIXM9VGGIFD', ), )
async def test_generate_single_key(self): """ Generating a single key. """ keys = [PrivateKey(self.trytes1, 0)] mock_get_keys = mock.Mock(return_value=keys) with mock.patch('iota.crypto.signing.KeyGenerator.get_keys', mock_get_keys): result = await self.command(seed=Seed.random(), securityLevel=2) self.assertDictEqual(result, {'keys': keys}) mock_get_keys.assert_called_once_with( count=1, iterations=2, start=0, )
def create_generator(self, start=0, step=1, iterations=1): # type: (int, int) -> Generator[PrivateKey] """ Creates a generator that can be used to progressively generate new keys. :param start: Starting index. Warning: This method may take awhile to reset if ``start`` is a large number! :param step: Number of indexes to advance after each key. This value can be negative; the generator will exit if it reaches an index < 0. Warning: The generator may take awhile to advance between iterations if ``step`` is a large number! :param iterations: Number of _transform iterations to apply to each key. Must be >= 1. Increasing this value makes key generation slower, but more resistant to brute-forcing. """ if start < 0: raise with_context( exc = ValueError('``start`` cannot be negative.'), context = { 'start': start, 'step': step, 'iterations': iterations, }, ) if iterations < 1: raise with_context( exc = ValueError('``iterations`` must be >= 1.'), context = { 'start': start, 'step': step, 'iterations': iterations, }, ) current = start fragment_length = FRAGMENT_LENGTH * TRITS_PER_TRYTE hashes_per_fragment = FRAGMENT_LENGTH // Hash.LEN while current >= 0: sponge = self._create_sponge(current) key = [0] * (fragment_length * iterations) buffer = [0] * HASH_LENGTH # type: MutableSequence[int] for fragment_seq in range(iterations): # Squeeze trits from the buffer and append them to the key, one # hash at a time. for hash_seq in range(hashes_per_fragment): sponge.squeeze(buffer) key_start =\ (fragment_seq * fragment_length) + (hash_seq * HASH_LENGTH) key_stop = key_start + HASH_LENGTH key[key_start:key_stop] = buffer private_key = PrivateKey.from_trits(key) private_key.key_index = current yield private_key current += step
def test_random(self): """ Generating a random PrivateKey should fail. """ with self.assertRaises(TypeError): random_digest = PrivateKey.random()
def test_get_digest_multiple_fragments(self): """ Generating digest from a PrivateKey longer than 1 fragment. """ key =\ PrivateKey( b'LXZFBGXJCSEHJFVQOJBSBDWVPNHSTKGMNZQYVFKAJTFSIVMXQIRIQYHRCFVDKYCCVK' b'VGPRZRZUXXUIV9ZPJSWXZ9FUHBVYFGNWTGMX9LXPTALCML9ASKROTEVORSSQZHWEMF' b'UPNFQCEHXTEALKZVSHHALJXAPMGFASSHHCREWFCSYJFWLSKJZOFLLMTGWSSJZLJQOH' b'GQAHICAMRHHWZAIAALSUDPWBSRILGBQILJQUGIIOCNDGSYUSXRVPAZFKARRXVBDQLW' b'YZFR9FKIDUBODORNUXBOKDURIFHBRLTSIWOTUVQNMKXJGWYEVXCTKVQWDXJ9ZPLTIH' b'DEW9ERC9EFNKCWBNSUXGYLPG9PYERCIHBWNGTHWRSNNYPADKIUWMJVNWALHCCVSMYZ' b'GFIBFUXULLAJNZYQRLVYZHOQEPEURBITZIF9XWSOTEXEI9DBCM9VZPLURONGEIXMVU' b'RPZRUSAOLZPYMIXKPV9SWSXSPQSRALB99IVDBFXJC9SPXPUTMKTEKKJMPNC9SFDGIR' b'BVMRQKGG9FWVZMWSCLGANOQENXZZVHESO9TXRRZGGKVGIJYZKULWSBWYFALOXFWHFI' b'TTQWIQGJSEYRH9CIYPTYOERARZQVRUTIBR9QTJUIQXZ9FFKGPBBWHUVIGGKSXVBCUP' b'YGESTDRCVKDJLHNXJUTGUFPOTTTDYVMOOE9DDXAAJVSULTWCQOJBAWKVZSLKGAEYOV' b'WXNULJZPPJGJJXMIEQWKPHBHWZEUJYOZ9FXMKFT9RMBTXTPAKAWMJTPZVPT9SKCRHU' b'KOSFPQWLIFQYOVOBISWFKARPKR9JZMQOXHLNZVVUQGZVAWKMI9KZBGELPCCYENZUKX' b'FVGZJTDZZIPTJESWSFJUSRU9IHGEJXSHBRRSJZAHCK9STAKIDYTVXEVHZFKYXUSTTM' b'ERPQGBIINLMXHZHVWGFKBMQXULTONGQPLHMUACQSIVCYMHKGSVWEHYARSVECJMWBWW' b'DLSGVTPZAKCRYXYLEEAHOUNVLNLFPXGNRKAZSSLVTVBDTBVCTEBW9FP9IROYSINOFH' b'PZNYPHX9CVWDMTYXUFLHR9R9MCI9BGLIBHKCDENREOEPXCLMSYQZDIDES9KIURUSJQ' b'JL9IEUAOLJYKJTLE9UYVBSPRAGMTQYKOHNWGHXUBYZAOMBBTMGOEXKJEYMWUSSIRDO' b'IMHNTWWOKHYVDDKOYFTYFOGAZ9MHJVNKRYGFXYEUFBQPMYFCFBAIXXIFHVTPRPDOXS' b'QVIKTSNONSNQKYIRULCQRMEOKSAXTDGJGSZKUPLWJITS9ZQOLEFPPSDSSA9DHGDJMT' b'MAETSNDB9BSIVVPYIKD9ESAYOSYJSKJBRJOJOWBEJWSI9PJT9BYJDROWYHAZJBLUJX' b'GAZGUYJKTRJJIRCRUWRRKVDAKMFGHJQKYDENHJYNLBUTVNKNFYYHEYGPLVGGPLBWZR' b'HUMEHELSDRJDLRIYORNSLNOWCDBFKPESBQSNSDZUGCCJHLJJEHUWGOYBBAFJNL9QCF' b'ROADVYXELOOO9OFRM9OMJYS9VZLVUONKTPXJBHKYMUDSYKHUJBJCNRZXQBYYVAHDJS' b'WOVPGWQUUWKHFWI9PTCKFROSFNSZUKBBNJ9NZWWGXWEMSLTQ9YJFBPBFEACG9WLTK9' b'MNBNEYDPCLQVRIHMCIBEHNTQOXQRUXKQFCJYHJREBTSYAHDCWJBDVKAKKHULI99BIS' b'9IVUDVCDFWTUUNFAGEKFGTQBEIYYUCOLIBTUSCNTQCJXZWCHQATRPOTJP9LNCEMSVO' b'BNGMYVXTJWWLFXPDVNOIVIMBNBPEIGJCONYPLVSHVVDNOPMQMINRXCWFCOSYMDV9S9' b'ZA9YFXAAVRWXWSAQLYTKKZAZEZCTWVHMBG9HTTJXYJSGBUJZXRPDGHBQIHWQQVRPNN' b'WAYISDZCLKWZLPLUEF9TKCCA9YBUYQBZFVLVDRZ9AHZAEQNAQ9IQWKKXCMVDDJRBKE' b'LJHVTLDUUMQLDXYTOWYKPMCQW9YBGD9VUJLCJWQEN9RISZKTNNCDLXVFMNGNBCDWQG' b'WRLPWKALPJDRDZFCLTONVQUZPUISJRVYOBVCXEICEQRNOTXMWTPTEHAYROEVQNPO9K' b'IFCIBXHL9MJM9JYOXYDKZEF9DLURXGXPQGVUZQB9EKPLBQXQQYCXBYUBAQVCKUJDJA' b'CCXQINZTZWMSEBNGBDORPZKMVGGZSPIUKLRAMXGKSIULOJBRBTGXWEVMWQEALSZVLC' b'MXQIKZIIMLSVRDGIZWBVZUUIKGYXNTFNSLBXEQKBBUOYPLSDCGJPTVGYAGDD9JNVZY' b'UUXWUQJ9DUPDGWCXOEEVVQPOZLRGYBMPAWGMKNUCMWDIKIHHAPPN9BIKCFHDEORXRX' b'STBFGBCRDSPNBZDRZHFSMXNXHSKAZF9XYKOWFNTGUUHMUOWXHAROKHZOLWECDVRDXO' b'RDHANPIYZFETYBAOPPHTMTZMLDLQXZVYGXYKUDUNFWVPESWBFRTOJRRCPMKIBTQHFG' b'SPATWEXLWRFFQI9RKZBY9RZDVMVZCCWTS9PNRCTP9FRCGPOCVUJZIRZPU9WJPBHDTB' b'DSZSGI9HYHRBEBRQECBJEIZDXZOGGYZUPSEQLMQBTRQANDWG9RWGXAUYPRBSJRULMS' b'BJVPIFJWQPWEMY9YHDULM99VOIIDHRJQMHCZQAZCITZPKNSOBGSQDLOVWCZOLQEHBD' b'VIMDRWWXY9LWHTRBWUASPTMA9UPRILCALBIUFUELQDAKSD9WADUZESCBNNNZCQLXBI' b'FCNGGUBZTWSKQ9QHQLE9LBLWNKOQJYNSD9SRASRCGLICBCX9VNAGXAP9NFJUGWCZAI' b'QLBCQKSLFGXDRMEXKAHLMOE9VKFRFKCBLRNZVIARBRKEZMLEKIMMMGEJRLWMJFCLHT' b'LMXYYVKJFX9M9HIDHLBVFUKHMJRJOCWRHHTGLXDEWTTFGSMUHVOK9VDPOABLMZQGGP' b'FYIDMQIELYYLOCIXYAASYUFGVQDCEESUEJWOJCNNRMFKHXFCYMLXIEFMAHJRZ9TBZF' b'BSZOCDJPUPBLNBTNYHIAUYQKLPMMNNDEIPEFUAMTMYMXCENQCIJRWWZASXIHCMYLMB' b'GYRUDEYCYJPYPOEOAWENQLKMGCFMLVRJYMCHEYWBJZMOLSATAVIORHIEAHVPDEKPZW' b'KTPPGTTCRWJTDKABHHETSYLXJOQXJSYKMT9OJEEIOKAYWTLIWUTSAYZ9IDNWJLKKOY' b'VMGCJQIMROINJVPRKUQJCTDLFHZQDAOMDIAJYY9NQ9WZZIKHBFLYXOOWRHDRGJYNCD' b'BIEYCBAZMQNMNBTLGOBUTBMUDFOKTZ9BCBPOVNJXDHGMGITUMSPKAQ9R9PFCNCKPDP' b'HZLVTQCSKVJOIEYXUEOOIMWVIKKKNRNENRDFUXP9WJNWXJHBJIXPJQBRNOHOBQGKSY' b'UKCAMZKLWJETFNZGYIWBLARTNYHWLUBXRBHOO99RECDLSWBOOVJ9OEAWKPRBVWUUK9' b'ASGWAIS9CIPFAJRXFEDCSSMOXFASWKDZZKRGMBLD9GU9CWWBXW9DEU9IKENDNYEWOP' b'ZRUJUEK9YMNERGQOXUBGVNIGWDXXUVBKMSQWCGSDSIMKEFOBLIGPFCPNQ9QLNSLK9O' b'NMGNJMRI9KUQNTSMFGXAGYJVUQO9JDLDBUIQQJIEZCTFJS9VIKIIIDSQFBBAGUGOTA' b'VO9WZQXKBJSZBZDUTUSZ9GZAZQXTUHYTLCZQLRMURZLTYMNBPE9QFZOUVRRDRAEEAI' b'9OVJXPEWOWEESPUKMBGGBAYLLTFLBPNM9VVYNWTCRCIHEKKGU9RGQWGKEREBUXTELB' b'XTP9VQQMPGZHIJFBIWE9GSPTJHCMSKE9HXU9XISYRVCFXSQZO9CSXGAZUBINTCRKFH' b'OPFXUHDTWAZVMQWRZQQVMUVACIIDETVJLUXY9TEJGMWLGMMJ9SWTFNUHRI9SFVHBSJ' b'J9MRWCKFRJJJL9DECJL9XDHKWHYHLMSSXRIBBHC9PNWKIIQYITKUHENQWBMNALETH9' b'F9KIWDJXHPGSGYIKLJNQEZGXZJDKWCNGPFKSATLYNNYRCKCBBCEH9ADIZICTXOUKSS' b'WAPSHQKIBMOZKIPHLNHDSDVNRMWIFDYATUHFJSZFGYCSRKFERXBPVWUU9WKFPHAZJ9' b'LQCDSMZJWQGMFTHZNYEFBTNJ9TCNWMEZWQVRYFBVIWNSWDJDVJMFCRRDYLBYECAFW9' b'KXMX9LRLWLFIGAHBGF9YJODGYKULATHVYBCHUQTDZXKUKGVVJCDBJUJKRDN9EKCTBY' b'NQMGSIPDCTJVCX9INTPUZ9BXITIPKLHO9ESBOFSWLYNYXPCWRQCEOZTM9UYAAZSDHB' b'9BTFJNLZA9NTCKSAIZ' ) self.assertEqual( key.get_digest(), # Note that the digest is 2 hashes long, because the key # is 2 fragments long. TryteString( b'XCLECABPSBFYWJQNKXJAHB9QPJLAIJJBFUQNGUWDNVCVFQWXECVLYXUYHKW9XQECWC' b'IVNEDMSJWL9PDEQGVKTYZQXPAMHIJGJXQIJJRSLPCVNAUUYJSIDOHYXUNDQYVBPYDD' b'EZMFJQRAIMPVATMWLFHJXAISQTQYWX'), )