Implement display artifacts, pricing integrity, draft base and publish preview bundle
This commit is contained in:
162
backend/app/api/routes/admin.py
Normal file
162
backend/app/api/routes/admin.py
Normal file
@@ -0,0 +1,162 @@
|
||||
from fastapi import APIRouter, Depends, Query
|
||||
|
||||
from app.core.config import settings
|
||||
from app.repositories.scheme_artifacts import artifact_exists, list_scheme_artifacts
|
||||
from app.repositories.scheme_versions import get_current_scheme_version
|
||||
from app.repositories.schemes import get_scheme_record_by_scheme_id, list_scheme_records
|
||||
from app.repositories.uploads import get_upload_record_by_upload_id
|
||||
from app.security.auth import require_api_key
|
||||
from app.services.display_regenerator import regenerate_display_artifact
|
||||
from app.services.scheme_validation import build_scheme_validation_report
|
||||
|
||||
router = APIRouter()
|
||||
|
||||
|
||||
@router.get(f"{settings.api_v1_prefix}/admin/schemes/{{scheme_id}}/current/artifacts")
|
||||
async def list_current_scheme_artifacts(
|
||||
scheme_id: str,
|
||||
role: str = Depends(require_api_key),
|
||||
):
|
||||
scheme = await get_scheme_record_by_scheme_id(scheme_id)
|
||||
version = await get_current_scheme_version(
|
||||
scheme_id=scheme.scheme_id,
|
||||
current_version_number=scheme.current_version_number,
|
||||
)
|
||||
rows = await list_scheme_artifacts(scheme_version_id=version.scheme_version_id)
|
||||
|
||||
return {
|
||||
"scheme_id": scheme.scheme_id,
|
||||
"scheme_version_id": version.scheme_version_id,
|
||||
"items": [
|
||||
{
|
||||
"artifact_id": row.artifact_id,
|
||||
"artifact_type": row.artifact_type,
|
||||
"artifact_variant": row.artifact_variant,
|
||||
"status": row.status,
|
||||
"storage_path": row.storage_path,
|
||||
"meta_json": row.meta_json,
|
||||
"created_at": row.created_at.isoformat(),
|
||||
}
|
||||
for row in rows
|
||||
],
|
||||
"total": len(rows),
|
||||
}
|
||||
|
||||
|
||||
@router.get(f"{settings.api_v1_prefix}/admin/schemes/{{scheme_id}}/current/validation")
|
||||
async def validate_current_scheme(
|
||||
scheme_id: str,
|
||||
role: str = Depends(require_api_key),
|
||||
):
|
||||
scheme = await get_scheme_record_by_scheme_id(scheme_id)
|
||||
version = await get_current_scheme_version(
|
||||
scheme_id=scheme.scheme_id,
|
||||
current_version_number=scheme.current_version_number,
|
||||
)
|
||||
|
||||
report = await build_scheme_validation_report(
|
||||
scheme_id=scheme.scheme_id,
|
||||
scheme_version_id=version.scheme_version_id,
|
||||
)
|
||||
|
||||
return {
|
||||
"scheme_id": scheme.scheme_id,
|
||||
"scheme_version_id": version.scheme_version_id,
|
||||
"report": report,
|
||||
}
|
||||
|
||||
|
||||
@router.post(f"{settings.api_v1_prefix}/admin/schemes/{{scheme_id}}/current/display/regenerate")
|
||||
async def regenerate_current_display(
|
||||
scheme_id: str,
|
||||
mode: str = Query(default="passthrough"),
|
||||
role: str = Depends(require_api_key),
|
||||
):
|
||||
scheme = await get_scheme_record_by_scheme_id(scheme_id)
|
||||
version = await get_current_scheme_version(
|
||||
scheme_id=scheme.scheme_id,
|
||||
current_version_number=scheme.current_version_number,
|
||||
)
|
||||
upload = await get_upload_record_by_upload_id(scheme.source_upload_id)
|
||||
|
||||
return await regenerate_display_artifact(
|
||||
scheme_id=scheme.scheme_id,
|
||||
scheme_version_id=version.scheme_version_id,
|
||||
upload_id=upload.upload_id,
|
||||
original_filename=upload.original_filename,
|
||||
sanitized_storage_path=upload.sanitized_storage_path,
|
||||
mode=mode,
|
||||
)
|
||||
|
||||
|
||||
@router.post(f"{settings.api_v1_prefix}/admin/display/backfill")
|
||||
async def bulk_backfill_display_artifacts(
|
||||
mode: str = Query(default="passthrough"),
|
||||
limit: int = Query(default=100, ge=1, le=1000),
|
||||
only_missing: bool = Query(default=True),
|
||||
role: str = Depends(require_api_key),
|
||||
):
|
||||
schemes = await list_scheme_records(limit=limit, offset=0)
|
||||
|
||||
processed: list[dict] = []
|
||||
skipped: list[dict] = []
|
||||
failed: list[dict] = []
|
||||
|
||||
for scheme in schemes:
|
||||
try:
|
||||
version = await get_current_scheme_version(
|
||||
scheme_id=scheme.scheme_id,
|
||||
current_version_number=scheme.current_version_number,
|
||||
)
|
||||
|
||||
if only_missing:
|
||||
exists = await artifact_exists(
|
||||
scheme_version_id=version.scheme_version_id,
|
||||
artifact_type="display_svg",
|
||||
artifact_variant=mode,
|
||||
)
|
||||
if exists:
|
||||
skipped.append(
|
||||
{
|
||||
"scheme_id": scheme.scheme_id,
|
||||
"scheme_version_id": version.scheme_version_id,
|
||||
"reason": "artifact already exists",
|
||||
}
|
||||
)
|
||||
continue
|
||||
|
||||
upload = await get_upload_record_by_upload_id(scheme.source_upload_id)
|
||||
result = await regenerate_display_artifact(
|
||||
scheme_id=scheme.scheme_id,
|
||||
scheme_version_id=version.scheme_version_id,
|
||||
upload_id=upload.upload_id,
|
||||
original_filename=upload.original_filename,
|
||||
sanitized_storage_path=upload.sanitized_storage_path,
|
||||
mode=mode,
|
||||
)
|
||||
processed.append(
|
||||
{
|
||||
"scheme_id": scheme.scheme_id,
|
||||
"scheme_version_id": version.scheme_version_id,
|
||||
"artifact_variant": result["artifact_variant"],
|
||||
}
|
||||
)
|
||||
except Exception as exc:
|
||||
failed.append(
|
||||
{
|
||||
"scheme_id": scheme.scheme_id,
|
||||
"reason": f"{exc.__class__.__name__}: {exc}",
|
||||
}
|
||||
)
|
||||
|
||||
return {
|
||||
"mode": mode,
|
||||
"limit": limit,
|
||||
"only_missing": only_missing,
|
||||
"processed_count": len(processed),
|
||||
"skipped_count": len(skipped),
|
||||
"failed_count": len(failed),
|
||||
"processed": processed,
|
||||
"skipped": skipped,
|
||||
"failed": failed,
|
||||
}
|
||||
Reference in New Issue
Block a user