feat: S07 operations hardening and OpenConnector integration
Deploy Claude Dev (Dev) / deploy-claude-dev-dev (push) Failing after 2m3s
Deploy Dashboard (Main) / Backend Tests (push) Successful in 3m7s
Deploy Dashboard (Main) / Frontend Tests (push) Successful in 6s
Deploy Dashboard (Main) / Deploy to Production (push) Has been cancelled
Deploy Dashboard (Main) / Build Main Image (push) Has been cancelled
Deploy Dashboard (Dev) / Backend Tests (push) Successful in 1m18s
Deploy Dashboard (Dev) / Frontend Tests (push) Successful in 51s
Deploy Dashboard (Dev) / Build Dev Image (push) Successful in 1m42s
Deploy Dashboard (Dev) / Deploy to Dev (push) Successful in 58s

This commit is contained in:
Gan, Jimmy
2026-07-11 04:42:05 +08:00
parent 0348dd1eab
commit 8faba05b5b
8 changed files with 93 additions and 4 deletions
+44 -2
View File
@@ -143,12 +143,13 @@ async def security_headers(request: Request, call_next):
# Audit logger
import os
from logging.handlers import RotatingFileHandler
_audit_log_path = os.path.join(VOLUME_ROOT, "docker/nas-dashboard/audit.log")
os.makedirs(os.path.dirname(_audit_log_path), exist_ok=True)
_audit_logger = logging.getLogger("audit")
_audit_logger.setLevel(logging.INFO)
_audit_handler = logging.FileHandler(_audit_log_path)
_audit_handler = RotatingFileHandler(_audit_log_path, maxBytes=10 * 1024 * 1024, backupCount=5)
_audit_handler.setFormatter(logging.Formatter("%(message)s"))
_audit_logger.addHandler(_audit_handler)
_audit_logger.propagate = False
@@ -229,7 +230,48 @@ async def monitor_containers():
@app.get("/api/health")
async def health():
return {"status": "ok"}
import shutil
import docker
import logging
from fastapi.responses import JSONResponse
from fastapi import status
from db import opc_db
from config import DOCKER_HOST, VOLUME_ROOT
db_ok = False
try:
pool = await opc_db.get_pool()
async with pool.acquire() as conn:
await conn.execute("SELECT 1")
db_ok = True
except Exception as e:
logging.getLogger(__name__).error("Health check DB connection failed: %s", e)
docker_ok = False
try:
client = docker.DockerClient(base_url=DOCKER_HOST)
docker_ok = client.ping()
except Exception as e:
logging.getLogger(__name__).error("Health check Docker connection failed: %s", e)
free_gb = 0.0
try:
total, used, free = shutil.disk_usage(VOLUME_ROOT)
free_gb = round(free / (1024 ** 3), 2)
except Exception as e:
logging.getLogger(__name__).error("Health check disk usage failed: %s", e)
status_code = status.HTTP_200_OK if (db_ok and docker_ok) else status.HTTP_503_SERVICE_UNAVAILABLE
return JSONResponse(
status_code=status_code,
content={
"status": "ok" if (db_ok and docker_ok) else "degraded",
"db": "connected" if db_ok else "disconnected",
"docker": "healthy" if docker_ok else "unhealthy",
"disk": {"free_gb": free_gb}
}
)
@app.get("/api/client-ip")