diff --git a/.gitignore b/.gitignore index 2fe3678..78eddc5 100644 --- a/.gitignore +++ b/.gitignore @@ -7,6 +7,9 @@ PyOTA.egg-info/* build/* dist/* +# Sphinx documentation +docs/_build/ + # Created by ``setup.py test``. .eggs/* @@ -18,4 +21,4 @@ dist/* # Note: For environment- or IDE-specific metadata (e.g., .DS_Store, .idea, etc. # you can add these to your own "global" .gitignore file. # https://help.github.com/articles/ignoring-files/#create-a-global-gitignore -# +# \ No newline at end of file diff --git a/MANIFEST.in b/MANIFEST.in index 7b92f7f..7e586bf 100644 --- a/MANIFEST.in +++ b/MANIFEST.in @@ -1,3 +1,4 @@ include LICENSE +include README.rst recursive-include examples *.py recursive-include test *.py *.csv diff --git a/README.rst b/README.rst index 4340460..997fd9b 100644 --- a/README.rst +++ b/README.rst @@ -1,6 +1,9 @@ -.. image:: https://travis-ci.org/iotaledger/iota.lib.py.svg?branch=develop +.. image:: https://travis-ci.org/iotaledger/iota.lib.py.svg?branch=master :target: https://travis-ci.org/iotaledger/iota.lib.py +.. image:: https://readthedocs.org/projects/pyota/badge/?version=latest + :target: http://pyota.readthedocs.io/en/latest/?badge=latest + ===== PyOTA ===== diff --git a/docs/Makefile b/docs/Makefile new file mode 100644 index 0000000..b030706 --- /dev/null +++ b/docs/Makefile @@ -0,0 +1,20 @@ +# Minimal makefile for Sphinx documentation +# + +# You can set these variables from the command line. +SPHINXOPTS = +SPHINXBUILD = python -msphinx +SPHINXPROJ = PyOTA +SOURCEDIR = . +BUILDDIR = _build + +# Put it first so that "make" without argument is like "make help". +help: + @$(SPHINXBUILD) -M help "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) + +.PHONY: help Makefile + +# Catch-all target: route all unknown targets to Sphinx using the new +# "make mode" option. $(O) is meant as a shortcut for $(SPHINXOPTS). +%: Makefile + @$(SPHINXBUILD) -M $@ "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) \ No newline at end of file diff --git a/docs/conf.py b/docs/conf.py new file mode 100644 index 0000000..d719762 --- /dev/null +++ b/docs/conf.py @@ -0,0 +1,172 @@ +#!/usr/bin/env python3 +# -*- coding: utf-8 -*- +# +# PyOTA documentation build configuration file, created by +# sphinx-quickstart on Tue Oct 3 20:46:23 2017. +# +# This file is execfile()d with the current directory set to its +# containing dir. +# +# Note that not all possible configuration values are present in this +# autogenerated file. +# +# All configuration values have a default; values that are commented out +# serve to show the default. + +# If extensions (or modules to document with autodoc) are in another directory, +# add these directories to sys.path here. If the directory is relative to the +# documentation root, use os.path.abspath to make it absolute, like shown here. +# +# import os +# import sys +# sys.path.insert(0, os.path.abspath('.')) + + +# -- General configuration ------------------------------------------------ + +# If your documentation needs a minimal Sphinx version, state it here. +# +# needs_sphinx = '1.0' + +# Add any Sphinx extension module names here, as strings. They can be +# extensions coming with Sphinx (named 'sphinx.ext.*') or your custom +# ones. +extensions = [] + +# Add any paths that contain templates here, relative to this directory. +templates_path = ['_templates'] + +# The suffix(es) of source filenames. +# You can specify multiple suffix as a list of string: +# +# source_suffix = ['.rst', '.md'] +source_suffix = '.rst' + +# The master toctree document. +master_doc = 'index' + +# General information about the project. +project = 'PyOTA' +copyright = '2017, Phoenix Zerin' +author = 'Phoenix Zerin' + +# The version info for the project you're documenting, acts as replacement for +# |version| and |release|, also used in various other places throughout the +# built documents. +# +# The short X.Y version. +version = '' +# The full version, including alpha/beta/rc tags. +release = '' + +# The language for content autogenerated by Sphinx. Refer to documentation +# for a list of supported languages. +# +# This is also used if you do content translation via gettext catalogs. +# Usually you set "language" from the command line for these cases. +language = None + +# List of patterns, relative to source directory, that match files and +# directories to ignore when looking for source files. +# This patterns also effect to html_static_path and html_extra_path +exclude_patterns = ['_build', 'Thumbs.db', '.DS_Store'] + +# The name of the Pygments (syntax highlighting) style to use. +pygments_style = 'sphinx' + +# If true, `todo` and `todoList` produce output, else they produce nothing. +todo_include_todos = False + + +# -- Options for HTML output ---------------------------------------------- + +# The theme to use for HTML and HTML Help pages. See the documentation for +# a list of builtin themes. +# +# html_theme = 'alabaster' + +# Theme options are theme-specific and customize the look and feel of a theme +# further. For a list of options available for each theme, see the +# documentation. +# +# html_theme_options = {} + +# Add any paths that contain custom static files (such as style sheets) here, +# relative to this directory. They are copied after the builtin static files, +# so a file named "default.css" will overwrite the builtin "default.css". +html_static_path = ['_static'] + +# Custom sidebar templates, must be a dictionary that maps document names +# to template names. +# +# This is required for the alabaster theme +# refs: http://alabaster.readthedocs.io/en/latest/installation.html#sidebars +html_sidebars = { + '**': [ + 'about.html', + 'navigation.html', + 'relations.html', # needs 'show_related': True theme option to display + 'searchbox.html', + 'donate.html', + ] +} + + +# -- Options for HTMLHelp output ------------------------------------------ + +# Output file base name for HTML help builder. +htmlhelp_basename = 'PyOTAdoc' + + +# -- Options for LaTeX output --------------------------------------------- + +latex_elements = { + # The paper size ('letterpaper' or 'a4paper'). + # + # 'papersize': 'letterpaper', + + # The font size ('10pt', '11pt' or '12pt'). + # + # 'pointsize': '10pt', + + # Additional stuff for the LaTeX preamble. + # + # 'preamble': '', + + # Latex figure (float) alignment + # + # 'figure_align': 'htbp', +} + +# Grouping the document tree into LaTeX files. List of tuples +# (source start file, target name, title, +# author, documentclass [howto, manual, or own class]). +latex_documents = [ + (master_doc, 'PyOTA.tex', 'PyOTA Documentation', + 'Phoenix Zerin', 'manual'), +] + + +# -- Options for manual page output --------------------------------------- + +# One entry per manual page. List of tuples +# (source start file, name, description, authors, manual section). +man_pages = [ + (master_doc, 'pyota', 'PyOTA Documentation', + [author], 1) +] + + +# -- Options for Texinfo output ------------------------------------------- + +# Grouping the document tree into Texinfo files. List of tuples +# (source start file, target name, title, author, +# dir menu entry, description, category) +texinfo_documents = [ + (master_doc, 'PyOTA', 'PyOTA Documentation', + author, 'PyOTA', 'One line description of project.', + 'Miscellaneous'), +] + + + diff --git a/docs/getting_started.rst b/docs/getting_started.rst new file mode 100644 index 0000000..6da3a62 --- /dev/null +++ b/docs/getting_started.rst @@ -0,0 +1,84 @@ +Installation +============ +PyOTA is compatible with Python 3.6, 3.5 and 2.7. + +Install PyOTA using `pip`: + +.. code-block:: bash + + pip install pyota[ccurl] + +.. note:: + + The ``[ccurl]`` extra installs the optional `PyOTA-CCurl extension`_. + + This extension boosts the performance of certain crypto operations + significantly (speedups of 60x are common). + +Getting Started +=============== +In order to interact with the IOTA network, you will need access to a node. + +You can: + +- `Run your own node.`_ +- `Use a light wallet node.`_ +- `Use the sandbox node.`_ + +Note that light wallet nodes often disable certain features like PoW for +security reasons. + +Once you've gotten access to an IOTA node, initialize an :py:class:`iota.Iota` +object with the URI of the node, and optional seed: + +.. code-block:: python + + from iota import Iota + + # Generate a random seed. + api = Iota('http://localhost:14265') + + # Specify seed. + api = Iota('http://localhost:14265', 'SEED9GOES9HERE') + +Test your connection to the server by sending a ``getNodeInfo`` command: + +.. code-block:: python + + print(api.get_node_info()) + +You are now ready to send commands to your IOTA node! + +Using the Sandbox Node +---------------------- +To connect to the sandbox node, you will need to inject a +:py:class:`SandboxAdapter` into your :py:class:`Iota` object. This will modify +your API requests so that they contain the necessary authentication metadata. + +.. code-block:: python + + from iota.adapter.sandbox import SandboxAdapter + + api = Iota( + # To use sandbox mode, inject a ``SandboxAdapter``. + adapter = SandboxAdapter( + # URI of the sandbox node. + uri = 'https://sandbox.iotatoken.com/api/v1/', + + # Access token used to authenticate requests. + # Contact the node maintainer to get an access token. + auth_token = 'auth token goes here', + ), + + # Seed used for cryptographic functions. + # If null, a random seed will be generated. + seed = b'SEED9GOES9HERE', + ) + +.. _forum: https://forum.iota.org/ +.. _official api: https://iota.readme.io/ +.. _pyota-ccurl extension: https://pypi.python.org/pypi/PyOTA-CCurl +.. _run your own node.: http://iotasupport.com/headlessnode.shtml +.. _slack: http://slack.iota.org/ +.. _use a light wallet node.: http://iotasupport.com/lightwallet.shtml +.. _use the sandbox node.: http://dev.iota.org/sandbox diff --git a/docs/index.rst b/docs/index.rst new file mode 100644 index 0000000..625e1ba --- /dev/null +++ b/docs/index.rst @@ -0,0 +1,13 @@ +.. toctree:: + :maxdepth: 1 + :hidden: + + getting_started + types + +.. note:: + **🚧 PyOTA documentation is still under construction. 🚧** + + Follow https://github.com/iotaledger/iota.lib.py/issues/78 for updates. + +.. include:: ../README.rst diff --git a/docs/make.bat b/docs/make.bat new file mode 100644 index 0000000..dbe2641 --- /dev/null +++ b/docs/make.bat @@ -0,0 +1,36 @@ +@ECHO OFF + +pushd %~dp0 + +REM Command file for Sphinx documentation + +if "%SPHINXBUILD%" == "" ( + set SPHINXBUILD=python -msphinx +) +set SOURCEDIR=. +set BUILDDIR=_build +set SPHINXPROJ=PyOTA + +if "%1" == "" goto help + +%SPHINXBUILD% >NUL 2>NUL +if errorlevel 9009 ( + echo. + echo.The Sphinx module was not found. Make sure you have Sphinx installed, + echo.then set the SPHINXBUILD environment variable to point to the full + echo.path of the 'sphinx-build' executable. Alternatively you may add the + echo.Sphinx directory to PATH. + echo. + echo.If you don't have Sphinx installed, grab it from + echo.http://sphinx-doc.org/ + exit /b 1 +) + +%SPHINXBUILD% -M %1 %SOURCEDIR% %BUILDDIR% %SPHINXOPTS% +goto end + +:help +%SPHINXBUILD% -M help %SOURCEDIR% %BUILDDIR% %SPHINXOPTS% + +:end +popd diff --git a/docs/types.rst b/docs/types.rst new file mode 100644 index 0000000..aa9b54e --- /dev/null +++ b/docs/types.rst @@ -0,0 +1,264 @@ +================ +PyOTA Data Types +================ +.. important:: + + Before diving into the API, it's important to understand the fundamental data + types of IOTA. + + For an introduction to the IOTA protocol and the Tangle, give the + `protocol documentation`_ a once-over. + +PyOTA defines a few types that will make it easy for you to model objects like +Transactions and Bundles in your own code. + +TryteString +----------- +A :py:class:`TryteString` is an ASCII representation of a sequence of trytes. +In many respects, it is similar to a Python ``bytes`` object (which is an ASCII +representation of a sequence of bytes). + +In fact, the two objects behave very similarly; they support concatenation, +comparison, can be used as dict keys, etc. + +However, unlike ``bytes``, a :py:class:`TryteString` can only contain uppercase +letters and the number 9 (as a regular expression: ``^[A-Z9]*$``). + +.. admonition:: Why only these characters? + + You can find the answer on the + `IOTA Forum `__. + +As you go through the API documentation, you will see many references to +:py:class:`TryteString` and its subclasses: + +- :py:class:`Fragment` + + A signature or message fragment inside a transaction. + Fragments are always 2187 trytes long. + +- :py:class:`Hash` + + An object identifier. Hashes are always 81 trytes long. + + There are many different types of hashes: + + :py:class:`Address` + Identifies an address on the Tangle. + :py:class:`BundleHash` + Identifies a bundle on the Tangle. + :py:class:`TransactionHash` + Identifies a transaction on the Tangle. + +- :py:class:`Seed` + + A TryteString that is used for crypto functions such as generating addresses, + signing inputs, etc. + + .. important:: + + Seeds can be any length, but 81 trytes offers the best security. + More information is available on the + `IOTA Forum `__. + +- :py:class:`Tag` + + A tag used to classify a transaction. Tags are always 27 trytes long. + +- :py:class:`TransactionTrytes` + + A TryteString representation of a transaction on the Tangle. + :py:class:`TransactionTrytes` are always 2673 trytes long. + +Creating TryteStrings +~~~~~~~~~~~~~~~~~~~~~ +To create a new :py:class:`TryteString` from a sequence of trytes, simply +wrap the trytes inside the :py:class:`TryteString` initializer: + +.. code-block:: python + + from iota import TryteString + + trytes = TryteString('RBTC9D9DCDQAEASBYBCCKBFA') + +To encode ASCII text into trytes, use the :py:meth:`TryteString.from_string` +method: + +.. code-block:: python + + from iota import TryteString + + message_trytes = TryteString.from_string('Hello, IOTA!') + + print(message_trytes) # RBTC9D9DCDQAEASBYBCCKBFA + +To decode a sequence of trytes back into ASCII text, use +:py:meth:`TryteString.as_string`: + +.. code-block:: python + + from iota import TryteString + + message_trytes = TryteString('RBTC9D9DCDQAEASBYBCCKBFA') + + message_str = message_trytes.as_string() + + print(message_str) # Hello, IOTA! + +.. note:: + + PyOTA also supports encoding non-ASCII characters, but this functionality is + **experimental** and has not yet been standardized. + + If you encode non-ASCII characters, be aware that other IOTA libraries + (possibly including future versions of PyOTA!) might not be able to decode + them! + +Transaction Types +----------------- +PyOTA defines two different types used to represent transactions: + +:py:class:`Transaction` + A transaction that has been loaded from the Tangle. + +:py:class:`ProposedTransaction` + A transaction that was created locally and hasn't been broadcast to the + Tangle yet. + +Transaction +~~~~~~~~~~~ +Generally, you will never need to create `Transaction` objects; the API will +build them for you, as the result of various API methods. + +.. tip:: + + If you have a TryteString representation of a transaction, and you'd like to + convert it into a :py:class:`Transaction` object, use the + :py:meth:`Transaction.from_tryte_string` method: + + .. code-block:: python + + from iota import Transaction + + txn_1 =\ + Transaction.from_tryte_string( + 'GYPRVHBEZOOFXSHQBLCYW9ICTCISLHDBNMMVYD9JJHQMPQCTIQ...', + ) + + This is equivalent to the `Paste Trytes`_ feature from the IOTA Wallet. + +Each :py:class:`Transaction` object has the following attributes: + +- ``address`` (:py:class:`Address`) + + The address associated with this transaction. Depending on the transaction's + ``value``, this address may be a sender or a recipient. + +- ``attachment_timestamp`` (:py:class:`int`) + Timestamp after completing the Proof of Work process. + + See the `timestamps white paper`_ for more information. + +- ``attachment_timestamp_lower_bound`` (:py:class:`int`) + Lower bound of the timestamp. + + See the `timestamps white paper`_ for more information. + +- ``attachment_timestamp_upper_bound`` (:py:class:`int`) + Upper bound of the timestamp. + + See the `timestamps white paper`_ for more information. + +- ``branch_transaction_hash`` (:py:class:`TransactionHash`) + + An unrelated transaction that this transaction "approves". + Refer to the `protocol documentation`_ for more information. + +- ``bundle_hash`` (:py:class:`BundleHash`) + + The bundle hash, used to identify transactions that are part of the same + bundle. This value is generated by taking a hash of the metadata from all + transactions in the bundle. + +- ``current_index`` (:py:class:`int`) + + The transaction's position in the bundle. + + - If the ``current_index`` value is 0, then this is the "tail transaction". + - If it is equal to ``last_index``, then this is the "head transaction". + +- ``hash`` (:py:class:`TransactionHash`) + + The transaction hash, used to uniquely identify the transaction on the + Tangle. This value is generated by taking a hash of the raw transaction + trytes. + +- ``last_index`` (:py:class:`int`) + + The index of the final transaction in the bundle. This value is attached to + every transaction to make it easier to traverse and verify bundles. + +- ``nonce`` (:py:class:`Nonce`) + + This is the product of the PoW process. + + Refer to the `protocol documentation`_ for more information. + +- ``signature_message_fragment`` (:py:class:`Fragment`) + + Additional data attached to the transaction: + + - If ``value < 0``, this value contains a fragment of the cryptographic + signature authorizing the spending of the IOTAs. + - If ``value > 0``, this value is an (optional) string message attached to + the transaction. + - If ``value = 0``, this value could be either a signature or message + fragment, depending on the previous transaction. + + .. tip:: + + Read this as "Signature/Message Fragment". That is, it could be a + fragment of a signature **or** a message, depending on the transaction. + +- ``tag`` (:py:class:`Tag`) + + Used to classify the transaction. + + Every transaction has a tag, but many transactions have empty tags. + +- ``timestamp`` (:py:class:`int`) + + Unix timestamp when the transaction was created. + + Note that devices can specify any timestamp when creating transactions, so + this value is not safe to use by itself for security measures (such as + resolving double-spends). + + .. note:: + + The IOTA protocol does support verifiable timestamps. Refer to the + `timestamps white paper`_ for more information. + +- ``trunk_transaction_hash`` (:py:class:`TransactionHash`) + + The transaction hash of the next transaction in the bundle. + + If this transaction is the head transaction, its ``trunk_transaction_hash`` + will be pseudo-randomly selected, similarly to ``branch_transaction_hash``. + +- ``value`` (:py:class:`int`) + + The number of IOTAs being transferred in this transaction: + + - If this value is negative, then the ``address`` is spending IOTAs. + - If it is positive, then the ``address`` is receiving IOTAs. + - If it is zero, then this transaction is being used to carry metadata (such + as a signature fragment or a message) instead of transferring IOTAs. + + +:todo: ProposedTransaction + + +.. _protocol documentation: https://iota.readme.io/docs/ +.. _paste trytes: https://forum.iota.org/t/3457/3 +.. _timestamps white paper: https://iota.org/timestamps.pdf diff --git a/iota/__init__.py b/iota/__init__.py index 9f28d4c..ad412f1 100644 --- a/iota/__init__.py +++ b/iota/__init__.py @@ -28,7 +28,7 @@ } -# Activate TrytesCodec. +# Activate codecs. from .codecs import * # Make some imports accessible from the top level of the package. @@ -37,6 +37,7 @@ from .transaction import * from .adapter import * from .api import * +from .trits import * # :see: http://stackoverflow.com/a/2073599/ from pkg_resources import require diff --git a/iota/adapter/__init__.py b/iota/adapter/__init__.py index 69fedee..5227f78 100644 --- a/iota/adapter/__init__.py +++ b/iota/adapter/__init__.py @@ -11,11 +11,14 @@ from typing import Container, Dict, List, Optional, Text, Tuple, Union from requests import Response, codes, request +from six import PY2, binary_type, iteritems, moves as compat, text_type, \ + with_metaclass + from iota.exceptions import with_context from iota.json import JsonEncoder -from six import PY2, binary_type, moves as compat, text_type, with_metaclass __all__ = [ + 'API_VERSION', 'AdapterSpec', 'BadApiResponse', 'InvalidUri', @@ -30,6 +33,13 @@ __all__ = map(binary_type, __all__) +API_VERSION = '1' +""" +API protocol version. +https://github.com/iotaledger/iota.lib.py/issues/84 +""" + + # Custom types for type hints and docstrings. AdapterSpec = Union[Text, 'BaseAdapter'] @@ -201,6 +211,18 @@ class HttpAdapter(BaseAdapter): """ supported_protocols = ('http', 'https',) + DEFAULT_HEADERS = { + 'Content-type': 'application/json', + + # https://github.com/iotaledger/iota.lib.py/issues/84 + 'X-IOTA-API-Version': API_VERSION, + } + """ + Default headers sent with every request. + These can be overridden on a per-request basis, by specifying values + in the ``headers`` kwarg. + """ + def __init__(self, uri): # type: (Union[Text, SplitResult]) -> None super(HttpAdapter, self).__init__() @@ -265,7 +287,8 @@ def get_uri(self): def send_request(self, payload, **kwargs): # type: (dict, dict) -> dict kwargs.setdefault('headers', {}) - kwargs['headers']['Content-type'] = 'application/json' + for key, value in iteritems(self.DEFAULT_HEADERS): + kwargs['headers'].setdefault(key, value) response = self._send_http_request( # Use a custom JSON encoder that knows how to convert Tryte values. diff --git a/iota/codecs.py b/iota/codecs.py index 594498c..640eb08 100644 --- a/iota/codecs.py +++ b/iota/codecs.py @@ -3,12 +3,13 @@ unicode_literals from codecs import Codec, CodecInfo, register as lookup_function +from warnings import warn from iota.exceptions import with_context from six import PY3, binary_type __all__ = [ - 'TrytesCodec', + 'AsciiTrytesCodec', 'TrytesDecodeError', ] @@ -20,11 +21,26 @@ class TrytesDecodeError(ValueError): pass -class TrytesCodec(Codec): +class AsciiTrytesCodec(Codec): """ - Codec for converting byte strings into trytes, and vice versa. + Legacy codec for converting byte strings into trytes, and vice versa. + + This method encodes each pair of trytes as an ASCII code point (and + vice versa when decoding). + + The end result requires more space than if the trytes were converted + mathematically, but because the result is ASCII, it's easier to work + with. + + Think of this kind of like Base 64 for balanced ternary (: + """ + name = 'trytes_ascii' + + compat_name = 'trytes' + """ + Old name for this codec. + Note: Will be removed in PyOTA v2.1! """ - name = 'trytes' # :bc: Without the bytearray cast, Python 2 will populate the dict # with characters instead of integers. @@ -173,7 +189,25 @@ def decode(self, input, errors='strict'): @lookup_function def check_trytes_codec(encoding): - if encoding == TrytesCodec.name: - return TrytesCodec.get_codec_info() + """ + Determines which codec to use for the specified encoding. + + References: + - https://docs.python.org/3/library/codecs.html#codecs.register + """ + if encoding == AsciiTrytesCodec.name: + return AsciiTrytesCodec.get_codec_info() + + elif encoding == AsciiTrytesCodec.compat_name: + warn( + '"{old_codec}" codec will be removed in PyOTA v2.1. ' + 'Use "{new_codec}" instead.'.format( + new_codec = AsciiTrytesCodec.name, + old_codec = AsciiTrytesCodec.compat_name, + ), + + DeprecationWarning, + ) + return AsciiTrytesCodec.get_codec_info() return None diff --git a/iota/crypto/__init__.py b/iota/crypto/__init__.py index 85f44aa..8338ae6 100644 --- a/iota/crypto/__init__.py +++ b/iota/crypto/__init__.py @@ -20,3 +20,10 @@ Fragments are used to divide up really long tryte sequences into manageable chunks (similar in concept to AES blocks). """ + + +class SeedWarning(Warning): + """ + Warning for inappropriate seeds. + """ + pass diff --git a/iota/crypto/signing.py b/iota/crypto/signing.py index e741c1e..d23548e 100644 --- a/iota/crypto/signing.py +++ b/iota/crypto/signing.py @@ -11,6 +11,7 @@ from iota.crypto.kerl import Kerl from iota.crypto.types import PrivateKey, Seed from iota.exceptions import with_context +from iota.trits import add_trits, trits_from_int __all__ = [ 'KeyGenerator', @@ -307,20 +308,8 @@ def _create_sponge(self, index): """ seed = self.seed_as_trits[:] - for i in range(index): - # Treat ``seed`` like a really big number and add ``index``. - # Note that addition works a little bit differently in balanced - # ternary. - for j in range(len(seed)): - seed[j] += 1 - - if seed[j] > 1: - seed[j] = -1 - else: - break - sponge = Kerl() - sponge.absorb(seed) + sponge.absorb(add_trits(seed, trits_from_int(index))) # Squeeze all of the trits out of the sponge and re-absorb them. # Note that the sponge transforms several times per operation, so diff --git a/iota/crypto/types.py b/iota/crypto/types.py index e22f8f0..25f940c 100644 --- a/iota/crypto/types.py +++ b/iota/crypto/types.py @@ -2,9 +2,10 @@ from __future__ import absolute_import, division, print_function, \ unicode_literals +import warnings from typing import MutableSequence, Optional, Tuple -from iota.crypto import FRAGMENT_LENGTH, HASH_LENGTH +from iota.crypto import FRAGMENT_LENGTH, HASH_LENGTH, SeedWarning from iota.crypto.kerl import Kerl from iota.exceptions import with_context from iota.transaction.base import Bundle @@ -73,9 +74,22 @@ class Seed(TryteString): IMPORTANT: For maximum security, a seed must be EXACTLY 81 trytes! + WARNINGS: + .. warning:: :py:class:`SeedWarning` if seed has inappropriate length. + References: - https://forum.iota.org/t/why-arent-seeds-longer-than-81-trytes-more-secure/1278 """ + + def __init__(self, trytes=None): + # type: (Optional[TrytesCompatible]) -> None + if trytes and len(trytes) > Hash.LEN: + warnings.warn("Seed has inappropriate length! " + "(https://forum.iota.org/t/why-arent-seeds-longer-than-81-trytes-more-secure/1278)", + category=SeedWarning) + + super(Seed, self).__init__(trytes) + @classmethod def random(cls, length=Hash.LEN): """ diff --git a/iota/transaction/base.py b/iota/transaction/base.py index a8cf296..b5cdf21 100644 --- a/iota/transaction/base.py +++ b/iota/transaction/base.py @@ -9,10 +9,10 @@ from iota.codecs import TrytesDecodeError from iota.crypto import Curl, HASH_LENGTH from iota.json import JsonSerializable -from iota.transaction.types import BundleHash, Fragment, TransactionHash, \ - TransactionTrytes, Nonce -from iota.types import Address, Hash, Tag, TryteString, TrytesCompatible, \ - int_from_trits, trits_from_int +from iota.transaction.types import BundleHash, Fragment, Nonce, TransactionHash, \ + TransactionTrytes +from iota.trits import int_from_trits, trits_from_int +from iota.types import Address, Tag, TryteString, TrytesCompatible __all__ = [ 'Bundle', @@ -69,60 +69,59 @@ def from_tryte_string(cls, trytes, hash_=None): def __init__( self, - hash_, - signature_message_fragment, - address, - value, - timestamp, - current_index, - last_index, - bundle_hash, - trunk_transaction_hash, - branch_transaction_hash, - tag, - attachment_timestamp, - attachment_timestamp_lower_bound, - attachment_timestamp_upper_bound, - nonce, - legacy_tag = None + hash_, # type: Optional[TransactionHash] + signature_message_fragment, # type: Optional[Fragment] + address, # type: Address + value, # type: int + timestamp, # type: int + current_index, # type: Optional[int] + last_index, # type: Optional[int] + bundle_hash, # type: Optional[BundleHash] + trunk_transaction_hash, # type: Optional[TransactionHash] + branch_transaction_hash, # type: Optional[TransactionHash] + tag, # type: Optional[Tag] + attachment_timestamp, # type: Optional[int] + attachment_timestamp_lower_bound, # type: Optional[int] + attachment_timestamp_upper_bound, # type: Optional[int] + nonce, # type: Optional[Nonce] + legacy_tag = None # type: Optional[Tag] ): - # type: (Optional[TransactionHash], Optional[Fragment], Address, int, int, Optional[int], Optional[int], Optional[BundleHash], Optional[TransactionHash], Optional[TransactionHash], Optional[Tag], Optional[int], Optional[int], Optional[int] Optional[Hash]) -> None - self.hash = hash_ # type: Optional[TransactionHash] + self.hash = hash_ """ Transaction ID, generated by taking a hash of the transaction trits. """ - self.bundle_hash = bundle_hash # type: Optional[BundleHash] + self.bundle_hash = bundle_hash """ Bundle hash, generated by taking a hash of metadata from all the transactions in the bundle. """ - self.address = address # type: Address + self.address = address """ The address associated with this transaction. If ``value`` is != 0, the associated address' balance is adjusted as a result of this transaction. """ - self.value = value # type: int + self.value = value """ Amount to adjust the balance of ``address``. Can be negative (i.e., for spending inputs). """ - self._legacy_tag = legacy_tag # type: Optional[Tag] + self._legacy_tag = legacy_tag """ Optional classification legacy_tag applied to this transaction. """ - self.nonce = nonce # type: Optional[Nonce] + self.nonce = nonce """ Unique value used to increase security of the transaction hash. """ - self.timestamp = timestamp # type: int + self.timestamp = timestamp """ Timestamp used to increase the security of the transaction hash. @@ -130,7 +129,7 @@ def __init__( Do not rely on it when resolving conflicts! """ - self.current_index = current_index # type: Optional[int] + self.current_index = current_index """ The position of the transaction inside the bundle. @@ -139,12 +138,12 @@ def __init__( last. """ - self.last_index = last_index # type: Optional[int] + self.last_index = last_index """ The position of the final transaction inside the bundle. """ - self.trunk_transaction_hash = trunk_transaction_hash # type: Optional[TransactionHash] + self.trunk_transaction_hash = trunk_transaction_hash """ In order to add a transaction to the Tangle, you must perform PoW to "approve" two existing transactions, called the "trunk" and @@ -154,7 +153,7 @@ def __init__( a bundle. """ - self.branch_transaction_hash = branch_transaction_hash # type: Optional[TransactionHash] + self.branch_transaction_hash = branch_transaction_hash """ In order to add a transaction to the Tangle, you must perform PoW to "approve" two existing transactions, called the "trunk" and @@ -162,19 +161,19 @@ def __init__( The branch transaction generally has no significance. """ - - self.tag = tag # type: Optional[Tag] + + self.tag = tag """ Optional classification tag applied to this transaction. """ - - self.attachment_timestamp = attachment_timestamp # type: int - - self.attachment_timestamp_lower_bound = attachment_timestamp_lower_bound # type: int - - self.attachment_timestamp_upper_bound = attachment_timestamp_upper_bound # type: int - self.signature_message_fragment = signature_message_fragment # type: Optional[Fragment] + self.attachment_timestamp = attachment_timestamp + + self.attachment_timestamp_lower_bound = attachment_timestamp_lower_bound + + self.attachment_timestamp_upper_bound = attachment_timestamp_upper_bound + + self.signature_message_fragment = signature_message_fragment """ "Signature/Message Fragment" (note the slash): @@ -246,7 +245,7 @@ def last_index_as_trytes(self): """ # Note that we are padding to 27 _trits_. return TryteString.from_trits(trits_from_int(self.last_index, pad=27)) - + @property def attachment_timestamp_as_trytes(self): # type: () -> TryteString @@ -256,7 +255,7 @@ def attachment_timestamp_as_trytes(self): """ #Note that we are padding to 27 _trits_. return TryteString.from_trits(trits_from_int(self.attachment_timestamp, pad=27)) - + @property def attachment_timestamp_lower_bound_as_trytes(self): # type: () -> TryteString @@ -266,7 +265,7 @@ def attachment_timestamp_lower_bound_as_trytes(self): """ #Note that we are padding to 27 _trits_. return TryteString.from_trits(trits_from_int(self.attachment_timestamp_lower_bound, pad=27)) - + @property def attachment_timestamp_upper_bound_as_trytes(self): # type: () -> TryteString @@ -341,7 +340,7 @@ def get_signature_validation_trytes(self): + self.current_index_as_trytes + self.last_index_as_trytes ) - + @property def legacy_tag(self): # type: () -> Tag @@ -458,7 +457,7 @@ def tail_transaction(self): return self[0] def get_messages(self, errors='drop'): - # type: () -> List[Text] + # type: (Text) -> List[Text] """ Attempts to decipher encoded messages from the transactions in the bundle. diff --git a/iota/transaction/creation.py b/iota/transaction/creation.py index 25c0a0b..9d08829 100644 --- a/iota/transaction/creation.py +++ b/iota/transaction/creation.py @@ -9,17 +9,19 @@ from iota.crypto import HASH_LENGTH from iota.crypto.kerl import Kerl -from iota.crypto.signing import KeyGenerator +from iota.crypto.signing import KeyGenerator, normalize from iota.crypto.types import PrivateKey from iota.exceptions import with_context from iota.transaction.base import Bundle, Transaction -from iota.transaction.types import BundleHash, Fragment, TransactionHash, Nonce +from iota.transaction.types import BundleHash, Fragment, Nonce, TransactionHash from iota.transaction.utils import get_current_timestamp -from iota.types import Address, Hash, Tag, TryteString +from iota.trits import add_trits +from iota.types import Address, Tag, TryteString __all__ = [ 'ProposedBundle', 'ProposedTransaction', + 'Transfer', ] @@ -82,6 +84,24 @@ def as_tryte_string(self): return super(ProposedTransaction, self).as_tryte_string() + def increment_legacy_tag(self): + """ + Increments the transaction's legacy tag, used to fix insecure + bundle hashes when finalizing a bundle. + + References: + - https://github.com/iotaledger/iota.lib.py/issues/84 + """ + self._legacy_tag =\ + Tag.from_trits(add_trits(self.legacy_tag.as_trits(), [1])) + + +Transfer = ProposedTransaction +""" +Follow naming convention of other libs. +https://github.com/iotaledger/iota.lib.py/issues/72 +""" + class ProposedBundle(Bundle, Sequence[ProposedTransaction]): """ @@ -314,20 +334,31 @@ def finalize(self): ) # Generate bundle hash. - sponge = Kerl() - last_index = len(self) - 1 + while True: + sponge = Kerl() + last_index = len(self) - 1 + + for (i, txn) in enumerate(self): # type: Tuple[int, ProposedTransaction] + txn.current_index = i + txn.last_index = last_index - for (i, txn) in enumerate(self): # type: Tuple[int, ProposedTransaction] - txn.current_index = i - txn.last_index = last_index + sponge.absorb(txn.get_signature_validation_trytes().as_trits()) - sponge.absorb(txn.get_signature_validation_trytes().as_trits()) + bundle_hash_trits = [0] * HASH_LENGTH # type: MutableSequence[int] + sponge.squeeze(bundle_hash_trits) - bundle_hash_trits = [0] * HASH_LENGTH # type: MutableSequence[int] - sponge.squeeze(bundle_hash_trits) + bundle_hash = BundleHash.from_trits(bundle_hash_trits) + + # Check that we generated a secure bundle hash. + # https://github.com/iotaledger/iota.lib.py/issues/84 + if any(13 in part for part in normalize(bundle_hash)): + # Increment the legacy tag and try again. + tail_transaction = self.tail_transaction # type: ProposedTransaction + tail_transaction.increment_legacy_tag() + else: + break # Copy bundle hash to individual transactions. - bundle_hash = BundleHash.from_trits(bundle_hash_trits) for txn in self: txn.bundle_hash = bundle_hash diff --git a/iota/trits.py b/iota/trits.py new file mode 100644 index 0000000..872ad92 --- /dev/null +++ b/iota/trits.py @@ -0,0 +1,128 @@ +# coding=utf-8 +""" +Provides functions for manipulating sequences of trits. + +Based on: +https://github.com/iotaledger/iota.lib.js/blob/v0.4.2/lib/crypto/helpers/adder.js +""" + +from __future__ import absolute_import, division, print_function, \ + unicode_literals + +from typing import Iterable, List, Optional, Sequence, Tuple + +__all__ = [ + 'add_trits', + 'int_from_trits', + 'trits_from_int', +] + + +def add_trits(left, right): + # type: (Sequence[int], Sequence[int]) -> List[int] + """ + Adds two sequences of trits together. + + The result is a list of trits equal in length to the longer of the + two sequences. + + Note: Overflow is possible. + For example, ``add_trits([1], [1])`` returns ``[-1]``. + """ + target_len = max(len(left), len(right)) + + res = [0] * target_len + left += [0] * (target_len - len(left)) + right += [0] * (target_len - len(right)) + + carry = 0 + for i in range(len(res)): + res[i], carry = _full_add_trits(left[i], right[i], carry) + + return res + + +def int_from_trits(trits): + # type: (Iterable[int]) -> int + """ + Converts a sequence of trits into an integer value. + """ + # Normally we'd have to wrap ``enumerate`` inside ``reversed``, but + # balanced ternary puts least significant digits first. + return sum(base * (3 ** power) for power, base in enumerate(trits)) + + +def trits_from_int(n, pad=1): + # type: (int, Optional[int]) -> List[int] + """ + Returns a trit representation of an integer value. + + :param n: + Integer value to convert. + + :param pad: + Ensure the result has at least this many trits. + + References: + - https://dev.to/buntine/the-balanced-ternary-machines-of-soviet-russia + - https://en.wikipedia.org/wiki/Balanced_ternary + - https://rosettacode.org/wiki/Balanced_ternary#Python + """ + if n == 0: + trits = [] + else: + quotient, remainder = divmod(n, 3) + + if remainder == 2: + # Lend 1 to the next place so we can make this trit negative. + quotient += 1 + remainder = -1 + + trits = [remainder] + trits_from_int(quotient, pad=0) + + if pad: + trits += [0] * max(0, pad - len(trits)) + + return trits + + +def _cons_trits(left, right): + # type: (int, int) -> int + """ + Compares two trits. If they have the same value, returns that value. + Otherwise, returns 0. + """ + return left if left == right else 0 + + +def _add_trits(left, right): + # type: (int, int) -> int + """ + Adds two individual trits together. + + The result is always a single trit. + """ + res = left + right + return res if -2 < res < 2 else (res < 0) - (res > 0) + + +def _any_trits(left, right): + # type: (int, int) -> int + """ + Adds two individual trits together and returns a single trit + indicating whether the result is positive or negative. + """ + res = left + right + return (res > 0) - (res < 0) + + +def _full_add_trits(left, right, carry): + # type: (int, int, int) -> Tuple[int, int] + """ + Adds two trits together, with support for a carry trit. + """ + sum_both = _add_trits(left, right) + cons_left = _cons_trits(left, right) + cons_right = _cons_trits(sum_both, carry) + + return _add_trits(sum_both, carry), _any_trits(cons_left, cons_right) diff --git a/iota/types.py b/iota/types.py index d5a9a4c..9671f3f 100644 --- a/iota/types.py +++ b/iota/types.py @@ -6,17 +6,18 @@ from itertools import chain from math import ceil from random import SystemRandom -from typing import AnyStr, Generator, Iterable, Iterator, List, \ +from typing import Any, AnyStr, Generator, Iterable, Iterator, List, \ MutableSequence, Optional, Text, Union from six import PY2, binary_type, itervalues, python_2_unicode_compatible, \ text_type -from iota import TRITS_PER_TRYTE, TrytesCodec +from iota import AsciiTrytesCodec, TRITS_PER_TRYTE from iota.crypto import HASH_LENGTH from iota.crypto.kerl import Kerl from iota.exceptions import with_context from iota.json import JsonSerializable +from iota.trits import int_from_trits, trits_from_int __all__ = [ 'Address', @@ -25,57 +26,11 @@ 'Tag', 'TryteString', 'TrytesCompatible', - 'int_from_trits', - 'trits_from_int', ] # Custom types for type hints and docstrings. -TrytesCompatible = Union[AnyStr, bytearray, 'TryteString'] - - -def trits_from_int(n, pad=None): - # type: (int, Optional[int]) -> List[int] - """ - Returns a trit representation of an integer value. - - :param n: - Integer value to convert. - - :param pad: - Ensure the result has at least this many trits. - - References: - - https://dev.to/buntine/the-balanced-ternary-machines-of-soviet-russia - - https://en.wikipedia.org/wiki/Balanced_ternary - - https://rosettacode.org/wiki/Balanced_ternary#Python - """ - if n == 0: - trits = [] - else: - quotient, remainder = divmod(n, 3) - - if remainder == 2: - # Lend 1 to the next place so we can make this trit negative. - quotient += 1 - remainder = -1 - - trits = [remainder] + trits_from_int(quotient) - - if pad: - trits += [0] * max(0, pad - len(trits)) - - return trits - - -def int_from_trits(trits): - # type: (Iterable[int]) -> int - """ - Converts a sequence of trits into an integer value. - """ - # Normally we'd have to wrap ``enumerate`` inside ``reversed``, but - # balanced ternary puts least significant digits first. - return sum(base * (3 ** power) for power, base in enumerate(trits)) +TrytesCompatible = Union[AnyStr, bytearray, 'TryteString'] @python_2_unicode_compatible @@ -99,7 +54,7 @@ def random(cls, length): :param length: Number of trytes to generate. """ - alphabet = list(itervalues(TrytesCodec.alphabet)) + alphabet = list(itervalues(AsciiTrytesCodec.alphabet)) generator = SystemRandom() # :py:meth:`SystemRandom.choices` wasn't added until Python 3.6; @@ -111,30 +66,35 @@ def random(cls, length): ) @classmethod - def from_bytes(cls, bytes_, *args, **kwargs): - # type: (Union[binary_type, bytearray], ...) -> TryteString + def from_bytes(cls, bytes_, codec=AsciiTrytesCodec.name, *args, **kwargs): + # type: (Union[binary_type, bytearray], Text, *Any, **Any) -> TryteString """ Creates a TryteString from a sequence of bytes. :param bytes_: Source bytes. + :param codec: + Which codec to use: + + - 'binary': Converts each byte into a sequence of trits with + the same value (this is usually what you want). + - 'ascii': Uses the legacy ASCII codec. + :param args: Additional positional arguments to pass to the initializer. :param kwargs: Additional keyword arguments to pass to the initializer. """ - return cls(encode(bytes_, 'trytes'), *args, **kwargs) + return cls(encode(bytes_, codec), *args, **kwargs) @classmethod def from_string(cls, string, *args, **kwargs): - # type: (Text, ...) -> TryteString + # type: (Text, *Any, **Any) -> TryteString """ Creates a TryteString from a Unicode string. - Note: The string will be encoded using UTF-8. - :param string: Source string. @@ -144,11 +104,16 @@ def from_string(cls, string, *args, **kwargs): :param kwargs: Additional keyword arguments to pass to the initializer. """ - return cls.from_bytes(string.encode('utf-8'), *args, **kwargs) + return cls.from_bytes( + bytes_ = string.encode('utf-8'), + codec = AsciiTrytesCodec.name, + *args, + **kwargs + ) @classmethod def from_trytes(cls, trytes, *args, **kwargs): - # type: (Iterable[Iterable[int]], ...) -> TryteString + # type: (Iterable[Iterable[int]], *Any, **Any) -> TryteString """ Creates a TryteString from a sequence of trytes. @@ -174,13 +139,13 @@ def from_trytes(cls, trytes, *args, **kwargs): if converted < 0: converted += 27 - chars.append(TrytesCodec.alphabet[converted]) + chars.append(AsciiTrytesCodec.alphabet[converted]) return cls(chars, *args, **kwargs) @classmethod def from_trits(cls, trits, *args, **kwargs): - # type: (Iterable[int], ...) -> TryteString + # type: (Iterable[int], *Any, **Any) -> TryteString """ Creates a TryteString from a sequence of trits. @@ -275,7 +240,7 @@ def __init__(self, trytes, pad=None): trytes = bytearray(trytes) for i, ordinal in enumerate(trytes): - if ordinal not in TrytesCodec.index: + if ordinal not in AsciiTrytesCodec.index: raise with_context( exc = ValueError( 'Invalid character {char!r} at position {i} ' @@ -313,9 +278,9 @@ def __bytes__(self): Note: This does not decode the trytes into bytes/characters; it only returns an ASCII representation of the trytes themselves! - If you want to: - - Decode trytes into bytes: use :py:meth:`as_bytes`. - - Decode trytes into Unicode: use :py:meth:`as_string`. + If you want to... + - ... decode trytes into bytes: use :py:meth:`as_bytes`. + - ... decode trytes into Unicode: use :py:meth:`as_string`. """ return binary_type(self._trytes) @@ -479,8 +444,8 @@ def iter_chunks(self, chunk_size): """ return ChunkIterator(self, chunk_size) - def as_bytes(self, errors='strict'): - # type: (Text) -> binary_type + def as_bytes(self, errors='strict', codec=AsciiTrytesCodec.name): + # type: (Text, Text) -> binary_type """ Converts the TryteString into a byte string. @@ -490,12 +455,19 @@ def as_bytes(self, errors='strict'): - 'replace': replace with '?'. - 'ignore': omit the tryte from the result. + :param codec: + Which codec to use: + + - 'binary': Converts each sequence of 5 trits into a byte with + the same value (this is usually what you want). + - 'ascii': Uses the legacy ASCII codec. + :raise: - :py:class:`iota.codecs.TrytesDecodeError` if the trytes cannot be decoded into bytes. """ - # :bc: In Python 2, `decode` does not accept keyword arguments. - return decode(self._trytes, 'trytes', errors) + # In Python 2, :py:func:`decode` does not accept keyword arguments. + return decode(self._trytes, codec, errors) def as_string(self, errors='strict', strip_padding=True): # type: (Text, bool) -> Text @@ -523,10 +495,10 @@ def as_string(self, errors='strict', strip_padding=True): if strip_padding and (trytes[-1] == ord(b'9')): trytes = trytes.rstrip(b'9') - # Put one back to preserve even length. + # Put one back to preserve even length for ASCII codec. trytes += b'9' * (len(trytes) % 2) - return decode(trytes, 'trytes', errors).decode('utf-8', errors) + return decode(trytes, AsciiTrytesCodec.name, errors).decode('utf-8', errors) def as_json_compatible(self): # type: () -> Text @@ -546,7 +518,7 @@ def as_integers(self): Each integer is a value between -13 and 13. """ return [ - self._normalize(TrytesCodec.index[c]) + self._normalize(AsciiTrytesCodec.index[c]) for c in self._trytes ] diff --git a/setup.py b/setup.py index e214a29..535abcb 100644 --- a/setup.py +++ b/setup.py @@ -6,8 +6,14 @@ from codecs import StreamReader, open +import setuptools from setuptools import find_packages, setup +from distutils.version import LooseVersion +if LooseVersion(setuptools.__version__) < LooseVersion('20.5'): + import sys + sys.exit('Installation failed: Upgrade setuptools to version 20.5 or later') + ## # Load long description for PyPi. with open('README.rst', 'r', 'utf-8') as f: # type: StreamReader @@ -21,7 +27,7 @@ name = 'PyOTA', description = 'IOTA API library for Python', url = 'https://github.com/iotaledger/iota.lib.py', - version = '2.0.0', + version = '2.0.1', long_description = long_description, diff --git a/test/adapter/sandbox_test.py b/test/adapter/sandbox_test.py index 8e0468b..4e37791 100644 --- a/test/adapter/sandbox_test.py +++ b/test/adapter/sandbox_test.py @@ -9,6 +9,7 @@ from six import text_type from iota import BadApiResponse +from iota.adapter import API_VERSION from iota.adapter.sandbox import SandboxAdapter from test import mock from test.adapter_test import create_http_response @@ -42,8 +43,9 @@ def test_regular_command(self): # Auth token automatically added to the HTTP request. headers = { - 'Authorization': 'token ACCESS-TOKEN', - 'Content-type': 'application/json', + 'Authorization': 'token ACCESS-TOKEN', + 'Content-type': 'application/json', + 'X-IOTA-API-Version': API_VERSION, }, ) @@ -233,7 +235,8 @@ def test_regular_command_null_token(self): headers = { # No auth token, so no Authorization header. # 'Authorization': 'token ACCESS-TOKEN', - 'Content-type': 'application/json', + 'Content-type': 'application/json', + 'X-IOTA-API-Version': API_VERSION, }, ) diff --git a/test/adapter_test.py b/test/adapter_test.py index 71f2ca0..06c3852 100644 --- a/test/adapter_test.py +++ b/test/adapter_test.py @@ -8,7 +8,7 @@ import requests from iota import BadApiResponse, InvalidUri, TryteString -from iota.adapter import HttpAdapter, MockAdapter, resolve_adapter +from iota.adapter import API_VERSION, HttpAdapter, MockAdapter, resolve_adapter from six import BytesIO, text_type from test import mock @@ -140,19 +140,29 @@ def test_success_response(self): """ adapter = HttpAdapter('http://localhost:14265') - expected_result = { - 'message': 'Hello, IOTA!', - } + payload = {'command': 'helloWorld'} + expected_result = {'message': 'Hello, IOTA!'} mocked_response = create_http_response(json.dumps(expected_result)) mocked_sender = mock.Mock(return_value=mocked_response) # noinspection PyUnresolvedReferences with mock.patch.object(adapter, '_send_http_request', mocked_sender): - result = adapter.send_request({'command': 'helloWorld'}) + result = adapter.send_request(payload) self.assertEqual(result, expected_result) + # https://github.com/iotaledger/iota.lib.py/issues/84 + mocked_sender.assert_called_once_with( + headers = { + 'Content-type': 'application/json', + 'X-IOTA-API-Version': API_VERSION, + }, + + payload = json.dumps(payload), + url = adapter.node_url, + ) + def test_error_response(self): """ Simulates sending a command to the node and getting an error @@ -343,6 +353,7 @@ def test_trytes_in_request(): }), headers = { - 'Content-type': 'application/json', + 'Content-type': 'application/json', + 'X-IOTA-API-Version': API_VERSION, }, ) diff --git a/test/codecs_test.py b/test/codecs_test.py index 79c44ed..32a5f30 100644 --- a/test/codecs_test.py +++ b/test/codecs_test.py @@ -2,53 +2,67 @@ from __future__ import absolute_import, division, print_function, \ unicode_literals -from codecs import encode, decode +from codecs import decode, encode from unittest import TestCase +from warnings import catch_warnings, simplefilter as simple_filter +from six import text_type -# noinspection SpellCheckingInspection -from iota.codecs import TrytesDecodeError +from iota.codecs import AsciiTrytesCodec, TrytesDecodeError # noinspection SpellCheckingInspection -class TrytesCodecTestCase(TestCase): +class AsciiTrytesCodecTestCase(TestCase): def test_encode_byte_string(self): - """Encoding a byte string into trytes.""" + """ + Encoding a byte string into trytes. + """ self.assertEqual( - encode(b'Hello, IOTA!', 'trytes'), + encode(b'Hello, IOTA!', AsciiTrytesCodec.name), b'RBTC9D9DCDQAEASBYBCCKBFA', ) def test_encode_bytearray(self): - """Encoding a bytearray into trytes.""" + """ + Encoding a bytearray into trytes. + """ self.assertEqual( - encode(bytearray(b'Hello, IOTA!'), 'trytes'), + encode(bytearray(b'Hello, IOTA!'), AsciiTrytesCodec.name), b'RBTC9D9DCDQAEASBYBCCKBFA', ) def test_encode_error_wrong_type(self): - """Attempting to encode a value with an incompatible type.""" + """ + Attempting to encode a value with an incompatible type. + """ with self.assertRaises(TypeError): # List value not accepted; it can contain things other than bytes - # (ordinals in range(255), that is). - encode([72, 101, 108, 108, 111, 44, 32, 73, 79, 84, 65, 33], 'trytes') + # (ordinals in range(255), that is). + encode( + [72, 101, 108, 108, 111, 44, 32, 73, 79, 84, 65, 33], + AsciiTrytesCodec.name, + ) with self.assertRaises(TypeError): # Unicode strings not accepted; it is ambiguous whether and how # to encode to bytes. - encode('Hello, IOTA!', 'trytes') + encode('Hello, IOTA!', AsciiTrytesCodec.name) def test_decode_byte_string(self): - """Decoding trytes to a byte string.""" + """ + Decoding trytes to a byte string. + """ self.assertEqual( - decode(b'RBTC9D9DCDQAEASBYBCCKBFA', 'trytes'), + decode(b'RBTC9D9DCDQAEASBYBCCKBFA', AsciiTrytesCodec.name), b'Hello, IOTA!', ) def test_decode_bytearray(self): - """Decoding a bytearray of trytes into a byte string.""" + """ + Decoding a bytearray of trytes into a byte string. + """ self.assertEqual( - decode(bytearray(b'RBTC9D9DCDQAEASBYBCCKBFA'), 'trytes'), + decode(bytearray(b'RBTC9D9DCDQAEASBYBCCKBFA'), AsciiTrytesCodec.name), b'Hello, IOTA!', ) @@ -57,14 +71,14 @@ def test_decode_wrong_length_errors_strict(self): Attempting to decode an odd number of trytes with errors='strict'. """ with self.assertRaises(TrytesDecodeError): - decode(b'RBTC9D9DCDQAEASBYBCCKBFA9', 'trytes', 'strict') + decode(b'RBTC9D9DCDQAEASBYBCCKBFA9', AsciiTrytesCodec.name, 'strict') def test_decode_wrong_length_errors_ignore(self): """ Attempting to decode an odd number of trytes with errors='ignore'. """ self.assertEqual( - decode(b'RBTC9D9DCDQAEASBYBCCKBFA9', 'trytes', 'ignore'), + decode(b'RBTC9D9DCDQAEASBYBCCKBFA9', AsciiTrytesCodec.name, 'ignore'), b'Hello, IOTA!', ) @@ -73,34 +87,51 @@ def test_decode_wrong_length_errors_replace(self): Attempting to decode an odd number of trytes with errors='replace'. """ self.assertEqual( - decode(b'RBTC9D9DCDQAEASBYBCCKBFA9', 'trytes', 'replace'), + decode(b'RBTC9D9DCDQAEASBYBCCKBFA9', AsciiTrytesCodec.name, 'replace'), b'Hello, IOTA!?', ) def test_decode_invalid_pair_errors_strict(self): """ Attempting to decode an un-decodable pair of trytes with - errors='strict'. + errors='strict'. """ with self.assertRaises(TrytesDecodeError): - decode(b'ZJVYUGTDRPDYFGFXMK', 'trytes', 'strict') + decode(b'ZJVYUGTDRPDYFGFXMK', AsciiTrytesCodec.name, 'strict') def test_decode_invalid_pair_errors_ignore(self): """ Attempting to decode an un-decodable pair of trytes with - errors='ignore'. + errors='ignore'. """ self.assertEqual( - decode(b'ZJVYUGTDRPDYFGFXMK', 'trytes', 'ignore'), + decode(b'ZJVYUGTDRPDYFGFXMK', AsciiTrytesCodec.name, 'ignore'), b'\xd2\x80\xc3', ) def test_decode_invalid_pair_errors_replace(self): """ Attempting to decode an un-decodable pair of trytes with - errors='replace'. + errors='replace'. """ self.assertEqual( - decode(b'ZJVYUGTDRPDYFGFXMK', 'trytes', 'replace'), + decode(b'ZJVYUGTDRPDYFGFXMK', AsciiTrytesCodec.name, 'replace'), b'??\xd2\x80??\xc3??', ) + + def test_compat_name(self): + """ + A warning is raised when using the codec's old name. + """ + with catch_warnings(record=True) as warnings: + simple_filter('always', category=DeprecationWarning) + + self.assertEqual( + # Provide the old codec name to :py:func:`encode`. + encode(b'Hello, IOTA!', AsciiTrytesCodec.compat_name), + b'RBTC9D9DCDQAEASBYBCCKBFA', + ) + + self.assertEqual(len(warnings), 1) + self.assertEqual(warnings[0].category, DeprecationWarning) + self.assertIn('codec will be removed', text_type(warnings[0].message)) diff --git a/test/commands/extended/prepare_transfer_test.py b/test/commands/extended/prepare_transfer_test.py index e266995..5fc3c92 100644 --- a/test/commands/extended/prepare_transfer_test.py +++ b/test/commands/extended/prepare_transfer_test.py @@ -403,15 +403,13 @@ class PrepareTransferCommandTestCase(TestCase): .. code-block:: javascript + // Init environment. This only has to be done once. var Bundle = require('./lib/crypto/bundle/bundle'), Converter = require('./lib/crypto/converter/converter'), IOTA = require('./lib/iota'), Signing = require('./lib/crypto/signing/signing'), - Utils = require('./lib/utils/utils'); - - // Set the seed that will be used to generate signing keys. - // Skip this step if there are no inputs. - var seed = 'SEED9GOES9HERE'; + Utils = require('./lib/utils/utils'), + iota = new IOTA(); // Specify constant timestamp value to use for transactions. var timestamp = 1482938294; @@ -427,9 +425,12 @@ class PrepareTransferCommandTestCase(TestCase): ... ]; + // Set the seed that will be used to generate signing keys. + // Skip this step if there are no inputs. + var seed = 'SEED9GOES9HERE'; + // Assemble the bundle. var bundle = new Bundle(); - var iota = new IOTA(); // Add spend transaction(s) to the bundle. // See ``lib/crypto/bundle/bundle.js:Bundle.prototype.addEntry`` @@ -529,25 +530,29 @@ def test_pass_inputs_not_needed(self): """ response =\ self.command( - seed = Seed.random(), + seed = + Seed( + 'TESTVALUE9DONTUSEINPRODUCTION99999HORPYY' + 'TGKQQTQSNMSZBXYLAFXFHZVPWVGCPRGXKXREJKI9B', + ), transfers = [ ProposedTransaction( address = Address( - b'TESTVALUE9DONTUSEINPRODUCTION99999KJUPKN' - b'RMTHKVJYWNBKBGCKOQWBTKBOBJIZZYQITTFJZKLOI', + 'TESTVALUE9DONTUSEINPRODUCTION99999KJUPKN' + 'RMTHKVJYWNBKBGCKOQWBTKBOBJIZZYQITTFJZKLOI', ), - tag = Tag(b'PYOTA9UNIT9TESTS9'), + tag = Tag('PYOTA9UNIT9TESTS9'), value = 0, ), ProposedTransaction( address = Address( - b'TESTVALUE9DONTUSEINPRODUCTION99999YMSWGX' - b'VNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN', + 'TESTVALUE9DONTUSEINPRODUCTION99999YMSWGX' + 'VNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN', ), value = 0, @@ -561,12 +566,12 @@ def test_pass_inputs_not_needed(self): # Note that the transactions are returned in reverse order. self.assertEqual( response['trytes'][0], - TryteString(b'999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUE9DONTUSEINPRODUCTION99999YMSWGXVNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN999999999999999999999999999999999999999999999999999999NYBKIVD99A99999999A99999999LK9ZCHYABJFCM9UGKNWDKPAH9KSSXJPOMYYHLHRAGVAZDDFUJLJBONPLNYQCEBEPVEELEZINMNC9QZYQW999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUE9DONTUSEINPRODUCTION99999YMSWGXVNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN999999999999999999999999999999999999999999999999999999NYBKIVD99A99999999A99999999VCXVP9VHDQGSGFL9UGWBXIOSCAZHVIVVGLKUEBDWTBBRFXFINBAEKZTUAIVDWIFKCUUHWOZTGRXHLRYPX999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) self.assertEqual( response['trytes'][1], - TryteString(b'999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUE9DONTUSEINPRODUCTION99999KJUPKNRMTHKVJYWNBKBGCKOQWBTKBOBJIZZYQITTFJZKLOI999999999999999999999999999PYOTA9UNIT9TESTS99999999999NYBKIVD99999999999A99999999LK9ZCHYABJFCM9UGKNWDKPAH9KSSXJPOMYYHLHRAGVAZDDFUJLJBONPLNYQCEBEPVEELEZINMNC9QZYQW999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999PYOTA9UNIT9TESTS99999999999999999999999999999999999999999999999999999999999999999'), + TryteString('999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUE9DONTUSEINPRODUCTION99999KJUPKNRMTHKVJYWNBKBGCKOQWBTKBOBJIZZYQITTFJZKLOI999999999999999999999999999ZYOTA9UNIT9TESTS99999999999NYBKIVD99999999999A99999999VCXVP9VHDQGSGFL9UGWBXIOSCAZHVIVVGLKUEBDWTBBRFXFINBAEKZTUAIVDWIFKCUUHWOZTGRXHLRYPX999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999PYOTA9UNIT9TESTS99999999999999999999999999999999999999999999999999999999999999999'), ) @@ -586,16 +591,16 @@ def test_pass_inputs_explicit_no_change(self): response = self.command( seed = Seed( - b'TESTVALUEONE9DONTUSEINPRODUCTION99999C9V' - b'C9RHFCQAIGSFICL9HIY9ZEUATFVHFGAEUHSECGQAK' + 'TESTVALUEONE9DONTUSEINPRODUCTION99999C9V' + 'C9RHFCQAIGSFICL9HIY9ZEUATFVHFGAEUHSECGQAK' ), transfers = [ ProposedTransaction( address = Address( - b'TESTVALUETWO9DONTUSEINPRODUCTION99999XYY' - b'NXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOW' + 'TESTVALUETWO9DONTUSEINPRODUCTION99999XYY' + 'NXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOW' ), value = 42, @@ -605,8 +610,8 @@ def test_pass_inputs_explicit_no_change(self): inputs = [ Address( trytes = - b'MQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIX' - b'PQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEB', + 'MQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIX' + 'PQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEB', # Normally, you would use an AddressGenerator to create # new addresses, so ``key_index`` would be populated @@ -620,8 +625,8 @@ def test_pass_inputs_explicit_no_change(self): Address( trytes = - b'TNNTKUYYZVIOPMQHXIYKKZVN9PELGAKAUUGKCBYR' - b'QOZJT9NLVDEVFQXIZKXIF9MOYTJTDTOQJYQLQKXQC', + 'TNNTKUYYZVIOPMQHXIYKKZVN9PELGAKAUUGKCBYR' + 'QOZJT9NLVDEVFQXIZKXIF9MOYTJTDTOQJYQLQKXQC', key_index = 5, security_level = 2, @@ -637,31 +642,31 @@ def test_pass_inputs_explicit_no_change(self): # Input #2, Part 2 of 2 self.assertEqual( response['trytes'][0], - TryteString(b'PNOHSCLHTDHBNES9REFELWTCKSFPFDPQOEEUKYBXFMRSHAAXBWUXMD9QNSQUWZMOBGDDAVIIHWGBLWIKCLTPZDVYRHYZWWJUKNWOLYDWRTRBOVMXMFJCBEJVMSPBQJQISISHSRNKEZXSOZHZISSMLCMCOBYN9DWGV9Z9GO9QEHNGIASTVPGWPBYQORFASXYDOTMJZVEJHZZRJSUDDTAFJDQFCZKFKJWEPQARTHCWKDWKITI9ZDCRNUWJQBDZZMRYNBDQPHJOCTQKMSFFCXGM9NGNGCBTUEEPAVOXDKHQNHSSUNA9CLTFAUIHSYPIESEVC9YWAWEBKNVAKGKZWWGRWYYPPOLTSOGTKEPCQQ9PLDDAMKGRPOHHHDYCLOJVBWWDTSLYZHKLOZBKHPCOUFPIBZQ9MOHHKMSRTXGXHERZREPSSAASILWCFDUFPXOKGTDSHWRBZSQSNCYFJZJTB9DGDJYISY9EZPLHJRMIQARDR9SIEMDYSBJXMWBGGRANNSAI9A9HYRPG9JEFFTIFSMJZHQWXXTABXPQXYOLTEFDAPZFMLTGGXCVPL9ZNBNNWVLMUHAXAWJNNVBPTXWNTFNQAYDBVCQSXJTPXABKG9PYIJEZRKSYBXTHGUSWORXZNKZNHIJW9KEPWANBKNNKOUKGLISUUTQRGMGHOQQDUUUWHFJQOFXXN9MOAOLSLOXLKPAQ9CRNSTKVRUMNLFPVIULPYXKOLDLARYUKLPMIEQYWSJYTYRMBHRHSPQJHJALMWUHLPIGQLQSXWDPVNIGFUOEMJJ9GIUVGNB9IWKIPBERFTPZOZVDJMBCKFTWLTQYDP9YHXAOU9DEEMDU9WBHPSRKFARYYCQBEKKQQFFTRUKJO9SECIZRQMMDOJZVPWSWWANMYVGHDCCGSKKGEGCKN9MYFG9ASYM9PEFX9DUJUYVTITKVMBKXWFTWUNVTFEDYSSTMWVGCYZIOCRKVRDGBPOVIDPAGIGZJYNI9TSAJCOSGQYQOTIXMBQXDGJTDJCIGKNLTZNEWEELSAXWYEBYCZILJWPKCGFHXTCDRANRRRUJWRIKTHQJNSDLZJTSDPHU9UMRPCHKJBHTYSNGIARREPPIMULJXFIATTWPQAAYSDSBTGYATXNDDIBMQEIBIUK9YAUPNBMKMZSRHK9UGN9YWOVMTFCSZWOMWHUHPYUMWJUNDMMVOAQUBQDLJLMCXFQEGBSZABKVTNFAJTLGVJ9VHAQGD9MSDYLOMCODQJIEBZARCRFVHFIGFFZRZPBFVX9OMHAAIXFKXWC99RINEESNHPYSFWESSKP9AQHJHWUPWYOOYVKFUNKXPXSKTHNWNULCRUMIHBJNAIQNGDLQSXNWRILYVJMYSELRBTLDYELCZVSVTDNVOHFXLPN9NDPSKA9YHVFRGPAFAKNOXBGWNRMYQCFCSMIBHUKKTNQBDDRQXZLWBLHRYTWSMJUJWSPQZPSBQTAZBVOIVIRXKJPSXNRB9ILEUAMGJKDGOEGVGOKFDKWWBRF9BYDQUYVEHFTNJQDAMEVFHQLSU9XTGFPOGGOYWTZONFSZWODUOMKA9AXWWIZL9GMNIXHWNJFHNONJUJGMFUGPAAMHZLXBOJFLJFHGNNWEU9DS9VKVBNVIUDXXGDQFQSNLMGWAMPETROFUFVCDMCARZAJICIXAVAM9YZAFSILIPOEOGHZ9TJQTKRLGTQNWFDAEDHZIOAMRHNUE9ANKIYKEKWBYZWFVUMKFTWBRACWZUWZSGWGWTAPXIILCFMLLLGOLHVVUIGRPO9CRDXECHIZYAJXXECRBMLNCYSFOH9PNJ9UXOWBGCYIRIAOI9VVAIYOLHTLBYEKOYMOCSVBFCHHCTGIBOUDCXXXKGBTWVBCAVOUQVOZCUSKORPYWBXCVYYBVFWSZACWFLRUWZORZULS9RNOBKHRQTR9IYTKFVXRWSWERUECAHVTAKTTSN9VNZOLGJJGAHPIJZQBITVDSXNXZTRMIDLH9XFIOEYUVJWIKLLEAIYBOFFUPCBEMMXBDGTZDICOBWWQ9EBAMLPQNHNHKDBZHACQW9GDQQQPSAWIAYLWWOYDTDRXKCNIWFXZRAXNSGDUSDTWTEFANWWTSAJQIVJQZGPXHUP99LYTNIESJDUZGHEELFJGSBLMEKJBRABTBZASNKLSAUB9GHHIHMJZSGJHXKWMKIJOQVBTNNTKUYYZVIOPMQHXIYKKZVN9PELGAKAUUGKCBYRQOZJT9NLVDEVFQXIZKXIF9MOYTJTDTOQJYQLQKXQC999999999999999999999999999999999999999999999999999999NYBKIVD99D99999999D99999999YBPL9FUHMJAALACSDMDFUKKBTUPCHTXNCASWTZJZMYLFPJH9MWDXUCNGAVYJWFFQNHCABKYIQBTJWSZID999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('RQOQNTDTZWGNBTVNHUYXYELHLRDTUSHIFZBAJDYYGKPUTHMBFMZPWHYULBANOYXDHVTRKLGXKUOZAWFZWJDFVUZKONYTRYSAGTWGDBIAHHMUEEGIPSKBCJPDBSMHAWWZZU9IFKCKJMMTCGGDHPUCBBRDKTQOTQGRDXEDQAYI9WNCNIVMBSAQVCVLJILCKHOUYPJXKNVXDHXPECIPVQQIDWBGRREGYYVROBJELIWPUWSOHSAUKSYSPQMNPRBMKKUQUWGNAWAOEDDVNRJBUSRKBJKWZLGAVDASMZ9GMKKLMIKFWAIAHAW9GIRAWZFYFEOIJ9TBNAVEUSTNUNABHJ9L9GSZTBHTGTRZSIWFVGMXQS9VDTF9ZUVNLDI9MOEVRRBDBAKATS9ACTIABCDWUFNRXZQ9MOHHKMSRTXGXHERZREPSSAASILWCFDUFPXOKGTDSHWRBZSQSNCYFJZJTB9DGDJYISY9EZPLHJRMIQAQJYYRZVHKWCGQLWFDYVZKCDAIBWYQQSUKACFRBALBKMBTBG9PPZEBU9TVRU9RMBHXCNOS9QLASMCDEFWCUBMHS9LHXEYANCHLEFNVGJJKKUITNEYVLPYQIYQHAIIGSTSAURJOAL9SVATHGOVP9CQXMGCYLSYFUQDOWY9ZWJADWVQGPZZISPAWHTMNPVKKPTCSODG9WECGVUANJXZRDYPMPVCLRF9WVGWKKQQWPAKCZQVK9KHBGXJRKGD9IHKRNJQVKSXXQMVPLGVSEWPEXNLBHGOQJUWDOIEXDGIZLFIZWXSIAWWDUOBLSDGTSFLIKGBBGJWTDOMSQWNRSYOWPBJTAJDLRPCRMKNRYEATYBMAZIN9WNMRIHLXGGVIEFZQGAGUSUNQKFAFUI9FR9AIKNBCGGFFECROHFURFC9GFMAUXMPJFWQVRXPLYF99OILFIQIJYSH9HGAZPCJIFHGTZIVGENZHBCMNHOYNAESF9FNMZWLLLCCRMUUFOZVCXLN9OQSODU9QOZKBOVBLBIVZXPFOEZEEXAUBWRWPWRNRYVIKQKBBVOHI9OH9FCQAVQPVVMWFVKZKOCUUSQRZOESNVQR9ULQGQBJEKYEZLXHHIGIAINTHUAXOYJS9NFTZAQIIFPXYMGAFHKYQHADRPQNBWGQXMNSIARLUODCINRFH9CMDIQYAKNJKDSBHGBQJQVA9VHGIHFFSWAIQEHKRGITSLCDBTCHDSEAJSVGGGBCRYHOMFEYEDLDRQVQBBRFLFM9UBOYTIMBYTWTF9VUKUJDRWKJMNFPKKVHRRSJFOFMWJ9QG9SIXCFHNYFTAGQKRUIHVXJ9USSDBJGWLGDBBPRXCOAQPWSFLZXMTCWLFNPEJQFH99YPMFOZDHJYWAJOBECPWONQCPPFNLCAGNJRI9XPK9O9NPWM9WRJKQCDLVWP9HZNGNCJZVKTEUOXEDRVSFBWEREFDKPCU9QATTUXXUHWJFNJSUIHMND9EALDXYCYWEUPJITOTKACDUYCHS9GVTJGFTCLZPIARZAWNGPUWMQRDEIXDOIFUDEWXFVVGVDRKTQIQXLEVULRUJEJGTCDLAOLEFNLDOGLWHYUKGBHSSRURELGFYKTVQUVUXJLMY9ICDMPHG9INCBNABNXEEWOMWQ9J9NQSIASZJLKMXDIXMVFPCFKLM9YEMZOGZVTIF9WHYTYKTRKDXAUIIGJXKPQ9DPVEACFPLZHGVIUVJWML9IEGJXIZNSUETRYORJ9RTEAOZXMTQHAGVFZKHEQCSBZFDD9XAME9ENSFTJZDHRVSQW9XECHIZYAJXXECRBMLNCYSFOH9PNJ9UXOWBGCYIRIAOI9VVAIYOLHTLBYEKOYMOCSVBFCHHCTGIBOUDCXXOCUCRMKTANWHIIXW9LSBYWJAQOPMPMATNGUHWNCBNL9IYJEAUMWSXAKBTIPWWSGXZZCOBRIXZFZMHLGNWAHVTAKTTSN9VNZOLGJJGAHPIJZQBITVDSXNXZTRMIDLH9XFIOEYUVJWIKLLEAIYBOFFUPCBEMMXBDGTZDGFJCBGZSD9CRIGSQSJQOPFIBWSGDSVCTQUHWQWRDLMEQWNIMCSQA9QGQIRSTBXHFVLAOHUTUZBUIWHFTZEDEZGVDKIBUZ9CDJHKWLMIMQZSVIOKCLSURPXHROHGGWKF9IRA9GCOJUDKXYPNBRRDQTNLVKUGCAZHLKZTNNTKUYYZVIOPMQHXIYKKZVN9PELGAKAUUGKCBYRQOZJT9NLVDEVFQXIZKXIF9MOYTJTDTOQJYQLQKXQC999999999999999999999999999999999999999999999999999999NYBKIVD99D99999999D99999999WNQNUFDDEVEKCLVLUJCFRRWBHSHXQQKSCWACHBLWXPEBWWEBJWJXQQBFJ9HSSDATPLVLL9SLSRFAVRE9Z999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Input #2, Part 1 of 2 self.assertEqual( response['trytes'][1], - TryteString(b'MJ9UDTLPAAOHPYNXBLEOLLHTXEBTGAKYONGZUFJAFEDKZYUBAEDUQZMAMSYKPPWCGBK99QAJVXCDXYKJXTQFTG9BSWEKXKWY9ADZVHAMQQAUCEOIQPRULPHGCINEAI9ORHTTCEHU9GPIFDYMOZORWNZYUZNEFGF9WYRBKLSAZTXIFKODGYAMKFJODJRWMLXUFQ9WFJKLWT9TAVINDIALUWQIZISLXDOVKGZPIYNRAQYWRZW9AFCEMTOBSHJEEYN9GZ9ZUULYDHYNEQSSETKYZVQYRIPNRWGRBCFLHRUAKJODCEMYRFBP9EVFKXL9ZTERUVFCXNTYFJBHN9GUGYDTIXXTKTEWSDM9POVBSQSKGBPSPTLAZQ9SENKYBEHGHPXVLI9UJULIDA9KXVRRQBKKAQM9QVZ9GEOUMSMMMZSBQVAYWUJPUKCLDZBHDQIGUK9DOADAVEO9GQTVHLMPXSJQZHEYDCCDHTWKPUEJBAIQ9ZDYLLYTEIBCFZKLZCNYEZULRNSUGPTXZBEWGFVYRBZLSTRGCYSTML9ZGVNXJAQTDASQENWWGBAPNCZHQOQWDXWSUCYDDIDIXRUJXCETUDIDBZJZTNJG9GUDYYBLHRPSZORPOITTJVAGNTPKFURHWMGU9E9DSQQCVAEYEYDPZWBUVPXAFGLKZZWRINYOVSAZCINPQSUKCFDGDSRCCLKLGGOQIJQWGCKTLRBQOQMGSOVYGBVACOOUFINHRQGQBBDWWMVJTEZJEBB9LD9ZNUEYBFRKUZEFT9WRTZRAXQPHHCNGBHRERZDCBCPP9JQ9MH9RBZPGSL9HJBDHPL9WHKCRUVHFWHJSJFWAWEXCTHU9OYKNPBUMSIMONQRHWDIQXETDHT9QGSNPXGTDNUCCFHCJONIDIJADUINVPAVDZQJNOQJQPBMOSCHMPEGHGPMHMRUUWURB9ZPGENHERLURYWLTVVR9GXYGCDCNZLVWVRPKVRXNSXBGDLBBKVGUAJUGGNUYVJSWHKVYT9LYFLVMNBUJDBLVXGDDIJAQKPGUHRTPWNOTLUKDMXGP9BZFKGGJRRNOUNBWZAUZSMMVGZOKGDJEECERVCMJKXHNLFTI9XCZQXN9WGGQMKXXQSIDSXT99KGAOOTGLDJHCPQJPLJDCZQAGRXYADFXCFBCXQGEVEOCKEICIVKVOMKGBXPZHQ9SXDXBFZZI9THLXOPTTGTPSQJTBBC9VYZUXWNENXQRVGKDY9JWCYNXTSAOLIDCBINWLLQDUNYAQRHAZBBROWSCMANZJZYCKZGAVQEI9CLDNKFDXWZMBMGHFEAXD9CW9WHZJ9LTZWEWKETMHHYINLADMLTQEQEVAJOVCZBHEASNWRATZNQWFIVEIXAJEBPLCRYA9JCO9XJPSUCKISZ9FKXVYDLRIKVIFISWWEXMHEREKXIUBFTBWWYVRKWJOPPVSYTZZRLFWAKHBYETICAKPPAJPADYVSFXSY9IVADYPWTULJOIAYWCUBBCPJBEVWIFNWDSWGVZSFSFFIIEJXIVWJDNHJKXPHTRQGWMVYOUQYUZQWNEHEXCARMOKYQSKWEJKKKLDGKJBXQKODOGJXDSACUDHVREMWBSAUAAKUYVAHTUGVSUEVLWRFYTURXKSVRMTFLEEGQUORVNPXEHTIJIGC9MPCOFKARODEORLUGHDVFXVQZYFFIXBSLWVVOICMPPFIEK9APVOCENJ9DFAQ9CQ9LUAQVSDNSYKXBCSLCGYOIVRGRGUSBTBIMSQTNQYCZ9TFARMHY9XXJMHFUVDWOYRBNBSADQTZAKRLYQFVAMSCXBTHVWPFJTVENWKHHOCURLKGCCGK9SKGFIASFHPTJDGKOIRSKNCODYCEBSSCZNZAMSOTXBCFPGLNJHEPJOP9IIIZXRHTMFEXXZUVKDXTEIUXKBFRTXZTMGSXRWBQQGKBSJWHEXVZL9EKECRQQGWG9OTMQSBBAZAMBOHNGVDBM9NSXMRDJIEOOYLISNGNIVKKQHWC9ZIPWHJUWCXVQZOMRKZ9JCHAXS9RZWC9RACAE9EKZGJHYNLWPMZYDYP9MD9YVA9RCWHMFDRVEHLQV9RORXMULAKDOJOZBOYDFNLTUEJHIPL9CQKTPFYKBUREGDWUAUMZUXMCJFQMZUZXLTGZSDTLW9DFFWGKFIOODTMMXMCQHRNWRUXCGYQGTBMR9NQDBTNNTKUYYZVIOPMQHXIYKKZVN9PELGAKAUUGKCBYRQOZJT9NLVDEVFQXIZKXIF9MOYTJTDTOQJYQLQKXQCYZ9999999999999999999999999999999999999999999999999999NYBKIVD99C99999999D99999999YBPL9FUHMJAALACSDMDFUKKBTUPCHTXNCASWTZJZMYLFPJH9MWDXUCNGAVYJWFFQNHCABKYIQBTJWSZID999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('AGW9TDZZYGMN9CAHSJCFOBFJCWGBEKETZPUJK9IXAWDXZTCVFTNJSHHEVTCQHBVPMFLPLDCSGPFFWWBDCTQFTG9BSWEKXKWY9ADZVHAMQQAUCEOIQPRULPHGCINEAI9ORHTTCEHU9GPIFDYMOZORWNZYUZNEFGF9WYDXK9CZSKLXVGBHOMBDBGFEMPQXOXBECKEXCQEEDRXNK9YAFEYWXPPURGPKSEXGIAOJDDRLFLGTUHTIHY9EMTOBSHJEEYN9GZ9ZUULYDHYNEQSSETKYZVQYRIPNRWGRBCFLHRUAKJODCEMYRFBP9EVFKXL9ZTERUVFCHH9KZQKBSWZHCGVWDQYMLXDFVDQESOHZVYEUHCROFERIOBOKEWHPWATWEYLCBMQUUVTEWGJBSHGNARCU9QM9QVZ9GEOUMSMMMZSBQVAYWUJPUKCLDZBHDQIGUK9DOADAVEO9GQTVHLMPXSJQZHEYDCCDHTWKPUEJBADZLKXTQKPWUJNZAEILVYCMQFQURKDVQJPOMTJHGUKPYTQHJGIMICF9RVAYQEJDADAHBOYXWRCMESMKZWZSBICV9VSEEGQFNNRJWPBSPZQLDYETZ9TBQGTCEIDEYBRXUYHUQCILZULX9NPUFFYNGIFJJGBYMUTBJMHYOWQEPUXMFKTLTFYEPNQVWRZQ9FFISZBUADRSZTRLQSQCGJXXPN9AUREQNXXGOZCYDVDJWVFDKMJG9CNGXUJQELTWJMRB9IEOGCKGE9RQDANXMTVMPXCEOEQNZG9YJCUC9HEC9QYZTNPPUO9IUKSNDAIAFIXPDONVZXIQJRQCBCTJXIDJGYHXXVUMYNFTGBOPRYRNQDVOXLDLDCACNLOJEOSDVZIDMOVPVKOARQUQNCKWKFHBSHBQXBUDBMZ9PUJBBWVSL9RPUDORRVIQCKADBUDIUVPZDHU9QHDHAWZCKNKVVHCRULLGJDSINCHUILZDWAACAIUVBIF9NRBSODKJGBMTWOBKJANMJLNDRN9FQNOGYQTMQNVS99LAIYNGSMIVRDGRRUJYZUEATJNGXBACDVHTKHGRQELJUPIUYLPFBRREZLFMFUOQGKJWJPSEAFJIALJCHPKZWGJAEVNPQCTGFJTNSBAOMUOXTURUCCKYZCAESRJHEMMYSADNYZKTMPFZAQRHYFMNXZYC9FAHDJPNSLWFUE9MRLUHQYBOLYYGMFJLCIECWPJIRAAZTB9YHLJNCVOUKKKBAHAVFOXSHLDMO9OAYLYCJWXINBHFLHGFBPIDIATUZAU9HCMQZFZLUROQQDTWPRUDEG9AUGBGFNUXIWGQZQAXQX9QFXQPJARKGEZRQFGQEEOUPCYVWHLBP9OCUZZSPOIWFJVXLWSMKORXPAYG9TVOCNNHDIS9CHZLZJBUQRKEA9BSWPYCEXKUGSXXVQAQSVVDWMEACSXHYFDRXLILR9Q9SK9VYJWQEJRJVWSL9KPEHGZPBQYNPQZVQPNYCOOJVCTOHOKQNFKDPEFMKDTTLJZTURRGOXEVUNEEKPNTQDPDWFANWZPBAJYMVYOUQYUZQWNEHEXCARMOKYQSKWEJKKKLDGKJBXQKODOGJXDSACUDHVREMWBSAUAAKUYVAHTUGVSUEVLWKQADVMKRNUYIBEO9BCSPSVFLWLTZBMFOFSGEKFTOAGHAVJ9YRSWFBXMMACGKKBLFPALET9ORLUPLQNQWWYW9EWRLSPTSPF9S9CAHGXEKDLVXFDTVVJDLQEOJNOZMUBJUHQXIUVD9ZFCIGCFCWUJUALQFDULVEHHOWWQXYHXXVSVCJCAXPTJBWOZRXNHBW9DRSBVEWHDDQJUPGZQVBDL9OATVSZKQQFNTHNFFPXJSQZXJJJZDEQZNZAMSOTXBCFPGLNJHEPJOP9IIIZXRHTMFEXXZUVKDXTEIUXKBFRTXZTMGSXRWBQQGKBSJWHEXVZL9EKECPAFTVMVVGKE9TGGTE9YLGGYMK9PKBERBILUCPIQZTKCXSATLRKBGGDSWORLQUKSMQLDLUMMML9VCMZUJZJVGHGAXDELKIAZYNAHPCYSPUYNNBZ9MBUQGRKBEKIHNIOGIWQLIS9NBBWDPWGABMIGADUMG9WKFZHQIPYKDMJTTYQRJWYXSBAPDJSKEIUJNOMNDNGUHEFBSDSNNKABHEJBKBRIRLKSQBQIRPCQJPRXWDDBIXANTCLWTNNTKUYYZVIOPMQHXIYKKZVN9PELGAKAUUGKCBYRQOZJT9NLVDEVFQXIZKXIF9MOYTJTDTOQJYQLQKXQCYZ9999999999999999999999999999999999999999999999999999NYBKIVD99C99999999D99999999WNQNUFDDEVEKCLVLUJCFRRWBHSHXQQKSCWACHBLWXPEBWWEBJWJXQQBFJ9HSSDATPLVLL9SLSRFAVRE9Z999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Input #1, Part 2 of 2 self.assertEqual( response['trytes'][2], - TryteString(b'EOWARUTCGMPDDIK9HLSBJUNJNKFQ9W9EHNWAWCVBOWZNPDPI9MDARRBMMCQTVNYKQYKO99FJY9ULJLRYZQRC9XTVDAFGNRNJHXBWCUQEUNJKTCXKIPHQWRV9KAGREYBHXIUFNS9DIQWJEN9FEAXBOZDNHSCLOSGKTDFLVVEDDRSXKSFOAIIDHDVEW9YWNQZQUHGCBYDZUZGINOLCFKHAPPSYMEIGRHZUVP9BLFFGHYWIOLYF9DXXYUKVSYMLDGMLKDEVERGZ9AWDXSOTVCWQVES9H9YE9LJJJQJCPUVFNCJCVHPAVMBVPODVWGZQJ9ZQWITDKH9DIRSGNGN9ZYJPVZOJAOXOPOQSZCSDILTOAUUMLGOIYG9MYSYBQUVDDDBCFTDWUMPXUDHZBDBAHTUXZWINNALMYDJHGJLCFCJ9KZZNTFPZGSLXGEVEGOWSOUAFBJAY9IOEVNLHFTIWEFURULVEFSDURVWBMNUTNAQAX9NYD9BSA9XKUOEKSSVI9HSAIXLG9PCZKWKSLGOBRKGHSPCTREBYTKUBUWRCCHTDQPFMQBIKTAVXVOCTGUEZCEHGXOGSBYYZFQ9WTBUKSJEUIXJVCWBWQILYUAZ9LBXRRQCQWGMEMU9YNU9RYUBEJQYDZOOFXBLWBRLIGVP9RZKMLPDCMKBEHY9CUBUDVPFHLOFPFOEHUCFFFKQC9NXTNDHGSVNVONLXUZANIAOUWDOUY9LFXGFFBFYPECHONGIXDXXRFAXZIJIXZRTXOOGLZKUVNPDSBSQPWZIOWQQQDQHZJRRXMPYVYHFAPYLESHJXJDGYHOGZUHDWVIXGJEIMQAQACAGJXDESBXPMZM9SOMNEWFVLWJHHBPQRCXVXDGQIAPNTPWNZEXTBZJGSKRXKJPMWPUSZYVUGRJHFHQBLLMGXZWWOQME9PUUEAQNZCZNNGN9LDHAQMDXTSRV9LDMGRXBLUIDEJPIDT9TZDHWYQZQWCUVKTUZGNZ9RHIBWMQNFRQL9BDBRACLIVCWLNZQNEADVMHAYFLMTGZSYRIZDWIWMVGU9TBFEC9XIHFK9GMGVGYBADQBGMQB9IWKASSSLC9OWZG9AZEYRPMHQGRCFKUOPEIOZXUHTUDDLIRHENPXFWOQMFBAKZHKOL9RZLCEKCFTOHWWTBVFOWDKUDWSSMDZEKPEBQUIE9TUSDAMHIRKRGHOGRURYOCTYSDRLIZIADWXZRPCBVHOFZCJLZTQZLPCDRNGBREQTKTPMWVDDNLKYPVCUGPBAQBYCQGDVOKBGMX9WHKNEDIJXEPIKPIQWZVO9UVYVG9QB9KPNHIDAMHTVVCHVKAJREZCZETYPQFKRCNDYGGLDYSMHBTUXGNFPHZVQOQQUBTADRQKZCVCVIABGGNPDGBVWC9FBPHVVUFBPPBBCLXLKYBFH9LH9AVKBIFKSPWZYKQPRGNKMAHQCTYFQWAKIY9KYSCFGZTTAOGWPMKDMQGQSVANQL9YLOQCCIATBEEOTELNTXVJTLOTZUPYJQEAQMDCCSU9ORYZBQJULDQVXPMDNBWFXFPEBIE9MFFPIIWKXDVCPKDGBJFWTICOBRUNKJEFBKXAAFWXYPSCVFRLUVKDSBSUYCIV9UPLJTFYWGFJ9ZFYNOM9YXMHOYWFDDPIJOMTD9KGA9XCXGQHLZVBEKEUWLSC9BFSUTFJGTUHNMKOJ9NQC9UXJXFQSBDOUZRTMPOMURVXUAYGFLGHNKRDDTCASPTBUIDLUHH9HBQHPBRIUICIGNYMGPVNUPIQZOVFHLTAENGAYPWLCQE9DQPLMNPCJUFBPKYGHPHBRTALLMFUHIATKTSQBNTHGRCZILLNCTSZKJHQNVYZ9LOVYYSEXJDBHBBXEKCJEUDDDTUBLWCWWRRGHSZFMJIIEMVABUFNTNLWMVYG9UUVONDX9AMEO9WEPWAJDLRISKO9YCBIYQGGDMJDFDERJNNIKRROFSVLEBYFRJJOOSEWWBYMTIQXBQBYMSFAFBXPMVZAKU9LOGBEHKMOZDMSYXRVEZHPPZPKWCTEEAPFLHOGHJPCFQFLSFHTKRMZEKNEYHQZHLG9E9EUHKKUYSAQTOZWVPQSGFPRAZT9VSYKWRBEEHWPDJUKDCDXUCQCRAGSNAMLCSFOBMIRJFINXNGTGHXSRGFQCI9JFWNBCM9WDEWDPDGMNXMNKLITPRVXYHHCMQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIXPQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEB999999999999999999999999999999999999999999999999999999NYBKIVD99B99999999D99999999YBPL9FUHMJAALACSDMDFUKKBTUPCHTXNCASWTZJZMYLFPJH9MWDXUCNGAVYJWFFQNHCABKYIQBTJWSZID999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('KVTQSEYVEVEGDETHHKGCXAATAPNN9GDDCUFVOGJXFFC9HAGIMRLGXZMDUCNTJBMGDZWSGPPLZSUOKONNZKRMJQJHRNHPUX9YEIIPOKZLBZUZLDKPMVNVRLUTQFKQIRZLEBIIGBROFFMQVCPQQMGNC9RTZOURPDUNRXVDJUCLZFBEWJDVGCAEDFT9GQSRAAITNLENXSQDILMILGXYHEVCBWCWTHDAMST9IAXCLHDKKMJDWLZDGKD9SNZS9VIDJIFJNHNMHZCBINTWMWFTUPPCUAKEHAXLANHIBDSLPFLTRQSDWONBI9NYJFZVFCTRXOUMWOWDEIJBDBHIORZUVJXIIAXDWPNHXIBKPXFXMXRGWGXRQQG9NXHM9DDYUIOZMEHXTTIZQHNQGQVBKUMSCNABDWINNALMYDJHGJLCFCJ9KZZNTFPZGSLXGEVEGOWSOUAFBJAY9IOEVNLHFTIWEFURULVEFSDURVWBMNUTNAVCEOXRKBZTSCZN9IODZATCQUSPOWMWNBBNWXMA9HVAMYKYAQYHFFKFLBIWYDNDCTXPYVBNKREIGKGMTDCQKIHMAPQGWUMICACHQJODIQPVVWCPUBJC9NWAXSAXUHPMNJEJF9MQJCAJ9LMPCT9XLPLOLCDSAJYPZYUCMURTVZIOZSRMLKANEEYSJAGVVPBWTN9RDUJWEGBJSN9RDPWQDSKDXFXXIPUQATFRAFTZFUVKOKEISVCYZM9LRSLJ9BYNPLUMAQNUHXHPDLHQCUHJUNKRFSUSVWLEPCRIZHWKXVJCAPPGVMRXXXEPNELUREVCCNMEGA9LHXJZRCRWJIRYJPDRYOBG9YQUVIYJPAFQTMIKM9Y9MASZA9DALXZDXFUFJBMBPTNNENFPVGUNLXSNHTXSUVAMYEVRAHPLJDIMJCDUNN9QCJKHDXFSW9CEEAGXOUJLELTFGOQNCSSANOCDNMBMRDKNXAWLXWSTFKPYRRSBCWQJHWGPBRDQNKGHWIIJGZTANNFBUCGHJKCWPLFTVLYWBWTCASCSNHQKSOLKRJILIAVLBTYVWFMA9VWCLNQAMGUGXSLUJFDXZNMXZXNSTTQOZ9RTXF9QOUSFVTZOTRNZ9SUHXFAVITYCNYJGGOKYTWZQCFOQRCRGRSQVMZZNOIOJAELHG9JYUDLUTSOQLWNGIJTHGVELCK9VFZSFOTYHJWAFMMKDGGUSNSUCRKGYCRUFSPWEJLMLAHDNTCGVIEBSO9SC9NDIZYIMBRXCURBHYMAEB9JMAPWFUZRRCGRTLZRXJVLEPZ9QNKMERNSMFKAXPLZQIJXAAWY9SYMFXXOKGIGPF9UVTXEMSZZOINHKANZOVGSEZPGUSYKLAUJKZKNVDZJMS9CZRXCVGFUO9UMYVJZCUIKIXJTUFCRW9E9CJEPWLENSXWVMFA9PJZTLFFXYWRCWTDPICHS9IINY9ZOPNJWZ99IWJJQFRXTCEQAMBFQNXCFXNAPAGDMUJMKVDHGHSZZFQRUINOYWNXTT9FGWYAXWVXJ9YGZYEIKG9MWN99CBNOQWZVYYPZ9NPCYQQKVTWVKUBSTOYWRMFDUPDB9XGAOTEUPAFDVYAEIQHBPBHF9CXEDSOOF9DTGBJOAWHJYKNJ9CWRCATOWWAPTXQQTITZUQ9LXCFDQPCJHFVDPIVQHPJKSHRDOIOQBKECCNOOHDUYKYFYWUBJJGWQMIIMFNZZAOGXPSVZSZQPUPBVUTJNGQLRM9N9AYJJHBBINQJFNDATEPMKYDQNPKPJ9NXIUCXSOSQOC9M9SSLTBHGWLCQE9DQPLMNPCJUFBPKYGHPHBRTALLMFUHIATKTSQBNTHGRCZILLNCTSZKJHQNVYZ9LOVYYSEXJDBHBBXHOFKVWHVOKUAYPGNGRGARFGEINTOJVMDSJKENFJADXBOZMKEJGAMSQMMETTCTDWNQWKYIGVYQVFMC99N9MJDFDERJNNIKRROFSVLEBYFRJJOOSEWWBYMTIQXBQBYMSFAFBXPMVZAKU9LOGBEHKMOZDMSYXRVEZHPPZZCBNLPDUDVEPPYTCLKF9OE9YROSAJMJHNCWVYADGEYXIBPLDZBQMIESEYBJKONUUWGDDCD9SBPHTMJFBXPS9SOROVFBXDGFJFYWARMPRRMRYN9VDRKBDKHSZCPRDYBZOXCUWRZXXAYRHELLWMDTMV9VHVICXSRJVOCMQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIXPQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEB999999999999999999999999999999999999999999999999999999NYBKIVD99B99999999D99999999WNQNUFDDEVEKCLVLUJCFRRWBHSHXQQKSCWACHBLWXPEBWWEBJWJXQQBFJ9HSSDATPLVLL9SLSRFAVRE9Z999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Input #1, Part 1 of 2 self.assertEqual( response['trytes'][3], - TryteString(b'UZW99YV9GMPLXSPRTMJFFGOVNMUNUIPSIJTLBUZT9YCAXBKRWYDVKOMTKHW9STWCMHUBUQHZUGNFMALYCPTSOEEYANVTHWJRFHRYJ9D9JIBDVQLTQFDBYLXBJWAEJPPRHOXSZP9KWKNLQCUGMOKMHJQYODRVVYOZ9DEGJAFBQNIXYXJ9PFGAMZXOBZDQTKQGSTLSXEJBJ9IXICGUFPONWTRIPZXVUAJQIRXYMKONHSEFMCJML9DGQRGLMGLGKEHWTQZWOMIZIF9FWUUMVVWS9CWUMWCHZIRKTODTRLEJTRNA9CCRFJNCVCDCQID9UDQJHGN9YIFJZEFEDVMT9PUYWCABIHJMPNQTSQQEJBKRVQYLGHPYRCOLWKCTKMPFCMOMC9PABJNHFPNJVCYNPAIMCFDVHWOEJIVJOIKPMTCAQZZEFEL9YSOSRWWGBQEPFJNTLVWOXIEPZHHCIQF9DZOQGUKYOJSIFHARSBORDAJRVCTTIEBUD9ISDDLULQQQPHZJTNXOBSDGDWRGCBURMWUP9XQTYIYRLCGWGIWWDO9SQLQIUZOGXQQOZ9CZZINSZAYSLXJHVRQT9DGTLTIERBHIEYFGCHLFUEZJHUUKCZKRCOWSTYIGNFB9TZACBURMAGZQIPEKPHUZ9HIYGWZKOEECUJPKYFXMW9TDITMEOBNNQVJHECBQPXXAETVTHCYCKJGEYVSMWRAXBREMDKCHHVPAED9DYFFSRP9WOFAARRNLONJDNYLCBDKPUM9HYKRURNIOFJBIDJBKYNRVZKTAITEWNMZLA9XMJHIPNUJDWQ9ZRDBJXNZCXADAFREDEDG9EVDYWVFDOEZNFJKJVEXGVSUSOHKUFIGKRZWCVDAWBHVIAEGRENQJSPZMSJXK9VDSLNPWFEVZPFD9JRSV9YOOTJHYKV9ZWKPGBEAPATMINAESECJXMULWYQUENYNTAEYITFUZOTFXVCOWTPMCDKWBYOPWHJMUFRJYQNJLIXIBQHYKZTVGFRDMENVRUAGPBXHJEDVXPEEYWHALUAIFUCPTIFBHMYXSSYSPWOHRXDIKGLRHRHKXIOPBQFQBHQTKGPMYL9THJFRGIFBY9WKIMQSUHKUKFQRDHFUBGPWZNE9SWREBKNIOCAZXFSKEHYBZPWOLDTPVUNVUTURRERGDVEUOCE9NDEHIZWRQCSNUEWYMOAHJGEARXYYLGJGQGASBVJAYZCCUTXIFIHQUMKI9MPRXRZAFUYYSPZQWIDLHJ9NGU9WYNLNRWYKNGEZIKGSZEXL9BVIUNFUWMDLONJTFIIXWUETTMSPBUGHYTHJTJCCXQXLGMHUDJEBVQPCHKYTXJQBBIGRGRWPYCNCYRIOMNSCITUCWHIVOMKCXIW9UZAXRQLKUEH9PZBVPHB9VETTZWFIDEWCHJIHW9QVZHPVUSAEBTLUENJAMSYSDVNPVEDXJBGYYBQLQDXLUEAFJMDYEGDKRTUV9DCJNFZZSFMQX9DCZ9LQLVDOCNFDSNGR9PP9CNHAIAPFGVUUMSMOBUQJWDBAFJXHLZFZOCSK9OQIJYFBRVREMNRJDDHOPPITCXZYJYEAARBNUZYBVETPPZHMFCOIQLJRQYDZYBZCSHERQOZDKOSZWP9QHWMRSYESTDRPGW9HZKKBGHHPBHAUYXLE99OMBYHUFJUYGGWVUEPUXJVEVAEBFJRRFPTOIBPDXSIVJWPZYQVXY9VF9GFTRNRBZEHWFSCNUPGETVYGEJJJQEVFIUFMTFHMDWBTEIWFXGERGZLLMPMKNJSI9AGNZNXWYTJTXLUJHQHAUPZZIAXKCBAECERGTBPCKQZEGSRZIZTYRULGOAXETODFXIKBEZQETMZ99LLTUMLYWA9DREHWALIM9AYCBQQFRNNHUIKVJVIGTGIF9MUMSYJIZJAPOXHIFXH9PPOUOGAQWAKFGXNJDDISLFELAOKYBHMJUYHKXNZQAYWPHPICVMMQOSNOJFDOGPOPMZITNCRT9EXZPRYGOGDIZBWXRNLCGJCNGQDXYYGOFBARMWTPNNTLJBHHPKDDBULTHKEHDTTZUETG9LWVQCRWADOQFMIF9GOCZKBZSWECWORPZUXGLO9WXIZ9QOBANDWNBPMHBGCJ9TLS9WKPGCAJDPBUNU9OMCKMZJVLTUKPZLD9HYOAFKBKLFEVPJGPAVNGRMDYYBARNZHRKULBMQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIXPQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEBN99999999999999999999999999999999999999999999999999999NYBKIVD99A99999999D99999999YBPL9FUHMJAALACSDMDFUKKBTUPCHTXNCASWTZJZMYLFPJH9MWDXUCNGAVYJWFFQNHCABKYIQBTJWSZID999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('HSXQRKCIYXEEEEYMESAEWHGVRBNNFUPVHVHYDUFFDCAPYCLGTMMSYVZPGMVMGZFNDAKUFEKKKMMLCDLCYPTSOEEYANVTHWJRFHRYJ9D9JIBDVQLTQFDBYLXBJWAEJPPRHOXSZP9KWKNLQCUGMOKMHJQYODRVVYOZ9DMMYLMVBCNZSWASLFGJJY9NZO9XAIAIOWBYDHLNIBMQJLRBPZJGJUNOKYFYD9VNESPEZNIPUABKFNIAGEWGQRGLMGLGKEHWTQZWOMIZIF9FWUUMVVWS9CWUMWCHZIRKTODTRLEJTRNA9CCRFJNCVCDCQID9UDQJHGN9ZSGJGRSBVBYBKSBZNEJGZZHIECIVPPV99PVRHUBHLGHAZNJRY9LDB9SJGTXXHG99HQAOAI9JVPIYOOWHXFDVHWOEJIVJOIKPMTCAQZZEFEL9YSOSRWWGBQEPFJNTLVWOXIEPZHHCIQF9DZOQGUKYOJSIFHARSBORDAASWFIBAYHLPUTCUPJONWNQVKIHGKUFHSYKQJCNHYBKETAGEZKMPPCOECTMFZPXPLDHMVOSSU9RMQAQNJZYOXVJLKYZJDXUO9BKZBAK9M9RL9NGNUOVZBAJKCAEEBFFGZZJHLGL9KHOQQVKJYQZJYDTCYJXBJBUZZPACRUDDGXWKVRTVNOAVMYVGPEU9IPLHWFXZEHHUMJRQSQOILKMOKTSEBKEYSFRLH9YLDGGPPLSGFCJVINBCKIMXJKWLM9HTTAIVNKGUOHGJYPPDVSYAZLIFJBKQYQLLXBQUZJMEWUPLRVUOMXBHBUJYGDEGOPWNODYSZPQGBYZKQVXFPRAJNKIMMBWJWLIZLIHPWBSJINAPLU9NYHS9ANDORELEDICPYGWQQRGCMQXSWNBIHCSXPATVHEITSOTMKPSBBACQMKLTCDNTIYBXBCGFGIIPERFKHQKOONRHFEPMRIFJBNUEQEFCVMAXHARRHZZQGYALRQHZFBUTFQRVPWWPMWFQCNFDYKFDEGLGSILJRTSVGSLURIZPERJRLSGOMESSMZDUVPBXMOCFGBUWFZBCNYOBGZWGD9HQJOOLESVVAEIWHEKZXGHBEQHAMAPCLPQQRACGTWHMDCHSDGFEOISFMWWITNNDRLJ9TVIBAWKFLQIEHBRUQHYZYCGJWQIMODPIPHFELJCWRCIIKYEQNRSYCUGWXMJSOFUEBCKPXIOCXP9OTZOIDOSWPDNUTQXEHILCONJHHJFPAJEVEBVXROKKLJCZGXMOLB9U9NLCKZ9XUVHVUMWFFPAJZYTDJ9DIXFDQYRD9LPASBDIDHRHHUPOFWUAPVTCAAPNLDPLPN9XTEMOJSBBCHWBULFNHFMMPRSDQCNP9TFMFJFUON9ORDEORLGHZA9JZTRGUTOWLO9XWMAQZXHLUPVTFRSQUDDHYQRGPBLCOHDMLFKQVJAAKWFINZKCTFOESRDVWYWUAVGVBY9RLBQIC9GNXZIRQTY9VHAOIAXXIOVIMSVVIVONDRAXXGUAKFEXLUZYXVMZXOZKHJOKUSRVBUGZXFFDIYZOCSK9OQIJYFBRVREMNRJDDHOPPITCXZYJYEAARBNUZYBVETPPZHMFCOIQLJRQYDZYBZCSHERQOZDKOSZWQJFUMPXYZWLMDZJFYBNYFSKSJUHGOVSAIIIQVDFQWLCRVKTXRAORLNWKZEQRCCTJRMRYCXUJDWFPG9U9WODMOJKYJFMFINHBQSYVGJNNTJCNGOGKIUCDKTNMGFZZLZYYXNP9HPTGPINRDBDLQOJAEOYKAKBICWYZLDSZWZGNUHVOXYLMGCOLJSCXNPMVPPRSBRVEAQDAX9CEDRXRUAJSULVKAAKRMXMMWLPTYTYZZLOUFLBRUGDREHWALIM9AYCBQQFRNNHUIKVJVIGTGIF9MUMSYJIZJAPOXHIFXH9PPOUOGAQWAKFGXNJDDISLFELAOKYBAKBDTCTZDIOCPVXGTJILYQMPOKIVPJLGPEJFQE9SBVGBDPWMPWZPCNGBOVQSJLLHPKJIKPA9AIQZVHJYYDXSSNXAUDLKEGPCGZQZRXUWXTZMBXLUYJZBEPOTCHZGSLXUDI9PGFNHOZRQLQDWFURIXMDINYQDCSCUZBIDRQOKQYTXKSDTXT9YZDQBGJLVQAM9TWRHPKPJG9OAHJNRQIHPUSDLJHSTRHSTSQURNPOKQYVTIIOY9DDMQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIXPQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEBN99999999999999999999999999999999999999999999999999999NYBKIVD99A99999999D99999999WNQNUFDDEVEKCLVLUJCFRRWBHSHXQQKSCWACHBLWXPEBWWEBJWJXQQBFJ9HSSDATPLVLL9SLSRFAVRE9Z999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Spend transaction, Part 1 of 1 self.assertEqual( response['trytes'][4], - TryteString(b'999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUETWO9DONTUSEINPRODUCTION99999XYYNXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOWOB9999999999999999999999999999999999999999999999999999NYBKIVD99999999999D99999999YBPL9FUHMJAALACSDMDFUKKBTUPCHTXNCASWTZJZMYLFPJH9MWDXUCNGAVYJWFFQNHCABKYIQBTJWSZID999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUETWO9DONTUSEINPRODUCTION99999XYYNXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOWOB9999999999999999999999999OJ9999999999999999999999999NYBKIVD99999999999D99999999WNQNUFDDEVEKCLVLUJCFRRWBHSHXQQKSCWACHBLWXPEBWWEBJWJXQQBFJ9HSSDATPLVLL9SLSRFAVRE9Z999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) def test_pass_inputs_explicit_with_change(self): @@ -680,16 +685,16 @@ def test_pass_inputs_explicit_with_change(self): response = self.command( seed = Seed( - b'TESTVALUEONE9DONTUSEINPRODUCTION99999C9V' - b'C9RHFCQAIGSFICL9HIY9ZEUATFVHFGAEUHSECGQAK' + 'TESTVALUEONE9DONTUSEINPRODUCTION99999C9V' + 'C9RHFCQAIGSFICL9HIY9ZEUATFVHFGAEUHSECGQAK' ), transfers = [ ProposedTransaction( address = Address( - b'TESTVALUETWO9DONTUSEINPRODUCTION99999XYY' - b'NXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOW' + 'TESTVALUETWO9DONTUSEINPRODUCTION99999XYY' + 'NXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOW' ), value = 42, @@ -699,8 +704,8 @@ def test_pass_inputs_explicit_with_change(self): inputs = [ Address( trytes = - b'MQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIX' - b'PQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEB', + 'MQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIX' + 'PQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEB', key_index = 4, security_level = 2, @@ -709,8 +714,8 @@ def test_pass_inputs_explicit_with_change(self): changeAddress = Address( - b'TESTVALUEFOUR9DONTUSEINPRODUCTION99999WJ' - b'RBOSBIMNTGDYKUDYYFJFGZOHORYSQPCWJRKHIOVIY', + 'TESTVALUEFOUR9DONTUSEINPRODUCTION99999WJ' + 'RBOSBIMNTGDYKUDYYFJFGZOHORYSQPCWJRKHIOVIY', ), ) @@ -722,25 +727,25 @@ def test_pass_inputs_explicit_with_change(self): # Change transaction, Part 1 of 1 self.assertEqual( response['trytes'][0], - TryteString(b'999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUEFOUR9DONTUSEINPRODUCTION99999WJRBOSBIMNTGDYKUDYYFJFGZOHORYSQPCWJRKHIOVIYQB9999999999999999999999999999999999999999999999999999NYBKIVD99C99999999C99999999XRHLMDZPZTK9DIVUOHZIVOOLNKFYRMOX9WJZVXCKRITLLRPVGZJKBEWGAZYCTPS9DDAZTOORMO9AFQLDY999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUEFOUR9DONTUSEINPRODUCTION99999WJRBOSBIMNTGDYKUDYYFJFGZOHORYSQPCWJRKHIOVIYQB9999999999999999999999999999999999999999999999999999NYBKIVD99C99999999C99999999GZTLUWOGA9QLYBHUHB9GVUABQHPIJRWUIUOXFIBGYEJWUA9QUZVAKCFLDVUUZEFIDZIUOWUHSFOQIWJFD999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Input, Part 2 of 2 self.assertEqual( response['trytes'][1], - TryteString(b'EOWARUTCGMPDDIK9HLSBJUNJNKFQ9W9EHNWAWCVBOWZNPDPI9MDARRBMMCQTVNYKQYKO99FJY9ULJLRYZFIWJBYENOJJQLK9WPNZOYKIVFEGDEYESZXRKUPXQCGCIMRFCRESTNQFLISJRDZYJYPFXIFJEPKSDUCRTXSKXGTEVVQLWKHCQDQDQYTHRVZDGYALJOQYIVPUGQCWFGXSLIAQZKKMFIHHU9DIJHUCAGJFNFVYLKSCYFDPOQIJUKSFLDRETJJGOIHQOQRIBCVTUEDEKTEQPPZGWBUCLMRUSQZLMWCGKHZRFQKSTCAEJXJSJGZOOKMDEFDEAVOPEPIZAFFGXPJBKOF9YWUGNVZZBWAUMRUBHUGSMLXX9JARMUUQOEHESMAUBYEEDASGN9ZPQUTIXAOWQTYIKNENEXTUVYWRZWBXAATTNJUGBWQEVUQNXGOLGESNXUTRENPIZDHJVTGSTDJJTJXR9VWBYVXILZVCEOXRKBZTSCZN9IODZATCQUSPOWMWNBBNWXMA9HVAMYKYAQYHFFKFLBIWYDNDCTXPYVBNKREIGKGMTDCRAMM9NORHYGETYEKPOGVUICDBCQQVGCWXISODSCBTVMYCHW9PWMSPWRVBGUUBNMUM9PCNHTXKBLYWKSCCNKMCYNFWFJQBSLIAJMCILGJUNCNLXFULXNHEZDW9OZMNWCTKFVKARMJPTBEFH9BBBZKTOZNTACATBNWW9FZ9BIOMKIGAWBPFHZFGXQZJDTAMP9EXDDSBLLQRZKJILUFPMQM9SVZUUOMMLJBHHSYQQIKXLGRKDOBTPC9KWBYQZYCZLAWICDRDKMHWDCWTXQAPKAYQSCSDTNDU9JVUECMPEFHZPXCZEAVLIHNLC9ADFY9IFFCMVPYQFFPWUXIAPIRIGLMIESRRCK9DAUALK9DPHKTUMGUOVDJSGCYXXOZJXRSYFHEKE9LCZXVFFZMBGBIMLNTWDKEOKUMLIRZWB9WHIIYDFRHLSULEBOHHPBOQCWVTKJZYQFEYFXBJVGKQGVLYTILI9VDVXDEHAWMQLLRGBUJJHKSXBPNBWXQGYLMHWVRLOGYCCBTFVSLFNXTH9EHPRCVDTVXWMOHU9MBYMSLK9LPRIZAROMFPPWKI9WSWRPROZZACGLUWVMDKABBNFWBFIRQJRICGHCYODVPTH9GDDLZPBUSXZVYTFNQUHIRFMQAHHLPNNAPFLPXQNXEDFNCOWXUV9F99CFXLKMOSMOE9CKMOHJX9CUKV9CDYBGGEKYKVTMBAAWAVEU99PPO9PMBLQFFRLQGCFIQVJMKNOVHTSUWXXTEKKZCT9RQASRZHCLAIPNEAED9Y9YIHKNUTJOYOYWTMNRNEBMXHCABTDHRNDOQAWATLOGRLRTPOJOGKKIGDWSAUDV9MNXP9IHETL9ZHUOK9GSNJZUSA9KGXLV9GYZQDQETXHETWPDMECU9W9BVVUMKMQRJQF9CTGCXMG9YZWYSWRXDXDZNAXDVOALJAXYVFUPNHAOZHCULZTBADQRMCHLFUJLU9XCBPBPYJMKFKJMSRPKPGWUWITCOOSHUNMGQHFSUSZFGKFCAVXGNOROHKVSNNTIKBATGSGFYWOHNXYBSQQIFKNDRYXMUOQBMKPNCCKNBRSHSIRZSROZLHKPKTSCANHLMWJGFMRJLAEIXSFZXMGCZCKNCXORYKQUX9TSXFBAWMCNFED9PLCXBDEMCDXLKCKVABBGLZEGCESXGTPXPVACXXQLQ99AZMPQPLRMK9IHSQIKQUHQGQYOAGOXSADYDQDTUQMXPNPEXARZQVYTNCTLBWN9DWTBMNFMIGRZVPOUCHOEZSMZRUYYAZBL9KOCKNPKEQHPOLOOURWZ9HOFKVWHVOKUAYPGNGRGARFGEINTOJVMDSJKENFJADXBOZMKEJGAMSQMMETTCTDWNQWKYIGVYQVFMC99N9UTUWXKVLQSJGEQJEZJNXXLQRT9PKTPUZJYDLWUDHZNG9TPZZCHBMELIYUZ9KTDEJSLYVGIQNZQOJCOHCDFBU9JPQUGKGWSVMAW99LBLPJPZOPNDOFOSYAKWREJMJ99SMQWTGBWBKXLQPSFREJOQTOYDLHGSRQJEYHCOGEXPJMDLQYAPQWJGDOEHYFUQZUWSFRVNISOQIDASYGRYJQGEONSAZXCDV9ANDFLGYPFUSLJOILSMMFKXMQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIXPQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEB999999999999999999999999999999999999999999999999999999NYBKIVD99B99999999C99999999XRHLMDZPZTK9DIVUOHZIVOOLNKFYRMOX9WJZVXCKRITLLRPVGZJKBEWGAZYCTPS9DDAZTOORMO9AFQLDY999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('RINVQCDVEUGCVRPVHTSXDJAMCTTUXOAGNEHOPRTTJOHBOMCMB9DFPQKXA9RCNNGDSDNZQSOZBTLQGHEFWPCVANMWPQRPYDDLQYFAOMQSENXSPXERDAKQLGVEENDOTQBUSSUJTG9NNBMYXEJJFWQGW9VXJWXYN9POPADKNBNVJFBNRNLDOEZULNHIZJCQ9ABVP9RWBVQRDSCWFSQSLDWUEXVWVTV9GIITYLOOZDYWLWHDIIUX9O9HIR9NBEYDNTRJGOQRGHUWFJNOQDDFIGJYQLBSWEDTOTKKGSWKG9SUKYMKCZXIDEMUKEQEUYQZXTXVKDF9HKOJKFZDQXOR9QFE9JRORKCLZ9PKNJDXKZRYWZEIDGACMRGULPJIO9CUNLCESVTQOYKYEYVSVVNOZRJXXZHPVFLKCFLBJUPWAVVKDSVZQJTFZIMLDVVTOQKFZDIISJJTTFUTCEOGWQGSDNZPLQLOHVRDFIQKDKCJTWSDCQSYXAFHKGBKPJTHHANZCDBOVBK9MLJFYMRRSPWSYIKUJGYMGWLBZVIFBGABX9HHTWTWJKPVOWKQVFXABHO9UTRMKMXVUWLPTELVSVPBSNMSHJAUDKTYWOSZJLUNUDP9PKECZ9SOYQRZHQGNBPSGKNCZDEWWFYQ9SBKBHBKMJHWHECMFOWCY9IKFZCMZBWQEGZ9PMMNGMPAEBDOQMKJDWGBKYAJZFKTPLHCXEJREIIYIFQAHWWUBRTKGZOZIHC9J9YYDSYSTDRWSGGTWMEYAKJDECPQTLUQSJOJXLTHDPEGWSVGEZSQHHIVACNMABJAZCDUNRTHEBFOJEVEPQTWYXCLTFXAVRLZVLIULKVWYYJPQUOTLFHRLXFTCMQNASKATJGQ9XDPYRH9JZU9TWWYPGDXMWMHPSLKRWUYEKOZUQGVCBWHYDMOXGIDZKIZIUDAUGJMXNISYEXMM9BBCJPSAO9YLRJNSFSEPSCOWJUJRZJCRO9KEZGNXXMREWLCW9BVHCDNZ9KTXAEWJZ9ESEAYYTLWIPVGYY9NTIICOTNDFCTLYANOLMYAYXARMLDPPFSBGBWTTLRGYFOPLEUOYUYKBWXOBTSLRXAKSNIWDDVVBMZ9QMRHYLNPIMEVYVVVDUGERRFKMTBREKFTVZMNN9MKHHBVZQGQSCQXCOXKXSLWZMHMMYXVMTXSKEWMPZYYXQJXJBJFGWHNWSQLVVZSISUJCGMBWWALQKGMTVXIDXABVLDNDRWATSJEKCPHBOL9YAJUIQJBWXSDIRADNWD9BNZGXRBRJEYIAASTQPXURHZYXYHHE99MC9EXHMGGBUJYKHFPCBHGDVNGSQLJHNUIOJDZUVZELWYWEGMLJWOMALTZQDTEDJIROH9RDP9GVXCEWTULWE9IRWLXHKWSWGMFMALPOISEGBGAUJFSVDNMPOGEHSFDSPZYF9TDQVRSZSNVWHOWABD9PHRWBCXECMSXCUAQDEXKXJZXNNEQFZI9WYZMWGLTHECXNVNALCHTKLOOKJQMOAWBNYYDFJWOPWDBZSQFI9GKOQZCGDBECV9JOIWWUSJN9KDADSHSEUK9MY9XTNJQCAPHEYJJTRWUPFWDFKZTNGUBBSPVYSGQWXQNRXYXWPIE9RWYIPTDHRFUNHZULIDHKZGHPMKIYFMBQALENPZBGXQKVAZPWQDHGPYQAMQLSDBOTYHAXFXMNHABVUNUJDJ9IPNZSIFWUPAMJEADYGRJTYNQTLNDXEXZFTFHOW9CWQ99MZ9WUXBWTGORUWFOBYLAWD9UBDCXPTBFPUWDQDTUQMXPNPEXARZQVYTNCTLBWN9DWTBMNFMIGRZVPOUCHOEZSMZRUYYAZBL9KOCKNPKEQHPOLOOURWZ9VKXAQVTIDRT9ZNOFPG9YERTSIIJGRFNIFUJJQ9IDWOSTQEXUPWOFRGJNCFYYQMVYUJSLVCKSEAI9UHILAPEJSMDB9YIBPRUGGKOVQMRINXHBHRMAEI9UTMDCAGWIGHXCECLB9UTPGJUB9IJVJBHWBECQXUSEVBTKYBXMB9IBJFV9GNINACFBUGNE9GSVGJJS9BGPFOSGSSMEOLXISUMQNQPXYVNN9P9TG9OZQIZWD9N9JUFQOAAPDJUKDCDXUCQCRAGSNAMLCSFOBMIRJFINXNGTGHXSRGFQCI9JFWNBCM9WDEWDPDGMNXMNKLITPRVXYHHCMQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIXPQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEB999999999999999999999999999999999999999999999999999999NYBKIVD99B99999999C99999999GZTLUWOGA9QLYBHUHB9GVUABQHPIJRWUIUOXFIBGYEJWUA9QUZVAKCFLDVUUZEFIDZIUOWUHSFOQIWJFD999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Input, Part 1 of 2 self.assertEqual( response['trytes'][2], - TryteString(b'FRPHPZRQUPWTFQMAPXTNOWFIUPGARU9DKHZWAJVAVBYONCVLMLU9LZOOIZNZDJRWB9HPSXUVEB9VVMLTATOHTODTLYG9GNMHHAFFIEQX9YN9KXURYYNV9BGOXNPXGFVLSOPAMFLKVVOLNRGNUQENIZVNJBBNIHSFOBUOVJDEQRATJLX9TTZWCMRQBJETDZCKYEBQXOSESYFGAAAJVFDGVRIRNVGSQROY9UNTORVGREMHZLDHBXDIWPKCEVEFETRILNWE9Z9WPIOLYHWAEROAZX9WXDMSRIZWXAHFWRAHGKCFAZFBHQTCLCVLS9OHVBCNPXXCZHWYJNEZHNEUZ9X9APMBWQZ9GYBZPIYAGXGKN9D9CMTTHGHCZR9CPQPQYPV9PGWAOKOXSZSRIACP9OAACJSKBLFZBSWTEKTGDL9NGGFDCMB9LGGY9AOUNQLAUSREFIZQGUZAPTHWCTJPILUFEOPDFNREQOXLFKCHTBLKZGEDWPLJPKRFYVQFGQMFRSUHKMNXTWFMFRHRLTSIMVYQCDH9JCNWRHPYRMGARJSQDEMGCSQAWDZI9D9OGBJZEKSEMUUSHTCAUSAORPOBCXJ9LNKNPKJGREVHTZUEFNCGFHGMWLZFCMDTFXCYYFUHFPUFUPNWDKOXFIUCQIB9GYCQYMUKBLY9ZRPUCGU9DQOFHYIEMZNYDESWSLMEWPPQICQUVYWJVKDKDAPOOUMBKSVCVZRECGMBNLPAKEDXVFKBAOPKFOXIFBUNOICBRGMYWTFSFRYCDOKZGZDGWXSREFADMP9HUHJUZWVIFYZFOJKEMZ9DJINBQTVDLDVOSYDVZIPKGQXEBUCMNTVMB9HXWDNPANGOQAVXJAECUFYLIF9VAHUELULAJSYHEIGY9XYPSHIL9PGWF9ZZEDNJFOBHENKVLSFBDTY9YFFSOIQBP9LDOINEWGOABLN9TRFWH9AWXEAKAQDZGBFBHGOAUUSIIMWQ9LQTINFIHIYAVRSYRBJQGDAJKHEOLPCP9VRYDKQJGKFSCVHVHUGITCMHIIOTEQBCO9UQRPSTXOQRAZVVTZNUSJKEYRYYVUIVQR9KFQUVAOZPEHJMANKIEBW9PZOGGCREWHERBLIBK9NZRZUEIE9XBSCJMYWKFLQIEHBRUQHYZYCGJWQIMODPIPHFELJCWRCIIKYEQNRSYCUGWXMJSOFUEBCKPXIOCXP9OTZOIDOSWPDTIIOYGUNUYBL9JJI9GPTIP9FEZIGEBZCZSSVGAYDKDAMPNBCXVBZJJSJ9JGDFMDPMONUGAOFLS9GUREOWVZIX9BGRLZ99HFCUWSZQSRRNAMWXSTK9WUUSJNQSBXPUASIKAXQFLUUSOSRAHUKN9WBOUMCYSDZELDMICVAFNTVPTHCYHVORHNUPPLEJXBMZCCXTWEWSIIHNJAFYPLTLVLGKBJUZGOVIMKJRLLLSJXSUXZCBYZD9BYUFUCXAJCOVTU9AKOQIGUTPUKCJGLHWASEWFLEQ9LBNZGHSQRADCMOHDEFCTZXEMSEGTLAQHRRNZOZDGSYVQDRLQUQ9MFYMWGZSLSYZOXSJXBFEUVTZU9OXQSJKIQPMCBVMHFISFCFVPPQRIDT9ZAFHZGBXJUVUVTNWYAKGDPHRUOARINT9CYAQEHIPXYXJVMYWXZKKHPLTD9LLVLTCMAPSGVV9VQ9WPOOPZYLXNYHCZIUPVFCGAPGSAVXZRMWAUFXEGD9VRODALCTZPXABVSRYADTMMCOLHWKAI9JAPKOTYXEQHRXGRPMDVFPQFPYTLJZOJYVIDNDQTGHNWVSHBHTSACYAYUZUNXWVNOAZAOUAPPKVPCKWJXANORWQGYYTSNZYPPPAQFVZYZEPG9KZUCAAMGDHCDRXDNIOLGCMP9JDOVYYZOCSZYSBT9JUDNHXCIZOMSAPVNRCHTYKUQK9PCTKHIFLNYIWELZTLJUXEEIIGIFFRRGUXARDUPXUGDCUDYE9ENRRASYDWELETZKUIAFQAIQSOGWRFGSFUSOCWASBBBEZFMYULJYOYDFNOQO9HFZXVWTWXVSTGQHGMLESYJPMH9CJCZPEKMJVUPGELRLVZTTZKAC9GHLZCNVRQ9ITLCUDGGUJGCUGNCNHLAZIANRVAKHDMMAYCTCZJYGFOQPMOT9WJWNJJYBEK9CMEKSYFWDKENYTCIPEQIWDG9VHQINPFOAMQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIXPQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEBVX9999999999999999999999999999999999999999999999999999NYBKIVD99A99999999C99999999XRHLMDZPZTK9DIVUOHZIVOOLNKFYRMOX9WJZVXCKRITLLRPVGZJKBEWGAZYCTPS9DDAZTOORMO9AFQLDY999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('TRVDSILRJBTGVOUIVTUHPJHGAFPTJFTXEZXRZQUZLVUEEWAQDC9BVGFSCBHKUVKHUXW9ONG9WWTOLKSMBFDGIZ9LPH9IOAUXBTGOGIGFDTNXNBNZDBXKWVHJUSBEQBTCYJRFEMVEDRYMKRFELUVHDCPRSR9U99RUDCKOZHLNZTWDYGKECDXTNWZQRTUWZAWYKEQKWOA9PZJMIXWQOJUVUPFEKPEYNOIVPFGTGVBCTYUXH9K9WECIWPKCEVEFETRILNWE9Z9WPIOLYHWAEROAZX9WXDMSRIZWXAHFWRAHGKCFAZFBHQTCLCVLS9OHVBCNPXXCZSGJGRSBVBYBKSBZNEJGZZHIECIVPPV99PVRHUBHLGHAZNJRY9LDB9SJGTXXHG99HQAOAI9JVPIYOOWHXCITIIZJCJXHJWCENGRVK9CNUQWERVSKADGOGROJAXXZDRWQTILHMSWEPOZK9FREBNMWHOIMRCYINWUQJXFATZPXU9SKHPHXOJSADTWBUNHDY9XCHXGEZSHUDLTZCAVGHCMZSCQGOI9CBZJYAIAKUQPXONNMMSMM9TZX9FDUSHXSTVHKKGMTAFOQGJFHNYPTIPSJOM9UYPGIM9RLTYRBYADWKCOUPJFAYKOLHSOTGJYI9MJJVBTCHUHCHYA9TKIEEJJWCLLKLOJHRXSDMXPQMLUAL9MRANVGOTHQFKRKYDPJZPPQHJAZIXQZMDTWCUJFPCXBDUHBRCTYLKJFNHICXPVKXRYFNGDRZJDVLVQWEYRLIMFMIMZIZHLLYQGFOPXEVLINAQHZEXWNUEWBYFWBBCTPWL9JXNECPRCXXMOTPNCSFYRRGCNGCGQK9XUWWKJICDELKHMVRHHWVOBAKTNXBYENITXWTDUNLJAAKUDGTFPWROHAORLBWFCMDKKTPCOMDZQVJSMZHKVUSRBGZGKAHZCTQTEWA9LQMPGNPEXCXJNBDXZRMV9BYCRBU9SCKXZWDKMCFLTGRIKESL9PVIV9XFUPAVEBWM9OWWNIEVJNRUOKEUAIFEZCNPXAQYWOMKZNMMHWOIG9WRCKUWAAFIVKIDIEXJ9YUWSHXZVFJKFR9IGYQLOVXRDBVQZAATAONPQKDKSP9RZBBXMONAOAZDIEJQAPXCJTNVCDAAQQGH9RGQASOBOEMLAMBRIXGTGULJJIRPHGEURVV9OHOOVBRBFXXXKWIDGNKWXVK9WPRVTONDYTIIOYGUNUYBL9JJI9GPTIP9FEZIGEBZCZSSVGAYDKDAMPNBCXVBZJJSJ9JGDFMDPMONUGAOFLS9GUREOWWKJHZBBXCE9NMIHZXVGPKFW9DIILQXNKCQYEENGFBRIQBX9LSZNZSRXWFKBJVKFCXSJALC9HR9CCZTHDDP9SJUSBVC9ZEDKMMSPHDDFRKJ9FVOLTE99SLVHDANNKVEA9TOGXFEFMVQUOLEWFWALQZ9VSLBR9JTGO9ZSQUIMGEQRIYEULTLVRPNXLAUGQZLSYVYEOWUID9ZDFFGJ9GEJFFDLPPZFMAXUREXHJNWPFGIDD9AMMHYBILHSBBXI9EQRUSEDLJARDFWJCVBZHBFMDXMV9GUXZDZEYPTXJAIREDJPKOZJECUWGUABAATUKQWTFBICCYAKGDPHRUOARINT9CYAQEHIPXYXJVMYWXZKKHPLTD9LLVLTCMAPSGVV9VQ9WPOOPZYLXNYHCZIUPVFCGA9CSIHHIHSGNPHEFMOGIZEB9NRXRBUWFZNGYWHVZ9O9VQFOCMVYFCRVLAWJND9SRMQRCIUBPCGLPBVDPOBAUDOYTDEPQKYUFFVOZ9NEUHVXKDMDQHZLJC9SLV9DFAVHGPRHTRCNPQDOGKVABABZN9VLMBFCSBLYIKCBREHWALIM9AYCBQQFRNNHUIKVJVIGTGIF9MUMSYJIZJAPOXHIFXH9PPOUOGAQWAKFGXNJDDISLFELAOKYBVILXCVP9RSKDEFYZJEKIFV9OCAFXQFJOQKIJBHNDDEPQTAEKIRGUHARHPYABGSJQWHWJN9PLYCQJZVDAXBZFHSMNQQ9SJXUBHBKPWODAN9MJRWGIWTCJMIATTBLFEXKGOJQRGTPIRXCLSGVBEHUTKUQVCFQTFTQBACNBPMHBGCJ9TLS9WKPGCAJDPBUNU9OMCKMZJVLTUKPZLD9HYOAFKBKLFEVPJGPAVNGRMDYYBARNZHRKULBMQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIXPQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEBVX9999999999999999999999999999999999999999999999999999NYBKIVD99A99999999C99999999GZTLUWOGA9QLYBHUHB9GVUABQHPIJRWUIUOXFIBGYEJWUA9QUZVAKCFLDVUUZEFIDZIUOWUHSFOQIWJFD999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Spend transaction, Part 1 of 1 self.assertEqual( response['trytes'][3], - TryteString(b'999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUETWO9DONTUSEINPRODUCTION99999XYYNXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOWOB9999999999999999999999999999999999999999999999999999NYBKIVD99999999999C99999999XRHLMDZPZTK9DIVUOHZIVOOLNKFYRMOX9WJZVXCKRITLLRPVGZJKBEWGAZYCTPS9DDAZTOORMO9AFQLDY999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUETWO9DONTUSEINPRODUCTION99999XYYNXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOWOB9999999999999999999999999UA9999999999999999999999999NYBKIVD99999999999C99999999GZTLUWOGA9QLYBHUHB9GVUABQHPIJRWUIUOXFIBGYEJWUA9QUZVAKCFLDVUUZEFIDZIUOWUHSFOQIWJFD999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) def test_fail_inputs_explicit_insufficient(self): @@ -802,8 +807,8 @@ def test_pass_inputs_implicit_no_change(self): 'inputs': [ Address( trytes = - b'MQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIX' - b'PQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEB', + 'MQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIX' + 'PQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEB', balance = 13, key_index = 4, @@ -812,8 +817,8 @@ def test_pass_inputs_implicit_no_change(self): Address( trytes = - b'TNNTKUYYZVIOPMQHXIYKKZVN9PELGAKAUUGKCBYR' - b'QOZJT9NLVDEVFQXIZKXIF9MOYTJTDTOQJYQLQKXQC', + 'TNNTKUYYZVIOPMQHXIYKKZVN9PELGAKAUUGKCBYR' + 'QOZJT9NLVDEVFQXIZKXIF9MOYTJTDTOQJYQLQKXQC', balance = 29, key_index = 5, @@ -833,16 +838,16 @@ def test_pass_inputs_implicit_no_change(self): self.command( seed = Seed( - b'TESTVALUEONE9DONTUSEINPRODUCTION99999C9V' - b'C9RHFCQAIGSFICL9HIY9ZEUATFVHFGAEUHSECGQAK' + 'TESTVALUEONE9DONTUSEINPRODUCTION99999C9V' + 'C9RHFCQAIGSFICL9HIY9ZEUATFVHFGAEUHSECGQAK' ), transfers = [ ProposedTransaction( address = Address( - b'TESTVALUETWO9DONTUSEINPRODUCTION99999XYY' - b'NXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOW' + 'TESTVALUETWO9DONTUSEINPRODUCTION99999XYY' + 'NXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOW' ), value = 42, @@ -858,31 +863,31 @@ def test_pass_inputs_implicit_no_change(self): # Input #2, Part 2 of 2 self.assertEqual( response['trytes'][0], - TryteString(b'PNOHSCLHTDHBNES9REFELWTCKSFPFDPQOEEUKYBXFMRSHAAXBWUXMD9QNSQUWZMOBGDDAVIIHWGBLWIKCLTPZDVYRHYZWWJUKNWOLYDWRTRBOVMXMFJCBEJVMSPBQJQISISHSRNKEZXSOZHZISSMLCMCOBYN9DWGV9Z9GO9QEHNGIASTVPGWPBYQORFASXYDOTMJZVEJHZZRJSUDDTAFJDQFCZKFKJWEPQARTHCWKDWKITI9ZDCRNUWJQBDZZMRYNBDQPHJOCTQKMSFFCXGM9NGNGCBTUEEPAVOXDKHQNHSSUNA9CLTFAUIHSYPIESEVC9YWAWEBKNVAKGKZWWGRWYYPPOLTSOGTKEPCQQ9PLDDAMKGRPOHHHDYCLOJVBWWDTSLYZHKLOZBKHPCOUFPIBZQ9MOHHKMSRTXGXHERZREPSSAASILWCFDUFPXOKGTDSHWRBZSQSNCYFJZJTB9DGDJYISY9EZPLHJRMIQARDR9SIEMDYSBJXMWBGGRANNSAI9A9HYRPG9JEFFTIFSMJZHQWXXTABXPQXYOLTEFDAPZFMLTGGXCVPL9ZNBNNWVLMUHAXAWJNNVBPTXWNTFNQAYDBVCQSXJTPXABKG9PYIJEZRKSYBXTHGUSWORXZNKZNHIJW9KEPWANBKNNKOUKGLISUUTQRGMGHOQQDUUUWHFJQOFXXN9MOAOLSLOXLKPAQ9CRNSTKVRUMNLFPVIULPYXKOLDLARYUKLPMIEQYWSJYTYRMBHRHSPQJHJALMWUHLPIGQLQSXWDPVNIGFUOEMJJ9GIUVGNB9IWKIPBERFTPZOZVDJMBCKFTWLTQYDP9YHXAOU9DEEMDU9WBHPSRKFARYYCQBEKKQQFFTRUKJO9SECIZRQMMDOJZVPWSWWANMYVGHDCCGSKKGEGCKN9MYFG9ASYM9PEFX9DUJUYVTITKVMBKXWFTWUNVTFEDYSSTMWVGCYZIOCRKVRDGBPOVIDPAGIGZJYNI9TSAJCOSGQYQOTIXMBQXDGJTDJCIGKNLTZNEWEELSAXWYEBYCZILJWPKCGFHXTCDRANRRRUJWRIKTHQJNSDLZJTSDPHU9UMRPCHKJBHTYSNGIARREPPIMULJXFIATTWPQAAYSDSBTGYATXNDDIBMQEIBIUK9YAUPNBMKMZSRHK9UGN9YWOVMTFCSZWOMWHUHPYUMWJUNDMMVOAQUBQDLJLMCXFQEGBSZABKVTNFAJTLGVJ9VHAQGD9MSDYLOMCODQJIEBZARCRFVHFIGFFZRZPBFVX9OMHAAIXFKXWC99RINEESNHPYSFWESSKP9AQHJHWUPWYOOYVKFUNKXPXSKTHNWNULCRUMIHBJNAIQNGDLQSXNWRILYVJMYSELRBTLDYELCZVSVTDNVOHFXLPN9NDPSKA9YHVFRGPAFAKNOXBGWNRMYQCFCSMIBHUKKTNQBDDRQXZLWBLHRYTWSMJUJWSPQZPSBQTAZBVOIVIRXKJPSXNRB9ILEUAMGJKDGOEGVGOKFDKWWBRF9BYDQUYVEHFTNJQDAMEVFHQLSU9XTGFPOGGOYWTZONFSZWODUOMKA9AXWWIZL9GMNIXHWNJFHNONJUJGMFUGPAAMHZLXBOJFLJFHGNNWEU9DS9VKVBNVIUDXXGDQFQSNLMGWAMPETROFUFVCDMCARZAJICIXAVAM9YZAFSILIPOEOGHZ9TJQTKRLGTQNWFDAEDHZIOAMRHNUE9ANKIYKEKWBYZWFVUMKFTWBRACWZUWZSGWGWTAPXIILCFMLLLGOLHVVUIGRPO9CRDXECHIZYAJXXECRBMLNCYSFOH9PNJ9UXOWBGCYIRIAOI9VVAIYOLHTLBYEKOYMOCSVBFCHHCTGIBOUDCXXXKGBTWVBCAVOUQVOZCUSKORPYWBXCVYYBVFWSZACWFLRUWZORZULS9RNOBKHRQTR9IYTKFVXRWSWERUECAHVTAKTTSN9VNZOLGJJGAHPIJZQBITVDSXNXZTRMIDLH9XFIOEYUVJWIKLLEAIYBOFFUPCBEMMXBDGTZDICOBWWQ9EBAMLPQNHNHKDBZHACQW9GDQQQPSAWIAYLWWOYDTDRXKCNIWFXZRAXNSGDUSDTWTEFANWWTSAJQIVJQZGPXHUP99LYTNIESJDUZGHEELFJGSBLMEKJBRABTBZASNKLSAUB9GHHIHMJZSGJHXKWMKIJOQVBTNNTKUYYZVIOPMQHXIYKKZVN9PELGAKAUUGKCBYRQOZJT9NLVDEVFQXIZKXIF9MOYTJTDTOQJYQLQKXQC999999999999999999999999999999999999999999999999999999NYBKIVD99D99999999D99999999YBPL9FUHMJAALACSDMDFUKKBTUPCHTXNCASWTZJZMYLFPJH9MWDXUCNGAVYJWFFQNHCABKYIQBTJWSZID999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('RQOQNTDTZWGNBTVNHUYXYELHLRDTUSHIFZBAJDYYGKPUTHMBFMZPWHYULBANOYXDHVTRKLGXKUOZAWFZWJDFVUZKONYTRYSAGTWGDBIAHHMUEEGIPSKBCJPDBSMHAWWZZU9IFKCKJMMTCGGDHPUCBBRDKTQOTQGRDXEDQAYI9WNCNIVMBSAQVCVLJILCKHOUYPJXKNVXDHXPECIPVQQIDWBGRREGYYVROBJELIWPUWSOHSAUKSYSPQMNPRBMKKUQUWGNAWAOEDDVNRJBUSRKBJKWZLGAVDASMZ9GMKKLMIKFWAIAHAW9GIRAWZFYFEOIJ9TBNAVEUSTNUNABHJ9L9GSZTBHTGTRZSIWFVGMXQS9VDTF9ZUVNLDI9MOEVRRBDBAKATS9ACTIABCDWUFNRXZQ9MOHHKMSRTXGXHERZREPSSAASILWCFDUFPXOKGTDSHWRBZSQSNCYFJZJTB9DGDJYISY9EZPLHJRMIQAQJYYRZVHKWCGQLWFDYVZKCDAIBWYQQSUKACFRBALBKMBTBG9PPZEBU9TVRU9RMBHXCNOS9QLASMCDEFWCUBMHS9LHXEYANCHLEFNVGJJKKUITNEYVLPYQIYQHAIIGSTSAURJOAL9SVATHGOVP9CQXMGCYLSYFUQDOWY9ZWJADWVQGPZZISPAWHTMNPVKKPTCSODG9WECGVUANJXZRDYPMPVCLRF9WVGWKKQQWPAKCZQVK9KHBGXJRKGD9IHKRNJQVKSXXQMVPLGVSEWPEXNLBHGOQJUWDOIEXDGIZLFIZWXSIAWWDUOBLSDGTSFLIKGBBGJWTDOMSQWNRSYOWPBJTAJDLRPCRMKNRYEATYBMAZIN9WNMRIHLXGGVIEFZQGAGUSUNQKFAFUI9FR9AIKNBCGGFFECROHFURFC9GFMAUXMPJFWQVRXPLYF99OILFIQIJYSH9HGAZPCJIFHGTZIVGENZHBCMNHOYNAESF9FNMZWLLLCCRMUUFOZVCXLN9OQSODU9QOZKBOVBLBIVZXPFOEZEEXAUBWRWPWRNRYVIKQKBBVOHI9OH9FCQAVQPVVMWFVKZKOCUUSQRZOESNVQR9ULQGQBJEKYEZLXHHIGIAINTHUAXOYJS9NFTZAQIIFPXYMGAFHKYQHADRPQNBWGQXMNSIARLUODCINRFH9CMDIQYAKNJKDSBHGBQJQVA9VHGIHFFSWAIQEHKRGITSLCDBTCHDSEAJSVGGGBCRYHOMFEYEDLDRQVQBBRFLFM9UBOYTIMBYTWTF9VUKUJDRWKJMNFPKKVHRRSJFOFMWJ9QG9SIXCFHNYFTAGQKRUIHVXJ9USSDBJGWLGDBBPRXCOAQPWSFLZXMTCWLFNPEJQFH99YPMFOZDHJYWAJOBECPWONQCPPFNLCAGNJRI9XPK9O9NPWM9WRJKQCDLVWP9HZNGNCJZVKTEUOXEDRVSFBWEREFDKPCU9QATTUXXUHWJFNJSUIHMND9EALDXYCYWEUPJITOTKACDUYCHS9GVTJGFTCLZPIARZAWNGPUWMQRDEIXDOIFUDEWXFVVGVDRKTQIQXLEVULRUJEJGTCDLAOLEFNLDOGLWHYUKGBHSSRURELGFYKTVQUVUXJLMY9ICDMPHG9INCBNABNXEEWOMWQ9J9NQSIASZJLKMXDIXMVFPCFKLM9YEMZOGZVTIF9WHYTYKTRKDXAUIIGJXKPQ9DPVEACFPLZHGVIUVJWML9IEGJXIZNSUETRYORJ9RTEAOZXMTQHAGVFZKHEQCSBZFDD9XAME9ENSFTJZDHRVSQW9XECHIZYAJXXECRBMLNCYSFOH9PNJ9UXOWBGCYIRIAOI9VVAIYOLHTLBYEKOYMOCSVBFCHHCTGIBOUDCXXOCUCRMKTANWHIIXW9LSBYWJAQOPMPMATNGUHWNCBNL9IYJEAUMWSXAKBTIPWWSGXZZCOBRIXZFZMHLGNWAHVTAKTTSN9VNZOLGJJGAHPIJZQBITVDSXNXZTRMIDLH9XFIOEYUVJWIKLLEAIYBOFFUPCBEMMXBDGTZDGFJCBGZSD9CRIGSQSJQOPFIBWSGDSVCTQUHWQWRDLMEQWNIMCSQA9QGQIRSTBXHFVLAOHUTUZBUIWHFTZEDEZGVDKIBUZ9CDJHKWLMIMQZSVIOKCLSURPXHROHGGWKF9IRA9GCOJUDKXYPNBRRDQTNLVKUGCAZHLKZTNNTKUYYZVIOPMQHXIYKKZVN9PELGAKAUUGKCBYRQOZJT9NLVDEVFQXIZKXIF9MOYTJTDTOQJYQLQKXQC999999999999999999999999999999999999999999999999999999NYBKIVD99D99999999D99999999WNQNUFDDEVEKCLVLUJCFRRWBHSHXQQKSCWACHBLWXPEBWWEBJWJXQQBFJ9HSSDATPLVLL9SLSRFAVRE9Z999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Input #2, Part 1 of 2 self.assertEqual( response['trytes'][1], - TryteString(b'MJ9UDTLPAAOHPYNXBLEOLLHTXEBTGAKYONGZUFJAFEDKZYUBAEDUQZMAMSYKPPWCGBK99QAJVXCDXYKJXTQFTG9BSWEKXKWY9ADZVHAMQQAUCEOIQPRULPHGCINEAI9ORHTTCEHU9GPIFDYMOZORWNZYUZNEFGF9WYRBKLSAZTXIFKODGYAMKFJODJRWMLXUFQ9WFJKLWT9TAVINDIALUWQIZISLXDOVKGZPIYNRAQYWRZW9AFCEMTOBSHJEEYN9GZ9ZUULYDHYNEQSSETKYZVQYRIPNRWGRBCFLHRUAKJODCEMYRFBP9EVFKXL9ZTERUVFCXNTYFJBHN9GUGYDTIXXTKTEWSDM9POVBSQSKGBPSPTLAZQ9SENKYBEHGHPXVLI9UJULIDA9KXVRRQBKKAQM9QVZ9GEOUMSMMMZSBQVAYWUJPUKCLDZBHDQIGUK9DOADAVEO9GQTVHLMPXSJQZHEYDCCDHTWKPUEJBAIQ9ZDYLLYTEIBCFZKLZCNYEZULRNSUGPTXZBEWGFVYRBZLSTRGCYSTML9ZGVNXJAQTDASQENWWGBAPNCZHQOQWDXWSUCYDDIDIXRUJXCETUDIDBZJZTNJG9GUDYYBLHRPSZORPOITTJVAGNTPKFURHWMGU9E9DSQQCVAEYEYDPZWBUVPXAFGLKZZWRINYOVSAZCINPQSUKCFDGDSRCCLKLGGOQIJQWGCKTLRBQOQMGSOVYGBVACOOUFINHRQGQBBDWWMVJTEZJEBB9LD9ZNUEYBFRKUZEFT9WRTZRAXQPHHCNGBHRERZDCBCPP9JQ9MH9RBZPGSL9HJBDHPL9WHKCRUVHFWHJSJFWAWEXCTHU9OYKNPBUMSIMONQRHWDIQXETDHT9QGSNPXGTDNUCCFHCJONIDIJADUINVPAVDZQJNOQJQPBMOSCHMPEGHGPMHMRUUWURB9ZPGENHERLURYWLTVVR9GXYGCDCNZLVWVRPKVRXNSXBGDLBBKVGUAJUGGNUYVJSWHKVYT9LYFLVMNBUJDBLVXGDDIJAQKPGUHRTPWNOTLUKDMXGP9BZFKGGJRRNOUNBWZAUZSMMVGZOKGDJEECERVCMJKXHNLFTI9XCZQXN9WGGQMKXXQSIDSXT99KGAOOTGLDJHCPQJPLJDCZQAGRXYADFXCFBCXQGEVEOCKEICIVKVOMKGBXPZHQ9SXDXBFZZI9THLXOPTTGTPSQJTBBC9VYZUXWNENXQRVGKDY9JWCYNXTSAOLIDCBINWLLQDUNYAQRHAZBBROWSCMANZJZYCKZGAVQEI9CLDNKFDXWZMBMGHFEAXD9CW9WHZJ9LTZWEWKETMHHYINLADMLTQEQEVAJOVCZBHEASNWRATZNQWFIVEIXAJEBPLCRYA9JCO9XJPSUCKISZ9FKXVYDLRIKVIFISWWEXMHEREKXIUBFTBWWYVRKWJOPPVSYTZZRLFWAKHBYETICAKPPAJPADYVSFXSY9IVADYPWTULJOIAYWCUBBCPJBEVWIFNWDSWGVZSFSFFIIEJXIVWJDNHJKXPHTRQGWMVYOUQYUZQWNEHEXCARMOKYQSKWEJKKKLDGKJBXQKODOGJXDSACUDHVREMWBSAUAAKUYVAHTUGVSUEVLWRFYTURXKSVRMTFLEEGQUORVNPXEHTIJIGC9MPCOFKARODEORLUGHDVFXVQZYFFIXBSLWVVOICMPPFIEK9APVOCENJ9DFAQ9CQ9LUAQVSDNSYKXBCSLCGYOIVRGRGUSBTBIMSQTNQYCZ9TFARMHY9XXJMHFUVDWOYRBNBSADQTZAKRLYQFVAMSCXBTHVWPFJTVENWKHHOCURLKGCCGK9SKGFIASFHPTJDGKOIRSKNCODYCEBSSCZNZAMSOTXBCFPGLNJHEPJOP9IIIZXRHTMFEXXZUVKDXTEIUXKBFRTXZTMGSXRWBQQGKBSJWHEXVZL9EKECRQQGWG9OTMQSBBAZAMBOHNGVDBM9NSXMRDJIEOOYLISNGNIVKKQHWC9ZIPWHJUWCXVQZOMRKZ9JCHAXS9RZWC9RACAE9EKZGJHYNLWPMZYDYP9MD9YVA9RCWHMFDRVEHLQV9RORXMULAKDOJOZBOYDFNLTUEJHIPL9CQKTPFYKBUREGDWUAUMZUXMCJFQMZUZXLTGZSDTLW9DFFWGKFIOODTMMXMCQHRNWRUXCGYQGTBMR9NQDBTNNTKUYYZVIOPMQHXIYKKZVN9PELGAKAUUGKCBYRQOZJT9NLVDEVFQXIZKXIF9MOYTJTDTOQJYQLQKXQCYZ9999999999999999999999999999999999999999999999999999NYBKIVD99C99999999D99999999YBPL9FUHMJAALACSDMDFUKKBTUPCHTXNCASWTZJZMYLFPJH9MWDXUCNGAVYJWFFQNHCABKYIQBTJWSZID999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('AGW9TDZZYGMN9CAHSJCFOBFJCWGBEKETZPUJK9IXAWDXZTCVFTNJSHHEVTCQHBVPMFLPLDCSGPFFWWBDCTQFTG9BSWEKXKWY9ADZVHAMQQAUCEOIQPRULPHGCINEAI9ORHTTCEHU9GPIFDYMOZORWNZYUZNEFGF9WYDXK9CZSKLXVGBHOMBDBGFEMPQXOXBECKEXCQEEDRXNK9YAFEYWXPPURGPKSEXGIAOJDDRLFLGTUHTIHY9EMTOBSHJEEYN9GZ9ZUULYDHYNEQSSETKYZVQYRIPNRWGRBCFLHRUAKJODCEMYRFBP9EVFKXL9ZTERUVFCHH9KZQKBSWZHCGVWDQYMLXDFVDQESOHZVYEUHCROFERIOBOKEWHPWATWEYLCBMQUUVTEWGJBSHGNARCU9QM9QVZ9GEOUMSMMMZSBQVAYWUJPUKCLDZBHDQIGUK9DOADAVEO9GQTVHLMPXSJQZHEYDCCDHTWKPUEJBADZLKXTQKPWUJNZAEILVYCMQFQURKDVQJPOMTJHGUKPYTQHJGIMICF9RVAYQEJDADAHBOYXWRCMESMKZWZSBICV9VSEEGQFNNRJWPBSPZQLDYETZ9TBQGTCEIDEYBRXUYHUQCILZULX9NPUFFYNGIFJJGBYMUTBJMHYOWQEPUXMFKTLTFYEPNQVWRZQ9FFISZBUADRSZTRLQSQCGJXXPN9AUREQNXXGOZCYDVDJWVFDKMJG9CNGXUJQELTWJMRB9IEOGCKGE9RQDANXMTVMPXCEOEQNZG9YJCUC9HEC9QYZTNPPUO9IUKSNDAIAFIXPDONVZXIQJRQCBCTJXIDJGYHXXVUMYNFTGBOPRYRNQDVOXLDLDCACNLOJEOSDVZIDMOVPVKOARQUQNCKWKFHBSHBQXBUDBMZ9PUJBBWVSL9RPUDORRVIQCKADBUDIUVPZDHU9QHDHAWZCKNKVVHCRULLGJDSINCHUILZDWAACAIUVBIF9NRBSODKJGBMTWOBKJANMJLNDRN9FQNOGYQTMQNVS99LAIYNGSMIVRDGRRUJYZUEATJNGXBACDVHTKHGRQELJUPIUYLPFBRREZLFMFUOQGKJWJPSEAFJIALJCHPKZWGJAEVNPQCTGFJTNSBAOMUOXTURUCCKYZCAESRJHEMMYSADNYZKTMPFZAQRHYFMNXZYC9FAHDJPNSLWFUE9MRLUHQYBOLYYGMFJLCIECWPJIRAAZTB9YHLJNCVOUKKKBAHAVFOXSHLDMO9OAYLYCJWXINBHFLHGFBPIDIATUZAU9HCMQZFZLUROQQDTWPRUDEG9AUGBGFNUXIWGQZQAXQX9QFXQPJARKGEZRQFGQEEOUPCYVWHLBP9OCUZZSPOIWFJVXLWSMKORXPAYG9TVOCNNHDIS9CHZLZJBUQRKEA9BSWPYCEXKUGSXXVQAQSVVDWMEACSXHYFDRXLILR9Q9SK9VYJWQEJRJVWSL9KPEHGZPBQYNPQZVQPNYCOOJVCTOHOKQNFKDPEFMKDTTLJZTURRGOXEVUNEEKPNTQDPDWFANWZPBAJYMVYOUQYUZQWNEHEXCARMOKYQSKWEJKKKLDGKJBXQKODOGJXDSACUDHVREMWBSAUAAKUYVAHTUGVSUEVLWKQADVMKRNUYIBEO9BCSPSVFLWLTZBMFOFSGEKFTOAGHAVJ9YRSWFBXMMACGKKBLFPALET9ORLUPLQNQWWYW9EWRLSPTSPF9S9CAHGXEKDLVXFDTVVJDLQEOJNOZMUBJUHQXIUVD9ZFCIGCFCWUJUALQFDULVEHHOWWQXYHXXVSVCJCAXPTJBWOZRXNHBW9DRSBVEWHDDQJUPGZQVBDL9OATVSZKQQFNTHNFFPXJSQZXJJJZDEQZNZAMSOTXBCFPGLNJHEPJOP9IIIZXRHTMFEXXZUVKDXTEIUXKBFRTXZTMGSXRWBQQGKBSJWHEXVZL9EKECPAFTVMVVGKE9TGGTE9YLGGYMK9PKBERBILUCPIQZTKCXSATLRKBGGDSWORLQUKSMQLDLUMMML9VCMZUJZJVGHGAXDELKIAZYNAHPCYSPUYNNBZ9MBUQGRKBEKIHNIOGIWQLIS9NBBWDPWGABMIGADUMG9WKFZHQIPYKDMJTTYQRJWYXSBAPDJSKEIUJNOMNDNGUHEFBSDSNNKABHEJBKBRIRLKSQBQIRPCQJPRXWDDBIXANTCLWTNNTKUYYZVIOPMQHXIYKKZVN9PELGAKAUUGKCBYRQOZJT9NLVDEVFQXIZKXIF9MOYTJTDTOQJYQLQKXQCYZ9999999999999999999999999999999999999999999999999999NYBKIVD99C99999999D99999999WNQNUFDDEVEKCLVLUJCFRRWBHSHXQQKSCWACHBLWXPEBWWEBJWJXQQBFJ9HSSDATPLVLL9SLSRFAVRE9Z999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Input #1, Part 2 of 2 self.assertEqual( response['trytes'][2], - TryteString(b'EOWARUTCGMPDDIK9HLSBJUNJNKFQ9W9EHNWAWCVBOWZNPDPI9MDARRBMMCQTVNYKQYKO99FJY9ULJLRYZQRC9XTVDAFGNRNJHXBWCUQEUNJKTCXKIPHQWRV9KAGREYBHXIUFNS9DIQWJEN9FEAXBOZDNHSCLOSGKTDFLVVEDDRSXKSFOAIIDHDVEW9YWNQZQUHGCBYDZUZGINOLCFKHAPPSYMEIGRHZUVP9BLFFGHYWIOLYF9DXXYUKVSYMLDGMLKDEVERGZ9AWDXSOTVCWQVES9H9YE9LJJJQJCPUVFNCJCVHPAVMBVPODVWGZQJ9ZQWITDKH9DIRSGNGN9ZYJPVZOJAOXOPOQSZCSDILTOAUUMLGOIYG9MYSYBQUVDDDBCFTDWUMPXUDHZBDBAHTUXZWINNALMYDJHGJLCFCJ9KZZNTFPZGSLXGEVEGOWSOUAFBJAY9IOEVNLHFTIWEFURULVEFSDURVWBMNUTNAQAX9NYD9BSA9XKUOEKSSVI9HSAIXLG9PCZKWKSLGOBRKGHSPCTREBYTKUBUWRCCHTDQPFMQBIKTAVXVOCTGUEZCEHGXOGSBYYZFQ9WTBUKSJEUIXJVCWBWQILYUAZ9LBXRRQCQWGMEMU9YNU9RYUBEJQYDZOOFXBLWBRLIGVP9RZKMLPDCMKBEHY9CUBUDVPFHLOFPFOEHUCFFFKQC9NXTNDHGSVNVONLXUZANIAOUWDOUY9LFXGFFBFYPECHONGIXDXXRFAXZIJIXZRTXOOGLZKUVNPDSBSQPWZIOWQQQDQHZJRRXMPYVYHFAPYLESHJXJDGYHOGZUHDWVIXGJEIMQAQACAGJXDESBXPMZM9SOMNEWFVLWJHHBPQRCXVXDGQIAPNTPWNZEXTBZJGSKRXKJPMWPUSZYVUGRJHFHQBLLMGXZWWOQME9PUUEAQNZCZNNGN9LDHAQMDXTSRV9LDMGRXBLUIDEJPIDT9TZDHWYQZQWCUVKTUZGNZ9RHIBWMQNFRQL9BDBRACLIVCWLNZQNEADVMHAYFLMTGZSYRIZDWIWMVGU9TBFEC9XIHFK9GMGVGYBADQBGMQB9IWKASSSLC9OWZG9AZEYRPMHQGRCFKUOPEIOZXUHTUDDLIRHENPXFWOQMFBAKZHKOL9RZLCEKCFTOHWWTBVFOWDKUDWSSMDZEKPEBQUIE9TUSDAMHIRKRGHOGRURYOCTYSDRLIZIADWXZRPCBVHOFZCJLZTQZLPCDRNGBREQTKTPMWVDDNLKYPVCUGPBAQBYCQGDVOKBGMX9WHKNEDIJXEPIKPIQWZVO9UVYVG9QB9KPNHIDAMHTVVCHVKAJREZCZETYPQFKRCNDYGGLDYSMHBTUXGNFPHZVQOQQUBTADRQKZCVCVIABGGNPDGBVWC9FBPHVVUFBPPBBCLXLKYBFH9LH9AVKBIFKSPWZYKQPRGNKMAHQCTYFQWAKIY9KYSCFGZTTAOGWPMKDMQGQSVANQL9YLOQCCIATBEEOTELNTXVJTLOTZUPYJQEAQMDCCSU9ORYZBQJULDQVXPMDNBWFXFPEBIE9MFFPIIWKXDVCPKDGBJFWTICOBRUNKJEFBKXAAFWXYPSCVFRLUVKDSBSUYCIV9UPLJTFYWGFJ9ZFYNOM9YXMHOYWFDDPIJOMTD9KGA9XCXGQHLZVBEKEUWLSC9BFSUTFJGTUHNMKOJ9NQC9UXJXFQSBDOUZRTMPOMURVXUAYGFLGHNKRDDTCASPTBUIDLUHH9HBQHPBRIUICIGNYMGPVNUPIQZOVFHLTAENGAYPWLCQE9DQPLMNPCJUFBPKYGHPHBRTALLMFUHIATKTSQBNTHGRCZILLNCTSZKJHQNVYZ9LOVYYSEXJDBHBBXEKCJEUDDDTUBLWCWWRRGHSZFMJIIEMVABUFNTNLWMVYG9UUVONDX9AMEO9WEPWAJDLRISKO9YCBIYQGGDMJDFDERJNNIKRROFSVLEBYFRJJOOSEWWBYMTIQXBQBYMSFAFBXPMVZAKU9LOGBEHKMOZDMSYXRVEZHPPZPKWCTEEAPFLHOGHJPCFQFLSFHTKRMZEKNEYHQZHLG9E9EUHKKUYSAQTOZWVPQSGFPRAZT9VSYKWRBEEHWPDJUKDCDXUCQCRAGSNAMLCSFOBMIRJFINXNGTGHXSRGFQCI9JFWNBCM9WDEWDPDGMNXMNKLITPRVXYHHCMQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIXPQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEB999999999999999999999999999999999999999999999999999999NYBKIVD99B99999999D99999999YBPL9FUHMJAALACSDMDFUKKBTUPCHTXNCASWTZJZMYLFPJH9MWDXUCNGAVYJWFFQNHCABKYIQBTJWSZID999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('KVTQSEYVEVEGDETHHKGCXAATAPNN9GDDCUFVOGJXFFC9HAGIMRLGXZMDUCNTJBMGDZWSGPPLZSUOKONNZKRMJQJHRNHPUX9YEIIPOKZLBZUZLDKPMVNVRLUTQFKQIRZLEBIIGBROFFMQVCPQQMGNC9RTZOURPDUNRXVDJUCLZFBEWJDVGCAEDFT9GQSRAAITNLENXSQDILMILGXYHEVCBWCWTHDAMST9IAXCLHDKKMJDWLZDGKD9SNZS9VIDJIFJNHNMHZCBINTWMWFTUPPCUAKEHAXLANHIBDSLPFLTRQSDWONBI9NYJFZVFCTRXOUMWOWDEIJBDBHIORZUVJXIIAXDWPNHXIBKPXFXMXRGWGXRQQG9NXHM9DDYUIOZMEHXTTIZQHNQGQVBKUMSCNABDWINNALMYDJHGJLCFCJ9KZZNTFPZGSLXGEVEGOWSOUAFBJAY9IOEVNLHFTIWEFURULVEFSDURVWBMNUTNAVCEOXRKBZTSCZN9IODZATCQUSPOWMWNBBNWXMA9HVAMYKYAQYHFFKFLBIWYDNDCTXPYVBNKREIGKGMTDCQKIHMAPQGWUMICACHQJODIQPVVWCPUBJC9NWAXSAXUHPMNJEJF9MQJCAJ9LMPCT9XLPLOLCDSAJYPZYUCMURTVZIOZSRMLKANEEYSJAGVVPBWTN9RDUJWEGBJSN9RDPWQDSKDXFXXIPUQATFRAFTZFUVKOKEISVCYZM9LRSLJ9BYNPLUMAQNUHXHPDLHQCUHJUNKRFSUSVWLEPCRIZHWKXVJCAPPGVMRXXXEPNELUREVCCNMEGA9LHXJZRCRWJIRYJPDRYOBG9YQUVIYJPAFQTMIKM9Y9MASZA9DALXZDXFUFJBMBPTNNENFPVGUNLXSNHTXSUVAMYEVRAHPLJDIMJCDUNN9QCJKHDXFSW9CEEAGXOUJLELTFGOQNCSSANOCDNMBMRDKNXAWLXWSTFKPYRRSBCWQJHWGPBRDQNKGHWIIJGZTANNFBUCGHJKCWPLFTVLYWBWTCASCSNHQKSOLKRJILIAVLBTYVWFMA9VWCLNQAMGUGXSLUJFDXZNMXZXNSTTQOZ9RTXF9QOUSFVTZOTRNZ9SUHXFAVITYCNYJGGOKYTWZQCFOQRCRGRSQVMZZNOIOJAELHG9JYUDLUTSOQLWNGIJTHGVELCK9VFZSFOTYHJWAFMMKDGGUSNSUCRKGYCRUFSPWEJLMLAHDNTCGVIEBSO9SC9NDIZYIMBRXCURBHYMAEB9JMAPWFUZRRCGRTLZRXJVLEPZ9QNKMERNSMFKAXPLZQIJXAAWY9SYMFXXOKGIGPF9UVTXEMSZZOINHKANZOVGSEZPGUSYKLAUJKZKNVDZJMS9CZRXCVGFUO9UMYVJZCUIKIXJTUFCRW9E9CJEPWLENSXWVMFA9PJZTLFFXYWRCWTDPICHS9IINY9ZOPNJWZ99IWJJQFRXTCEQAMBFQNXCFXNAPAGDMUJMKVDHGHSZZFQRUINOYWNXTT9FGWYAXWVXJ9YGZYEIKG9MWN99CBNOQWZVYYPZ9NPCYQQKVTWVKUBSTOYWRMFDUPDB9XGAOTEUPAFDVYAEIQHBPBHF9CXEDSOOF9DTGBJOAWHJYKNJ9CWRCATOWWAPTXQQTITZUQ9LXCFDQPCJHFVDPIVQHPJKSHRDOIOQBKECCNOOHDUYKYFYWUBJJGWQMIIMFNZZAOGXPSVZSZQPUPBVUTJNGQLRM9N9AYJJHBBINQJFNDATEPMKYDQNPKPJ9NXIUCXSOSQOC9M9SSLTBHGWLCQE9DQPLMNPCJUFBPKYGHPHBRTALLMFUHIATKTSQBNTHGRCZILLNCTSZKJHQNVYZ9LOVYYSEXJDBHBBXHOFKVWHVOKUAYPGNGRGARFGEINTOJVMDSJKENFJADXBOZMKEJGAMSQMMETTCTDWNQWKYIGVYQVFMC99N9MJDFDERJNNIKRROFSVLEBYFRJJOOSEWWBYMTIQXBQBYMSFAFBXPMVZAKU9LOGBEHKMOZDMSYXRVEZHPPZZCBNLPDUDVEPPYTCLKF9OE9YROSAJMJHNCWVYADGEYXIBPLDZBQMIESEYBJKONUUWGDDCD9SBPHTMJFBXPS9SOROVFBXDGFJFYWARMPRRMRYN9VDRKBDKHSZCPRDYBZOXCUWRZXXAYRHELLWMDTMV9VHVICXSRJVOCMQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIXPQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEB999999999999999999999999999999999999999999999999999999NYBKIVD99B99999999D99999999WNQNUFDDEVEKCLVLUJCFRRWBHSHXQQKSCWACHBLWXPEBWWEBJWJXQQBFJ9HSSDATPLVLL9SLSRFAVRE9Z999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Input #1, Part 1 of 2 self.assertEqual( response['trytes'][3], - TryteString(b'UZW99YV9GMPLXSPRTMJFFGOVNMUNUIPSIJTLBUZT9YCAXBKRWYDVKOMTKHW9STWCMHUBUQHZUGNFMALYCPTSOEEYANVTHWJRFHRYJ9D9JIBDVQLTQFDBYLXBJWAEJPPRHOXSZP9KWKNLQCUGMOKMHJQYODRVVYOZ9DEGJAFBQNIXYXJ9PFGAMZXOBZDQTKQGSTLSXEJBJ9IXICGUFPONWTRIPZXVUAJQIRXYMKONHSEFMCJML9DGQRGLMGLGKEHWTQZWOMIZIF9FWUUMVVWS9CWUMWCHZIRKTODTRLEJTRNA9CCRFJNCVCDCQID9UDQJHGN9YIFJZEFEDVMT9PUYWCABIHJMPNQTSQQEJBKRVQYLGHPYRCOLWKCTKMPFCMOMC9PABJNHFPNJVCYNPAIMCFDVHWOEJIVJOIKPMTCAQZZEFEL9YSOSRWWGBQEPFJNTLVWOXIEPZHHCIQF9DZOQGUKYOJSIFHARSBORDAJRVCTTIEBUD9ISDDLULQQQPHZJTNXOBSDGDWRGCBURMWUP9XQTYIYRLCGWGIWWDO9SQLQIUZOGXQQOZ9CZZINSZAYSLXJHVRQT9DGTLTIERBHIEYFGCHLFUEZJHUUKCZKRCOWSTYIGNFB9TZACBURMAGZQIPEKPHUZ9HIYGWZKOEECUJPKYFXMW9TDITMEOBNNQVJHECBQPXXAETVTHCYCKJGEYVSMWRAXBREMDKCHHVPAED9DYFFSRP9WOFAARRNLONJDNYLCBDKPUM9HYKRURNIOFJBIDJBKYNRVZKTAITEWNMZLA9XMJHIPNUJDWQ9ZRDBJXNZCXADAFREDEDG9EVDYWVFDOEZNFJKJVEXGVSUSOHKUFIGKRZWCVDAWBHVIAEGRENQJSPZMSJXK9VDSLNPWFEVZPFD9JRSV9YOOTJHYKV9ZWKPGBEAPATMINAESECJXMULWYQUENYNTAEYITFUZOTFXVCOWTPMCDKWBYOPWHJMUFRJYQNJLIXIBQHYKZTVGFRDMENVRUAGPBXHJEDVXPEEYWHALUAIFUCPTIFBHMYXSSYSPWOHRXDIKGLRHRHKXIOPBQFQBHQTKGPMYL9THJFRGIFBY9WKIMQSUHKUKFQRDHFUBGPWZNE9SWREBKNIOCAZXFSKEHYBZPWOLDTPVUNVUTURRERGDVEUOCE9NDEHIZWRQCSNUEWYMOAHJGEARXYYLGJGQGASBVJAYZCCUTXIFIHQUMKI9MPRXRZAFUYYSPZQWIDLHJ9NGU9WYNLNRWYKNGEZIKGSZEXL9BVIUNFUWMDLONJTFIIXWUETTMSPBUGHYTHJTJCCXQXLGMHUDJEBVQPCHKYTXJQBBIGRGRWPYCNCYRIOMNSCITUCWHIVOMKCXIW9UZAXRQLKUEH9PZBVPHB9VETTZWFIDEWCHJIHW9QVZHPVUSAEBTLUENJAMSYSDVNPVEDXJBGYYBQLQDXLUEAFJMDYEGDKRTUV9DCJNFZZSFMQX9DCZ9LQLVDOCNFDSNGR9PP9CNHAIAPFGVUUMSMOBUQJWDBAFJXHLZFZOCSK9OQIJYFBRVREMNRJDDHOPPITCXZYJYEAARBNUZYBVETPPZHMFCOIQLJRQYDZYBZCSHERQOZDKOSZWP9QHWMRSYESTDRPGW9HZKKBGHHPBHAUYXLE99OMBYHUFJUYGGWVUEPUXJVEVAEBFJRRFPTOIBPDXSIVJWPZYQVXY9VF9GFTRNRBZEHWFSCNUPGETVYGEJJJQEVFIUFMTFHMDWBTEIWFXGERGZLLMPMKNJSI9AGNZNXWYTJTXLUJHQHAUPZZIAXKCBAECERGTBPCKQZEGSRZIZTYRULGOAXETODFXIKBEZQETMZ99LLTUMLYWA9DREHWALIM9AYCBQQFRNNHUIKVJVIGTGIF9MUMSYJIZJAPOXHIFXH9PPOUOGAQWAKFGXNJDDISLFELAOKYBHMJUYHKXNZQAYWPHPICVMMQOSNOJFDOGPOPMZITNCRT9EXZPRYGOGDIZBWXRNLCGJCNGQDXYYGOFBARMWTPNNTLJBHHPKDDBULTHKEHDTTZUETG9LWVQCRWADOQFMIF9GOCZKBZSWECWORPZUXGLO9WXIZ9QOBANDWNBPMHBGCJ9TLS9WKPGCAJDPBUNU9OMCKMZJVLTUKPZLD9HYOAFKBKLFEVPJGPAVNGRMDYYBARNZHRKULBMQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIXPQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEBN99999999999999999999999999999999999999999999999999999NYBKIVD99A99999999D99999999YBPL9FUHMJAALACSDMDFUKKBTUPCHTXNCASWTZJZMYLFPJH9MWDXUCNGAVYJWFFQNHCABKYIQBTJWSZID999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('HSXQRKCIYXEEEEYMESAEWHGVRBNNFUPVHVHYDUFFDCAPYCLGTMMSYVZPGMVMGZFNDAKUFEKKKMMLCDLCYPTSOEEYANVTHWJRFHRYJ9D9JIBDVQLTQFDBYLXBJWAEJPPRHOXSZP9KWKNLQCUGMOKMHJQYODRVVYOZ9DMMYLMVBCNZSWASLFGJJY9NZO9XAIAIOWBYDHLNIBMQJLRBPZJGJUNOKYFYD9VNESPEZNIPUABKFNIAGEWGQRGLMGLGKEHWTQZWOMIZIF9FWUUMVVWS9CWUMWCHZIRKTODTRLEJTRNA9CCRFJNCVCDCQID9UDQJHGN9ZSGJGRSBVBYBKSBZNEJGZZHIECIVPPV99PVRHUBHLGHAZNJRY9LDB9SJGTXXHG99HQAOAI9JVPIYOOWHXFDVHWOEJIVJOIKPMTCAQZZEFEL9YSOSRWWGBQEPFJNTLVWOXIEPZHHCIQF9DZOQGUKYOJSIFHARSBORDAASWFIBAYHLPUTCUPJONWNQVKIHGKUFHSYKQJCNHYBKETAGEZKMPPCOECTMFZPXPLDHMVOSSU9RMQAQNJZYOXVJLKYZJDXUO9BKZBAK9M9RL9NGNUOVZBAJKCAEEBFFGZZJHLGL9KHOQQVKJYQZJYDTCYJXBJBUZZPACRUDDGXWKVRTVNOAVMYVGPEU9IPLHWFXZEHHUMJRQSQOILKMOKTSEBKEYSFRLH9YLDGGPPLSGFCJVINBCKIMXJKWLM9HTTAIVNKGUOHGJYPPDVSYAZLIFJBKQYQLLXBQUZJMEWUPLRVUOMXBHBUJYGDEGOPWNODYSZPQGBYZKQVXFPRAJNKIMMBWJWLIZLIHPWBSJINAPLU9NYHS9ANDORELEDICPYGWQQRGCMQXSWNBIHCSXPATVHEITSOTMKPSBBACQMKLTCDNTIYBXBCGFGIIPERFKHQKOONRHFEPMRIFJBNUEQEFCVMAXHARRHZZQGYALRQHZFBUTFQRVPWWPMWFQCNFDYKFDEGLGSILJRTSVGSLURIZPERJRLSGOMESSMZDUVPBXMOCFGBUWFZBCNYOBGZWGD9HQJOOLESVVAEIWHEKZXGHBEQHAMAPCLPQQRACGTWHMDCHSDGFEOISFMWWITNNDRLJ9TVIBAWKFLQIEHBRUQHYZYCGJWQIMODPIPHFELJCWRCIIKYEQNRSYCUGWXMJSOFUEBCKPXIOCXP9OTZOIDOSWPDNUTQXEHILCONJHHJFPAJEVEBVXROKKLJCZGXMOLB9U9NLCKZ9XUVHVUMWFFPAJZYTDJ9DIXFDQYRD9LPASBDIDHRHHUPOFWUAPVTCAAPNLDPLPN9XTEMOJSBBCHWBULFNHFMMPRSDQCNP9TFMFJFUON9ORDEORLGHZA9JZTRGUTOWLO9XWMAQZXHLUPVTFRSQUDDHYQRGPBLCOHDMLFKQVJAAKWFINZKCTFOESRDVWYWUAVGVBY9RLBQIC9GNXZIRQTY9VHAOIAXXIOVIMSVVIVONDRAXXGUAKFEXLUZYXVMZXOZKHJOKUSRVBUGZXFFDIYZOCSK9OQIJYFBRVREMNRJDDHOPPITCXZYJYEAARBNUZYBVETPPZHMFCOIQLJRQYDZYBZCSHERQOZDKOSZWQJFUMPXYZWLMDZJFYBNYFSKSJUHGOVSAIIIQVDFQWLCRVKTXRAORLNWKZEQRCCTJRMRYCXUJDWFPG9U9WODMOJKYJFMFINHBQSYVGJNNTJCNGOGKIUCDKTNMGFZZLZYYXNP9HPTGPINRDBDLQOJAEOYKAKBICWYZLDSZWZGNUHVOXYLMGCOLJSCXNPMVPPRSBRVEAQDAX9CEDRXRUAJSULVKAAKRMXMMWLPTYTYZZLOUFLBRUGDREHWALIM9AYCBQQFRNNHUIKVJVIGTGIF9MUMSYJIZJAPOXHIFXH9PPOUOGAQWAKFGXNJDDISLFELAOKYBAKBDTCTZDIOCPVXGTJILYQMPOKIVPJLGPEJFQE9SBVGBDPWMPWZPCNGBOVQSJLLHPKJIKPA9AIQZVHJYYDXSSNXAUDLKEGPCGZQZRXUWXTZMBXLUYJZBEPOTCHZGSLXUDI9PGFNHOZRQLQDWFURIXMDINYQDCSCUZBIDRQOKQYTXKSDTXT9YZDQBGJLVQAM9TWRHPKPJG9OAHJNRQIHPUSDLJHSTRHSTSQURNPOKQYVTIIOY9DDMQAKZPG9RTXSDGXWZRZJWGHEJIZLZWSMHBLHFFIXPQZOFFHNRIOQNJEBWZBDTZDJCUKSQDWR9ALZVDUEBN99999999999999999999999999999999999999999999999999999NYBKIVD99A99999999D99999999WNQNUFDDEVEKCLVLUJCFRRWBHSHXQQKSCWACHBLWXPEBWWEBJWJXQQBFJ9HSSDATPLVLL9SLSRFAVRE9Z999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Spend Transaction, Part 1 of 1 self.assertEqual( response['trytes'][4], - TryteString(b'999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUETWO9DONTUSEINPRODUCTION99999XYYNXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOWOB9999999999999999999999999999999999999999999999999999NYBKIVD99999999999D99999999YBPL9FUHMJAALACSDMDFUKKBTUPCHTXNCASWTZJZMYLFPJH9MWDXUCNGAVYJWFFQNHCABKYIQBTJWSZID999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUETWO9DONTUSEINPRODUCTION99999XYYNXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOWOB9999999999999999999999999OJ9999999999999999999999999NYBKIVD99999999999D99999999WNQNUFDDEVEKCLVLUJCFRRWBHSHXQQKSCWACHBLWXPEBWWEBJWJXQQBFJ9HSSDATPLVLL9SLSRFAVRE9Z999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) def test_pass_inputs_implicit_with_change(self): @@ -902,8 +907,8 @@ def test_pass_inputs_implicit_with_change(self): 'inputs': [ Address( trytes = - b'UFHYUCWLLEHDLXJWUSPODWEIFMIURCMLSUZV9BMI' - b'VEAJZBSEWOVBUBC9DZNSQUBPMPTNDD9GTVSMMQBNX', + 'UFHYUCWLLEHDLXJWUSPODWEIFMIURCMLSUZV9BMI' + 'VEAJZBSEWOVBUBC9DZNSQUBPMPTNDD9GTVSMMQBNX', balance = 86, key_index = 6, @@ -922,16 +927,16 @@ def test_pass_inputs_implicit_with_change(self): response = self.command( seed = Seed( - b'TESTVALUEONE9DONTUSEINPRODUCTION99999C9V' - b'C9RHFCQAIGSFICL9HIY9ZEUATFVHFGAEUHSECGQAK', + 'TESTVALUEONE9DONTUSEINPRODUCTION99999C9V' + 'C9RHFCQAIGSFICL9HIY9ZEUATFVHFGAEUHSECGQAK', ), transfers = [ ProposedTransaction( address = Address( - b'TESTVALUETWO9DONTUSEINPRODUCTION99999XYY' - b'NXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOW' + 'TESTVALUETWO9DONTUSEINPRODUCTION99999XYY' + 'NXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOW' ), value = 42, @@ -940,8 +945,8 @@ def test_pass_inputs_implicit_with_change(self): changeAddress = Address( - b'TESTVALUEFOUR9DONTUSEINPRODUCTION99999WJ' - b'RBOSBIMNTGDYKUDYYFJFGZOHORYSQPCWJRKHIOVIY', + 'TESTVALUEFOUR9DONTUSEINPRODUCTION99999WJ' + 'RBOSBIMNTGDYKUDYYFJFGZOHORYSQPCWJRKHIOVIY', ), ) @@ -953,25 +958,25 @@ def test_pass_inputs_implicit_with_change(self): # Change transaction, Part 1 of 1 self.assertEqual( response['trytes'][0], - TryteString(b'999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUEFOUR9DONTUSEINPRODUCTION99999WJRBOSBIMNTGDYKUDYYFJFGZOHORYSQPCWJRKHIOVIYQB9999999999999999999999999999999999999999999999999999NYBKIVD99C99999999C99999999KBXWFFMA9LJHXBHJKCKMYUGRZVBREIPFWYBU9TQJYCQIU9FISPRP9B9SARHRCIZHTTOGZYKZLBSJCLCFC999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUEFOUR9DONTUSEINPRODUCTION99999WJRBOSBIMNTGDYKUDYYFJFGZOHORYSQPCWJRKHIOVIYQB9999999999999999999999999999999999999999999999999999NYBKIVD99C99999999C99999999FWVD9JAZQGWBOFXANTLCCUHZTKWDDTBRICCOXGWGDDZSXJXKYAJJSCRWSVWVLXKNGOBUJLASABZRJXKVX999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Input #1, Part 2 of 2 self.assertEqual( response['trytes'][1], - TryteString(b'SUNYXMMYXSLOBXJAZOEGFTFDRABKOWLWNVNKWUQNNFAJZFUBLCSM9RHRNSEVRQYMXSUHLCBSTRAJ9MPKZHMGHRMSAOPOHZLNDZHOBMMNCFOVJLJJREPCHGDAUKHIOBXXNPPWAPDIFFLPJHTQKWBH9RVDKFHIOZFOJCMDRQQZQBPJBABWJKDZJQPA9CNLA9HONOGWCKOYSMLFTXU9QOXTTWARYURGLESFK9DLEL9ELNBOFTDJVRZSVFSZSYDZIAJXVPRAZPNWFEIQUBKOEUOOIJCWYBHBVQLYIDJ9QZMRXJEYXVFGJPMZHPQUPZZSDHNENXBZTWZCSNOUXM9OCAPCXAU9GSQSWDPLTKYBAORSAUAWCELG9TTRTP9JLXRXEINIQYJQMIYGNPECOFPRGYYXBWR9KXLEKBAKDHIAJUJUIDODRAAXJTDKQP9DCADLODZYULKHZABYG9NLTKGNPPBTGUTZBCVXAUNPYGPPQ9WAWB9PYZB9QJGVDCTWFJNAQQPA9NLJEQENMKMCZ9KIUZTFYDSFAQPUEVICSRPARJVCGHZBSISXA9IHAYXVAJNXJGRGLZPLSYOOEGKDFYRDLIXNLYVXSLISFLGQJDPPYYXTNNCGPCKYIZBYBHOGBVVWEXCJUJBW9RVAFLCJ9XWMIEVNBXTAPLZZRNZLNATFXRYHRXKIVETTJEMOSEEJHLVJVCMLCOSDVHDZPI9MKHKJEUBPNJOSWSCXOG9UMJAZMSXGBZWIYBBXUNUZQMKTKXASJDNPRRLFPVHW9SEJLDFZWWBVWSOFVPLPZUXCYUWTHODALXTVSCMKPKLFXXWBIANSBMLY9WWU9NESINMACVFAVUQNZVRFYIDCEJXUPAQMPWNITOWLJZWHHPFYBKULZM9POPHIMEFUXPZMAKZCQXFNQBPHGUMCHRRLSCUZYRUOAYLESIXRQHERYHM9NJUYMGYGBLBOVNYOLO9VBOAXXZPJGRDWQGQKRERHWDVIISUTJAVKLFYVKLZSUZYSABCGNHQEW9TTSPDVKLUKWRDDZCAR99DKTAVEBTTGYBHXXTYPSJISVCSXVOZVASWTSZTOSCTZCB9JOQSJXAYUNKCZZGUAXDLFZHPLGCCRCS9CHDSHWRVIEKTHU9PUANYYZWWHQISAWVVJPUXGTIVHIJSBOPPYBSRNKTDIHDEEAZOPTHSDGDRVCQLTXFOFNPPKJJXMTIOZAMADXDGWVNITQWGKLAKBG9NCRPJZMSNORPHQABNDBCTIP9UYDRXYRAXMSLKVPPG9YPSZHYXDHBKIZB9OHNMDSA9IVVHU9BCFU9PZQJAAFXGSHLPGLRJGZCHJRSXYNKCHLSJFYMQGTRWQNRGZWKBKVTGSRTOKWSAAKXZMCGEWSWCAXKOVOQMQTLAVXYXCPZTDCFXPOSXXIAYSIIHEZJ9DNYTKKYMWRTLWGWNXVJAYISGRDIGQGUTSQWWUWYSAHSOELZLPGAALRXCWFCCZMY9GGI9DEKPQMC9DTHQXQ99BJRKXYQUPSQUOO9YIWWWQO9RUFYZJOXYIOFYXHYADLICRBQ9WR9EWOCFQKQHSTAVURWXDVMZTKBDEIANACYAMNCUDAQPIJYOUFYNGWCFKVTWLKLMDDVBZLDHKOQSUZUUHGBOJYEL9NYWCHULZYVELSILWUREVAEKVFSKFFPYEBRUPQMWHHAEAHLPOGDPJDKHI9KTJFJVYN9KIRGO9UMQVASVOAHHMKL9NJVXHSBTLWUWLNOP9IRP9BHOLSXKSRZWNVUWQGQQWFOFYGDPCOWRPOWKYUPSBFPEGFPE9LBWMA9MIE9DQKTUJJCAHNQNDQJUOP9VFKSYBELBHULNQTRCHXGYIYWQCAYVLKKZMEPTEWTKMCGRABHAMQWWCVDGNGOWNVFTBGKPCPXOFRKJRQPSXZCO9MI9FVBZVBTBLEAWUJQGMROZATOUYEMRZBAWKMCAALRBTPBEOTV9RULJ9IUFXLUYEBSCNUJNC9MZTYKRFWSYFSUWOZIMX9SXCMHEDKWXBRUHFYUWDSHUEOLWG9K9VJEXO9QFKVFEZLCXQLQMRQ9DPD9S9PQZXCCUOK99VGDEGQSLPJUFRPWNULNVRYVUJUWIY9PAIYHMJDDGOWQRRTXWMTGMTUFR9NNHTZGAZHQKIHKABBNQIFVXYFCAXOGFVOX9MQEWDYTVXTAAGMIWUFHYUCWLLEHDLXJWUSPODWEIFMIURCMLSUZV9BMIVEAJZBSEWOVBUBC9DZNSQUBPMPTNDD9GTVSMMQBNX999999999999999999999999999999999999999999999999999999NYBKIVD99B99999999C99999999KBXWFFMA9LJHXBHJKCKMYUGRZVBREIPFWYBU9TQJYCQIU9FISPRP9B9SARHRCIZHTTOGZYKZLBSJCLCFC999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('RRRWOYADWJHJLPCMQLIFYTHXLKTAHTTGUZEWOLVYLQLNLTECZXWCYRKDYNHVTJKANOEJVDKRFQOWSKRSCHTOSWVIABTBYJOAGGPFHWTZXURZGZXSY9TRG9XQIZOSPSVIROZDYPKSPZANCKVFRSZWITVIGTFHQD9CRWPINACBPNKQIWLQSQRRWU9LJQNEYTHPAKOBFHEJNXCXFFMSQC99SEIPJYKNMTFVDFRHSHSBYHPAEFAAC9CQQXL9FUSXGERKHQQDNTJBSAHLKYWCCQEKFZOBJ9YDT9AJRMQLLKUOKCXBASRRAPTUCYCXDZWXSBODNTG9Z9IPZI9WBFVZVCJEBKFKKKXCVLY9SSGFSFALNMXLBNWNJPE9CLI9XGILJDJNKNOZZUB9RSMFLSNBEOAVZIZKWDRKOMVVRFZTLMMZHTZJDOBYD9ACJCJOVMIWLRCKXGLLYRTUCYIDUZZHKALZHWAWQJUPKGNBMAUFICSNDLJU99U9WWCWKTEWVNAQNWDPBA9EWREQWDJDNTUDXIZYXPTHNRJJHOJTSQOIE9KOUEOTDVMUCSNZUZXJYSIO9UMQVKOTMCM9VNLWMCLHLNJXOWJTBLYU9CWSHYWNPNBWZWZLXJUXNFTOKOSUGAPTXNKEJN9YRJYDCRHNHIWNRQEFAILFYCX9IZVFVXLJFVVRMRAUBTZAGMJBLMRJEPMHFAPGOAZFCNVFABVDL9OXHSOD9QHNYPHFHCYRZRG9PCQDTDPSWZPNSFFNLRLJU9YPOTNGZWGGASLOAGQNVTWNZBFZZDBCKMXPQQJYYNLROJWGKACUEEOOTZIC9R9BWFUJPTNAEFPCWRBNLVOFQLRKFJYNGLREKVVCROUSVJBTXOINRHPKISOIUOGFEBRTAZWCJTHTJGUEVPTENCYCKBJTPZN9KQQEFNDVVC9MALGIMMPCNUYWXXNSLJNLKGFK9RCWO9UKPEXTXEVRGEZWZGOLUPRKWJF9ZEITZDJDKZXKAUWBFCLGPCAGIYTTALOKVCIZ9DFFXEZJBRVLPJXOQHCTZQXPHYHRJEWWXPSFIOTJKJUOKBMOMGHVIAAHJVUJRVPGGTITOMFIMGQKJMBUOBBOCOTDKBMDVGENDEHBCNCCNKLDEYAZZC9PSTLIPZILITHGIRZVLTAYHZVYQYBZCXBCMUPBFUPXSZVECQDCEPAHFZHLOOZKWKSQGEIAFMKYPOVRKDDAXHJOARAJBJWDUNMINSUVUCPYEERXVPBXSBJONSFDBOZNO9BUIWRMTCWSGJFKIVGDDZHRUQXIHMMFYRVZBEPTZGLZZBHROEZSXHT9PVRO9O9F9ZUGCDQIKDQKUJFTDZI9EDITJMN9MSDNXXWVOKSDFLQYEOCTAJCCY9RXEPEQNYVYWUUCD9YLVPGLDXVHS9WEZXHJEEBTMWWZRDCVP9FMMC9VQAWMZXRMYTVMDUOICCQZSIUDBBVPXVQP9LTIDDV9ERMOIXSNIDIPJYSSVGNOTECEZKMOXXUO9VFVITXOFDZKELQUCBJOGBTGBEOXDFTUEMCVXAH9TKGLM9ISCWBUEWQLLIXXWEFMIIGTZYJVYPFNBXQZSMPIQWDTVXYJHMTTTXBBS9LXO9GJQVJAONI9CODDHZOKLFYQQLOKSIGSUCOCMXJRCB9OKNTOCPLXBEKZZLCOFERMEHXQNMJAXMOPXZHQB9MCDVQLYKYMDOMCWIVGJCZGUGIXKGWNYOILFQAMRQXMFUKXMILIOE9INLAPJMUXMOMOYILRFKURQMLQPVRZYXB9NRFNFCDWLRNTFNWCCWNUKZXGYYHNMYDX9GSLN9OUVPXQPIVLPXQTMWNGOFAMYCLCRNSWALVNYTUFYZAHYAHFDWYKLWQOSFOZAQSNSMMYNBBX9WSZMJ9NHK9FNVTLAKBBTGXVBCIHSFB99KHXMTUYPMOZJFCMFFIJMAHKKXXBASKBWREAWSFCLKKDOKHFFKLMFVXTIVEBBIQJRGZFTOLOT9MDAZQNQBWZDXUFTBHVYGLYHMSHEIFYVQMPXC9ZZBXYGQEUIXYNUPXNOLYKJKMJ9XXFWCOPAYBWZSEWLMXK9KTHHMSWDWXLFNQBXMOUMYVOSFMTOQWTGZYYRZSEAGHPVHFBPG9AQBPLC9IIIKGPKCXYLVA9RLCHOPJLONGSIAYCUETOMNGNFCRETLXPHMGKXZXVM9XUFHYUCWLLEHDLXJWUSPODWEIFMIURCMLSUZV9BMIVEAJZBSEWOVBUBC9DZNSQUBPMPTNDD9GTVSMMQBNX999999999999999999999999999999999999999999999999999999NYBKIVD99B99999999C99999999FWVD9JAZQGWBOFXANTLCCUHZTKWDDTBRICCOXGWGDDZSXJXKYAJJSCRWSVWVLXKNGOBUJLASABZRJXKVX999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Input #1, Part 1 of 2 self.assertEqual( response['trytes'][2], - TryteString(b'BUKUGOBJ9OGJGTXCAYHYGZOSYEIGBBXPNYEIBIYCTACBTKXDHGMHYJNREPKPIAZCUOZFWLUXNGMKHIDQXZSQEN9JHHNMYQFGXXYQQDLYQROXZIRRDEVBEJWIJGMDFJCIRTGFTAEPLJAQBWAJMIOMPWJBBK99UYXXVBQQIOPJHS9SVTWKJGLCEKQNDSBBCZOMIVDACSTJAJWEWEEMKZLNDNDZOOXGWFFNHDMYWOTMJUXFNXATB9WQZIZGMEVCNZMBRZZFKVTXHFQNNKMMLAPHTIYZGDDPCDYIZIRHSTHWTFLLIUTHDMSAGMTFUFORGEJVYSUWA9EF9GXJVJKJAYFJJVGIVNMYIQGRVGEOMPLFXVGCKQHUJVMQPGAHXYJYERPCGFLEEIBXFWJSQJBNXQDDWPJTVIQS9XDTCIQMCYBLQVIONVNBHREGRKXDNFALNNXRPAPXTPSXZAPPNKRHVLVEMFQSOBHSEAXLX9JLHYBMKNCFWHOWJYDOCCPBAAAYJVTMRZMXODUATBFE9ZUB9MSLLCELNVSNQIQ9QAACRYIU9IQDOQVLYJGJMOWXPGAOAHWKVFMVQKVLZXGODQZGQQFSILMRYROYKTJWJSSYXTXOMPRGSJNOYM9ZQJWFB9BIADZJBOWLKVODOFFAXQKCPGTTWPW9CUCBFC9ZUGVVZCHRAMNKWKEDMFIFFDKURRTITLNQUEHBCWEOFHKKHJVHHJISQNJFCCMZOQCGIMGZCKJMLDHAEHJMFCUCAZNERDQCFIWWAVFWBVOQUCAWOAA99ZAMBFHCZBQBPQHKQCMEHGPTJ9KKRZDCOZGQHRNPUMPZTGSNFPMRBKKPVA9CDKAQUIXSBYLTSJKNWZJCEFIVYTYHMUHAYGUCMJUMFZWDIEWAPFFXVS9FTVYENQKOCMLEJMGQKBVLEMCHHIQBYNGFRPXWZCARCVHXUOKFDYMSQYMGUKRJJGHQRGYLNXBDSOYDNLJGPGXWCFSNEWP9URDSOPSDRCNSQUIFHEJUSSNXWQGCEZCYBCNHKOOTSXNMYPRCRPBOAECXUNORAHAIUHAVLRUAU9PROLDHSXQLROIQZLSDW9NQRKFBIRNVMACMQPESHPUHSHG9ATAYMK9JPLETEJPFDLSPZYJLWNSEJZMZERZEIAJNU9AQLKKTYETEXYYNZ9DALLXGDLBSZJOSFG99HYSBYPOLGB9EFHGHFWEXOTPHPSAZR9FDSPBCZMBFTMKZMGALUARAMMPIPGILHTQRCHAYDEXMY9CTHBHJVZJJXWRAUHMNCHRQRXWYOFJG9DIZFAIYUJHNMYAWHGCEBTOH9QPLIYNDHEEJSOYZAEMGUWSAZUGPFFINPNQYARM9OTSCUTPDOZUGSJBADUQQCVESMDRKDFQICMTYBBICIADAFMVOA9IDYDZFJ9GMYQGCLAQCLIVOBANCGSLTAVWYLKWCPFBXXTNTDNKCBZZRKWLARIA9NACFGTOHYRY9SKEABGCOPOZGGQEFRDQSFWUYGDYNBJEIACRXNQSUBKMKSGSWWKSQOLAOWWDWICAHQTCZEGCUVZC9AWORNNRALONIZUIVYJSWBCCGBFJPEFDGOWRWJVZAVGEBGXZTJMVTTFTUVVE9AFXWZYBLHNVKJELEGLWJKCKSAGBUQSWZXY9IZUDOFSLDAIGGAILAKTLOHWFTNHJ9NSXGBTCSKGNSUEWQ9EEDXYEMVMQJPSITVWDCX9ZMGGHFQKPJAJHXAVWNBSNOJH9U9QWOLRYI9AQ9JIEYTSQ9BLFZSEB9PQTDGEHNUXCJKADKUEYUJOMSPKFANVQWOFHFWHVAOTBVRWSGSSKOIBJKNXTKHLCERGZLLGYOMGATPEPG9NTQUARULDWTCAHB9X99CVCWEJAHNZVZDESTMPAZVEWUDHTNGIYI9HXIYWLYMU9YKJVMERWGFBBUQKJ9JJEE9LLNPLZASNXRVGEHYAPVVQSSGGFB9UUVKFSKWTGB9AUYLNAZJ9WXORLNIRMBSEVIJENPNZNCZBJTLHZIQFMJMERPDMVFJFQYAWGGYHMSMZGNJKVZ9JW9DO9GQUTYEALMCYH9SMRMF9JAAHTI9UISSHFLAGXQQSXVEWELHPNS9WSULBQMHJMFERANBLXEDLXTWAUKKJJLHYDWSVAKTAASJLXMAMA9ECGOTCYRWBXLDXSINUPYUK9GLWIUODCUFHYUCWLLEHDLXJWUSPODWEIFMIURCMLSUZV9BMIVEAJZBSEWOVBUBC9DZNSQUBPMPTNDD9GTVSMMQBNXVX9999999999999999999999999999999999999999999999999999NYBKIVD99A99999999C99999999KBXWFFMA9LJHXBHJKCKMYUGRZVBREIPFWYBU9TQJYCQIU9FISPRP9B9SARHRCIZHTTOGZYKZLBSJCLCFC999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('JFSQQFKZLBCXAVCDQVFXRNSLJUQQIWCVDGWAUZLSKMYNHY9RUOKZILRZ9OW9ITKBTYHAYTTD9KEUGLCGYQJYMDAYHQMGUIOTVZXQJLTQAKV9PZLQIGDAZJTNQ9BLRMQBDVCAIBCTTNEAVECQBNUUIBVEMQAFSYUCNWQCRSICILWHWSGQCVPQBWESGVVAEWY9WLIIMUWYMGSMJORUMIJLMQIVMLBQXIWEZDYESPLXQOVJGCTRRNZEBBHHZOPAPFIWGNFOAPIR9ZSZSMHZODPTJCYVHQLTKAGU9UBA9URUOKBDUYFCTVHJXYDVVERKRPTOHNXBEG9BI9BSJSLOAWOLUUNBBWCRILOKWWD9FKOBPWXAJOLKVULWW9EEBMBPUBSRJHOMHEJJHOY9LKJCQZBZZX9KSXVHUBYXVEQJLYWGYNHDCKWHUDNAHHIJYCBADZMIIGZHOXYOQ9PNWCKZAZKWNRNM9ALALV9IOZYJSYHILATWVNKGIDTW9ONJTXFA9MXKUDPND9ONGJNMTYZUJKWRMFVNGRNIOPRWLUKMXHWKFKD9IKZSJBWBMQAXNTKERHEXELMAAXFHEJUUYCCBHNUGGE9TBJNABKO9RVFZSZNPEKBQHNIHMUCGBWDJEUXREV9YUSUVHXQXCPCPFFBZBEJMGLGVWDGINYLAJORMFTVNLSZBH9RIVOGRZKQSJYWRPHBPZ9MNVQJOFSUWZMOHUHVCNDIVDMCMWCTKEBQNKGFBRIQRRLZSQPQ9PVRKLHJODCWVPCHSLALPPOWVXCIXLDSUOL9COAPYBOVPVBUAUBCI9YKZRYMXEE9NCVYBNAIDPXIXMBLVLUXOTDUDQGNKPVJUDPPTIHCCIYQBSHNRIBBMFB9AGSNUZPSPNZEORZ9LGDEUELGFOZZEYZDT9A9XVZXLOKYL9GJXVAHEZNVYSWP9ZNWT9GOJLMELMXJDSDRMYTSVOOWMNUNQFPVXJVOXXJEVPSNPZGLGTALECVACGTBEP9FTYHWFKRCEXOKTUIFYWYRLJPJZEP9RICV9EVAFLTAXSGCRRMPEAVIGRPVPTHWKMNMNWPLTVJIRMPIUFLAIWIFTCAZOVBDQEEB9TQEPBPIJINMHQBBUBDDQDOW9RYJBAFUKZZZBTBEKVWIXMMIVHGMPDLT9FDPKFDCZGQLCJUDZXNDLIRPKAPDGCYEWPOWLSKGRAARVVHC9ZZ9QNVJGFV9IFTUQOSOXPOOMRFKNKWLANREIMEEPSRRRIELVF9UMPZNFBALDOQWALSFUGZECVFKIOIHZOVQKJAKXCCVWWWMPLLRWZXQFPQZDLOHIETRUI9HRKLFOAVEH9M9EOD9LKDY9TDZRZPAPBIUVLFJAUFDDRRTSAGRE9QDRXWFUTOR9WWWQFPBROYRCQCZEFKH9FOGTLQXJHBSKO9ADIGFZLJVOATVIHXVX9ZEVLLLWYFTHRMTVDGAFMXDSUIMXMUDDUVMSIXLCMYIDTLEO9ZGBRSAYRINB9EGDMUNFLD9GKZVLNWADRTGHNJIWWCCHH9WILBUBGDWUEOUZFRCHHHMFOFHWTQTKPXHNZQPXWEPRLGEDZTRHDXUVBGONUDXTZYFCUNCJTVGRFGUWXNZGBWYKCYTCDSJ99MSHKMKBLFZYZQQWPAAKZYKVSOYBWOHBFM9IKDLXR9WDXQFUEW9D9FQCXZJZSLAOKRBVEAYQBSFIXYEMVMQJPSITVWDCX9ZMGGHFQKPJAJHXAVWNBSNOJH9U9QWOLRYI9AQ9JIEYTSQ9BLFZSEB9PQTDGEHNUXPAHQONJRBBNWAS9CEAPIGPRFCTYCPRDUC9GQOXBIOAVCEPUSXCXDGUKCPCM9IJJHWDEOJJPL9GXIRNOMYUTPAOXEVCIWORREAKHYGAG9QCJLPKTA9SYEWLFARCXUMYMXIUAWPM9HBU9FR9XRIYJIJUILXUJETIIFFZZENYOIPQKQSFGFJHGAYXUSEMUJYKHDIKOAKGTMAZFKFN9NTUECRU9EXC9DFVCVPDGRDYVOHUSETERJWT9MGVHNV9WBVXFFIISMAVTIGESBJBHGTT9CJPROCGJZYSVGFJTJOVOMFLROFRMQVNNCXTNUIYMKWRDMFMOYYSTFKIOAEIOPZZLBDLP9WTFLDSBENOONPETOS9QHLOSPYDPRHKCIGUAGKQXVBVUSJTIOAMNAXICQ9CLPCUFHYUCWLLEHDLXJWUSPODWEIFMIURCMLSUZV9BMIVEAJZBSEWOVBUBC9DZNSQUBPMPTNDD9GTVSMMQBNXVX9999999999999999999999999999999999999999999999999999NYBKIVD99A99999999C99999999FWVD9JAZQGWBOFXANTLCCUHZTKWDDTBRICCOXGWGDDZSXJXKYAJJSCRWSVWVLXKNGOBUJLASABZRJXKVX999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) # Spend transaction, Part 1 of 1 self.assertEqual( response['trytes'][3], - TryteString(b'999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUETWO9DONTUSEINPRODUCTION99999XYYNXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOWOB9999999999999999999999999999999999999999999999999999NYBKIVD99999999999C99999999KBXWFFMA9LJHXBHJKCKMYUGRZVBREIPFWYBU9TQJYCQIU9FISPRP9B9SARHRCIZHTTOGZYKZLBSJCLCFC999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), + TryteString('999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUETWO9DONTUSEINPRODUCTION99999XYYNXZLKBYNFPXA9RUGZVEGVPLLFJEM9ZZOUINE9ONOWOB9999999999999999999999999BI9999999999999999999999999NYBKIVD99999999999C99999999FWVD9JAZQGWBOFXANTLCCUHZTKWDDTBRICCOXGWGDDZSXJXKYAJJSCRWSVWVLXKNGOBUJLASABZRJXKVX999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999'), ) def test_fail_inputs_implicit_insufficient(self): @@ -1113,18 +1118,22 @@ def test_pass_message_short(self): Adding a message to a transaction. """ response = self.command( - seed = Seed.random(), + seed = + Seed( + 'TESTVALUE9DONTUSEINPRODUCTION99999HORPYY' + 'TGKQQTQSNMSZBXYLAFXFHZVPWVGCPRGXKXREJKI9B', + ), transfers = [ ProposedTransaction( address = Address( - b'TESTVALUE9DONTUSEINPRODUCTION99999YMSWGX' - b'VNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN' + 'TESTVALUE9DONTUSEINPRODUCTION99999YMSWGX' + 'VNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN' ), message = TryteString.from_string('สวัสดีชาวโลก!'), - tag = Tag(b'PYOTA9UNIT9TESTS9'), + tag = Tag('PYOTA9UNIT9TESTS9'), value = 0, ), ], @@ -1135,7 +1144,7 @@ def test_pass_message_short(self): self.assertEqual( response['trytes'][0], - TryteString(b'HHVFHFHHVFEFHHVFOFHHVFHFHHVFMEHHVFSFHHVFCEHHVFPFHHVFEFHHWFVDHHVFCFHHVFUDFA9999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUE9DONTUSEINPRODUCTION99999YMSWGXVNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN999999999999999999999999999PYOTA9UNIT9TESTS99999999999NYBKIVD99999999999999999999XYAMEGAPMZ9HQCPAOUEQLDKHPMLJGJFEOGDAHWNSMRETQRKBKFNBVSEESVOIGRFDRMXWOG9LARRSIZ9QD999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999PYOTA9UNIT9TESTS99999999999999999999999999999999999999999999999999999999999999999'), + TryteString('HHVFHFHHVFEFHHVFOFHHVFHFHHVFMEHHVFSFHHVFCEHHVFPFHHVFEFHHWFVDHHVFCFHHVFUDFA9999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUE9DONTUSEINPRODUCTION99999YMSWGXVNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN999999999999999999999999999YAOTA9UNIT9TESTS99999999999NYBKIVD999999999999999999999DRTUWFTZIDCUOAWLSDGIAWAIOGDYWFZNJHCEXDGAHCPKOIUIICUWGPXTGCRJWZBV9AXBCBRAKLDPRKQW999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999PYOTA9UNIT9TESTS99999999999999999999999999999999999999999999999999999999999999999'), ) def test_pass_message_long(self): @@ -1144,14 +1153,18 @@ def test_pass_message_long(self): """ response =\ self.command( - seed = Seed.random(), + seed = + Seed( + 'TESTVALUE9DONTUSEINPRODUCTION99999HORPYY' + 'TGKQQTQSNMSZBXYLAFXFHZVPWVGCPRGXKXREJKI9B', + ), transfers = [ ProposedTransaction( address = Address( - b'TESTVALUE9DONTUSEINPRODUCTION99999YMSWGX' - b'VNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN' + 'TESTVALUE9DONTUSEINPRODUCTION99999YMSWGX' + 'VNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN' ), message = @@ -1179,7 +1192,7 @@ def test_pass_message_long(self): 'я не наплевать, что вы думаете, что вы имеете право!', ), - tag = Tag(b'PYOTA9UNIT9TESTS9'), + tag = Tag('PYOTA9UNIT9TESTS9'), value = 0, ), ], @@ -1191,15 +1204,15 @@ def test_pass_message_long(self): # Note that the transactions are returned in reverse order. self.assertEqual( response['trytes'][0], - TryteString(b'EASGBGTGTDSGNFSGPFSGAGFA999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUE9DONTUSEINPRODUCTION99999YMSWGXVNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN999999999999999999999999999PYOTA9UNIT9TESTS99999999999NYBKIVD99B99999999B99999999WNFMWSPCSGGIFVNVMLOFYLWQXKIRFEVEHVNBSCRHJ9XLSWYSKAO9LIZSYRJAGNNLBJBZKGCVPZEWKYXAW999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999PYOTA9UNIT9TESTS99999999999999999999999999999999999999999999999999999999999999999'), + TryteString('EASGBGTGTDSGNFSGPFSGAGFA999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999TESTVALUE9DONTUSEINPRODUCTION99999YMSWGXVNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN999999999999999999999999999PYOTA9UNIT9TESTS99999999999NYBKIVD99B99999999B99999999EKHBGESJFZXE9PY9UVFIPRHGGFKDFKQOQFKQAYISJOWCXIVBSGHOZGT9DZEQPPLTYHKTWBQZOFX9BEAID999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999PYOTA9UNIT9TESTS99999999999999999999999999999999999999999999999999999999999999999'), ) - + self.assertEqual( response['trytes'][1], - TryteString(b'FSG9GTGHEEASG9GSGNFEATGFETGVDSGAGSGWFEATGUDTGVDSGSFSG9GSGSFSAEASGKETGDEEASGRFSGAGSGYFSGTFSG9GTGDEEASGZFSGSFSG9GTGHEEASG9GSGNFEATGFETGVDSGAGSGWFEATGUDTGVDSGSFSG9GSGSFSAEASGUETGDEEASGVFTGUDSGBGSGAGSGYFTGEESGUFTGWDSGSFSGZFEATGVDSGNFSGXFSGVFSGSFEATGUDSGYFSGAGSGPFSGNFQAEASGXFSGNFSGXFEATG9ESGSFTGUDTGVDTGEEQAEASGXFSGAGSGRFQAEASGPFSGSFTGTDSG9GSGAGTGUDTGVDTGEEEASASASAEASGZFTGDEEASGVFTGUDSGBGSGAGSGYFTGEESGUFTGWDSGSFSGZFEATGFETGVDSGVFEATGUDSGYFSGAGSGPFSGNFEASGPFEASGXFSGNFTG9ESGSFTGUDTGVDSGPFSGSFEASGAGTGUDSG9GSGAGSGPFTGDEEASGXFEASGTFSGVFSGUFSG9GSGVFEASGBGTGTDSGAGSGPFSGSFSGYFQAEASGUFSGNFTGBESGVFTGBESGNFTGHEEATG9ETGVDSGAGRATGVDSGAGSAEASGKETGDEEASGZFSGAGSGTFSGSFTGVDSGSFEASGVFTGUDSGBGSGAGSGYFTGEESGUFSGAGSGPFSGNFTGVDTGEEEASGVFSGZFQAEASGXFSGNFSGXFEASGBGTGWDSGNFSG9GTGVDSGNFSAEASGAFEASGZFSGSFSG9GTGHEEASG9GSGSFTGVDEASG9GSGVFEASGPFTGTDSGSFSGZFSGSFSG9GSGVFQAEASG9GSGVFEASGTFSGSFSGYFSGNFSG9GSGVFTGHEQAEATG9ETGVDSGAGSGOFTGDEEASGAGSGOFTGCETGHETGUDSG9GSGVFTGVDTGEETGUDTGHEEATGUDEATG9ESGSFSGYFSGAGSGPFSGSFSGXFSGAGSGZFQAEASGXFSGAGTGVDSGAGTGTDTGDESGWFEASGBGSGAGSGRFSG9GSGVFSGZFSGNFSGSFTGVDTGUDTGHEEASGVFEATGUDSGBGSGVFTGVDEASGBGSGAGSGRFEASGAGSGRFSGSFTGHESGYFSGAGSGZFEATGUDSGNFSGZFSGAGSGWFEATGUDSGPFSGAGSGOFSGAGSGRFTGDEEATGHEEASGAGSGOFSGSFTGUDSGBGSGSFTG9ESGVFSGPFSGNFTGGEQAEATGVDSGAGEATGUDTGVDSGNFSGPFSGVFTGVDEASGBGSGAGSGRFEATGUDSGAGSGZFSG9GSGSFSG9GSGVFSGSFEATGVDSGAGQAEASGXFSGNFSGXFSGVFSGZFEASGAGSGOFTGTDSGNFSGUFSGAGSGZFEATGHEEASGBGTGTDSGSFSGRFSGAGTGUDTGVDSGNFSGPFSGVFTGVDTGEEEASGSFSGZFTGWDFAEASGMFEASGOFTGDEEASGBGTGTDSGSFSGRFSGBGSGAGTG9ESGSFSGYFQAEATG9ETGVDSGAGSGOFTGDEEASGPFTGDEEASGBGTGTDSGAGTGUDTGVDSGAGEATGUDSGXFSGNFSGUFSGNFSGYFEATGUDSGBGSGNFTGUDSGVFSGOFSGAGEASGVFEASGBGSGAGTGAESGSFSGYFEASG9GSGNFEATGUDSGPFSGAGSGSFSGZFEASGBGTGWDTGVDSGVFSAEASGKEEASGBGTGTDSGAGTGVDSGVFSGPFSG9GSGAGSGZFEATGUDSGYFTGWDTG9ESGNFSGSFQAEATGHEEASGBGTGTDSGSFSGRFSGYFSGNFSGQFSGNFTGGEEASGPFSGNFSGZFEASGBGSGAGSGRFSGAGSGOFTGTDSGNFTGVDTGEEEASGAGTGTDTGWDSGTFSGVFSGSFEASGVFEASGPFTGUDTGVDSGNFTGVDTGEEEASGBGSGAGTGUDTGVDSAEASGKEEASGYFTGGESGOFSGAGSGZFEATGUDSGYFTGWDTG9ESGNFSGSFQAEATGHEEASG9GSGSFEASG9GSGNFSGBGSGYFSGSFSGPFSGNFTGVDTGEEQAEATG9ETGVDSGAGEASGPFTGDEEASGRFTGWDSGZFSGNFSGSFTGVDSGSFQAEATG9ETGVDSGAGEASGPFTGDEEASGVFSGZFSGSFSGSFTGVDSGSFTESTVALUE9DONTUSEINPRODUCTION99999YMSWGXVNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN999999999999999999999999999PYOTA9UNIT9TESTS99999999999NYBKIVD99A99999999B99999999WNFMWSPCSGGIFVNVMLOFYLWQXKIRFEVEHVNBSCRHJ9XLSWYSKAO9LIZSYRJAGNNLBJBZKGCVPZEWKYXAW999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999PYOTA9UNIT9TESTS99999999999999999999999999999999999999999999999999999999999999999'), + TryteString('FSG9GTGHEEASG9GSGNFEATGFETGVDSGAGSGWFEATGUDTGVDSGSFSG9GSGSFSAEASGKETGDEEASGRFSGAGSGYFSGTFSG9GTGDEEASGZFSGSFSG9GTGHEEASG9GSGNFEATGFETGVDSGAGSGWFEATGUDTGVDSGSFSG9GSGSFSAEASGUETGDEEASGVFTGUDSGBGSGAGSGYFTGEESGUFTGWDSGSFSGZFEATGVDSGNFSGXFSGVFSGSFEATGUDSGYFSGAGSGPFSGNFQAEASGXFSGNFSGXFEATG9ESGSFTGUDTGVDTGEEQAEASGXFSGAGSGRFQAEASGPFSGSFTGTDSG9GSGAGTGUDTGVDTGEEEASASASAEASGZFTGDEEASGVFTGUDSGBGSGAGSGYFTGEESGUFTGWDSGSFSGZFEATGFETGVDSGVFEATGUDSGYFSGAGSGPFSGNFEASGPFEASGXFSGNFTG9ESGSFTGUDTGVDSGPFSGSFEASGAGTGUDSG9GSGAGSGPFTGDEEASGXFEASGTFSGVFSGUFSG9GSGVFEASGBGTGTDSGAGSGPFSGSFSGYFQAEASGUFSGNFTGBESGVFTGBESGNFTGHEEATG9ETGVDSGAGRATGVDSGAGSAEASGKETGDEEASGZFSGAGSGTFSGSFTGVDSGSFEASGVFTGUDSGBGSGAGSGYFTGEESGUFSGAGSGPFSGNFTGVDTGEEEASGVFSGZFQAEASGXFSGNFSGXFEASGBGTGWDSGNFSG9GTGVDSGNFSAEASGAFEASGZFSGSFSG9GTGHEEASG9GSGSFTGVDEASG9GSGVFEASGPFTGTDSGSFSGZFSGSFSG9GSGVFQAEASG9GSGVFEASGTFSGSFSGYFSGNFSG9GSGVFTGHEQAEATG9ETGVDSGAGSGOFTGDEEASGAGSGOFTGCETGHETGUDSG9GSGVFTGVDTGEETGUDTGHEEATGUDEATG9ESGSFSGYFSGAGSGPFSGSFSGXFSGAGSGZFQAEASGXFSGAGTGVDSGAGTGTDTGDESGWFEASGBGSGAGSGRFSG9GSGVFSGZFSGNFSGSFTGVDTGUDTGHEEASGVFEATGUDSGBGSGVFTGVDEASGBGSGAGSGRFEASGAGSGRFSGSFTGHESGYFSGAGSGZFEATGUDSGNFSGZFSGAGSGWFEATGUDSGPFSGAGSGOFSGAGSGRFTGDEEATGHEEASGAGSGOFSGSFTGUDSGBGSGSFTG9ESGVFSGPFSGNFTGGEQAEATGVDSGAGEATGUDTGVDSGNFSGPFSGVFTGVDEASGBGSGAGSGRFEATGUDSGAGSGZFSG9GSGSFSG9GSGVFSGSFEATGVDSGAGQAEASGXFSGNFSGXFSGVFSGZFEASGAGSGOFTGTDSGNFSGUFSGAGSGZFEATGHEEASGBGTGTDSGSFSGRFSGAGTGUDTGVDSGNFSGPFSGVFTGVDTGEEEASGSFSGZFTGWDFAEASGMFEASGOFTGDEEASGBGTGTDSGSFSGRFSGBGSGAGTG9ESGSFSGYFQAEATG9ETGVDSGAGSGOFTGDEEASGPFTGDEEASGBGTGTDSGAGTGUDTGVDSGAGEATGUDSGXFSGNFSGUFSGNFSGYFEATGUDSGBGSGNFTGUDSGVFSGOFSGAGEASGVFEASGBGSGAGTGAESGSFSGYFEASG9GSGNFEATGUDSGPFSGAGSGSFSGZFEASGBGTGWDTGVDSGVFSAEASGKEEASGBGTGTDSGAGTGVDSGVFSGPFSG9GSGAGSGZFEATGUDSGYFTGWDTG9ESGNFSGSFQAEATGHEEASGBGTGTDSGSFSGRFSGYFSGNFSGQFSGNFTGGEEASGPFSGNFSGZFEASGBGSGAGSGRFSGAGSGOFTGTDSGNFTGVDTGEEEASGAGTGTDTGWDSGTFSGVFSGSFEASGVFEASGPFTGUDTGVDSGNFTGVDTGEEEASGBGSGAGTGUDTGVDSAEASGKEEASGYFTGGESGOFSGAGSGZFEATGUDSGYFTGWDTG9ESGNFSGSFQAEATGHEEASG9GSGSFEASG9GSGNFSGBGSGYFSGSFSGPFSGNFTGVDTGEEQAEATG9ETGVDSGAGEASGPFTGDEEASGRFTGWDSGZFSGNFSGSFTGVDSGSFQAEATG9ETGVDSGAGEASGPFTGDEEASGVFSGZFSGSFSGSFTGVDSGSFTESTVALUE9DONTUSEINPRODUCTION99999YMSWGXVNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN999999999999999999999999999PYOTA9UNIT9TESTS99999999999NYBKIVD99A99999999B99999999EKHBGESJFZXE9PY9UVFIPRHGGFKDFKQOQFKQAYISJOWCXIVBSGHOZGT9DZEQPPLTYHKTWBQZOFX9BEAID999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999PYOTA9UNIT9TESTS99999999999999999999999999999999999999999999999999999999999999999'), ) self.assertEqual( response['trytes'][2], - TryteString(b'SGKETGDEEASG9GSGSFEASGZFSGAGSGTFSGSFTGVDSGSFEATGUDSGBGTGTDSGNFSGPFSGVFTGVDTGEETGUDTGHEEASGBGTGTDSGNFSGPFSGRFTGWDFAEASGZETGDESG9GQAEASGZFTGDEEASGTFSGVFSGPFSGSFSGZFEASGPFEASGZFSGVFTGTDSGSFQAEASGXFSGAGTGVDSGAGTGTDTGDESGWFEASGVFSGZFSGSFSGSFTGVDEATGUDTGVDSGSFSG9GTGDESAEASGQEEATGFETGVDSGVFEATGUDTGVDSGSFSG9GTGDEEASGRFSGAGSGYFSGTFSG9GTGDEEASGOFTGDETGVDTGEEEASGAGTGYDTGTDSGNFSG9GTGHETGGETGVDEASGYFTGGESGRFSGVFEATGUDEASGAGTGTDTGWDSGTFSGVFSGSFSGZFSAEASGSETGVDSGAGEASGOFTGWDSGRFSGSFTGVDEATGFETGVDSGAGEASGRFSGSFSGYFSGNFTGVDTGEEIBEASGKETGDEIBEASGKETGDEQAEASGYFSGSFSGWFTGVDSGSFSG9GSGNFSG9GTGVDEAFCTCXCBDQCTCFDVCIBEASGAFEASGZFSGSFSG9GTGHEEASGSFTGUDTGVDTGEEEASGOFSGAGSGYFTGEETGAESGNFTGHEEASGAGTGVDSGPFSGSFTGVDTGUDTGVDSGPFSGSFSG9GSG9GSGAGTGUDTGVDTGEEQAEATG9ESGSFSGZFEASGPFTGDEEASGZFSGAGSGTFSGSFTGVDSGSFEASGBGSGAGSG9GTGHETGVDTGEESAEASG9FTGDEEASGBGSGYFSGNFTG9ESGSFTGAETGEEEASGZESGNFSG9GTGVDTGEETGHESGQFSGAGEASGVFEASGBGTGTDSGAGSGXFSGYFTGHESG9GSGVFEASGZFSGAGTGTDTGUDSGXFSGVFTGYDEASGBGSGSFTGYDSGAGTGVDSGVFSG9GTGZDSGSFSGPFSAEASGAFEASGPFSGNFTGUDEASGSFTGUDTGVDTGEEEATGVDSGNFSGXFSGAGSGWFEATGTDSGAGTGUDSGXFSGAGTGAESGVFSAEASGAFEASGPFSGNFTGUDEASGSFTGUDTGVDTGEEEATGTDSGAGTGUDSGXFSGAGTGAETGEEQAEASG9GSGSFEASGUFSG9GSGNFTGHEQAEATG9ETGVDSGAGEATGHEEASGUFSG9GSGNFTGGEDBEATG9ETGVDSGAGEATGUDSGZFSGSFTGTDTGVDTGEEEASGZESGNFSG9GTGVDTGEETGHESGQFSGAGQAEASGPFEATGVDSGAGEASGPFTGTDSGSFSGZFTGHEEASGXFSGNFSGXFEATGVDTGTDSGNFSGQFSGVFTG9ESGSFTGUDSGXFSGVFSGWFQAEASGPFSGSFTGTDSGAGTGHETGVDSG9GSGAGQAEATGUDSGBGSGNFTGUDEASGTFSGVFSGUFSG9GTGEESAEASGQEEASGZFSGAGSGSFEATGUDTGWDTGBESGSFTGUDTGVDSGPFSGAGSGPFSGNFSG9GSGVFSGSFQAEASGPFEATGVDSGAGEASGPFTGTDSGSFSGZFTGHEEASGXFSGNFSGXFEASGQFTGTDSGAGTGVDSGSFTGUDSGXFEASGVFEASG9GSGSFSGBGSGAGSG9GTGHETGVDSG9GTGDESGZFSGVFEASGRFSGYFTGHEEASGPFSGNFTGUDQAEATGUDSGBGSGNFTGUDSGNFSGSFTGVDEASGTFSGVFSGUFSG9GSGVFEASASASAEASGKETGDEEASG9GSGSFEATGYDSGAGTGVDSGVFTGVDSGSFEASGUFSG9GSGNFTGVDTGEEEASGBGTGTDSGNFSGPFSGRFTGWDSAEASGXESGAGTGVDSGAGSGZFTGWDEATG9ETGVDSGAGEASGPFEASGQFSGYFTGWDSGOFSGVFSG9GSGSFEASGRFTGWDTGAESGVFQAEASGPFEATGVDSGSFTGYDEASGZFSGSFTGUDTGVDSGNFTGYDQAEASGPFTGDEEASG9GSGSFEASGQFSGAGSGPFSGAGTGTDSGVFTGVDSGSFEASGAGEASG9GSGNFEASGPFSGSFTG9ESGSFTGTDSGVFSG9GSGXFSGNFTGYDQAEASGPFTGDEEATGYDSGAGTGVDSGVFTGVDSGSFEASGZFSGSTESTVALUE9DONTUSEINPRODUCTION99999YMSWGXVNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN999999999999999999999999999PYOTA9UNIT9TESTS99999999999NYBKIVD99999999999B99999999WNFMWSPCSGGIFVNVMLOFYLWQXKIRFEVEHVNBSCRHJ9XLSWYSKAO9LIZSYRJAGNNLBJBZKGCVPZEWKYXAW999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999PYOTA9UNIT9TESTS99999999999999999999999999999999999999999999999999999999999999999'), + TryteString('SGKETGDEEASG9GSGSFEASGZFSGAGSGTFSGSFTGVDSGSFEATGUDSGBGTGTDSGNFSGPFSGVFTGVDTGEETGUDTGHEEASGBGTGTDSGNFSGPFSGRFTGWDFAEASGZETGDESG9GQAEASGZFTGDEEASGTFSGVFSGPFSGSFSGZFEASGPFEASGZFSGVFTGTDSGSFQAEASGXFSGAGTGVDSGAGTGTDTGDESGWFEASGVFSGZFSGSFSGSFTGVDEATGUDTGVDSGSFSG9GTGDESAEASGQEEATGFETGVDSGVFEATGUDTGVDSGSFSG9GTGDEEASGRFSGAGSGYFSGTFSG9GTGDEEASGOFTGDETGVDTGEEEASGAGTGYDTGTDSGNFSG9GTGHETGGETGVDEASGYFTGGESGRFSGVFEATGUDEASGAGTGTDTGWDSGTFSGVFSGSFSGZFSAEASGSETGVDSGAGEASGOFTGWDSGRFSGSFTGVDEATGFETGVDSGAGEASGRFSGSFSGYFSGNFTGVDTGEEIBEASGKETGDEIBEASGKETGDEQAEASGYFSGSFSGWFTGVDSGSFSG9GSGNFSG9GTGVDEAFCTCXCBDQCTCFDVCIBEASGAFEASGZFSGSFSG9GTGHEEASGSFTGUDTGVDTGEEEASGOFSGAGSGYFTGEETGAESGNFTGHEEASGAGTGVDSGPFSGSFTGVDTGUDTGVDSGPFSGSFSG9GSG9GSGAGTGUDTGVDTGEEQAEATG9ESGSFSGZFEASGPFTGDEEASGZFSGAGSGTFSGSFTGVDSGSFEASGBGSGAGSG9GTGHETGVDTGEESAEASG9FTGDEEASGBGSGYFSGNFTG9ESGSFTGAETGEEEASGZESGNFSG9GTGVDTGEETGHESGQFSGAGEASGVFEASGBGTGTDSGAGSGXFSGYFTGHESG9GSGVFEASGZFSGAGTGTDTGUDSGXFSGVFTGYDEASGBGSGSFTGYDSGAGTGVDSGVFSG9GTGZDSGSFSGPFSAEASGAFEASGPFSGNFTGUDEASGSFTGUDTGVDTGEEEATGVDSGNFSGXFSGAGSGWFEATGTDSGAGTGUDSGXFSGAGTGAESGVFSAEASGAFEASGPFSGNFTGUDEASGSFTGUDTGVDTGEEEATGTDSGAGTGUDSGXFSGAGTGAETGEEQAEASG9GSGSFEASGUFSG9GSGNFTGHEQAEATG9ETGVDSGAGEATGHEEASGUFSG9GSGNFTGGEDBEATG9ETGVDSGAGEATGUDSGZFSGSFTGTDTGVDTGEEEASGZESGNFSG9GTGVDTGEETGHESGQFSGAGQAEASGPFEATGVDSGAGEASGPFTGTDSGSFSGZFTGHEEASGXFSGNFSGXFEATGVDTGTDSGNFSGQFSGVFTG9ESGSFTGUDSGXFSGVFSGWFQAEASGPFSGSFTGTDSGAGTGHETGVDSG9GSGAGQAEATGUDSGBGSGNFTGUDEASGTFSGVFSGUFSG9GTGEESAEASGQEEASGZFSGAGSGSFEATGUDTGWDTGBESGSFTGUDTGVDSGPFSGAGSGPFSGNFSG9GSGVFSGSFQAEASGPFEATGVDSGAGEASGPFTGTDSGSFSGZFTGHEEASGXFSGNFSGXFEASGQFTGTDSGAGTGVDSGSFTGUDSGXFEASGVFEASG9GSGSFSGBGSGAGSG9GTGHETGVDSG9GTGDESGZFSGVFEASGRFSGYFTGHEEASGPFSGNFTGUDQAEATGUDSGBGSGNFTGUDSGNFSGSFTGVDEASGTFSGVFSGUFSG9GSGVFEASASASAEASGKETGDEEASG9GSGSFEATGYDSGAGTGVDSGVFTGVDSGSFEASGUFSG9GSGNFTGVDTGEEEASGBGTGTDSGNFSGPFSGRFTGWDSAEASGXESGAGTGVDSGAGSGZFTGWDEATG9ETGVDSGAGEASGPFEASGQFSGYFTGWDSGOFSGVFSG9GSGSFEASGRFTGWDTGAESGVFQAEASGPFEATGVDSGSFTGYDEASGZFSGSFTGUDTGVDSGNFTGYDQAEASGPFTGDEEASG9GSGSFEASGQFSGAGSGPFSGAGTGTDSGVFTGVDSGSFEASGAGEASG9GSGNFEASGPFSGSFTG9ESGSFTGTDSGVFSG9GSGXFSGNFTGYDQAEASGPFTGDEEATGYDSGAGTGVDSGVFTGVDSGSFEASGZFSGSTESTVALUE9DONTUSEINPRODUCTION99999YMSWGXVNDMLXPT9HMVAOWUUZMLSJZFWGKDVGXPSQAWAEBJN999999999999999999999999999GFOTA9UNIT9TESTS99999999999NYBKIVD99999999999B99999999EKHBGESJFZXE9PY9UVFIPRHGGFKDFKQOQFKQAYISJOWCXIVBSGHOZGT9DZEQPPLTYHKTWBQZOFX9BEAID999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999PYOTA9UNIT9TESTS99999999999999999999999999999999999999999999999999999999999999999'), ) diff --git a/test/commands/extended/replay_bundle_test.py b/test/commands/extended/replay_bundle_test.py index d041078..27e14a8 100644 --- a/test/commands/extended/replay_bundle_test.py +++ b/test/commands/extended/replay_bundle_test.py @@ -8,8 +8,8 @@ from filters.test import BaseFilterTestCase from six import binary_type -from iota import Address, Bundle, BundleHash, Fragment, Hash, Iota, Tag, \ - Transaction, TransactionHash, Nonce +from iota import Address, Bundle, BundleHash, Fragment, Iota, Nonce, Tag, \ + Transaction, TransactionHash from iota.adapter import MockAdapter from iota.commands.extended.replay_bundle import ReplayBundleCommand from iota.filters import Trytes diff --git a/test/crypto/signing_test.py b/test/crypto/signing_test.py index 48804dc..df7d586 100644 --- a/test/crypto/signing_test.py +++ b/test/crypto/signing_test.py @@ -2,9 +2,11 @@ from __future__ import absolute_import, division, print_function, \ unicode_literals +import warnings from unittest import TestCase from iota import Hash, TryteString +from iota.crypto import SeedWarning from iota.crypto.signing import KeyGenerator, SignatureFragmentGenerator from iota.crypto.types import PrivateKey @@ -34,144 +36,152 @@ def test_get_keys_single(self): """ Generating a single key. """ - kg = KeyGenerator( - seed = b'TESTSEED9DONTUSEINPRODUCTION99999ZTRFNBTRBSDIHWKOWCFBOQYQTENWL', - ) + with warnings.catch_warnings(record=True) as catched_warnings: - self.assertListEqual( - kg.get_keys(start=0), + # Cause all warnings to always be triggered + warnings.simplefilter("always") - # Note that the result is always a list, even when generating a - # single key. - [ - PrivateKey( - b'RYTWXBSSDDMFTHADVDRQN9HVOABBDMJDGAN9HPFAUOBZRKIWSVHJOPPETPFEF9UM9V' - b'ZETGGPMRJFPQAUWAVSHPZLGWNXLE9EKMGENDWUGRFBV9IVBAQZBVKF9GKTIAUFTSRZ' - b'NKGVITUYZDFRUXUJSVS9TRPMXJYKNBSHGUSUKVFLDHPSWNINOQLYTYYUY9W9EFDEHB' - b'CQZADZIIVSTOOQDVXKLCNHYZPUXTUUXTNAUDS9NZIVRHXNDMXNMOKHDEFGGLFMJIIT' - b'MJ9MVDMFYJ9SY9IWSVRWITSWFMQJZIBETXXSXUDNSJQIJLMNXJGUUKBAII9YLSQVQO' - b'SHZQJWPEJQTS9IJAEKPFLQYLUANQGJTWEVNXOFYHFUJCTSFT9GXVCAPHUMTTTVPXHE' - b'KORVSSMVWLALNGUSFRZYEUPJRDZ9ESSZYEHGYSYDKLLPLKUPUIGOKVBI9YJTN9MLQC' - b'HTLQYLLBXGKQM9DOIPOZEWOXJKHNASEUUCUVPCGL9HWCBQTTFIWUCMXVMEMVUKQWVU' - b'ELWBMRQQGY9DO9UISPLULEKORKJVPLHUSDRNZJCNNUZEKMUDQJNRNNQWQOBHIYMEQD' - b'LRHLNNSLRLWJEXRVUKXBLOKAXPKWVAGFUFFKCKCJAYYFNMVHLIMQABMM9O9BCANIZX' - b'YXYVSLWJOQEDKF9TGQGVGSRBZZCXTGAMROYCW9WCRDDBWSSHK9UOGASQBZVGLHLNKR' - b'EHXXS9UWCOQGSOGRYQIVX9EZQAP9KTRTOTTDCFRYHL9HGIJNRBADEGVVZGEQLKJNFN' - b'RDHIVSJARABAWPRB9DGQHROWIQZCFQJMNIDNDZRFFSABYCHRKGZNAXPNTCKAQAHXWS' - b'FHDZTSGZFOJQRSWDQOZELCYFHDVZADU9XCIPNKGAFQS9DFKYWJPQBRJK9MPXDTJOC9' - b'URFTMQXDQLOFFLQCNMTZLROECGMXUCENMYHVIBJIO9DWOKRDPVVUUBZ9DYBKEYEFYO' - b'SXAYBGJTEJKSBZJRPLZSTWG9YVVF9OWXIC9MNSDMACOVRHNSTTGARCCSDJAWSRWDKT' - b'OCDLZUAWQANXXX9RAFLIQUISYWPMDKTZWUZOKOWDHFJ9N9EMQVA9DRZGAIAJTIPBNI' - b'MTOL9JY9IIGYIXDIB9MZNTZYHJYMGAJEAOKZYYFAIVWQMQAJJJWECCJ9VZNMWNPMZA' - b'VTDWEZBZSIGGDDPTIPKEASMWBHXNKTGKHNNBURXLCOBR9CYSXZXUYVOCLRJTXDQCZB' - b'HKZ9TRWRHYZAMEHLKCAKUYXAGUUANNYTJKUEIENVYXBQLTKWYPDFCCSGQKWRYZDASY' - b'DKUMZYXEWUUROUXUHEFMWVRDNRVZJTANTDZIZUXQMBCIVAF9JCYQZEVAAQKRZY9OYL' - b'EURQGARRSDGSFEW9GIGFMJDPAY9NFXTQMXXTJUIMKKUE9BOOHUOHHENLI9DVYJJXLM' - b'UKWKNWTBODTHZFBNQOVJIXOOMBULE9IGIITWQACCWZCOPDHNLHCKACNETJJNSOHQFO' - b'99RLRZFLPGMBYZYHKSNKYSULKENZODTDKFKJEZNWK9IDIPQLYGSETEMLYFDQXDHVA9' - b'XJUUCWIDUMU9AE9HGOWDIVALKUVAZV9TBEGYPDWQKQOH9SNKLBTGEQZAJZXBJUIDA9' - b'YCBHONYIZTZWSAVXPGDDWN9PQWKXGGFUQSFUSPJIVLDDZUSZVRXMYZEBEXYFVLPZQQ' - b'YAUZOYIUWGXNJEXCQT9GDFLFDCPZBSRHZSGYUHUBGQSSQEXB9PDPRQQ9YICHOWTJRW' - b'XGCZRTXC9ERXFFHLDMMVKF9LULV9LDQPXJAHUKWZNINFHTCSYNAXFST9IFRAXPASIJ' - b'9WJWWFO9SYIQZNDMVXG9JXONUDMVGSNRQIJKVEDCGHWKEDOGED9YPQIXBUCZJRSMRM' - b'S9RJTFIYDIXAQMWNXGHHTCJLCSQNH9CNP9PJZCLIBQQBNMEY9PIJJLXPLREAHPKOZD' - b'JMPVYNUK9EMRVEJVMCQPPW9HOUHQ9YNNBXGLDLUJQEQFXTDTKHDREEIHHKIWWSPKWY' - b'QYXLGXUEFAIWSA9NSDXWPSKISBADFJHJCSCNRORALCQNMIJ9U9TNCHZOC9NARJWQPH' - b'O9HALCYZMNPCIV9VROERYT9UCNLZGKJEORFT9AMEZCXOVUIXSEPEIBMUNPPDEWIAAK' - b'GRYJANZDY' - ), - ], - ) + kg = KeyGenerator( + seed = b'TESTSEED9DONTUSEINPRODUCTION99999ZTRFNBTRBSDIHWKOWCFBOQYQTENWL', + ) - self.assertListEqual( - kg.get_keys(start=1), + # no warning must be raised, since seed has a valid length + self.assertEqual(len(catched_warnings), 0) - [ - PrivateKey( - b'PUQKFGMMWIEFMSGJI9QGVRYOCAPKTRJAOJLGGLURVTWDOWOI9ZHKHSVC9GPKNPHDTD' - b'MSMJNGNXDR9NDYDRMUM9CTOI9MCGMCRAARLPVUSJGXEYRRBUSUQLGMTDGGGWYASWTK' - b'KJHHBZ9BIYVNKGHKCTXVVJLFSWXW9WVU9NWTKO99ZZP9FOMLULMJPZZEAJBZXMW9BD' - b'IWBMZMAERMLVPW9ADZKWQLSSHCYZZQIGXDBRDEEHUBZV9FJBIOPPAAE9RMKMAQFHYW' - b'ELQPUAFTMBBXFSPOIVJL9QDYZLDTPMLZQSEJHWEBAUTWAIFAUSGHZMYPSVBDTKQKWQ' - b'UQNRIEMYMNS9AYZJGURKDWEZHVGBJIOJKHBVWXJVFUVBZKOMWIHNPKV9SWRHYNKN9T' - b'WNDYETPNXYKRMRPLDXUMGQ9GNSF9KHFXVQVIDCQRJJL9DFZHOFFNMJDO9EEAYTLHUT' - b'WHJWKKONESMCENCALGTLDZNBUWLBKMKEPXTTHLBQLTVDBXZNLFJRZM9MSGLUDYPBUD' - b'ISGNOAXXZNPEQQXFDZAKEPHJZHGDTXDBHPTQLPCLBXDZERTCNJQYLSKSVOAXUBQNWK' - b'GOIMHJIOBYPYUBANJTXBOGLSASYWMKV9JZTVNZVOZJCEOUVWXTWQPWNVIWUAB9IPGJ' - b'KREMJCAEMOZJJXQGZTAUBITQBMCARFG9NWLTWOYCWSBKTKXXJRRIFFDSKF9AMJBZIM' - b'FQXVRSSB9NXXLXORUHEKOWAQHZVFUETBTRCDQFFNGLTFKSQNOJWEXTOBWDGBMDSNLQ' - b'BORKWPMUNGIKQQNPBCFRDZKCEJUKFWAKJXKVVTJMP9NGUAYVCIHKKYOEQBONDIOIOQ' - b'AYYYGJDI9EIOIHFCBJTEUOHGASNXKVFR9QGWWQNQEWLNYLRBDLPBGSSEFGHIKLIYHR' - b'KR9YHZTMWSOSMPIJKNKYG9TRXMKIYZLTCQOEXYWDUTRXLMRWYZJVH9LPTIDYINNPZF' - b'TPCL9HRXJYQXEAXRXPN9RINJHBYJPHEFQJPDVHKJJKIAQWVNKRBD9WLVIDGKDXXGJF' - b'EIZJTYIC9HGYCZH9MQROVDVDVWFULPNSHZCUOUVABLAYGFSOVTABUUWUY9ACVPAJQC' - b'OJCXJOML9VJDSIHNVRR9RBNGCUAIVBWNGFDJWVWHJQFXMXYDWKOMFVPNBWJKIBXY9Z' - b'LYSHEMWPCDXIVOUKKTHYBHBNI9YYLNGYYDOLUAKUKFRJZA9FYCFNTFTNBCXLMMCZIJ' - b'OPJFIWYENQOHXWIAT9JODYDOEHESLGHZIMFGRKAVHZSZYLKTYSCHKQFSDTSHTOWHHQ' - b'XGFKAYYCMPYTTJFQPLEYFMLAQBPYMFPYYLR9JQPUBMJUVDYSGUXVVLSRXJJEERZVSY' - b'KDPCTOXQNMFWAXQXIGUQRDKUQD9XDTZHRZJGNQCNORSDHWSCZGFLZ9PCCUPSVQCYUT' - b'9HGXHZHPNMSBFQIDEHLMWGVJAWUXSSV9VRRIBRBOTSWUAVMWSTBVXNCAPMCQRSTMBF' - b'ZOCAYLBVSAXBTDIUYQMDDGT99YMUVTIHLGFUYJCYFJLLX9GBAGAVISAZ9QJSKNHXVX' - b'YIVKOARIA9YFDGSMPPWPJFCHAYGDRJJ9GYKYAMFS99OMOTEBOGODKUITJWFOMRQNBS' - b'9ZMCFIFJKISKKAJFPGVWWOERDSFCUEBSZPTKYMTTRAFLWYOZYJDNYIQWTBSLANDXQX' - b'QZUYCMKQINKOAXGHVMEGWLWTJPKJUPWCXRPZVDMBRDSQLTKLNIDXINWCRYYNSLDT99' - b'ORWVIFHY9DFXFXQM9LPRMFOVZJSMJAQAMRPAWNTGEA9VWBQTXJCGYZHPKWLL9VCVDQ' - b'PUIKFLGK9WKMMUWQPCJCWDK99QLUYUPJIVPMNL9QZK9QDTGFFKMMAOSEPWKOGLIVYD' - b'VKRAAGDFMEULWVCUPUV9ZOTSKORD9CTI9DFYBOJMEDOSOHNARELZNFPGXFLEPBLYQO' - b'WMRNZLVDRNBWOTRDMHEURDWGQKCXZEX9UAWBSEKOVDG9CGXOZXMPYCUWQTKLKAYGQN' - b'TPNUXAFOJTZRRPSAQ9HGOPFFVMYTEEFKOWZWVMIAYZULGWODOCOYHIJITYBDLQCTXZ' - b'TJUIGGWPUHOWVQSDDNVWNUNGUPUPYBZMSZTYXLRYSGVLVMGERUNIPZDDFHLJCDIHVI' - b'NETYGWNAY' - ), - ], - ) + self.assertListEqual( + kg.get_keys(start=0), - # You can request a key at any arbitrary index, and the result will - # always be consistent (assuming the seed doesn't change). - # Note: this can be a slow process, so we'll keep the numbers small - # so that tests don't take too long. - self.assertListEqual( - kg.get_keys(start=13), + # Note that the result is always a list, even when generating a + # single key. + [ + PrivateKey( + b'RYTWXBSSDDMFTHADVDRQN9HVOABBDMJDGAN9HPFAUOBZRKIWSVHJOPPETPFEF9UM9V' + b'ZETGGPMRJFPQAUWAVSHPZLGWNXLE9EKMGENDWUGRFBV9IVBAQZBVKF9GKTIAUFTSRZ' + b'NKGVITUYZDFRUXUJSVS9TRPMXJYKNBSHGUSUKVFLDHPSWNINOQLYTYYUY9W9EFDEHB' + b'CQZADZIIVSTOOQDVXKLCNHYZPUXTUUXTNAUDS9NZIVRHXNDMXNMOKHDEFGGLFMJIIT' + b'MJ9MVDMFYJ9SY9IWSVRWITSWFMQJZIBETXXSXUDNSJQIJLMNXJGUUKBAII9YLSQVQO' + b'SHZQJWPEJQTS9IJAEKPFLQYLUANQGJTWEVNXOFYHFUJCTSFT9GXVCAPHUMTTTVPXHE' + b'KORVSSMVWLALNGUSFRZYEUPJRDZ9ESSZYEHGYSYDKLLPLKUPUIGOKVBI9YJTN9MLQC' + b'HTLQYLLBXGKQM9DOIPOZEWOXJKHNASEUUCUVPCGL9HWCBQTTFIWUCMXVMEMVUKQWVU' + b'ELWBMRQQGY9DO9UISPLULEKORKJVPLHUSDRNZJCNNUZEKMUDQJNRNNQWQOBHIYMEQD' + b'LRHLNNSLRLWJEXRVUKXBLOKAXPKWVAGFUFFKCKCJAYYFNMVHLIMQABMM9O9BCANIZX' + b'YXYVSLWJOQEDKF9TGQGVGSRBZZCXTGAMROYCW9WCRDDBWSSHK9UOGASQBZVGLHLNKR' + b'EHXXS9UWCOQGSOGRYQIVX9EZQAP9KTRTOTTDCFRYHL9HGIJNRBADEGVVZGEQLKJNFN' + b'RDHIVSJARABAWPRB9DGQHROWIQZCFQJMNIDNDZRFFSABYCHRKGZNAXPNTCKAQAHXWS' + b'FHDZTSGZFOJQRSWDQOZELCYFHDVZADU9XCIPNKGAFQS9DFKYWJPQBRJK9MPXDTJOC9' + b'URFTMQXDQLOFFLQCNMTZLROECGMXUCENMYHVIBJIO9DWOKRDPVVUUBZ9DYBKEYEFYO' + b'SXAYBGJTEJKSBZJRPLZSTWG9YVVF9OWXIC9MNSDMACOVRHNSTTGARCCSDJAWSRWDKT' + b'OCDLZUAWQANXXX9RAFLIQUISYWPMDKTZWUZOKOWDHFJ9N9EMQVA9DRZGAIAJTIPBNI' + b'MTOL9JY9IIGYIXDIB9MZNTZYHJYMGAJEAOKZYYFAIVWQMQAJJJWECCJ9VZNMWNPMZA' + b'VTDWEZBZSIGGDDPTIPKEASMWBHXNKTGKHNNBURXLCOBR9CYSXZXUYVOCLRJTXDQCZB' + b'HKZ9TRWRHYZAMEHLKCAKUYXAGUUANNYTJKUEIENVYXBQLTKWYPDFCCSGQKWRYZDASY' + b'DKUMZYXEWUUROUXUHEFMWVRDNRVZJTANTDZIZUXQMBCIVAF9JCYQZEVAAQKRZY9OYL' + b'EURQGARRSDGSFEW9GIGFMJDPAY9NFXTQMXXTJUIMKKUE9BOOHUOHHENLI9DVYJJXLM' + b'UKWKNWTBODTHZFBNQOVJIXOOMBULE9IGIITWQACCWZCOPDHNLHCKACNETJJNSOHQFO' + b'99RLRZFLPGMBYZYHKSNKYSULKENZODTDKFKJEZNWK9IDIPQLYGSETEMLYFDQXDHVA9' + b'XJUUCWIDUMU9AE9HGOWDIVALKUVAZV9TBEGYPDWQKQOH9SNKLBTGEQZAJZXBJUIDA9' + b'YCBHONYIZTZWSAVXPGDDWN9PQWKXGGFUQSFUSPJIVLDDZUSZVRXMYZEBEXYFVLPZQQ' + b'YAUZOYIUWGXNJEXCQT9GDFLFDCPZBSRHZSGYUHUBGQSSQEXB9PDPRQQ9YICHOWTJRW' + b'XGCZRTXC9ERXFFHLDMMVKF9LULV9LDQPXJAHUKWZNINFHTCSYNAXFST9IFRAXPASIJ' + b'9WJWWFO9SYIQZNDMVXG9JXONUDMVGSNRQIJKVEDCGHWKEDOGED9YPQIXBUCZJRSMRM' + b'S9RJTFIYDIXAQMWNXGHHTCJLCSQNH9CNP9PJZCLIBQQBNMEY9PIJJLXPLREAHPKOZD' + b'JMPVYNUK9EMRVEJVMCQPPW9HOUHQ9YNNBXGLDLUJQEQFXTDTKHDREEIHHKIWWSPKWY' + b'QYXLGXUEFAIWSA9NSDXWPSKISBADFJHJCSCNRORALCQNMIJ9U9TNCHZOC9NARJWQPH' + b'O9HALCYZMNPCIV9VROERYT9UCNLZGKJEORFT9AMEZCXOVUIXSEPEIBMUNPPDEWIAAK' + b'GRYJANZDY' + ), + ], + ) - [ - PrivateKey( - b'TIUQQXOOYTKCESSBBGKKVJQPSJNVTAGCTAJVRJNXJUIHXWXQHSTACBRP9BJCSQD9CA' - b'FNQNNFVEPMYFCPYKXRCNWZHYKYCRSFTAZTPGQXBIMGAZEXABLUJQKEQMKAOUXYNICZ' - b'YWDIBLZVJYGUPET9BAV9PTM9TJLHTWLXV9NXMNDNDYHTLIVGZJSEHIBWOYIXABKP9O' - b'APPGWTUNLKYDFNWSFDTGRDPTMABYOPCTZM9LQIESPNNVZVYGGCJOHC9NSXMX9ETPGH' - b'NQACONLQJIHRNAKUYMLSGTEJUO9MZGEQZPQBTQXKWJDJLFSRBPERWKVHUZXANWMOKW' - b'QPPGVFZRVUEOWDMZM9IOZUCOYTQIRZXWDYWAHGOATEW9AMZNSTZRZCQYS9MYREAFMT' - b'BIQFUUZKBSWFSNZO9HDBVMNTXX9EAAVTIZSARDP9ZKCUBIRPPGWWXV9PDXLCSDKLWA' - b'NVLTXPTEBUAHJJL9LESHCQQWZIYMRNCVYMDQUQFWNAGTCOQBNCLHZMJRNYWIZXDLFF' - b'JVA9OTEVHOQZKUDHXLHLZLH9YZR9WBCMFOVRUCDBNVHRGMAYLIEKNDCSWMT9HXU9SD' - b'LMLKOBEISWYQCSXYINQNNHSOGTZTZNUXNVHBBOUCFIKIICILJADHTDBJNTPORFBQGC' - b'LJKOMVRRBBXZJLRVKBLELUDBQGFHOHRAXTHVUSJMZBO9KKXZZNNKJEN9GNYVBDFZDU' - b'QNYTENTFYUSOGJOOJJFGAADFKNKMVWKUWCCTACYZZEYTIKBJP9SCUGTRYLYCBXCIQP' - b'LQFKARVWU9VKUGUZYXZXCNSXGNZBXIZDDCSMTOHOCCI9GGXMNAYLVMITJXEN9MKUAP' - b'NUBBSZCXNWN9DKMHROJQPNWEGHDPKPVNZLFMHXDUOTBVBGDLWGSODW9ACJJIJW9NXD' - b'YOGFIPHPET9AJZXNKYWXKGRSINIODDS9IAT9LAEQWUODEBW9MQIDKZPIINGKUXZGKG' - b'NXTPDMUOKEKKM9TQQJCGMOGXITJAVODWPFCJX9UEDVABYLUIUUUCAXUFWZCYWGWL9Z' - b'FZP9YSD9RJCMZJQZEQJLAZNJPSPOPJCEPOJTFZOBTWWLHFAALRHISBVFUYAHNBMT9I' - b'TDDFKREXTZUXHCOL9VDDVQAXKBKZSLVEREOOSPPZHIWH9AQHVNZEXVCWPQLVUGPVBZ' - b'GIRYUMQXPJBGP9AUFCHZHTENRJAKJHLKORDSYZYISTFUPAZNIWUJUGEDFSI9XMZRLB' - b'HCZSGOVXINMDJZYSPHBOVTTDCYONQKZ9UJHNJDWR9YT9MJNSFFUQDCLPOXFV9RDQSA' - b'TGCCWAAZVVJSCZLZTPJXBFBUDLIBABLKLZFZUHGARDDFX9OZDXBZNSFEWYXNSLCMHF' - b'ROWWJHK9IRLEZZEVFWJ9KCEWGVHXTSXWMJSWPH99BU9GVXOIHTFTOGFMGZVCYCPDHZ' - b'OUUB9DEPJLJCFFKEGMBYLLSXEDGWNPMWCSQOAMDITYDHDPTDQRKMKPAJIRLMSAN9OW' - b'DOYZQHJJSVVOSYIYCMYVXEAOOFNNRWKJWNYDEZOLZ9MMMSUIPWIYKWZVEFKSTARVVO' - b'UONUBAXJEFKJRNLDBQTRYAWK9NZYFRBCYVPZOACJPZRSAFYQPA9KJGZMAKKPAAUYC9' - b'NQGEPWKUVCHPSUNQDDMOIMKCLLBSACBXDVXUDWYOUCVOVZCNNRAURQFUPQGNB9CAXS' - b'CPXPFPJENYWFBOJFFWZAUUTYRRQQMRBWUQOMJYPMONU9EYWJSGQQZHHZSHF9XQPIAD' - b'AUHDKOIWJJGRLIPZQJ9LKPJRBHRTKUBWQHAOKZKT9GPDTSRXDRESZXMCMRNGUJOJPC' - b'CSFMMPITLHU9FEBFMYLCBPCFEFXAZXYZRZFZ9KIQINS9GSN9BZLMMODAPNORGPMYNT' - b'XXASTKLVIGMUGJWRSLMLIDQYHXNTBDZR9EQDBDUZVSIALOEHBBUS9QILWCBIYYUSHZ' - b'RNICAYREZANRQWGGBJZCMSB9TRXXCUSPIIEJLKLEOMVCYHRNI9KEHPXAIUQIFUNSVK' - b'JMEUMLBXSIHQUFK9QLA9UTBJZQGAQHWXVHWXYSEPCDO9M99HYRPAXFXHQENZHNBWXD' - b'VN9KOMUINNCIMWKWI9QITAORLVJL9HRYSDNIQNAAQOQPSQNCQCGYAPIYSNOPHECZJY' - b'VTVVMKOUZ' - ), - ], - ) + self.assertListEqual( + kg.get_keys(start=1), + + [ + PrivateKey( + b'PUQKFGMMWIEFMSGJI9QGVRYOCAPKTRJAOJLGGLURVTWDOWOI9ZHKHSVC9GPKNPHDTD' + b'MSMJNGNXDR9NDYDRMUM9CTOI9MCGMCRAARLPVUSJGXEYRRBUSUQLGMTDGGGWYASWTK' + b'KJHHBZ9BIYVNKGHKCTXVVJLFSWXW9WVU9NWTKO99ZZP9FOMLULMJPZZEAJBZXMW9BD' + b'IWBMZMAERMLVPW9ADZKWQLSSHCYZZQIGXDBRDEEHUBZV9FJBIOPPAAE9RMKMAQFHYW' + b'ELQPUAFTMBBXFSPOIVJL9QDYZLDTPMLZQSEJHWEBAUTWAIFAUSGHZMYPSVBDTKQKWQ' + b'UQNRIEMYMNS9AYZJGURKDWEZHVGBJIOJKHBVWXJVFUVBZKOMWIHNPKV9SWRHYNKN9T' + b'WNDYETPNXYKRMRPLDXUMGQ9GNSF9KHFXVQVIDCQRJJL9DFZHOFFNMJDO9EEAYTLHUT' + b'WHJWKKONESMCENCALGTLDZNBUWLBKMKEPXTTHLBQLTVDBXZNLFJRZM9MSGLUDYPBUD' + b'ISGNOAXXZNPEQQXFDZAKEPHJZHGDTXDBHPTQLPCLBXDZERTCNJQYLSKSVOAXUBQNWK' + b'GOIMHJIOBYPYUBANJTXBOGLSASYWMKV9JZTVNZVOZJCEOUVWXTWQPWNVIWUAB9IPGJ' + b'KREMJCAEMOZJJXQGZTAUBITQBMCARFG9NWLTWOYCWSBKTKXXJRRIFFDSKF9AMJBZIM' + b'FQXVRSSB9NXXLXORUHEKOWAQHZVFUETBTRCDQFFNGLTFKSQNOJWEXTOBWDGBMDSNLQ' + b'BORKWPMUNGIKQQNPBCFRDZKCEJUKFWAKJXKVVTJMP9NGUAYVCIHKKYOEQBONDIOIOQ' + b'AYYYGJDI9EIOIHFCBJTEUOHGASNXKVFR9QGWWQNQEWLNYLRBDLPBGSSEFGHIKLIYHR' + b'KR9YHZTMWSOSMPIJKNKYG9TRXMKIYZLTCQOEXYWDUTRXLMRWYZJVH9LPTIDYINNPZF' + b'TPCL9HRXJYQXEAXRXPN9RINJHBYJPHEFQJPDVHKJJKIAQWVNKRBD9WLVIDGKDXXGJF' + b'EIZJTYIC9HGYCZH9MQROVDVDVWFULPNSHZCUOUVABLAYGFSOVTABUUWUY9ACVPAJQC' + b'OJCXJOML9VJDSIHNVRR9RBNGCUAIVBWNGFDJWVWHJQFXMXYDWKOMFVPNBWJKIBXY9Z' + b'LYSHEMWPCDXIVOUKKTHYBHBNI9YYLNGYYDOLUAKUKFRJZA9FYCFNTFTNBCXLMMCZIJ' + b'OPJFIWYENQOHXWIAT9JODYDOEHESLGHZIMFGRKAVHZSZYLKTYSCHKQFSDTSHTOWHHQ' + b'XGFKAYYCMPYTTJFQPLEYFMLAQBPYMFPYYLR9JQPUBMJUVDYSGUXVVLSRXJJEERZVSY' + b'KDPCTOXQNMFWAXQXIGUQRDKUQD9XDTZHRZJGNQCNORSDHWSCZGFLZ9PCCUPSVQCYUT' + b'9HGXHZHPNMSBFQIDEHLMWGVJAWUXSSV9VRRIBRBOTSWUAVMWSTBVXNCAPMCQRSTMBF' + b'ZOCAYLBVSAXBTDIUYQMDDGT99YMUVTIHLGFUYJCYFJLLX9GBAGAVISAZ9QJSKNHXVX' + b'YIVKOARIA9YFDGSMPPWPJFCHAYGDRJJ9GYKYAMFS99OMOTEBOGODKUITJWFOMRQNBS' + b'9ZMCFIFJKISKKAJFPGVWWOERDSFCUEBSZPTKYMTTRAFLWYOZYJDNYIQWTBSLANDXQX' + b'QZUYCMKQINKOAXGHVMEGWLWTJPKJUPWCXRPZVDMBRDSQLTKLNIDXINWCRYYNSLDT99' + b'ORWVIFHY9DFXFXQM9LPRMFOVZJSMJAQAMRPAWNTGEA9VWBQTXJCGYZHPKWLL9VCVDQ' + b'PUIKFLGK9WKMMUWQPCJCWDK99QLUYUPJIVPMNL9QZK9QDTGFFKMMAOSEPWKOGLIVYD' + b'VKRAAGDFMEULWVCUPUV9ZOTSKORD9CTI9DFYBOJMEDOSOHNARELZNFPGXFLEPBLYQO' + b'WMRNZLVDRNBWOTRDMHEURDWGQKCXZEX9UAWBSEKOVDG9CGXOZXMPYCUWQTKLKAYGQN' + b'TPNUXAFOJTZRRPSAQ9HGOPFFVMYTEEFKOWZWVMIAYZULGWODOCOYHIJITYBDLQCTXZ' + b'TJUIGGWPUHOWVQSDDNVWNUNGUPUPYBZMSZTYXLRYSGVLVMGERUNIPZDDFHLJCDIHVI' + b'NETYGWNAY' + ), + ], + ) + + # You can request a key at any arbitrary index, and the result will + # always be consistent (assuming the seed doesn't change). + # Note: this can be a slow process, so we'll keep the numbers small + # so that tests don't take too long. + self.assertListEqual( + kg.get_keys(start=13), + + [ + PrivateKey( + b'TIUQQXOOYTKCESSBBGKKVJQPSJNVTAGCTAJVRJNXJUIHXWXQHSTACBRP9BJCSQD9CA' + b'FNQNNFVEPMYFCPYKXRCNWZHYKYCRSFTAZTPGQXBIMGAZEXABLUJQKEQMKAOUXYNICZ' + b'YWDIBLZVJYGUPET9BAV9PTM9TJLHTWLXV9NXMNDNDYHTLIVGZJSEHIBWOYIXABKP9O' + b'APPGWTUNLKYDFNWSFDTGRDPTMABYOPCTZM9LQIESPNNVZVYGGCJOHC9NSXMX9ETPGH' + b'NQACONLQJIHRNAKUYMLSGTEJUO9MZGEQZPQBTQXKWJDJLFSRBPERWKVHUZXANWMOKW' + b'QPPGVFZRVUEOWDMZM9IOZUCOYTQIRZXWDYWAHGOATEW9AMZNSTZRZCQYS9MYREAFMT' + b'BIQFUUZKBSWFSNZO9HDBVMNTXX9EAAVTIZSARDP9ZKCUBIRPPGWWXV9PDXLCSDKLWA' + b'NVLTXPTEBUAHJJL9LESHCQQWZIYMRNCVYMDQUQFWNAGTCOQBNCLHZMJRNYWIZXDLFF' + b'JVA9OTEVHOQZKUDHXLHLZLH9YZR9WBCMFOVRUCDBNVHRGMAYLIEKNDCSWMT9HXU9SD' + b'LMLKOBEISWYQCSXYINQNNHSOGTZTZNUXNVHBBOUCFIKIICILJADHTDBJNTPORFBQGC' + b'LJKOMVRRBBXZJLRVKBLELUDBQGFHOHRAXTHVUSJMZBO9KKXZZNNKJEN9GNYVBDFZDU' + b'QNYTENTFYUSOGJOOJJFGAADFKNKMVWKUWCCTACYZZEYTIKBJP9SCUGTRYLYCBXCIQP' + b'LQFKARVWU9VKUGUZYXZXCNSXGNZBXIZDDCSMTOHOCCI9GGXMNAYLVMITJXEN9MKUAP' + b'NUBBSZCXNWN9DKMHROJQPNWEGHDPKPVNZLFMHXDUOTBVBGDLWGSODW9ACJJIJW9NXD' + b'YOGFIPHPET9AJZXNKYWXKGRSINIODDS9IAT9LAEQWUODEBW9MQIDKZPIINGKUXZGKG' + b'NXTPDMUOKEKKM9TQQJCGMOGXITJAVODWPFCJX9UEDVABYLUIUUUCAXUFWZCYWGWL9Z' + b'FZP9YSD9RJCMZJQZEQJLAZNJPSPOPJCEPOJTFZOBTWWLHFAALRHISBVFUYAHNBMT9I' + b'TDDFKREXTZUXHCOL9VDDVQAXKBKZSLVEREOOSPPZHIWH9AQHVNZEXVCWPQLVUGPVBZ' + b'GIRYUMQXPJBGP9AUFCHZHTENRJAKJHLKORDSYZYISTFUPAZNIWUJUGEDFSI9XMZRLB' + b'HCZSGOVXINMDJZYSPHBOVTTDCYONQKZ9UJHNJDWR9YT9MJNSFFUQDCLPOXFV9RDQSA' + b'TGCCWAAZVVJSCZLZTPJXBFBUDLIBABLKLZFZUHGARDDFX9OZDXBZNSFEWYXNSLCMHF' + b'ROWWJHK9IRLEZZEVFWJ9KCEWGVHXTSXWMJSWPH99BU9GVXOIHTFTOGFMGZVCYCPDHZ' + b'OUUB9DEPJLJCFFKEGMBYLLSXEDGWNPMWCSQOAMDITYDHDPTDQRKMKPAJIRLMSAN9OW' + b'DOYZQHJJSVVOSYIYCMYVXEAOOFNNRWKJWNYDEZOLZ9MMMSUIPWIYKWZVEFKSTARVVO' + b'UONUBAXJEFKJRNLDBQTRYAWK9NZYFRBCYVPZOACJPZRSAFYQPA9KJGZMAKKPAAUYC9' + b'NQGEPWKUVCHPSUNQDDMOIMKCLLBSACBXDVXUDWYOUCVOVZCNNRAURQFUPQGNB9CAXS' + b'CPXPFPJENYWFBOJFFWZAUUTYRRQQMRBWUQOMJYPMONU9EYWJSGQQZHHZSHF9XQPIAD' + b'AUHDKOIWJJGRLIPZQJ9LKPJRBHRTKUBWQHAOKZKT9GPDTSRXDRESZXMCMRNGUJOJPC' + b'CSFMMPITLHU9FEBFMYLCBPCFEFXAZXYZRZFZ9KIQINS9GSN9BZLMMODAPNORGPMYNT' + b'XXASTKLVIGMUGJWRSLMLIDQYHXNTBDZR9EQDBDUZVSIALOEHBBUS9QILWCBIYYUSHZ' + b'RNICAYREZANRQWGGBJZCMSB9TRXXCUSPIIEJLKLEOMVCYHRNI9KEHPXAIUQIFUNSVK' + b'JMEUMLBXSIHQUFK9QLA9UTBJZQGAQHWXVHWXYSEPCDO9M99HYRPAXFXHQENZHNBWXD' + b'VN9KOMUINNCIMWKWI9QITAORLVJL9HRYSDNIQNAAQOQPSQNCQCGYAPIYSNOPHECZJY' + b'VTVVMKOUZ' + ), + ], + ) def test_get_keys_long_seed(self): """ @@ -186,56 +196,66 @@ def test_get_keys_long_seed(self): References: - https://forum.iota.org/t/why-arent-seeds-longer-than-81-trytes-more-secure/1278/4 """ - kg = KeyGenerator( - b'TESTSEED9DONTUSEINPRODUCTION99999ZTRFNBTRBSDIHWKOWCFBOQYQTENWLTG9S' - b'IGVTKTOFGZAIMWHNQWWENEFBAYZXBYWK9QBIWKTMO9MFZIEQVJULQILER9GRDCBLEY' - b'OPLCYJALVJESQMIEZOVOPYYAOLJMIUCGAJLIUFKHTIHZSEOYYLTPHKSURQSWPQEESV' - b'99QM9DUSKSMLSCCDYMDAJIAPGJIHWBROISBLAA9GZFGPPRPHSTVNJMPUWGLTZEZEGQ' - b'HIHMCRZILISRFGVOJMXOYRALR9ZOUAMQXGW9XPFID', - ) + with warnings.catch_warnings(record=True) as catched_warnings: - self.assertListEqual( - kg.get_keys(start=0), + # Cause seed related warnings to be triggered + warnings.simplefilter("always", category=SeedWarning) - [ - PrivateKey( - b'BXBGJNNW9NXZYRHFVVXVVSRD9ECGQSXNWPLBDLMDYXWJJLVELFZZESFJYH9FCSTINR' - b'CCJODSWMHFWVGB9HYNHATWHWOJKNVWEVXGZBSXSYVKMEDEZVCME9MQOCFFGVWCZHDT' - b'9DTPOZYBEQQWCDVMJQC9BCTBJWIGW9B9PUHCBWOHN9OHYRMSBFCAPGOEC9GYIMRPNC' - b'VCZYZLEFFJBGEERRKQHVNFMPPSWZAAXOVJXEEIZI9DNNDDONRNSHUUCNYWIIXIRWLR' - b'AV9CYCNHCKSVWS9ERXCUQZLUAWEAU9IUGEQUCXDRTVWGPDRSOCSFKRZSSTKXXYWBBU' - b'JMGIIQUWKXGHJBEUONHMESPAHCUGRDPDDRPQJYWPIFVYNNTXZAWBWQPOOOLAIVI9HY' - b'UYIGXCUXDWTCL9YXUDXCEJRVBVXTMAFXHBXRKFXBYHMPZPKSVUKNSJXSCPTXTYITAT' - b'CLUWNTGMBTMCCBOCINJSXSYDLJAXCUWQKGLXVQWNIXKHN9KZOHFLFURSHOXSTJCUUH' - b'IOBEYWMWMNMFHEGKEINGIJFJOHAZAYQPIULXGNYZMTLJVUPWW9MAAWCUF9QAYATOPZ' - b'MMKZRSVBWRSAWAOYRF9BVSWMNKAFEUHOTLFARLV9NDGLCXUIQUCQSXFHCAS9EWBYNO' - b'VJ9HEKOACWDDQMPPIOE9UDLIGZJTBLWLWOMPAOCFDFJPKVGVEHEUKXFULTKRGMGKMZ' - b'T9AFWJ9VDFJIBSODRRBFFXIMONSSCLPKD9JZFSCDBBQIMBUYMMVCZVRCZJBSCIBJMY' - b'VNC99VUAWYBXDTPVBXJRZVOQQJFKHCGLTZPYSWMNBQUYHOXZXSYPMWBS9HCLPQGRVS' - b'9TNGKSGRWHEM99YA9BYUBJKJFGSN9XKQXHOJHKEIVSGYCEYARXUVJKVYHRJHMGDNVS' - b'NAXQDXYTYAME9BXJFZ9HEPVSYMSDAPIBJKPJFOAO9XQYWNFCFAMNOMOPIAHWOFSSFT' - b'VQVETQUHLCNAKGXICWCNBHMMJARWUXBLWFOLDRDYDOZAMDKMMXLGNSLNKHHMVKZTQO' - b'TJSZWAP9LUWVHGPUKWNUJANUZQGLMKDUCVSSBQMZCGZURESHMUWUEEPHSVRETSDCOW' - b'VNKMRPUTLRQCRHKCZBDDFQBELWMVCMIUELCJMKTKHMXSKSQNCAQOIJLSGWVOLWQCLG' - b'QBQKKMHRNJKJNWZMCNDNXAFXWDBSIDOMSJFUTQKAEZJNWYXPZDVXQQFDYPJXWCPCMW' - b'TWBQVSXCXTUFKWQKTFEATWSDFI9ETMWQOC9PY9VOMWDFBCLBRDTDSX9ICUQDEVCFLA' - b'UDNFCFJCWIGNGLAILHKFBG9NK9YXCIBZQGODDGZZRCMVIR9EXOYCCODKWASLVLBDQY' - b'VQYRBNGVSOPKZEGLWHTPAGPQQHGHVCTVDVBAWLDHUPZISMSDVJOAEUGOHUOOMBQEB9' - b'TSRMSWIAIGGYOFQAVHOKMAIDGFHZHQNBDILMKIFQPIWZRMKVOVSYDXTMIFMHGCZJZQ' - b'9CCYINX9DDGZHYMXXFEZXDTLOEOSNVULRD9VNBLTGDAMQSQKOGDLLDYDNFEVMMWYXZ' - b'IRJP9LMNAOEBZ9FXKLACMUPSIABFBDNCJTVCCDZGFQU9OKDUEDPCPCTHKAUZ9ZZXSG' - b'XHLYMFOVZXVHXFVJNMRBJJTSJPPBLZWMSOWYTLXXXYEVBVQJHRCLROVNPSVFLPRIIG' - b'GDGSPIHOEYNQELOYHXDRHXOWOMP9OPYCL9QUUOYBQQMDULTMZMOHZAELOUDVBVRGLD' - b'IN9DVYJPKYWILMWAYCLOPCXVBPPIQDILYPRFJZLFFTWFAESFTPBRRLJPATSIWKXJFO' - b'HV9BMDLLBRLCBABP9UZPFADGUKWBJZMHUN9URWOALIZIOLFTVNTNTHBHYMWJUU9MOB' - b'9NAKVBME9TAKCTLCSOEOBLRQLWHUEBTGJKYXBRLOCUKEVLGWSGNPHAYYHDPISOMDOL' - b'ALS9VODLNXXOBBCNDNHSBEVNRMLD9JPYUVOZVMORYRQJWXYBWSIQDYXOSAZABKYINW' - b'ZZJTONDTMMUQ9OLCUKBVCJDRPFVGIBJKAWEUVSBTIJWEVQP9LIHLKGHJYLBYOMIDKS' - b'BETUZYEFU9SNPHQDWUXKX9VRTTMWHZUFQMBRWQDVFZXVGBFEJRQVTFFTQBTIGVHBDZ' - b'9JPZYQEPW' - ), - ], - ) + kg = KeyGenerator( + b'TESTSEED9DONTUSEINPRODUCTION99999ZTRFNBTRBSDIHWKOWCFBOQYQTENWLTG9S' + b'IGVTKTOFGZAIMWHNQWWENEFBAYZXBYWK9QBIWKTMO9MFZIEQVJULQILER9GRDCBLEY' + b'OPLCYJALVJESQMIEZOVOPYYAOLJMIUCGAJLIUFKHTIHZSEOYYLTPHKSURQSWPQEESV' + b'99QM9DUSKSMLSCCDYMDAJIAPGJIHWBROISBLAA9GZFGPPRPHSTVNJMPUWGLTZEZEGQ' + b'HIHMCRZILISRFGVOJMXOYRALR9ZOUAMQXGW9XPFID', + ) + + # check attributes of warning + self.assertEqual(len(catched_warnings), 1) + self.assertIs(catched_warnings[-1].category, SeedWarning) + self.assertIn("inappropriate length", str(catched_warnings[-1].message)) + + self.assertListEqual( + kg.get_keys(start=0), + + [ + PrivateKey( + b'BXBGJNNW9NXZYRHFVVXVVSRD9ECGQSXNWPLBDLMDYXWJJLVELFZZESFJYH9FCSTINR' + b'CCJODSWMHFWVGB9HYNHATWHWOJKNVWEVXGZBSXSYVKMEDEZVCME9MQOCFFGVWCZHDT' + b'9DTPOZYBEQQWCDVMJQC9BCTBJWIGW9B9PUHCBWOHN9OHYRMSBFCAPGOEC9GYIMRPNC' + b'VCZYZLEFFJBGEERRKQHVNFMPPSWZAAXOVJXEEIZI9DNNDDONRNSHUUCNYWIIXIRWLR' + b'AV9CYCNHCKSVWS9ERXCUQZLUAWEAU9IUGEQUCXDRTVWGPDRSOCSFKRZSSTKXXYWBBU' + b'JMGIIQUWKXGHJBEUONHMESPAHCUGRDPDDRPQJYWPIFVYNNTXZAWBWQPOOOLAIVI9HY' + b'UYIGXCUXDWTCL9YXUDXCEJRVBVXTMAFXHBXRKFXBYHMPZPKSVUKNSJXSCPTXTYITAT' + b'CLUWNTGMBTMCCBOCINJSXSYDLJAXCUWQKGLXVQWNIXKHN9KZOHFLFURSHOXSTJCUUH' + b'IOBEYWMWMNMFHEGKEINGIJFJOHAZAYQPIULXGNYZMTLJVUPWW9MAAWCUF9QAYATOPZ' + b'MMKZRSVBWRSAWAOYRF9BVSWMNKAFEUHOTLFARLV9NDGLCXUIQUCQSXFHCAS9EWBYNO' + b'VJ9HEKOACWDDQMPPIOE9UDLIGZJTBLWLWOMPAOCFDFJPKVGVEHEUKXFULTKRGMGKMZ' + b'T9AFWJ9VDFJIBSODRRBFFXIMONSSCLPKD9JZFSCDBBQIMBUYMMVCZVRCZJBSCIBJMY' + b'VNC99VUAWYBXDTPVBXJRZVOQQJFKHCGLTZPYSWMNBQUYHOXZXSYPMWBS9HCLPQGRVS' + b'9TNGKSGRWHEM99YA9BYUBJKJFGSN9XKQXHOJHKEIVSGYCEYARXUVJKVYHRJHMGDNVS' + b'NAXQDXYTYAME9BXJFZ9HEPVSYMSDAPIBJKPJFOAO9XQYWNFCFAMNOMOPIAHWOFSSFT' + b'VQVETQUHLCNAKGXICWCNBHMMJARWUXBLWFOLDRDYDOZAMDKMMXLGNSLNKHHMVKZTQO' + b'TJSZWAP9LUWVHGPUKWNUJANUZQGLMKDUCVSSBQMZCGZURESHMUWUEEPHSVRETSDCOW' + b'VNKMRPUTLRQCRHKCZBDDFQBELWMVCMIUELCJMKTKHMXSKSQNCAQOIJLSGWVOLWQCLG' + b'QBQKKMHRNJKJNWZMCNDNXAFXWDBSIDOMSJFUTQKAEZJNWYXPZDVXQQFDYPJXWCPCMW' + b'TWBQVSXCXTUFKWQKTFEATWSDFI9ETMWQOC9PY9VOMWDFBCLBRDTDSX9ICUQDEVCFLA' + b'UDNFCFJCWIGNGLAILHKFBG9NK9YXCIBZQGODDGZZRCMVIR9EXOYCCODKWASLVLBDQY' + b'VQYRBNGVSOPKZEGLWHTPAGPQQHGHVCTVDVBAWLDHUPZISMSDVJOAEUGOHUOOMBQEB9' + b'TSRMSWIAIGGYOFQAVHOKMAIDGFHZHQNBDILMKIFQPIWZRMKVOVSYDXTMIFMHGCZJZQ' + b'9CCYINX9DDGZHYMXXFEZXDTLOEOSNVULRD9VNBLTGDAMQSQKOGDLLDYDNFEVMMWYXZ' + b'IRJP9LMNAOEBZ9FXKLACMUPSIABFBDNCJTVCCDZGFQU9OKDUEDPCPCTHKAUZ9ZZXSG' + b'XHLYMFOVZXVHXFVJNMRBJJTSJPPBLZWMSOWYTLXXXYEVBVQJHRCLROVNPSVFLPRIIG' + b'GDGSPIHOEYNQELOYHXDRHXOWOMP9OPYCL9QUUOYBQQMDULTMZMOHZAELOUDVBVRGLD' + b'IN9DVYJPKYWILMWAYCLOPCXVBPPIQDILYPRFJZLFFTWFAESFTPBRRLJPATSIWKXJFO' + b'HV9BMDLLBRLCBABP9UZPFADGUKWBJZMHUN9URWOALIZIOLFTVNTNTHBHYMWJUU9MOB' + b'9NAKVBME9TAKCTLCSOEOBLRQLWHUEBTGJKYXBRLOCUKEVLGWSGNPHAYYHDPISOMDOL' + b'ALS9VODLNXXOBBCNDNHSBEVNRMLD9JPYUVOZVMORYRQJWXYBWSIQDYXOSAZABKYINW' + b'ZZJTONDTMMUQ9OLCUKBVCJDRPFVGIBJKAWEUVSBTIJWEVQP9LIHLKGHJYLBYOMIDKS' + b'BETUZYEFU9SNPHQDWUXKX9VRTTMWHZUFQMBRWQDVFZXVGBFEJRQVTFFTQBTIGVHBDZ' + b'9JPZYQEPW' + ), + ], + ) def test_get_keys_multiple(self): """ diff --git a/test/crypto/types_test.py b/test/crypto/types_test.py index 7291344..79358d8 100644 --- a/test/crypto/types_test.py +++ b/test/crypto/types_test.py @@ -2,9 +2,13 @@ from __future__ import absolute_import, division, print_function, \ unicode_literals +import warnings from unittest import TestCase +from six import text_type + from iota import Hash, TryteString +from iota.crypto import SeedWarning from iota.crypto.types import Digest, PrivateKey, Seed @@ -13,7 +17,15 @@ def test_random(self): """ Generating a random seed. """ - seed = Seed.random() + + with warnings.catch_warnings(record=True) as catched_warnings: + + # all warnings should be triggered + warnings.simplefilter("always") + + seed = Seed.random() + + self.assertEqual(len(catched_warnings), 0) # Regression test: ``random`` MUST return a :py:class:`Seed`, NOT a # :py:class:`TryteString`! @@ -23,6 +35,28 @@ def test_random(self): # https://github.com/iotaledger/iota.lib.py/issues/44 self.assertEqual(len(seed), Hash.LEN) + def test_random_seed_too_long(self): + """ + Generating a random seed, which is too long. + """ + + with warnings.catch_warnings(record=True) as catched_warnings: + + # Cause seed related warnings to be triggered + warnings.simplefilter("always", category=SeedWarning) + + seed = Seed.random(length=Hash.LEN + 1) + + # check attributes of warning + self.assertEqual(len(catched_warnings), 1) + self.assertIs(catched_warnings[-1].category, SeedWarning) + self.assertIn( + "inappropriate length", + text_type(catched_warnings[-1].message), + ) + + self.assertEqual(len(seed), Hash.LEN + 1) + class DigestTestCase(TestCase): def test_init_error_too_long(self): diff --git a/test/transaction/creation_test.py b/test/transaction/creation_test.py index 4df328d..b0926af 100644 --- a/test/transaction/creation_test.py +++ b/test/transaction/creation_test.py @@ -8,6 +8,7 @@ TryteString from iota.crypto.signing import KeyGenerator from iota.crypto.types import Seed +from iota.transaction.types import BundleHash class ProposedBundleTestCase(TestCase): @@ -489,6 +490,51 @@ def test_finalize_error_positive_balance(self): with self.assertRaises(ValueError): self.bundle.finalize() + def test_finalize_insecure_bundle(self): + """ + When finalizing, the bundle detects an insecure bundle hash. + + References: + - https://github.com/iotaledger/iota.lib.py/issues/84 + """ + # noinspection SpellCheckingInspection + bundle =\ + ProposedBundle([ + ProposedTransaction( + address =\ + Address( + '9XV9RJGFJJZWITDPKSQXRTHCKJAIZZY9BYLBEQUX' + 'UNCLITRQDR9CCD99AANMXYEKD9GLJGVB9HIAGRIBQ', + ), + + tag = Tag('PPDIDNQDJZGUQKOWJ9JZRCKOVGP'), + timestamp = 1509136296, + value = 0, + ), + ]) + + bundle.finalize() + + # The resulting bundle hash is insecure (contains a [1, 1, 1]), so + # the legacy tag is manipulated until a secure hash is generated. + # noinspection SpellCheckingInspection + self.assertEqual(bundle[0].legacy_tag, Tag('ZTDIDNQDJZGUQKOWJ9JZRCKOVGP')) + + # The proper tag is left alone, however. + # noinspection SpellCheckingInspection + self.assertEqual(bundle[0].tag, Tag('PPDIDNQDJZGUQKOWJ9JZRCKOVGP')) + + # The bundle hash takes the modified legacy tag into account. + # noinspection SpellCheckingInspection + self.assertEqual( + bundle.hash, + + BundleHash( + 'NYSJSEGCWESDAFLIFCNJFWGZ9PCYDOT9VCSALKBD' + '9UUNKBJAJCB9KVMTHZDPRDDXC9UFJQBJBQFUPJKFC', + ) + ) + def test_sign_inputs(self): """ Signing inputs in a finalized bundle, using a key generator. diff --git a/test/trits_test.py b/test/trits_test.py new file mode 100644 index 0000000..70fed3c --- /dev/null +++ b/test/trits_test.py @@ -0,0 +1,32 @@ +# coding=utf-8 +from __future__ import absolute_import, division, print_function, \ + unicode_literals + +from unittest import TestCase + +from iota import trits_from_int + + +class TritsFromIntTestCase(TestCase): + """ + Explicit unit tests for :py:func:`trits_from_int`. + + Note that this function is used internally by many different classes + and functions, so we still have good coverage even though this + particular test case has limited scope. + """ + def test_zero(self): + """ + Zero is represented as ``[0]`` by default. + + https://github.com/iotaledger/iota.lib.py/issues/49 + """ + self.assertEqual(trits_from_int(0), [0]) + + def test_zero_unpadded(self): + """ + Converting zero to trits, without padding. + """ + self.assertEqual(trits_from_int(0, pad=None), []) + + diff --git a/test/types_test.py b/test/types_test.py index f7521e5..ee1f388 100644 --- a/test/types_test.py +++ b/test/types_test.py @@ -6,8 +6,8 @@ from six import binary_type, text_type -from iota import Address, AddressChecksum, Hash, Tag, TryteString, TrytesCodec, \ - TrytesDecodeError +from iota import Address, AddressChecksum, AsciiTrytesCodec, Hash, Tag, \ + TryteString, TrytesDecodeError # noinspection SpellCheckingInspection @@ -569,7 +569,7 @@ def test_as_trytes_single_tryte(self): self.assertDictEqual( { chr(c): TryteString(chr(c).encode('ascii')).as_trytes() - for c in TrytesCodec.alphabet.values() + for c in AsciiTrytesCodec.alphabet.values() }, { @@ -643,7 +643,7 @@ def test_as_trits_single_tryte(self): self.assertDictEqual( { chr(c): TryteString(chr(c).encode('ascii')).as_trits() - for c in TrytesCodec.alphabet.values() + for c in AsciiTrytesCodec.alphabet.values() }, {