Skip to content


Subversion checkout URL

You can clone with
Download ZIP
This project contains extensions to test Tornado apps under pyvows.
Python Makefile
Fetching latest commit...
Cannot retrieve the latest commit at this time.
Failed to load latest commit information.
tornado_pyvows bump to 0.6.1
.travis.yml Pyvows 2.0.5 has broken tornado_pyvows
Makefile Pyvows 2.0.5 has broken tornado_pyvows
README.mkd Update README.mkd
requirements.txt Add mock to requirements.txt Fixing for tornado 4




This project contains extensions to test Tornado apps under pyVows.


To test a tornado app (or handlers) use this context instead of the regular Vows.Context, like this:

import tornado
from tornado_pyvows import TornadoHTTPContext
from pyvows import Vows, expect

class HomeHandler(tornado.web.RequestHandler):

    def get(self):

    def post(self):

class SomeVows(TornadoHTTPContext):

    def get_app(self):
        application = tornado.web.Application([
            (r"/", HomeHandler),
        return application

    class HomeUrl(TornadoHTTPContext):
        def topic(self):
            self.http_client.fetch(self.get_url('/'), self.stop)
            response = self.wait()
            return response.body

        def should_be_hello_world(self, topic):

    class SameUrl(HomeUrl):
        def topic(self):
            For convenience you can also use ``get`` and ``post`` to wrap the 
            calls to the ``http_client``.
            response = self.get("/")
            return response.body

    class SimplePost(HomeUrl):
        def topic(self):
            response ="/")
            return response.body

Each TornadoHTTPContext provides Tornado's testing methods like http_client, get_url, stop, wait, fetch and others.

If you're developing based on Tornados HTTPClient you can just do that with simple wrappers as seen in


The new IsolatedTornadoHTTPContext creates a new HTTPServer that runs the application. This helps when testing handlers using mocks, e.g.::

class ASimpleTestWithAMock(TornadoHTTPContext):

    def get_handler_spec(self):
        return (r'^/echo$', ExampleHandler)

    def get_application_settings(self):
        return {'debug': True}

    class AndASimpleTestCase(IsolatedTornadoHTTPContext):

        def topic(self):
            mock = AsyncMock()
            mock.return_value = 'mocked echo'
            self.get_test_handler().echo = mock

            yield (mock, self.fetch('/echo'))

        def shouldWorkAsUsual(self, topic):

        def shouldReturnTheExpectedTopic(self, topic):
            (_, resp) = topic
            expect(resp.body).to_equal('mocked echo')

        class ThatBlahsBlahs(TornadoHTTPContext):

            def topic(self, topic):
                yield (topic, self.fetch('/echo'))

            def shouldReturnTheExpectedTopic(self, topic):
                (_, resp) = topic
                expect(resp.body).to_equal('mocked echo')

    class ThatHasNoSideEffects(IsolatedTornadoHTTPContext):

        def topic(self):
            yield self.fetch('/echo')

        def shouldWorkAsUsual(self, topic):

        def shouldReturnTheExpectedTopic(self, resp):


If you want to test a tornado based app without the HTTP overhead you may also use the TornadoContext:

def asyncMethod(callback):
    callback("Pseudo Async Result")

class AsyncVows(TornadoContext):

    class CallbacksShouldWork(TornadoContext):

        def topic(self):
            self.io_loop = self.get_new_ioloop()
            self.io_loop.add_callback(lambda: asyncMethod(self.stop))
            return self.wait()

        def and_have_the_correct_result(self, topic):
            expect(topic).to_equal("Pseudo Async Result")

The above example creates a new IOLoop for every test, which is nice. Some libraries add callbacks to the IOLoop.instance() singleton, such as tornado.httpclient.AsyncHTTPClient. These libraries can be tested by overloading the get_new_ioloop method to return the IOLoop.instance() singleton.

class AsyncVows(TornadoContext):

    class PyVowsSiteVows(TornadoContext):

        def get_new_ioloop(self):
            return IOLoop.instance()

        def topic(self):
            self.io_loop = self.get_new_ioloop()
            http_client = AsyncHTTPClient()
            return self.wait()

        def to_be_about_asynchronous_testing(self, topic):
            expect(topic.body).to_include('Asynchronous BDD for Python')


Contributions are very welcome. To contribute fork it and create a pull request.

The team behind Tornado_pyVows (in order of joining the project):

Something went wrong with that request. Please try again.