lavkach3
124 строки · 3.5 Кб
1from contextlib import asynccontextmanager2from typing import List3
4from fastapi import FastAPI, Request, Depends5from fastapi.middleware import Middleware6from fastapi.middleware.cors import CORSMiddleware7from fastapi.responses import JSONResponse8from starlette.requests import HTTPConnection9from starlette.types import ASGIApp, Scope, Receive, Send10
11from app.prescription.prescription_router import router12from core.db_config import config13from core.env import Env14from app.prescription import __domain__ as domains15from core.exceptions import CustomException16from core.fastapi.dependencies import Logging17from core.fastapi.middlewares import (18AuthenticationMiddleware,19AuthBackend,20SQLAlchemyMiddleware,21)
22from core.helpers.broker.tkq import broker23from core.helpers.cache import Cache, CustomKeyMaker24from core.helpers.cache import RedisBackend25
26
27class EnvMidlleWare:28"""29Адартер кладется в request для удобства
30"""
31
32def __init__(self, app: ASGIApp, *args, **kwargs):33self.app = app34
35async def __call__(self, scope: Scope, receive: Receive, send: Send):36if scope['type'] in ("http", "websocket"):37conn = HTTPConnection(scope)38scope['env'] = Env(domains, conn)39await self.app(scope, receive, send)40
41
42def init_routers(app_: FastAPI) -> None:43app_.include_router(router)44
45
46
47def init_listeners(app_: FastAPI) -> None:48# Exception handler49@app_.exception_handler(CustomException)50async def custom_exception_handler(request: Request, exc: CustomException):51return JSONResponse(52status_code=exc.code,53content={"error_code": exc.error_code, "message": exc.message},54)55
56
57def on_auth_error(request: Request, exc: Exception):58status_code, error_code, message = 401, None, str(exc)59if isinstance(exc, CustomException):60status_code = int(exc.code)61error_code = exc.error_code62message = exc.message63
64return JSONResponse(65status_code=status_code,66content={"error_code": error_code, "message": message},67)68
69
70def make_middleware() -> List[Middleware]:71middleware = [72Middleware(EnvMidlleWare),73Middleware(74CORSMiddleware,75allow_origins=["*"],76allow_credentials=False,77allow_methods=["*"],78allow_headers=["*"],79),80Middleware(81AuthenticationMiddleware,82backend=AuthBackend(),83on_error=on_auth_error,84),85Middleware(SQLAlchemyMiddleware),86]87return middleware88
89
90def init_cache() -> None:91Cache.init(backend=RedisBackend(), key_maker=CustomKeyMaker())92
93@asynccontextmanager
94async def lifespan(app: FastAPI):95"""96Старт сервера
97"""
98if not broker.is_worker_process:99await broker.startup()100yield101"""102Выключение сервера
103"""
104if not broker.is_worker_process:105await broker.shutdown()106
107def create_app() -> FastAPI:108app_ = FastAPI(109title="Hide",110lifespan=lifespan,111description="Hide API",112version="1.0.0",113# docs_url=None if config.ENV == "production" else "/api/prescription/docs",114# redoc_url=None if config.ENV == "production" else "/api/prescription/dredoc",115dependencies=[Depends(Logging)],116middleware=make_middleware(),117)118init_routers(app_=app_)119init_listeners(app_=app_)120init_cache()121return app_122
123
124app = create_app()125