11# -*- coding: utf-8 -*-
22
3- ###
4- ### DO NOT CHANGE THIS FILE
5- ###
6- ### The code is auto generated, your change will be overwritten by
7- ### code generating.
8- ###
3+ {% include ' _do_not_change.tpl' %}
94from __future__ import absolute_import, print_function
105
11- import re
126import json
137from datetime import date
148from functools import wraps
159
1610import six
17- from sanic import response
18- from sanic.exceptions import ServerError
19- from sanic.response import HTTPResponse
11+ import falcon
2012
2113from werkzeug.datastructures import MultiDict, Headers
22- from sanic.request import RequestParameters
2314from jsonschema import Draft4Validator
2415
2516from .schemas import (
2617 validators, filters, scopes, security, base_path, normalize)
2718
2819
29- def unpack(value):
30- """Return a three tuple of data, code, and headers"""
31- if not isinstance(value, tuple):
32- return value, 200, { }
33-
34- try:
35- data, code, headers = value
36- return data, code, headers
37- except ValueError:
38- pass
39-
40- try:
41- data, code = value
42- return data, code, { }
43- except ValueError:
44- pass
45-
46- return value, 200, { }
47-
48-
49- def _remove_characters(text, deletechars):
50- return text.translate({ ord(x): None for x in deletechars} )
20+ if six.PY3:
21+ def _remove_characters(text, deletechars):
22+ return text.translate({ ord(x): None for x in deletechars} )
23+ else:
24+ def _remove_characters(text, deletechars):
25+ return text.translate(None, deletechars)
5126
5227
5328def _path_to_endpoint(path):
54- endpoint = '_'.join(filter(None, re.sub(r'(/|<|>|-) ', r '_', path).split('_')) )
29+ endpoint = path.strip('/').replace('/ ', '_').replace('-', '_' )
5530 _base_path = base_path.strip('/').replace('/', '_').replace('-', '_')
5631 if endpoint.startswith(_base_path):
5732 endpoint = endpoint[len(_base_path)+1:]
@@ -66,7 +41,7 @@ class JSONEncoder(json.JSONEncoder):
6641 return json.JSONEncoder.default(self, o)
6742
6843
69- class SanicValidatorAdaptor (object):
44+ class FalconValidatorAdaptor (object):
7045
7146 def __init__(self, schema):
7247 self.validator = Draft4Validator(schema)
@@ -80,10 +55,10 @@ class SanicValidatorAdaptor(object):
8055 def type_convert(self, obj):
8156 if obj is None:
8257 return None
83- if isinstance(obj, (dict, list)) and not isinstance(obj, RequestParameters ):
58+ if isinstance(obj, (dict, list)) and not isinstance(obj, MultiDict ):
8459 return obj
8560 if isinstance(obj, Headers):
86- obj = MultiDict(obj.items( ))
61+ obj = MultiDict(six.iteritems(obj ))
8762 result = dict()
8863
8964 convert_funs = {
@@ -98,7 +73,7 @@ class SanicValidatorAdaptor(object):
9873 func = convert_funs.get(type_, lambda v: v[0])
9974 return [func([i]) for i in v]
10075
101- for k, values in obj.items ():
76+ for k, values in obj.lists ():
10277 prop = self.validator.schema['properties'].get(k, { } )
10378 type_ = prop.get('type')
10479 fun = convert_funs.get(type_, lambda v: v[0])
@@ -111,82 +86,83 @@ class SanicValidatorAdaptor(object):
11186
11287 def validate(self, value):
11388 value = self.type_convert(value)
114- errors = list(e. message for e in self.validator.iter_errors(value))
89+ errors = { e.path[0]: e. message for e in self.validator.iter_errors(value)}
11590 return normalize(self.validator.schema, value)[0], errors
11691
11792
118- def request_validate(view):
119-
120- @wraps(view)
121- def wrapper(*args, **kwargs):
122- request = args[1]
123- endpoint = _path_to_endpoint(request.uri_template)
124- # scope
125- if (endpoint, request.method) in scopes and not set(
126- scopes[(endpoint, request.method)]).issubset(set(security.scopes)):
127- raise ServerError('403', status_code=403)
128- # data
129- method = request.method
130- if method == 'HEAD':
131- method = 'GET'
132- locations = validators.get((endpoint, method), { } )
133- for location, schema in locations.items():
134- value = getattr(request, location, MultiDict())
135- if value is None:
136- value = MultiDict()
137- validator = SanicValidatorAdaptor(schema)
138- result, errors = validator.validate(value)
139- if errors:
140- raise ServerError('Unprocessable Entity', status_code=422)
141- request[location] = result
142- return view(*args, **kwargs)
143-
144- return wrapper
145-
146-
147- def response_filter(view):
148-
149- @wraps(view)
150- def wrapper(*args, **kwargs):
151- request = args[1]
152- resp = view(*args, **kwargs)
153-
154- if isinstance(resp, HTTPResponse):
155- return resp
156-
157- endpoint = _path_to_endpoint(request.uri_template)
158- method = request.method
159- if method == 'HEAD':
160- method = 'GET'
161- filter = filters.get((endpoint, method), None)
162- if not filter:
163- return resp
164-
165- headers = None
166- status = None
167- if isinstance(resp, tuple):
168- resp, status, headers = unpack(resp)
169-
170- if len(filter) == 1:
171- status = list(filter.keys())[0]
93+ def request_validate(req, resp, resource, params):
94+
95+ endpoint = _path_to_endpoint(req.uri_template)
96+ # scope
97+ if (endpoint, req.method) in scopes and not set(
98+ scopes[(endpoint, req.method)]).issubset(set(security.scopes)):
99+ falcon.HTTPUnauthorized('403403403')
100+ # data
101+ method = req.method
102+ if method == 'HEAD':
103+ method = 'GET'
104+ locations = validators.get((endpoint, method), { } )
105+ context = { }
106+ for location, schema in six.iteritems(locations):
107+ value = getattr(req, location, MultiDict())
108+ if location == 'headers':
109+ value = { k.capitalize(): v for k, v in value.items()}
110+ elif location == 'json':
111+ body = req.stream.read()
112+
113+ try:
114+ value = json.loads(body.decode('utf-8'))
115+ except (ValueError, UnicodeDecodeError):
116+ raise falcon.HTTPError(falcon.HTTP_753,
117+ 'Malformed JSON',
118+ 'Could not decode the request body. The '
119+ 'JSON was incorrect or not encoded as '
120+ 'UTF-8.')
121+ if value is None:
122+ value = MultiDict()
123+ validator = FalconValidatorAdaptor(schema)
124+ result, errors = validator.validate(value)
125+ if errors:
126+ raise falcon.HTTPUnprocessableEntity('Unprocessable Entity', description=errors)
127+ context[location] = result
128+ req.context = context
172129
173- schemas = filter.get(status)
174- if not schemas:
175- # return resp, status, headers
176- raise ServerError('`%d` is not a defined status code.' % status, 500)
177130
178- resp, errors = normalize(schemas['schema'], resp)
179- if schemas['headers']:
180- headers, header_errors = normalize(
181- { ' properties' : schemas[' headers' ]} , headers)
182- errors.extend(header_errors)
183- if errors:
184- raise ServerError('Expectation Failed', 500)
131+ def response_filter(req, resp, resource):
185132
186- return response.json(
187- resp,
188- status=status,
189- headers=headers,
190- )
133+ endpoint = _path_to_endpoint(req.uri_template)
134+ method = req.method
135+ if method == 'HEAD':
136+ method = 'GET'
137+ filter = filters.get((endpoint, method), None)
138+ if not filter:
139+ return resp
191140
192- return wrapper
141+ headers = None
142+ status = None
143+
144+ if len(filter) == 1:
145+ if six.PY3:
146+ status = list(filter.keys())[0]
147+ else:
148+ status = filter.keys()[0]
149+
150+ schemas = filter.get(status)
151+ if not schemas:
152+ # return resp, status, headers
153+ raise falcon.HTTPInternalServerError(
154+ 'Not defined',
155+ description='`%d` is not a defined status code.' % status)
156+
157+ _resp, errors = normalize(schemas['schema'], req.context['result'])
158+ if schemas['headers']:
159+ headers, header_errors = normalize(
160+ { ' properties' : schemas[' headers' ]} , headers)
161+ errors.extend(header_errors)
162+ if errors:
163+ raise falcon.HTTPInternalServerError(title='Expectation Failed',
164+ description=errors)
165+
166+ if 'result' not in req.context:
167+ return
168+ resp.body = json.dumps(_resp)
0 commit comments