Initial commit
This commit is contained in:
@@ -0,0 +1,87 @@
|
||||
"""FastAPI application entrypoint.
|
||||
|
||||
Opens a database connection on startup, runs Alembic migrations, registers
|
||||
routers, locks CORS to the configured frontend origin(s), and attaches a
|
||||
rate-limiter to the app (applied per-endpoint via decorators).
|
||||
"""
|
||||
|
||||
from contextlib import asynccontextmanager
|
||||
from collections.abc import AsyncIterator
|
||||
|
||||
from fastapi import FastAPI
|
||||
from fastapi.middleware.cors import CORSMiddleware
|
||||
from slowapi import Limiter, _rate_limit_exceeded_handler
|
||||
from slowapi.errors import RateLimitExceeded
|
||||
from slowapi.util import get_remote_address
|
||||
|
||||
from app.config import settings
|
||||
from app.db.connection import connect, run_migrations
|
||||
from app.routers import vacation_days
|
||||
from app.routers.analytics import router as analytics_router
|
||||
from app.routers.auth import router as auth_router
|
||||
from app.routers.fetch_data import router as fetch_data_router
|
||||
from app.routers.fetch_data import scraper_router
|
||||
from app.routers.planned_days import router as planned_days_router
|
||||
from app.routers.settings import break_router, child_router, settings_child_router, tips_router
|
||||
from app.routers.workspace import _inv_router as invitations_router
|
||||
from app.routers.workspace import router as workspace_router
|
||||
|
||||
limiter = Limiter(key_func=get_remote_address)
|
||||
|
||||
|
||||
@asynccontextmanager
|
||||
async def lifespan(app: FastAPI) -> AsyncIterator[None]:
|
||||
# Run pending migrations before accepting requests (dev convenience).
|
||||
# In production, run `alembic upgrade head` as a separate deploy step.
|
||||
if settings.database_type == "sqlite":
|
||||
try:
|
||||
run_migrations(f"sqlite:///{settings.sqlite_path}")
|
||||
except Exception:
|
||||
pass # migrations may fail in test envs without alembic installed
|
||||
|
||||
app.state.db_connection = await connect(settings.sqlite_path)
|
||||
try:
|
||||
yield
|
||||
finally:
|
||||
await app.state.db_connection.close()
|
||||
|
||||
|
||||
def create_app() -> FastAPI:
|
||||
app = FastAPI(title="Föräldraledigplannerare API", lifespan=lifespan)
|
||||
|
||||
app.state.limiter = limiter
|
||||
app.add_exception_handler(RateLimitExceeded, _rate_limit_exceeded_handler)
|
||||
|
||||
app.add_middleware(
|
||||
CORSMiddleware,
|
||||
allow_origins=list(settings.cors_origins),
|
||||
allow_credentials=True,
|
||||
allow_methods=["*"],
|
||||
allow_headers=["*"],
|
||||
)
|
||||
|
||||
_register_routers(app)
|
||||
return app
|
||||
|
||||
|
||||
def _register_routers(app: FastAPI) -> None:
|
||||
app.include_router(auth_router)
|
||||
app.include_router(workspace_router)
|
||||
app.include_router(invitations_router)
|
||||
app.include_router(fetch_data_router)
|
||||
app.include_router(scraper_router)
|
||||
app.include_router(analytics_router)
|
||||
app.include_router(tips_router)
|
||||
app.include_router(break_router)
|
||||
app.include_router(child_router)
|
||||
app.include_router(settings_child_router)
|
||||
app.include_router(planned_days_router)
|
||||
app.include_router(vacation_days.router)
|
||||
|
||||
|
||||
app = create_app()
|
||||
|
||||
|
||||
@app.get("/health", tags=["health"])
|
||||
async def health() -> dict[str, str]:
|
||||
return {"status": "ok"}
|
||||
Reference in New Issue
Block a user