Commit inicial - upload de todos os arquivos da pasta
This commit is contained in:
+89
@@ -0,0 +1,89 @@
|
||||
"""Ponto de entrada FastAPI do Lernotafiscal."""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
import logging
|
||||
from contextlib import asynccontextmanager
|
||||
from pathlib import Path
|
||||
|
||||
from fastapi import FastAPI
|
||||
from fastapi.staticfiles import StaticFiles
|
||||
from starlette.middleware.base import BaseHTTPMiddleware
|
||||
from starlette.middleware.sessions import SessionMiddleware
|
||||
from starlette.requests import Request
|
||||
from starlette.responses import RedirectResponse
|
||||
|
||||
from . import auth, database
|
||||
from .config import get_settings
|
||||
from .routes import (
|
||||
auth_routes,
|
||||
dashboard_routes,
|
||||
documents_routes,
|
||||
files_routes,
|
||||
upload_routes,
|
||||
)
|
||||
|
||||
logging.basicConfig(level=logging.INFO, format="%(asctime)s %(levelname)s %(name)s: %(message)s")
|
||||
logger = logging.getLogger("lernotafiscal")
|
||||
|
||||
# Caminhos liberados sem sessão (login e assets da própria UI).
|
||||
PUBLIC_PREFIXES = ("/login", "/static/", "/favicon.ico", "/healthz")
|
||||
|
||||
|
||||
class AuthGuardMiddleware(BaseHTTPMiddleware):
|
||||
async def dispatch(self, request: Request, call_next):
|
||||
path = request.url.path
|
||||
if any(path == p or path.startswith(p) for p in PUBLIC_PREFIXES):
|
||||
return await call_next(request)
|
||||
if not request.session.get("user"):
|
||||
return RedirectResponse("/login", status_code=303)
|
||||
return await call_next(request)
|
||||
|
||||
|
||||
@asynccontextmanager
|
||||
async def lifespan(app: FastAPI):
|
||||
settings = get_settings()
|
||||
with database.session() as conn:
|
||||
database.init_db(conn)
|
||||
if settings.secret_key_is_ephemeral:
|
||||
logger.warning("SECRET_KEY não definido: sessões não sobrevivem a reinícios. Defina SECRET_KEY em produção.")
|
||||
note = auth.seed_admin()
|
||||
if note:
|
||||
logger.warning(note)
|
||||
logger.info("OpenAI %s.", "habilitado (" + settings.openai_model + ")" if settings.openai_enabled else "desabilitado — usando OCR/heurística local")
|
||||
yield
|
||||
|
||||
|
||||
def create_app() -> FastAPI:
|
||||
settings = get_settings()
|
||||
app = FastAPI(title="Lernotafiscal", lifespan=lifespan)
|
||||
|
||||
# Ordem importa: SessionMiddleware é adicionado por último para ser o mais
|
||||
# externo e popular request.session ANTES da guarda de autenticação.
|
||||
app.add_middleware(AuthGuardMiddleware)
|
||||
app.add_middleware(
|
||||
SessionMiddleware,
|
||||
secret_key=settings.secret_key,
|
||||
session_cookie=settings.session_cookie,
|
||||
https_only=settings.session_https_only,
|
||||
max_age=settings.session_max_age,
|
||||
same_site="lax",
|
||||
)
|
||||
|
||||
static_dir = Path(__file__).resolve().parent / "static"
|
||||
app.mount("/static", StaticFiles(directory=str(static_dir)), name="static")
|
||||
|
||||
app.include_router(auth_routes.router)
|
||||
app.include_router(dashboard_routes.router)
|
||||
app.include_router(upload_routes.router)
|
||||
app.include_router(documents_routes.router)
|
||||
app.include_router(files_routes.router)
|
||||
|
||||
@app.get("/healthz")
|
||||
def healthz():
|
||||
return {"status": "ok"}
|
||||
|
||||
return app
|
||||
|
||||
|
||||
app = create_app()
|
||||
Reference in New Issue
Block a user