sanic/docs/custom_protocol.md
Cadel Watson 6176964bdf Clarify, reformat, and add to documentation guides (#318)
* Reorder and clarify the 'Request Data' guide, adding a section on RequestParameters

* Clarify routing guide, adding introduction and HTTP types sections

* Clarify the use-cases of middleware

* Clean up formatting in the exceptions guide and add some common exceptions.

* Fix formatting of blueprints and add use-case example.

* Clarify the class-based views guide

* Clarify and fix formatting of cookies guide

* Clarify static files guide

* Clarify the custom protocols guide.

* Add more information to the deploying guide

* Fix broken list in the community extensions list.

* Add introduction and improve warning to contributing guide

* Expand getting started guide

* Reorder guides and add links between them

* Standardise heading capitalisation
2017-01-19 21:18:52 -06:00

2.5 KiB

Custom Protocols

Note: this is advanced usage, and most readers will not need such functionality.

You can change the behavior of Sanic's protocol by specifying a custom protocol, which should be a subclass of asyncio.protocol. This protocol can then be passed as the keyword argument protocol to the sanic.run method.

The constructor of the custom protocol class receives the following keyword arguments from Sanic.

  • loop: an asyncio-compatible event loop.
  • connections: a set to store protocol objects. When Sanic receives SIGINT or SIGTERM, it executes protocol.close_if_idle for all protocol objects stored in this set.
  • signal: a sanic.server.Signal object with the stopped attribute. When Sanic receives SIGINT or SIGTERM, signal.stopped is assigned True.
  • request_handler: a coroutine that takes a sanic.request.Request object and a response callback as arguments.
  • error_handler: a sanic.exceptions.Handler which is called when exceptions are raised.
  • request_timeout: the number of seconds before a request times out.
  • request_max_size: an integer specifying the maximum size of a request, in bytes.

Example

An error occurs in the default protocol if a handler function does not return an HTTPResponse object.

By overriding the write_response protocol method, if a handler returns a string it will be converted to an HTTPResponse object.

from sanic import Sanic
from sanic.server import HttpProtocol
from sanic.response import text

app = Sanic(__name__)


class CustomHttpProtocol(HttpProtocol):

    def __init__(self, *, loop, request_handler, error_handler,
                 signal, connections, request_timeout, request_max_size):
        super().__init__(
            loop=loop, request_handler=request_handler,
            error_handler=error_handler, signal=signal,
            connections=connections, request_timeout=request_timeout,
            request_max_size=request_max_size)

    def write_response(self, response):
        if isinstance(response, str):
            response = text(response)
        self.transport.write(
            response.output(self.request.version)
        )
        self.transport.close()


@app.route('/')
async def string(request):
    return 'string'


@app.route('/1')
async def response(request):
    return text('response')

app.run(host='0.0.0.0', port=8000, protocol=CustomHttpProtocol)

Previous: Cookies

Next: Testing