Allow heading tags (h1-h6) in ContentSanitizer so news editor headings render
This commit is contained in:
100
services/enhance-worker/app/main.py
Normal file
100
services/enhance-worker/app/main.py
Normal file
@@ -0,0 +1,100 @@
|
||||
from __future__ import annotations
|
||||
|
||||
from contextlib import suppress
|
||||
|
||||
from fastapi import Depends, FastAPI, HTTPException, Request, status
|
||||
from fastapi.responses import FileResponse, JSONResponse
|
||||
|
||||
from .config import Settings, get_settings
|
||||
from .image_io import (
|
||||
cleanup_expired_files,
|
||||
delete_temp_file,
|
||||
download_source_image,
|
||||
ensure_directories,
|
||||
resolve_result_path,
|
||||
save_output_image,
|
||||
)
|
||||
from .schemas import HealthResponse, UpscaleRequest, UpscaleResponse
|
||||
from .security import verify_bearer_token
|
||||
from .upscaler import UpscaleEngineUnavailable, build_upscaler
|
||||
|
||||
|
||||
def create_app(settings: Settings | None = None) -> FastAPI:
|
||||
app = FastAPI(title="skinbase-enhance-worker", version="1.0.0")
|
||||
resolved_settings = settings or get_settings()
|
||||
ensure_directories(resolved_settings)
|
||||
cleanup_expired_files(resolved_settings)
|
||||
app.state.settings = resolved_settings
|
||||
app.state.upscaler = build_upscaler(resolved_settings)
|
||||
|
||||
@app.get("/health", response_model=HealthResponse)
|
||||
def health() -> HealthResponse:
|
||||
engine_health = app.state.upscaler.health()
|
||||
|
||||
with suppress(Exception):
|
||||
cleanup_expired_files(app.state.settings)
|
||||
|
||||
return HealthResponse(
|
||||
status=engine_health.status,
|
||||
service="skinbase-enhance-worker",
|
||||
engine=engine_health.engine,
|
||||
device=engine_health.device,
|
||||
models_loaded=engine_health.models_loaded,
|
||||
max_input_width=app.state.settings.max_input_width,
|
||||
max_input_height=app.state.settings.max_input_height,
|
||||
max_output_width=app.state.settings.max_output_width,
|
||||
max_output_height=app.state.settings.max_output_height,
|
||||
realesrgan=engine_health.details.get("realesrgan"),
|
||||
)
|
||||
|
||||
@app.post("/v1/upscale", response_model=UpscaleResponse)
|
||||
def upscale(payload: UpscaleRequest, request: Request, _: None = Depends(verify_bearer_token)):
|
||||
cleanup_expired_files(app.state.settings)
|
||||
downloaded = None
|
||||
|
||||
try:
|
||||
downloaded = download_source_image(payload.source_url, app.state.settings)
|
||||
result = app.state.upscaler.upscale(downloaded, payload.scale, payload.mode, payload.output_format)
|
||||
stored = save_output_image(result.image, payload.output_format, app.state.settings, payload.job_id)
|
||||
|
||||
return UpscaleResponse(
|
||||
success=True,
|
||||
job_id=payload.job_id,
|
||||
output_url=str(request.base_url).rstrip("/") + f"/v1/results/{stored.filename}",
|
||||
width=stored.width,
|
||||
height=stored.height,
|
||||
filesize=stored.filesize,
|
||||
mime=stored.mime,
|
||||
metadata=result.metadata,
|
||||
)
|
||||
except HTTPException as exc:
|
||||
return JSONResponse(status_code=exc.status_code, content={"success": False, "error": exc.detail})
|
||||
except UpscaleEngineUnavailable as exc:
|
||||
return JSONResponse(status_code=status.HTTP_503_SERVICE_UNAVAILABLE, content={"success": False, "error": str(exc)})
|
||||
finally:
|
||||
delete_temp_file(downloaded.path if downloaded is not None else None)
|
||||
|
||||
@app.get("/v1/results/{filename}")
|
||||
def result(filename: str):
|
||||
path = resolve_result_path(app.state.settings, filename)
|
||||
|
||||
if not path.exists() or not path.is_file():
|
||||
raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="Not found")
|
||||
|
||||
return FileResponse(path)
|
||||
|
||||
@app.delete("/v1/results/{filename}")
|
||||
def delete_result(filename: str, _: None = Depends(verify_bearer_token)):
|
||||
path = resolve_result_path(app.state.settings, filename)
|
||||
|
||||
if not path.exists() or not path.is_file():
|
||||
return {"success": True, "deleted": False}
|
||||
|
||||
path.unlink(missing_ok=True)
|
||||
|
||||
return {"success": True, "deleted": True}
|
||||
|
||||
return app
|
||||
|
||||
|
||||
app = create_app()
|
||||
Reference in New Issue
Block a user