Source code for pjrpc.server.integration.werkzeug

from typing import Any, Callable, Dict, Iterable

import werkzeug
from werkzeug import exceptions

import pjrpc.server


[docs]class JsonRPC: """ `werkzeug <https://werkzeug.palletsprojects.com/en/0.16.x/>`_ server JSON-RPC integration. :param path: JSON-RPC handler base path :param kwargs: arguments to be passed to the dispatcher :py:class:`pjrpc.server.Dispatcher` """ def __init__(self, path: str = '', **kwargs: Any): self._path = path self._dispatcher = pjrpc.server.Dispatcher(**kwargs) def __call__(self, environ: Dict[str, Any], start_response: Callable[..., Any]) -> Iterable[bytes]: return self.wsgi_app(environ, start_response) def wsgi_app(self, environ: Dict[str, Any], start_response: Callable[..., Any]) -> Iterable[bytes]: environ['app'] = self request = werkzeug.Request(environ) response = self._rpc_handle(request) return response(environ, start_response) @property def dispatcher(self) -> pjrpc.server.Dispatcher: """ JSON-RPC method dispatcher. """ return self._dispatcher def _rpc_handle(self, request: werkzeug.Request) -> werkzeug.Response: """ Handles JSON-RPC request. :returns: werkzeug response """ if request.content_type not in pjrpc.common.REQUEST_CONTENT_TYPES: raise exceptions.UnsupportedMediaType() try: request_text = request.get_data(as_text=True) except UnicodeDecodeError as e: raise exceptions.BadRequest() from e response_text = self._dispatcher.dispatch(request_text, context=request) if response_text is None: return werkzeug.Response() else: return werkzeug.Response(response_text, mimetype=pjrpc.common.DEFAULT_CONTENT_TYPE)