Files
@ 281d6fed47b7
Branch filter:
Location: NPO-Accounting/experimental-accounting-api/accounting/decorators.py - annotation
281d6fed47b7
2.5 KiB
text/x-python
[test] Added unit tests
- Moved the TransactionNotFound exception to a more appropriate place.
- Changed the serialization for AccountingExceptions
- Override the Exception.__init__ method in AccountingException
- Added __eq__ methods to accounting.models.*
- Catch the TransactionNotFound exception in transaction_get and return a
404 instead. This could be improved, perhaps in the jsonify_exceptions
decorator so that all endpoints that raise a TransactionNotFound
exception automatically return a 404.
- Moved the TransactionNotFound exception to a more appropriate place.
- Changed the serialization for AccountingExceptions
- Override the Exception.__init__ method in AccountingException
- Added __eq__ methods to accounting.models.*
- Catch the TransactionNotFound exception in transaction_get and return a
404 instead. This could be improved, perhaps in the jsonify_exceptions
decorator so that all endpoints that raise a TransactionNotFound
exception automatically return a 404.
fc2c3a6b4339 fc2c3a6b4339 fc2c3a6b4339 fc2c3a6b4339 6f2c875c7b76 6f2c875c7b76 2eecd641dda8 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 6f2c875c7b76 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 2eecd641dda8 | # Part of accounting-api project:
# https://gitorious.org/conservancy/accounting-api
# License: AGPLv3-or-later
from functools import wraps
from flask import jsonify, request
from accounting.exceptions import AccountingException
def jsonify_exceptions(func):
'''
Wraps a Flask endpoint and catches any AccountingException-based
exceptions which are returned to the client as JSON.
'''
@wraps(func)
def wrapper(*args, **kw):
try:
return func(*args, **kw)
except AccountingException as exc:
return jsonify(error=exc)
return wrapper
def cors(origin_callback=None):
'''
Flask endpoint decorator.
Example:
.. code-block:: python
@app.route('/cors-endpoint', methods=['GET', 'OPTIONS'])
@cors()
def cors_endpoint():
return jsonify(message='This is accessible via a cross-origin XHR')
# Or if you want to control the domains this resource can be requested
# from via CORS:
domains = ['http://wandborg.se', 'http://sfconservancy.org']
def restrict_domains(origin):
return ' '.join(domains)
@app.route('/restricted-cors-endpoint')
@cors(restrict_domains)
def restricted_cors_endpoint():
return jsonify(
message='This is accessible from %s' % ', '.join(domains))
:param function origin_callback: A callback that takes one str() argument
containing the ``Origin`` HTTP header from the :data:`request` object.
This can be used to filter out which domains the resource can be
requested via CORS from.
'''
if origin_callback is None:
origin_callback = allow_all_origins
def decorator(func):
@wraps(func)
def wrapper(*args, **kw):
response = func(*args, **kw)
cors_headers = {
'Access-Control-Allow-Origin':
origin_callback(request.headers.get('Origin')) or '*',
'Access-Control-Allow-Credentials': 'true',
'Access-Control-Max-Age': 3600,
'Access-Control-Allow-Methods': 'POST, GET, DELETE',
'Access-Control-Allow-Headers':
'Accept, Content-Type, Connection, Cookie'
}
for key, val in cors_headers.items():
response.headers[key] = val
return response
return wrapper
return decorator
def allow_all_origins(origin):
return origin
|