110 lines
3.3 KiB
Python
110 lines
3.3 KiB
Python
"""HSBG AI Assistant — Application FastAPI principale."""
|
|
from contextlib import asynccontextmanager
|
|
from pathlib import Path
|
|
|
|
import structlog
|
|
import uvicorn
|
|
from fastapi import FastAPI
|
|
from fastapi.middleware.cors import CORSMiddleware
|
|
from fastapi.staticfiles import StaticFiles
|
|
|
|
from backend.api.routes.advice import router as advice_router
|
|
from backend.api.routes.database_routes import router as db_router
|
|
from backend.api.routes.game import router as game_router
|
|
from backend.api.routes.learning import router as learning_router
|
|
from backend.api.routes.settings_routes import router as settings_router
|
|
from backend.api.routes.websocket_routes import router as ws_router
|
|
from backend.config.settings import get_settings
|
|
from backend.database.db import init_db
|
|
from backend.services.ai_service import AIService
|
|
from backend.services.vision_service import VisionService
|
|
|
|
log = structlog.get_logger()
|
|
cfg = get_settings()
|
|
|
|
|
|
@asynccontextmanager
|
|
async def lifespan(app: FastAPI):
|
|
"""Cycle de vie: démarrage → running → arrêt."""
|
|
log.info("hsbg_ai.starting", version="1.0.0")
|
|
|
|
# Initialiser la base de données
|
|
await init_db()
|
|
log.info("database.ready")
|
|
|
|
# Initialiser le service IA
|
|
ai = AIService(cfg)
|
|
await ai.initialize()
|
|
app.state.ai_service = ai
|
|
|
|
# Initialiser le service Vision
|
|
vis = VisionService(cfg)
|
|
if cfg.vision_enabled:
|
|
await vis.start()
|
|
app.state.vision_service = vis
|
|
|
|
log.info("hsbg_ai.ready", port=cfg.backend_port, llm=cfg.llm_model)
|
|
yield # Application en cours d'exécution
|
|
|
|
# Arrêt propre
|
|
log.info("hsbg_ai.stopping")
|
|
await vis.stop()
|
|
await ai.shutdown()
|
|
log.info("hsbg_ai.stopped")
|
|
|
|
|
|
def create_app() -> FastAPI:
|
|
app = FastAPI(
|
|
title="HSBG AI Assistant",
|
|
description="IA d'assistance temps réel pour Hearthstone Battlegrounds",
|
|
version="1.0.0",
|
|
lifespan=lifespan,
|
|
docs_url="/docs",
|
|
redoc_url="/redoc",
|
|
)
|
|
|
|
# CORS pour le frontend React
|
|
app.add_middleware(
|
|
CORSMiddleware,
|
|
allow_origins=cfg.cors_origins,
|
|
allow_credentials=True,
|
|
allow_methods=["*"],
|
|
allow_headers=["*"],
|
|
)
|
|
|
|
# Routes API REST
|
|
app.include_router(game_router, prefix="/api/game", tags=["Partie"])
|
|
app.include_router(advice_router, prefix="/api/advice", tags=["Conseils IA"])
|
|
app.include_router(learning_router, prefix="/api/learning", tags=["Apprentissage"])
|
|
app.include_router(db_router, prefix="/api/database", tags=["Base HSBG"])
|
|
app.include_router(settings_router, prefix="/api/settings", tags=["Paramètres"])
|
|
app.include_router(ws_router, prefix="/ws", tags=["WebSocket"])
|
|
|
|
# Servir le frontend buildé si disponible
|
|
frontend_dist = Path("frontend/dist")
|
|
if frontend_dist.exists():
|
|
app.mount("/", StaticFiles(directory=str(frontend_dist), html=True), name="static")
|
|
|
|
@app.get("/health", tags=["Système"])
|
|
async def health():
|
|
return {
|
|
"status": "ok",
|
|
"version": "1.0.0",
|
|
"llm_model": cfg.llm_model,
|
|
"patch": cfg.current_patch,
|
|
}
|
|
|
|
return app
|
|
|
|
|
|
app = create_app()
|
|
|
|
if __name__ == "__main__":
|
|
uvicorn.run(
|
|
"backend.main:app",
|
|
host=cfg.backend_host,
|
|
port=cfg.backend_port,
|
|
reload=cfg.debug,
|
|
log_config=None,
|
|
)
|