Docker Compose with 24+ services: - PostgreSQL (PostGIS), Valkey, MinIO, Qdrant - Vault (PKI/TLS), Nginx (Reverse Proxy) - Backend Core API, Consent Service, Billing Service - RAG Service, Embedding Service - Gitea, Woodpecker CI/CD - Night Scheduler, Health Aggregator - Jitsi (Web/XMPP/JVB/Jicofo), Mailpit Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
102 lines
2.6 KiB
Python
102 lines
2.6 KiB
Python
import logging
|
|
from contextlib import asynccontextmanager
|
|
|
|
import uvicorn
|
|
from fastapi import FastAPI
|
|
from fastapi.middleware.cors import CORSMiddleware
|
|
|
|
from config import settings
|
|
from qdrant_client_wrapper import qdrant_wrapper
|
|
from minio_client_wrapper import minio_wrapper
|
|
|
|
logging.basicConfig(
|
|
level=logging.INFO,
|
|
format="%(asctime)s [%(name)s] %(levelname)s: %(message)s",
|
|
)
|
|
logger = logging.getLogger("rag-service")
|
|
|
|
|
|
@asynccontextmanager
|
|
async def lifespan(app: FastAPI):
|
|
"""Startup: initialise Qdrant collections and MinIO bucket."""
|
|
logger.info("RAG-Service starting up ...")
|
|
try:
|
|
await qdrant_wrapper.init_collections()
|
|
logger.info("Qdrant collections ready")
|
|
except Exception as exc:
|
|
logger.error("Qdrant init failed (will retry on first request): %s", exc)
|
|
|
|
try:
|
|
await minio_wrapper.init_bucket()
|
|
logger.info("MinIO bucket ready")
|
|
except Exception as exc:
|
|
logger.error("MinIO init failed (will retry on first request): %s", exc)
|
|
|
|
yield
|
|
|
|
logger.info("RAG-Service shutting down ...")
|
|
|
|
|
|
app = FastAPI(
|
|
title="BreakPilot RAG Service",
|
|
description="Wraps Qdrant vector search and MinIO document storage for the BreakPilot platform.",
|
|
version="1.0.0",
|
|
lifespan=lifespan,
|
|
)
|
|
|
|
# ---- CORS -----------------------------------------------------------------
|
|
app.add_middleware(
|
|
CORSMiddleware,
|
|
allow_origins=["*"],
|
|
allow_credentials=True,
|
|
allow_methods=["*"],
|
|
allow_headers=["*"],
|
|
)
|
|
|
|
# ---- Routers --------------------------------------------------------------
|
|
from api import router as api_router # noqa: E402
|
|
|
|
app.include_router(api_router)
|
|
|
|
|
|
# ---- Health ---------------------------------------------------------------
|
|
@app.get("/health")
|
|
async def health():
|
|
"""Basic liveness probe."""
|
|
qdrant_ok = False
|
|
minio_ok = False
|
|
|
|
try:
|
|
qdrant_wrapper.client.get_collections()
|
|
qdrant_ok = True
|
|
except Exception:
|
|
pass
|
|
|
|
try:
|
|
minio_wrapper.client.bucket_exists(settings.MINIO_BUCKET)
|
|
minio_ok = True
|
|
except Exception:
|
|
pass
|
|
|
|
status = "healthy" if (qdrant_ok and minio_ok) else "degraded"
|
|
return {
|
|
"status": status,
|
|
"service": "rag-service",
|
|
"version": "1.0.0",
|
|
"dependencies": {
|
|
"qdrant": "ok" if qdrant_ok else "unavailable",
|
|
"minio": "ok" if minio_ok else "unavailable",
|
|
},
|
|
}
|
|
|
|
|
|
# ---- Main -----------------------------------------------------------------
|
|
if __name__ == "__main__":
|
|
uvicorn.run(
|
|
"main:app",
|
|
host="0.0.0.0",
|
|
port=settings.PORT,
|
|
reload=False,
|
|
log_level="info",
|
|
)
|