feat(metrics): C3 — Prometheus counters for L0/L1/format-loss/retry
All checks were successful
Deploy to Production / Build and Deploy (push) Successful in 2m30s
All checks were successful
Deploy to Production / Build and Deploy (push) Successful in 2m30s
This commit is contained in:
@@ -48,6 +48,13 @@ def run_l0_check(
|
||||
issues={"internal_error": 1},
|
||||
)
|
||||
|
||||
# Best-effort import of metrics; never let it break the check.
|
||||
try:
|
||||
from middleware.metrics import record_l0_result, record_l0_error
|
||||
except Exception:
|
||||
record_l0_result = None
|
||||
record_l0_error = None
|
||||
|
||||
try:
|
||||
result = evaluate_document(source_chunks, translated_chunks, target_lang)
|
||||
except Exception as e:
|
||||
@@ -60,6 +67,11 @@ def run_l0_check(
|
||||
error_type=type(e).__name__,
|
||||
elapsed_ms=elapsed_ms,
|
||||
)
|
||||
if record_l0_error:
|
||||
try:
|
||||
record_l0_error(file_type=file_extension or "unknown")
|
||||
except Exception:
|
||||
pass
|
||||
return empty
|
||||
|
||||
elapsed_ms = round((time.time() - start) * 1000, 2)
|
||||
@@ -75,6 +87,14 @@ def run_l0_check(
|
||||
issues=result.issues,
|
||||
elapsed_ms=elapsed_ms,
|
||||
)
|
||||
if record_l0_result:
|
||||
try:
|
||||
record_l0_result(
|
||||
passed=bool(result.passed),
|
||||
file_type=file_extension or "unknown",
|
||||
)
|
||||
except Exception:
|
||||
pass
|
||||
return result
|
||||
|
||||
|
||||
@@ -145,6 +165,7 @@ async def run_l1_check(
|
||||
reason="insufficient_chunks_or_all_flagged",
|
||||
chunk_count=len(source_chunks),
|
||||
)
|
||||
_record_l1_metric(verdict="skip", model="none")
|
||||
return skip
|
||||
|
||||
# Get the judge
|
||||
@@ -157,6 +178,7 @@ async def run_l1_check(
|
||||
job_id=job_id,
|
||||
reason="no_judge_configured",
|
||||
)
|
||||
_record_l1_metric(verdict="skip", model="none")
|
||||
return skip
|
||||
|
||||
# Get the language name for the prompt
|
||||
@@ -173,6 +195,7 @@ async def run_l1_check(
|
||||
error=str(e)[:200],
|
||||
error_type=type(e).__name__,
|
||||
)
|
||||
_record_l1_metric(verdict="error", model="unknown")
|
||||
return L1Result(
|
||||
verdict="skip",
|
||||
chunks_evaluated=0, chunks_passed=0, chunks_failed=0,
|
||||
@@ -195,9 +218,46 @@ async def run_l1_check(
|
||||
cost_estimate_usd=result.cost_estimate_usd,
|
||||
log_only=log_only,
|
||||
)
|
||||
|
||||
# Record Prometheus metric (best-effort, never breaks the job)
|
||||
duration_s = None
|
||||
if result.elapsed_ms is not None:
|
||||
try:
|
||||
duration_s = float(result.elapsed_ms) / 1000.0
|
||||
except Exception:
|
||||
duration_s = None
|
||||
_record_l1_metric(
|
||||
verdict=result.verdict or "skip",
|
||||
model=result.model_used or "unknown",
|
||||
duration_seconds=duration_s,
|
||||
cost_usd=result.cost_estimate_usd,
|
||||
)
|
||||
return result
|
||||
|
||||
|
||||
def _record_l1_metric(
|
||||
verdict: str,
|
||||
model: str = "unknown",
|
||||
duration_seconds: float = None,
|
||||
cost_usd: float = None,
|
||||
) -> None:
|
||||
"""Best-effort Prometheus metric emission for L1.
|
||||
|
||||
Never raises — if the metrics module fails to import or the
|
||||
counter is unavailable, we silently skip.
|
||||
"""
|
||||
try:
|
||||
from middleware.metrics import record_l1_verdict
|
||||
record_l1_verdict(
|
||||
verdict=verdict,
|
||||
model=model,
|
||||
duration_seconds=duration_seconds,
|
||||
cost_usd=cost_usd,
|
||||
)
|
||||
except Exception:
|
||||
pass
|
||||
|
||||
|
||||
def make_judge_from_env_safe() -> Optional[LLMJudge]:
|
||||
"""Read env vars and build a judge, or return None if not configured.
|
||||
|
||||
|
||||
Reference in New Issue
Block a user