QMetaRam / backend /brain_api.py
metarm's picture
Upload folder using huggingface_hub (part 4)
945aae0 verified
Raw History Blame Contribute Delete
5.46 kB
import os
import logging
from fastapi import FastAPI, Depends, HTTPException, Header
from qkernel import QKernel
from qkernel.auth import verify_token
from qkernel.memory import MemoryEngine
from qkernel.policy import PolicyEngine
from qkernel.observability import ObservabilityBrain
from qkernel.event_bus import EventBus
from qkernel.healing import SelfHealingEngine
from qkernel.executors import ChatExecutor, MemoryExecutor, ToolExecutor
from qkernel.queue import PersistentQueue
logging.basicConfig(level=logging.INFO)
logger = logging.getLogger("brain_api")
app = FastAPI(title="Q Brain API")
_queue = PersistentQueue()
def require_auth(authorization: str | None = Header(None)) -> dict:
if not authorization:
raise HTTPException(status_code=401, detail="missing_authorization")
token = authorization.removeprefix("Bearer ")
payload = verify_token(token)
if payload is None:
raise HTTPException(status_code=401, detail="invalid_or_expired_token")
return payload
def optional_auth(authorization: str | None = Header(None)) -> dict | None:
if not authorization:
return None
token = authorization.removeprefix("Bearer ")
return verify_token(token)
def build_kernel() -> QKernel:
kernel = QKernel()
from qkernel.policy import PolicyRule
kernel.policy.add_rule(PolicyRule(
name="boost_chat",
condition=lambda e: e.get("type") == "chat",
action=lambda e, ctx: setattr(ctx, "priority_boost", 5) or ctx,
))
kernel.policy.add_rule(PolicyRule(
name="long_message_route",
condition=lambda e: len(e.get("message", "")) > 500,
action=lambda e, ctx: setattr(ctx, "route_override", "brain") or ctx,
))
kernel.policy.add_rule(PolicyRule(
name="route_memory",
condition=lambda e: e.get("type") == "memory",
action=lambda e, ctx: setattr(ctx, "route_override", "memory") or ctx,
))
kernel.policy.add_rule(PolicyRule(
name="route_tool",
condition=lambda e: e.get("type") == "tool",
action=lambda e, ctx: setattr(ctx, "route_override", "tool") or ctx,
))
kernel.policy.add_rule(PolicyRule(
name="route_voice",
condition=lambda e: e.get("type") == "voice",
action=lambda e, ctx: setattr(ctx, "route_override", "brain") or ctx,
))
chat = ChatExecutor()
memory = MemoryExecutor()
tool = ToolExecutor()
tool.register("echo", lambda p: {"echo": p.get("text", "")})
tool.register("now", lambda p: {"utc_ms": __import__("time").time() * 1000})
kernel.register_service("brain", chat)
kernel.register_service("voice", chat)
kernel.register_service("network", chat)
kernel.register_service("chat", chat)
kernel.register_service("memory", memory)
kernel.register_service("tool", tool)
return kernel
async def _run_task(event: dict, auth: dict | None):
kernel = build_kernel()
user_id = (auth or {}).get("user_id", "anonymous")
event.setdefault("user_id", user_id)
result = await kernel.handle(event)
return result
@app.get("/health")
async def health():
return {
"status": "ok",
"brain": "q-core-v13",
"openai": bool(os.getenv("OPENAI_API_KEY", "")),
"groq": bool(os.getenv("GROQ_API_KEY", "")),
"stripe": bool(os.getenv("STRIPE_SECRET_KEY", "")),
"queue": _queue.stats(),
}
@app.post("/brain")
async def brain(request: dict, auth: dict | None = Depends(optional_auth)):
return await _run_task(
{
"type": "chat",
"message": request.get("message", ""),
"context": request.get("context", []),
"model": request.get("model", "fast"),
},
auth,
)
@app.post("/v13/task")
async def v13_task(request: dict, auth: dict | None = Depends(optional_auth)):
task_type = request.get("type", "chat")
payload = request.get("payload") or {}
mode = request.get("mode", "sync")
if mode != "async":
return await _run_task({"type": task_type, **payload}, auth)
task_id = _queue.enqueue(task_type, {"auth_user": (auth or {}).get("user_id"), **payload})
return {"task_id": task_id, "status": "queued", "mode": "async"}
@app.get("/v13/task/{task_id}")
async def v13_task_status(task_id: str, auth: dict | None = Depends(optional_auth)):
row = _queue.get(task_id)
if row is None:
raise HTTPException(status_code=404, detail="task_not_found")
return row
@app.post("/v13/task/process")
async def v13_process_queue(auth: dict | None = Depends(optional_auth)):
processed = []
while True:
task = _queue.dequeue()
if task is None:
break
result = await _run_task(
{"type": task["type"], **task["payload"]}, auth
)
if result.get("error"):
_queue.fail(task["id"], result["error"])
else:
_queue.complete(task["id"], result)
processed.append({"id": task["id"], "result": result})
return {"processed": processed, "stats": _queue.stats()}
@app.get("/v13/queue/stats")
async def v13_queue_stats(auth: dict | None = Depends(optional_auth)):
return _queue.stats()
@app.post("/event")
async def handle_event(event: dict, auth: dict | None = Depends(optional_auth)):
return await _run_task(event, auth)
if __name__ == "__main__":
import uvicorn
uvicorn.run(app, host="0.0.0.0", port=8001)