# -*- coding = utf-8 -*- # @Time : 2025/2/13 下午12:27 # @File : app.py # @Software : PyCharm # @Author : xingc # @Desc : import logging from fastapi import FastAPI, Request, status from fastapi.responses import UJSONResponse from fastapi.exceptions import HTTPException, RequestValidationError from fastapi_limiter import FastAPILimiter from config import settings from core.base.exceptions import CardBookException from core.db.engine import get_cache from core.routers.route import routers from core.routers.chat.handlers import socket_manager logger = logging.getLogger(__name__) async def exception_log(request: Request, exc): logger.error('\n'.join([ '', f'request method: {request.method}', f'request path: {request.path_params}', f'request host: {request.client.host}', f'query parameters: {dict(request.query_params)}', f'abnormal description: {exc}', ])) logger.exception(exc) def create_app() -> FastAPI: app = FastAPI( debug=settings.DEBUG, openapi_url='/openapi.json' if settings.DEBUG else None ) for router in routers: app.include_router(router) @app.on_event('startup') async def startup_event(): redis_conn = await get_cache() await FastAPILimiter.init(redis_conn) logger.info(f'Application ``{settings.NAME}`` is started') @app.on_event('shutdown') async def shutdown_event(): logger.info(f'Application ``{settings.NAME}`` is closed') await socket_manager.pubsub_client.disconnect() @app.exception_handler(HTTPException) async def http_exception_handler(request: Request, exc: HTTPException): await exception_log(request, exc) return UJSONResponse( status_code=exc.status_code, content={ 'status': exc.status_code, 'data': None, 'message': exc.detail } ) @app.exception_handler(RequestValidationError) async def http_exception_handler(request: Request, exc: RequestValidationError): await exception_log(request, exc) return UJSONResponse( status_code=status.HTTP_422_UNPROCESSABLE_ENTITY, content={ 'status': status.HTTP_422_UNPROCESSABLE_ENTITY, 'data': exc.errors(), 'message': 'Validation error' } ) @app.exception_handler(CardBookException) async def http_exception_handler(request: Request, exc: Exception): await exception_log(request, exc) return UJSONResponse( status_code=status.HTTP_500_INTERNAL_SERVER_ERROR, content={ 'status': status.HTTP_500_INTERNAL_SERVER_ERROR, 'data': None, 'message': str(exc) } ) @app.exception_handler(Exception) async def http_exception_handler(request: Request, exc: Exception): await exception_log(request, exc) return UJSONResponse( status_code=status.HTTP_500_INTERNAL_SERVER_ERROR, content={ 'status': status.HTTP_500_INTERNAL_SERVER_ERROR, 'data': None, 'message': 'Internal server error' } ) return app