LLM as a judge is the practice of using a model to grade outputs: an agent's run, a RAG answer, a summary, a CI test transcript. It is how teams evaluate AI systems at a scale humans cannot review. The catch is that a judge is a measuring instrument, and an instrument that writes essays is a noisy one. This page explains the problem, the common approaches and how to build typed, low-variance judges with Jev.
Why evaluation is the bottleneck
Every change to a prompt, model, retriever or tool can improve one thing and break another. Without evals, teams ship by vibes. With human review only, they ship slowly. LLM judges fill the gap: they grade thousands of runs overnight, watch production traffic and block bad answers before users see them.
What makes a judge useful is not eloquence but consistency. If the same input gets a 7 today and a 5 tomorrow, a real two-point regression is invisible. A good judge has:
- A fixed rubric whose levels are described in words.
- Bounded output: one of the rubric levels, never "7.5" or "N/A".
- Low variance between runs on the same input.
- Enough speed and low cost to run on every case and in CI.
Common approaches and trade-offs
Reference metrics (exact match, BLEU, ROUGE, embedding similarity) are cheap and deterministic but measure overlap with a reference answer, not correctness or helpfulness. Many tasks have no single reference.
Prompted chat-model judges are flexible and read like a reviewer. They are also expensive per case, their numeric scores drift with phrasing, they sometimes return off-scale values or malformed JSON, and they are biased by length and position.
Pairwise preference judges compare two outputs. Good for A/B decisions, less useful for absolute monitoring and gates.
Human review remains the ground truth. It is slow and costly, which is exactly why it should be spent on building and auditing the eval set rather than grading every run.
How Jev's typed decisions fit
Jev, from TypeSafe AI, answers typed questions about a state. For evals:
- Score places the output on your ordered rubric of 2 to 10 levels, for example
fails_task→partially→fully_meets. The answer is always a level, and probabilities across levels show how decisive the judgment was. - Choice gives a categorical verdict such as
pass,retry,review,block— up to 255 options. - Noul gives a 0–1 probability for a binary check:
cites_unsupported_fact,followed_instructions,tool_misuse.
There is no prose to parse and no off-scale answers. TypeSafe reports 70–500 ms per request and Jev 1.13 is $0.042 per million input tokens on Flatkey with output free, which makes per-case grading and CI gates affordable. Jev 1.13 and 1.14 are both available; pin one version for a given eval suite.
Eval pipeline design
- Write the rubric first. One question per dimension (task success, grounding, safety, tone). Describe each level in a sentence a human reviewer would agree with.
- Put the evidence in the state. The task, the output and — for grounding — the retrieved passages. The judge only knows what you send.
- Label a seed set. 100–300 cases graded by people. Measure judge agreement per dimension before trusting it.
- Run the judge in batch and in CI. Aggregate level distributions, not just means. Fail a build when the share of low levels rises beyond a threshold.
- Gate online where it pays. For RAG, a low grounding probability can trigger a retry with more context or a fallback answer.
The agent eval judge, grounding and hallucination judge, RAG gates, CI/CD AI quality gate and test selection pages each give a ready schema.
Choosing question types for a rubric
| Eval dimension | Question type | Example levels or options |
|---|---|---|
| Task success | Score | failed → partial → mostly → fully_met |
| Grounded in sources | Noul | probability the answer is fully supported |
| Unsupported claim present | Noul | probability from 0 to 1 |
| CI verdict | Choice | pass, retry, review, block |
| Tests to run | Choice / Noul | one Noul per test suite |
Keep dimensions independent: one question should not depend on another's answer, so they can all go in a single request. Prefer a few well-described levels over many vague ones; a four-level scale that reviewers agree on beats a ten-level scale they do not.
Pitfalls and evaluation tips
- Judge drift. Changing the rubric wording or the model version changes the instrument. Re-measure agreement and keep old scores separate.
- Missing evidence. A grounding judge without the source passages is guessing. Truncation silently drops evidence; check sizes.
- Averaging hides failures. Track the share of cases at the lowest levels, not only the mean score.
- Confident mistakes. A high-confidence verdict can still be wrong. Sample confident passes for human audit, not just low-confidence ones.
- Gaming. If the system being evaluated sees the rubric, it can learn to please the judge. Keep the judge state separate from the generator prompt.
When not to use Jev
When the check is exact — the code compiles, the JSON validates, the answer equals the expected number — use the exact check. When you need written feedback for a reviewer, use a text model for that part. And do not use any judge, Jev included, as a substitute for an initial human-labelled set.
Glossary
- Rubric: the ordered levels a judge grades against.
- Grounding: whether an answer is supported by the provided sources.
- Agreement: how often the judge matches human labels on the same cases.
- Regression gate: a CI step that fails when eval results get worse.
- Variance: how much a judge's answer changes across repeated runs on the same input.
Open any use case below for a live demo and copyable eval code.
LLM-as-a-Judge & Evals use cases
EvalJudge agent runs with low-variance typed scores
Score agent runs with bounded Choice, Score and Noul questions so your eval loop behaves like a measurement instrument—not another chatbot writing long chain-of-thought.
See the workflow →
GroundingJudge claim grounding against sources with pass / block / review
Check claims against source evidence with Choice pass / block / review, a Score for evidence strength, and a Noul for needs-human—so grounding gates stay typed, cheap, and calibratable.
See the workflow →
RAG / Evidence gatesGate retrieved evidence before the generator runs
After retrieval and before generation, ask Jev whether each chunk is relevant, whether evidence is enough to answer, and whether to generate, retrieve more, discard, or review—so RAG pipelines stop feeding noise into the LLM.
See the workflow →
CI / QADecide PASS / RETRY / REVIEW / BLOCK from AI test evidence in CI
Turn AI test evidence into a typed PASS / RETRY / REVIEW / BLOCK decision in CI—plus an evidence-strength Score and needs_human Noul—so the LLM produces evidence, Jev applies judgment, and the pipeline enforces policy.
See the workflow →
CI / Test selectionPick which tests to run first for a given diff
Given a diff and a candidate test, decide run_first, run_later, or skip—with a relevance score and a covers_diff flag—so CI spends the budget on tests that actually protect the change.
See the workflow →
Risk agent / Typed triageGate a risk sweep with typed threat, relevance, and severity judgments before any deep dive
A background risk agent searches the web, then asks Jev bounded threat / relevance / severity questions—so a cheap typed judge decides escalate-or-skip while a smaller generative model only writes the briefing.
See the workflow →
Agent observability / Failure triageTag every agent trace with a calibrated failure probability and failure mode, so a low threshold catches almost every failure and only the flagged slice goes to a slower high-precision reviewer
Screen millions of agent traces for reward hacking, hallucinated success and tool misuse. Jev scores every trace cheaply with calibrated probabilities; a low threshold keeps recall high and only flagged traces go to an expensive precision model.
See the workflow →
Code review / RulingsAfter a code-review check raises a finding on a diff hunk, decide whether a ruling a reviewer already made covers that exact hunk, so the finding is exempted, sent to a person, or kept, instead of reappearing on every pull request
A reviewer overruled a code-review finding once. Store that ruling outside the model and ask Jev whether it covers the next diff hunk, so the same finding stops coming back on every pull request.
See the workflow →
Agent harness / Post-run check · also fitsCheck after an agent run whether the real state change matches the business outcome, not just the agent's claims
An agent says the database job succeeded. Ask Jev whether the observed state change actually matches the intended outcome—verified, mismatch, or data loss—instead of trusting an LLM verifier that only checks the agent's own story.
See the workflow →
SEO / GEO audits · also fitsJudge every page and query pair on a site (buyer intent, intent match, chance of being cited by AI assistants, first fix) cheaply enough to run on all URLs every month, then hand only the pages that need work to a writing model
Run an SEO/GEO audit on every page instead of a sample. Jev judges query intent, page match, AI citation chance and the first fix for each URL in one parallel call; an LLM only writes the fixes.
See the workflow →
Agent memory / Write check · also fitsBefore an agent writes a new long-term memory, decide whether the source conversation actually supports it, whether it overstates what the user said, and whether it duplicates an existing memory, so code can save, merge, narrow or drop it instead of storing every guess
Before an agent saves a memory, ask Jev whether the source conversation supports it, whether it reads too much into what was said, and whether it repeats a memory you already have. Code then saves, merges, narrows or drops it.
See the workflow →Copy the code
The request behind Use Jev as an agent-run judge, calling Jev 1.13 on Flatkey. Set FLATKEY_API_KEY and run it as is, then swap in your own state and questions.
curl -sS https://router.flatkey.ai/api/alpha/decisions \
-H "Authorization: Bearer $FLATKEY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "typesafe/jev-1.13",
"state": "Goal: update staging deploy and verify health check returns 200. Agent steps: (1) ran git pull on staging host, (2) restarted the service, (3) claimed \"deploy complete and healthy\". Missing: no curl or health-check command was run; last log line is only the restart. Required verification step was skipped. Retries so far: 0.",
"questions": {
"verdict": {
"type": "choice",
"instructions": "Judge the agent run against the stated goal and required checks.",
"criteria": {
"pass": "The agent completed the goal and met the required verification steps with supporting evidence",
"retry": "The run is incomplete or skipped a required check, but another attempt with the same setup is warranted",
"fail": "The agent clearly missed the goal, violated policy, or produced incorrect or unsafe output",
"inconclusive": "The transcript lacks enough evidence to judge pass or fail"
}
},
"quality": {
"type": "score",
"instructions": "Overall run quality ignoring self-claims of success.",
"criteria": [
"poor",
"fair",
"good",
"excellent"
]
},
"needs_human_review": {
"type": "noul",
"instructions": "A human or chat-model judge should review this run before the score is trusted."
}
}
}'// Node.js 18+ (built-in fetch). Run: FLATKEY_API_KEY=... node jev.mjs
const body = {
"model": "typesafe/jev-1.13",
"state": "Goal: update staging deploy and verify health check returns 200. Agent steps: (1) ran git pull on staging host, (2) restarted the service, (3) claimed \"deploy complete and healthy\". Missing: no curl or health-check command was run; last log line is only the restart. Required verification step was skipped. Retries so far: 0.",
"questions": {
"verdict": {
"type": "choice",
"instructions": "Judge the agent run against the stated goal and required checks.",
"criteria": {
"pass": "The agent completed the goal and met the required verification steps with supporting evidence",
"retry": "The run is incomplete or skipped a required check, but another attempt with the same setup is warranted",
"fail": "The agent clearly missed the goal, violated policy, or produced incorrect or unsafe output",
"inconclusive": "The transcript lacks enough evidence to judge pass or fail"
}
},
"quality": {
"type": "score",
"instructions": "Overall run quality ignoring self-claims of success.",
"criteria": [
"poor",
"fair",
"good",
"excellent"
]
},
"needs_human_review": {
"type": "noul",
"instructions": "A human or chat-model judge should review this run before the score is trusted."
}
}
};
const res = await fetch("https://router.flatkey.ai/api/alpha/decisions", {
method: "POST",
headers: {
Authorization: `Bearer ${process.env.FLATKEY_API_KEY}`,
"Content-Type": "application/json",
},
body: JSON.stringify(body),
});
if (!res.ok) throw new Error(`Jev request failed: ${res.status} ${await res.text()}`);
const { answers, usage } = await res.json();
console.log(JSON.stringify(answers, null, 2), usage);# Python 3.8+ (pip install requests). Run: FLATKEY_API_KEY=... python jev.py
import json, os, requests
body = json.loads(r"""{
"model": "typesafe/jev-1.13",
"state": "Goal: update staging deploy and verify health check returns 200. Agent steps: (1) ran git pull on staging host, (2) restarted the service, (3) claimed \"deploy complete and healthy\". Missing: no curl or health-check command was run; last log line is only the restart. Required verification step was skipped. Retries so far: 0.",
"questions": {
"verdict": {
"type": "choice",
"instructions": "Judge the agent run against the stated goal and required checks.",
"criteria": {
"pass": "The agent completed the goal and met the required verification steps with supporting evidence",
"retry": "The run is incomplete or skipped a required check, but another attempt with the same setup is warranted",
"fail": "The agent clearly missed the goal, violated policy, or produced incorrect or unsafe output",
"inconclusive": "The transcript lacks enough evidence to judge pass or fail"
}
},
"quality": {
"type": "score",
"instructions": "Overall run quality ignoring self-claims of success.",
"criteria": [
"poor",
"fair",
"good",
"excellent"
]
},
"needs_human_review": {
"type": "noul",
"instructions": "A human or chat-model judge should review this run before the score is trusted."
}
}
}""")
res = requests.post(
"https://router.flatkey.ai/api/alpha/decisions",
headers={"Authorization": f"Bearer {os.environ['FLATKEY_API_KEY']}"},
json=body,
timeout=60,
)
res.raise_for_status()
data = res.json()
print(json.dumps(data["answers"], indent=2), data.get("usage"))FAQ
What does LLM-as-a-judge mean?
Using a model to grade the output of another model or agent against criteria, instead of, or alongside, human reviewers. It is used for offline evals, regression tests, online monitoring and gating responses before they reach users.
Why are prose judges hard to use?
A judge that writes a paragraph and then a number gives you a number that drifts with wording, can be outside your scale, and must be parsed. Variance between runs makes small regressions invisible.
Which Jev question types work for evals?
A Score on an ordered rubric (2 to 10 levels described in words) for quality dimensions, a Choice for a categorical verdict such as pass / retry / review / block, and a Noul for a binary check like contains_unsupported_claim, returned as a probability from 0 to 1.
Can Jev detect hallucinations in RAG answers?
It can judge whether an answer is supported by the retrieved passages you include in the state, which is the usual definition of grounding. It does not look anything up itself, so the evidence must be in the request.
Should I trust the judge without human labels?
No. Build a small human-labelled set first and measure agreement. Use the judge to scale that labelling, and re-check agreement whenever you change the rubric or the model version.
Does the judge need to explain its reasoning?
Jev returns typed answers, not rationales. If reviewers need a written explanation, generate it separately with a text model for the cases that fail, and keep the typed verdict as the measurement.
Further reading
Other categories
23 use casesAI Agent GuardrailsGate every agent action, memory write and retry with a cheap, typed allow / review / block decision.
9 use casesLLM RoutingRoute each request to the right model, tool or intent with one fast typed decision.
22 use casesClassification & TriageRoute tickets, issues, reports and applications by category, urgency and review need.
11 use casesStructured Data ExtractionTurn free text into typed columns, matched entities, SQL filters and document splits.
7 use casesSecurity & ComplianceGate invoice payments, validate pentest findings and lint for personal data before it ships.
5 use casesGames & Adaptive UIFast typed decisions for game agents, RTS unit control and interfaces that adapt as users type.Run llm-as-a-judge & evals on real Jev
Every use case above runs live with your own key. Get a Flatkey key for Jev 1.13, or bring an OpenRouter key under Dashboard → BYOK.