Metadata-Version: 1.1
Name: pytest-sanic
Version: 0.1.12
Summary: UNKNOWN
Home-page: UNKNOWN
Author: Yun Xu
Author-email: yunxu1992@gmail.com
License: UNKNOWN
Description: pytest-sanic
        ============
        
        .. image:: https://travis-ci.org/yunstanford/pytest-sanic.svg?branch=master
            :alt: build status
            :target: https://travis-ci.org/yunstanford/pytest-sanic
        
        .. image:: https://coveralls.io/repos/github/yunstanford/pytest-sanic/badge.svg?branch=master
            :alt: coverage status
            :target: https://coveralls.io/github/yunstanford/pytest-sanic?branch=master
        
        
        A pytest plugin for `Sanic <http://sanic.readthedocs.io/en/latest/>`_. It helps you to test your code asynchronously.
        
        This plugin provides:
        
        * very easy testing with async coroutines
        * common and useful fixtures
        * asynchronous fixture support
        * test_client for Sanic application
        * test_server for Sanic application
        
        
        You can find out more here:
        
        http://pytest-sanic.readthedocs.io/en/latest/
        
        
        -------
        Install
        -------
        
        .. code::
        
            pip install pytest-sanic
        
        
        -----------
        Quick Start
        -----------
        
        You don't have to load ``pytest-sanic`` explicitly. ``pytest`` will do it for you. Just write tests like,
        
        .. code-block:: python
        
            async def test_sanic_db_find_by_id(app):
                """
                Let's assume that, in db we have,
                    {
                        "id": "123",
                        "name": "Kobe Bryant",
                        "team": "Lakers",
                    }
                """
                doc = await app.db["players"].find_by_id("123")
                assert doc.name == "Kobe Bryant"
                assert doc.team == "Lakers"
        
        
        --------------------
        asynchronous fixture
        --------------------
        
        ``pytest-sanic`` also supports asynchronous fixtures, just writes them like common pytest fixtures.
        
        .. code-block:: python
        
            @pytest.fixture
            async def async_fixture_sleep():
                await asyncio.sleep(0.1)
                return "sleep..."
        
        
        --------
        Fixtures
        --------
        
        Some fixtures for easy testing.
        
        ``loop``
        ~~~~~~~~
        
        ``pytest-sanic`` creates an event loop and injects it as a fixture. ``pytest`` will use this event loop to run your ``async tests``.
        By default, fixture ``loop`` is an instance of `asyncio.new_event_loop`. But `uvloop` is also an option for you, by simpy passing
        ``--loop uvloop``. Keep mind to just use one single event loop.
        
        
        ``unused_port``
        ~~~~~~~~~~~~~~
        
        an unused TCP port on the localhost.
        
        
        ``test_server``
        ~~~~~~~~~~~~~~
        
        Creates a TestServer instance by giving a ``Sanic`` application. It's very easy to utilize ``test_server`` to create your `Sanic`
        application server for testing.
        
        .. code-block:: python
        
            @pytest.yield_fixture
            def app():
                app = Sanic("test_sanic_app")
        
                @app.route("/test_get", methods=['GET'])
                async def test_get(request):
                    return response.json({"GET": True})
        
                yield app
        
            @pytest.fixture
            def sanic_server(loop, app, test_server):
                return loop.run_until_complete(test_server(app))
        
        You can also very easily override this ``loop`` fixture by creating your own, simply like,
        
        .. code-block:: python
        
            @pytest.yield_fixture
            def loop():
                loop = MyEventLoop()
                yield loop
                loop.close()
        
        
        ``test_client``
        ~~~~~~~~~~~~~~
        
        Creates a TestClient instance by giving a ``Sanic`` application. You can simply have a client by using ``test_client``, like
        
        .. code-block:: python
        
            @pytest.yield_fixture
            def app():
                app = Sanic("test_sanic_app")
        
                @app.route("/test_get", methods=['GET'])
                async def test_get(request):
                    return response.json({"GET": True})
        
                @app.route("/test_post", methods=['POST'])
                async def test_post(request):
                    return response.json({"POST": True})
        
                @app.route("/test_put", methods=['PUT'])
                async def test_put(request):
                    return response.json({"PUT": True})
        
                @app.route("/test_delete", methods=['DELETE'])
                async def test_delete(request):
                    return response.json({"DELETE": True})
        
                @app.route("/test_patch", methods=['PATCH'])
                async def test_patch(request):
                    return response.json({"PATCH": True})
        
                @app.route("/test_options", methods=['OPTIONS'])
                async def test_options(request):
                    return response.json({"OPTIONS": True})
        
                @app.route("/test_head", methods=['HEAD'])
                async def test_head(request):
                    return response.json({"HEAD": True})
        
                @app.websocket("/test_ws")
                async def test_ws(request, ws):
                    data = await ws.recv()
                    await ws.send(data)
        
                yield app
        
            @pytest.fixture
            def test_cli(loop, app, test_client):
                return loop.run_until_complete(test_client(app, protocol=WebSocketProtocol))
        
            #########
            # Tests #
            #########
        
            async def test_fixture_test_client_get(test_cli):
                """
                GET request
                """
                resp = await test_cli.get('/test_get')
                assert resp.status == 200
                resp_json = await resp.json()
                assert resp_json == {"GET": True}
        
            async def test_fixture_test_client_post(test_cli):
                """
                POST request
                """
                resp = await test_cli.post('/test_post')
                assert resp.status == 200
                resp_json = await resp.json()
                assert resp_json == {"POST": True}
        
            async def test_fixture_test_client_put(test_cli):
                """
                PUT request
                """
                resp = await test_cli.put('/test_put')
                assert resp.status == 200
                resp_json = await resp.json()
                assert resp_json == {"PUT": True}
        
            async def test_fixture_test_client_delete(test_cli):
                """
                DELETE request
                """
                resp = await test_cli.delete('/test_delete')
                assert resp.status == 200
                resp_json = await resp.json()
                assert resp_json == {"DELETE": True}
        
            async def test_fixture_test_client_patch(test_cli):
                """
                PATCH request
                """
                resp = await test_cli.patch('/test_patch')
                assert resp.status == 200
                resp_json = await resp.json()
                assert resp_json == {"PATCH": True}
        
            async def test_fixture_test_client_options(test_cli):
                """
                OPTIONS request
                """
                resp = await test_cli.options('/test_options')
                assert resp.status == 200
                resp_json = await resp.json()
                assert resp_json == {"OPTIONS": True}
        
            async def test_fixture_test_client_head(test_cli):
                """
                HEAD request
                """
                resp = await test_cli.head('/test_head')
                assert resp.status == 200
                resp_json = await resp.json()
                # HEAD should not have body
                assert resp_json is None
        
            async def test_fixture_test_client_ws(test_cli):
                """
                Websockets
                """
                ws_conn = await test_cli.ws_connect('/test_ws')
                data = 'hello world!'
                await ws_conn.send_str(data)
                msg = await ws_conn.receive()
                assert msg.data == data
                await ws_conn.close()
        
        
        small notes:
        
        ``test_cli.ws_connect`` does not work in ``sanic.__version__ <= '0.5.4'``, because of a Sanic bug, but it
        has been fixed in master branch. And ``websockets.__version__ >= '4.0'`` has broken websockets in ``sanic.__version__ <= '0.6.0'``, but it has been fixed in `master <https://github.com/channelcat/sanic/commit/bca1e084116335fd939c2ee226070f0428cd5de8>`_.
        
        
        ----
        Tips
        ----
        
        * `Blueprints Testing <https://github.com/yunstanford/pytest-sanic/issues/3>`_
        * ``test_cli.ws_connect`` does not work in ``sanic.__version__ <= '0.5.4'``, because of a Sanic bug, but it has been fixed in master branch.
        * `Importing app has loop already running <https://github.com/yunstanford/pytest-sanic/issues/1>`_ when you have `db_init` listeners.
        * `Incorrect coverage report <https://github.com/pytest-dev/pytest-cov/issues/117>`_ with ``pytest-cov``, but we can have workarounds for this issue, it's a pytest loading plugin problem essentially.
        * Websockets > 4.0 has broken websockets in ``sanic.__version__ <= '0.6.0'``, but it has been fixed in `master <https://github.com/channelcat/sanic/commit/bca1e084116335fd939c2ee226070f0428cd5de8>`_
        
        
        Feel free to create issue if you have any question. You can also check out `closed issues <https://github.com/yunstanford/pytest-sanic/issues?q=is%3Aclosed>`_
        
        
        -----------
        Development
        -----------
        
        ``pytest-sanic`` accepts contributions on GitHub, in the form of issues or pull requests.
        
        
        Run unit tests.
        
        .. code::
        
            ./uranium test
        
        
        ---------
        Reference
        ---------
        
        Some useful pytest plugins:
        
        * `pytest-tornado <https://github.com/eugeniy/pytest-tornado>`_
        * `pytest-asyncio <https://github.com/pytest-dev/pytest-asyncio>`_
        * `pytest-aiohttp <https://github.com/aio-libs/pytest-aiohttp>`_
        
Platform: UNKNOWN
Classifier: Development Status :: 5 - Production/Stable
Classifier: Operating System :: MacOS
Classifier: Operating System :: POSIX :: Linux
Classifier: Topic :: System :: Software Distribution
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.5
