foxnouns/foxnouns/app.py
2024-04-10 20:59:57 +02:00

62 lines
1.8 KiB
Python

from quart import Quart, g, request
from quart_cors import cors
from quart_schema import QuartSchema, RequestSchemaValidationError
from . import blueprints
from .db.aio import async_session
from .db.util import validate_token
from .exceptions import ErrorCode, ExpectedError
from .settings import BASE_DOMAIN, SECRET_KEY
app = Quart(__name__, host_matching=True, static_host=BASE_DOMAIN)
app.secret_key = SECRET_KEY
app = cors(
app,
allow_origin="*",
allow_methods="*",
allow_headers=["Content-Type", "Authorization", "User-Agent"],
max_age=86400,
)
QuartSchema(app)
for bp in blueprints.__all__:
app.register_blueprint(bp)
@app.errorhandler(RequestSchemaValidationError)
async def handle_request_validation_error(error: RequestSchemaValidationError):
# TODO: parse the error and return a format closer to the draft APIv2
return {"code": ErrorCode.BadRequest, "message": "Bad request"}, 400
@app.errorhandler(ExpectedError)
async def handle_expected_error(error: ExpectedError):
return {"code": error.type, "message": error.msg}, error.status_code
@app.errorhandler(404)
async def handle_404(_):
return {"code": 404, "message": "Not found"}, 404
@app.errorhandler(500)
async def handle_500(_):
return {"code": 500, "message": "Internal server error"}, 500
@app.before_request
async def get_user_from_token():
"""Get the current user from a token given in the `Authorization` header.
If no token is set, does nothing; if an invalid token is set, raises an error."""
token = request.headers.get("Authorization", None)
if not token:
return
async with async_session() as session:
try:
token, user = await validate_token(session, token)
g.token = token
g.user = user
except:
raise