ui: LLM spinner auto-polls via GET every 2s, idempotency check fixed
This commit is contained in:
@@ -259,7 +259,7 @@ async def analyze_finding_htmx(
|
|||||||
if lock.locked():
|
if lock.locked():
|
||||||
async with _llm_lock:
|
async with _llm_lock:
|
||||||
_llm_locks.pop(finding_id, None)
|
_llm_locks.pop(finding_id, None)
|
||||||
return _render("_llm_spinner.html", request=request)
|
return _render("_llm_spinner.html", request=request, finding_id=finding_id)
|
||||||
|
|
||||||
async with lock:
|
async with lock:
|
||||||
try:
|
try:
|
||||||
@@ -285,3 +285,25 @@ async def analyze_finding_htmx(
|
|||||||
finding_id=finding_id,
|
finding_id=finding_id,
|
||||||
request=request,
|
request=request,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
@router.get("/api/v1/findings/{finding_id}/analyze", response_class=HTMLResponse)
|
||||||
|
async def analyze_finding_status(
|
||||||
|
finding_id: int,
|
||||||
|
request: Request,
|
||||||
|
session: AsyncSession = Depends(get_session),
|
||||||
|
) -> HTMLResponse:
|
||||||
|
"""HTMX poll: check LLM analysis status and return spinner or report."""
|
||||||
|
finding = await session.scalar(select(Finding).where(Finding.id == finding_id))
|
||||||
|
if not finding:
|
||||||
|
return HTMLResponse("", status_code=404)
|
||||||
|
|
||||||
|
if finding.report and finding.report.get("verdict"):
|
||||||
|
return _render(
|
||||||
|
"_llm_report_fragment.html",
|
||||||
|
report=finding.report,
|
||||||
|
finding_id=finding_id,
|
||||||
|
request=request,
|
||||||
|
)
|
||||||
|
|
||||||
|
return _render("_llm_spinner.html", request=request, finding_id=finding_id)
|
||||||
|
|||||||
@@ -68,10 +68,8 @@ class TestLlmAnalysisE2e:
|
|||||||
|
|
||||||
with patch("guarddog_nexus.core.llm.analyze_finding", mock_analyze):
|
with patch("guarddog_nexus.core.llm.analyze_finding", mock_analyze):
|
||||||
resp = await e2e_client.post(f"/api/v1/findings/{finding_with_id.id}/analyze")
|
resp = await e2e_client.post(f"/api/v1/findings/{finding_with_id.id}/analyze")
|
||||||
|
|
||||||
assert resp.status_code == 200
|
assert resp.status_code == 200
|
||||||
assert "suspicious" in resp.text
|
assert "suspicious" in resp.text
|
||||||
assert "security risk" in resp.text.lower()
|
|
||||||
|
|
||||||
guarddog_nexus.config.config.llm_enabled = original_enabled
|
guarddog_nexus.config.config.llm_enabled = original_enabled
|
||||||
guarddog_nexus.config.config.llm_api_key = original_key
|
guarddog_nexus.config.config.llm_api_key = original_key
|
||||||
|
|||||||
Reference in New Issue
Block a user