File size: 1,824 Bytes
48ebf82
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
"""FastAPI entrypoint for the KORA AI backend."""

from __future__ import annotations

import logging
from contextlib import asynccontextmanager

from fastapi import FastAPI

from app.routes.chat import router as chat_router
from app.services.model_service import ModelService
from app.services.prompt_service import PromptService
from app.utils.config import settings


def configure_logging() -> None:
    """Configure centralized application logging."""
    logging.basicConfig(
        level=getattr(logging, settings.log_level.upper(), logging.INFO),
        format="%(asctime)s | %(levelname)s | %(name)s | %(message)s",
    )


@asynccontextmanager
async def lifespan(app: FastAPI):
    """Initialize shared services for app lifecycle."""
    configure_logging()

    prompt_service = PromptService(settings=settings)
    model_service = ModelService(settings=settings)

    app.state.prompt_service = prompt_service
    app.state.model_service = model_service

    await model_service.startup()
    logging.getLogger(__name__).info("KORA backend initialized")

    try:
        yield
    finally:
        await model_service.shutdown()


app = FastAPI(
    title=settings.app_name,
    version="1.0.0",
    lifespan=lifespan,
)

app.include_router(chat_router)


@app.get("/healthz", tags=["health"])
async def healthz() -> dict[str, str]:
    """Liveness/readiness probe for orchestrators and HF Spaces."""
    return {"status": "ok", "service": settings.app_name}


@app.get("/", tags=["root"])
async def root() -> dict[str, str]:
    """Simple root route so HF Space URL does not return 404."""
    return {
        "service": settings.app_name,
        "status": "ok",
        "health": "/healthz",
        "chat": "/v1/chat/completions",
    }