Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Reworked test and deploy documentation #1497

Merged
merged 5 commits into from
Jun 27, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
28 changes: 28 additions & 0 deletions docs/deploying-contracts.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
.. index:: deploying;deploying;

.. _deploying:

********************
Deploying a Contract
********************

Once you are ready to deploy your contract to a public test net or the main net, you have several options:

* Take the bytecode generated by the vyper compiler and manually deploy it through mist or geth:

.. code-block:: bash

vyper yourFileName.vy
# returns bytecode

* Take the byte code and ABI and depoly it with your current browser on `myetherwallet's <https://www.myetherwallet.com/>`_ contract menu:

.. code-block:: bash

vyper -f abi yourFileName.vy
# returns ABI

* Use the remote compiler provided by the `Remix IDE <https://remix.ethereum.org>`_ to compile and deploy your contract on your net of choice. Remix also provides a JavaScript VM to test deploy your contract.

.. note::
While the vyper version of the Remix IDE compiler is updated on a regular basis it might be a bit behind the latest version found in the master branch of the repository. Make sure the byte code matches the output from your local compiler.
3 changes: 2 additions & 1 deletion docs/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -97,7 +97,8 @@ Glossary

installing-vyper.rst
compiling-a-contract.rst
testing-deploying-contracts.rst
testing-contracts.rst
deploying-contracts.rst
structure-of-a-contract.rst
vyper-by-example.rst
logging.rst
Expand Down
86 changes: 86 additions & 0 deletions docs/testing-contracts.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
.. index:: testing;testing;

.. _testing:

******************
Testing a Contract
******************

This documentation recommends the use of the `pytest <https://docs.pytest.org/en/latest/contents.html>`_ framework with
the `ethereum-tester <https://github.com/ethereum/ethereum-tester>`_ package.
Prior to testing, the vyper specific contract conversion and the blockchain related fixtures need to be set up.
These fixtures will be used in every test file and should therefore be defined in
`conftest.py <https://docs.pytest.org/en/latest/fixture.html#conftest-py-sharing-fixture-functions>`_.

.. note::
Since the testing is done in the pytest framework, you can make use of
`pytest.ini, tox.ini and setup.cfg <https://docs.pytest.org/en/latest/customize.html>`_ and you can use most IDEs'
pytest plugins.

=================================
Vyper Contract and Basic Fixtures
=================================

.. literalinclude:: ../tests/base_conftest.py
:language: python
:linenos:

This is the base requirement to load a vyper contract and start testing. The last two fixtures are optional and will be
discussed later. The rest of this chapter assumes, that you have this code set up in your ``conftest.py`` file.
Alternatively, you can import the fixtures to ``conftest.py`` or use
`pytest_plugins <https://docs.pytest.org/en/latest/plugins.html>`_.



=============================
Load Contract and Basic Tests
=============================

Assume the following simple contract ``storage.vy``. It has a single integer variable and a function to set that value.

.. literalinclude:: ../examples/storage/storage.vy
:language: python

We create a test file ``test_storage.py`` where we write our tests in pytest style.

.. literalinclude:: ../tests/examples/storage/test_storage.py
:language: python

First we create a fixture for the contract which will compile our contract and set up a Web3 contract object.
We then use this fixture for our test functions to interact with the contract.

.. note::
To run the tests, call ``pytest`` or ``python -m pytest`` from your project directory.

==============================
Events and Failed Transactions
==============================

To test events and failed transactions we expand our simple storage contract to include an event and two conditions for a failed transaction: ``advanced_storage.vy``

.. literalinclude:: ../examples/storage/advanced_storage.vy
:language: python

Next, we take a look at the two fixtures that will allow us to read the event logs and to check for failed transactions.

.. literalinclude:: ../tests/base_conftest.py
:language: python
:pyobject: assert_tx_failed

The fixture to assert failed transactions defaults to check for a ``TransactionFailed`` exception, but can be used to check for different exceptions too, as shown below.
Also note that the chain gets reverted to the state before the failed transaction.


.. literalinclude:: ../tests/base_conftest.py
:language: python
:pyobject: get_logs

This fixture will return a tuple with all the logs for a certain event and transaction. The length of the tuple equals the number of events (of the specified type) logged and should be checked first.


Finally, we create a new file ``test_advanced_storage.py`` where we use the new fixtures to test failed transactions and events.

.. literalinclude:: ../tests/examples/storage/test_advanced_storage.py
:language: python


77 changes: 0 additions & 77 deletions docs/testing-deploying-contracts.rst

This file was deleted.

18 changes: 18 additions & 0 deletions examples/storage/advanced_storage.vy
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
DataChange: event({_setter: indexed(address), _value: int128})

storedData: public(int128)

@public
def __init__(_x: int128):
self.storedData = _x

@public
def set(_x: int128):
assert _x >= 0 # No negative values
assert self.storedData < 100 # Storage will lock when 100 or more is stored
self.storedData = _x
log.DataChange(msg.sender, _x)

@public
def reset():
self.storedData = 0
9 changes: 9 additions & 0 deletions examples/storage/storage.vy
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
storedData: public(int128)

@public
def __init__(_x: int128):
self.storedData = _x

@public
def set(_x: int128):
self.storedData = _x
Loading