diff --git a/python/rest-api/rest_api.py b/python/rest-api/rest_api.py index d8f2744..68e3407 100644 --- a/python/rest-api/rest_api.py +++ b/python/rest-api/rest_api.py @@ -5,8 +5,6 @@ from operator import attrgetter VALID_HTTP_METHODS = ['GET', 'POST'] -def dump(obj): - return obj.__dict__ class User: def __init__(self, name): @@ -42,7 +40,7 @@ class User: return user -class Registry: +class MethodRegistry: def __init__(self): self.methods = {k: {} for k in VALID_HTTP_METHODS } @@ -50,57 +48,75 @@ class Registry: def actual_decorator(f): - self.methods[http_method][url] = f - @wraps(f) - def _impl(f_self, *f_args, **f_kwargs): - return f(f_self, *f_args, **f_kwargs) + def _wrapper(f_self, payload): + + if payload: + payload = json.loads(payload) + + f_result = f(f_self, payload) + + return json.dumps(f_result, default=lambda obj: obj.__dict__, sort_keys=True) + + self.methods[http_method][url] = _wrapper + return actual_decorator + class RestAPI: - registry = Registry() + registry = MethodRegistry() def __init__(self, database=None): self._users = {user['name'] : User.from_dict(user) for user in database['users']} if database else {} + def _process_request(self, method, url, payload): + methods = self.registry.methods[method] + if url in methods.keys(): +# try: +# return methods[url](self, payload) +# except json.JSONDecodeError: +# return 'Bad request' +# finally: +# return 'Internal server error' +# else: +# return 'Not found' + + return methods[url](self, payload) + + def get(self, url, payload=None): + return self._process_request('GET', url, payload) + + def post(self, url, payload=None): + return self._process_request('POST', url, payload) + @registry.register_url('/users', 'GET') def users(self, payload=None): if payload: - requested_users = json.loads(payload)['users'] + requested_users = payload['users'] response = [user for user in self._users.values() if user.name in requested_users] else: response = [user for user in self._users.values()] - return json.dumps({'users': response}, default=dump, sort_keys=True) + return {'users': response} @registry.register_url('/add', 'POST') def add(self, payload=None): - payload = json.loads(payload) - user = User(payload['user']) + + name = payload['user'] + user = User(name) self._users[user.name] = user - return json.dumps(user, default=dump) + return user @registry.register_url('/iou', 'POST') def iou(self, payload=None): - payload = json.loads(payload) + lender = payload['lender'] borrower = payload['borrower'] amount = payload['amount'] + self._users[lender].lend(borrower, amount) self._users[borrower].borrow(lender, amount) - return json.dumps({'users': sorted([self._users[lender], self._users[borrower]], key=attrgetter('name'))}, default=dump, sort_keys=True) - def get(self, url, payload=None): - methods = self.registry.methods['GET'] - if url in methods.keys(): - return methods[url](self, payload) - else: - raise Exception('Error 404') + return {'users': sorted([self._users[lender], self._users[borrower]], key=attrgetter('name'))} - def post(self, url, payload=None): - methods = self.registry.methods['POST'] - if url in methods.keys(): - return methods[url](self, payload) - else: - raise Exception('Error 404')