async def get_http_response( self, request: Request, execute: typing.Callable, process_result: typing.Callable, graphiql: bool, root_value: typing.Optional[typing.Any], context: typing.Optional[typing.Any], ) -> Response: if request.method == "GET": if not graphiql: return HTMLResponse(status_code=status.HTTP_404_NOT_FOUND) return self.get_graphiql_response() if request.method == "POST": content_type = request.headers.get("Content-Type", "") if "application/json" in content_type: data = await request.json() elif content_type.startswith("multipart/form-data"): multipart_data = await request.form() operations = json.loads(multipart_data.get("operations", "{}")) files_map = json.loads(multipart_data.get("map", "{}")) data = replace_placeholders_with_files( operations, files_map, multipart_data ) else: return PlainTextResponse( "Unsupported Media Type", status_code=status.HTTP_415_UNSUPPORTED_MEDIA_TYPE, ) else: return PlainTextResponse( "Method Not Allowed", status_code=status.HTTP_405_METHOD_NOT_ALLOWED, ) try: query = data["query"] variables = data.get("variables") operation_name = data.get("operationName") except KeyError: return PlainTextResponse( "No GraphQL query found in the request", status_code=status.HTTP_400_BAD_REQUEST, ) result = await execute( query, variables=variables, context=context, operation_name=operation_name, root_value=root_value, ) response_data = await process_result(request=request, result=result) return JSONResponse(response_data, status_code=status.HTTP_200_OK)
def parse_body(self, request) -> Dict[str, Any]: if request.content_type == "multipart/form-data": data = json.loads(request.POST.get("operations", "{}")) files_map = json.loads(request.POST.get("map", "{}")) data = replace_placeholders_with_files(data, files_map, request.FILES) return data return json.loads(request.body)
def parse_body(self, request: Request) -> dict: if request.content_type.startswith("multipart/form-data"): files = convert_request_to_files_dict(request) operations = json.loads(request.form.get("operations", "{}")) files_map = json.loads(request.form.get("map", "{}")) try: return replace_placeholders_with_files(operations, files_map, files) except KeyError: abort(400, "File(s) missing in form data") return request.json
def dispatch_request(self): if "text/html" in request.environ.get("HTTP_ACCEPT", ""): if not self.graphiql: abort(404) template = render_graphiql_page() return self.render_template(template=template) if request.content_type.startswith("multipart/form-data"): operations = json.loads(request.form.get("operations", "{}")) files_map = json.loads(request.form.get("map", "{}")) data = replace_placeholders_with_files(operations, files_map, request.files) else: data = request.json try: query = data["query"] variables = data.get("variables") operation_name = data.get("operationName") except KeyError: return Response("No valid query was provided for the request", 400) context = self.get_context() result = self.schema.execute_sync( query, variable_values=variables, context_value=context, operation_name=operation_name, root_value=self.get_root_value(), ) response_data = self.process_result(result) return Response( json.dumps(response_data), status=200, content_type="application/json", )
async def parse_multipart_body(self, request: web.Request) -> dict: reader = await request.multipart() operations: Dict[str, Any] = {} files_map: Dict[str, Any] = {} files: Dict[str, Any] = {} try: async for field in reader: if field.name == "operations": operations = (await field.json()) or {} elif field.name == "map": files_map = (await field.json()) or {} elif field.filename: assert field.name files[field.name] = BytesIO(await field.read(decode=False)) except ValueError: raise web.HTTPBadRequest(reason="Unable to parse the multipart body") try: return replace_placeholders_with_files(operations, files_map, files) except KeyError: raise web.HTTPBadRequest(reason="File(s) missing in form data")