Skip to content

fix(interface): flag rows whose coverage judge finds missed entities - #356

Merged
binaryaaron merged 3 commits into
mainfrom
aagonzales/bugfix/evaluate-coverage-review-flag
Nov 5, 2026
Merged

binaryaaron merged 3 commits into
mainfrom
aagonzales/bugfix/evaluate-coverage-review-flag

Conversation

@binaryaaron

@binaryaaron binaryaaron commented Nov 2, 2026 •

Copy link
Copy Markdown
Collaborator

In Rewrite mode, Anonymizer.evaluate() now sets needs_human_review to True on any record whose coverage judge reports a non-empty missed_entities. Until now the judge wrote entity_coverage and missed_entities and left the flag alone, so a name detection never caught could reach the output verbatim with needs_human_review False.

Why

In a 25-record run with a local open-weight model at low reasoning effort, GLiNER and the LLM augmenter both missed two subject surnames, which survived the rewrite verbatim. The coverage judge in evaluate() caught both, but nothing acted on it: 7 of 25 records had a non-empty missed_entities, 4 of them unflagged. A hosted model had found the same surnames every time, so the gap depends on the augmenter's model and effort, and the flag is where a user looks.

What changes

After the coverage judge runs in evaluate(), rows whose missed_entities is a non-empty list get needs_human_review = True. Empty lists, None and NaN leave the flag unchanged; frames without the column (Replace mode) are returned as is; the Boolean dtype is preserved; the run() result is not modified. docs/concepts/rewrite.md, docs/concepts/evaluation.md, docs/troubleshooting.md and the rewrite-evaluation devnote each gain one sentence naming the new cause.

13 source lines. No public signature, column or default changes; detection, the rewrite workflow and the repair loop are untouched.

Checks

  • ruff format --check, ruff check and make typecheck pass; make test: 1,587 passed.
  • New parametrized test in tests/interface/test_anonymizer_interface.py with a stubbed EntityCoverageWorkflow through the real evaluate() path: a missed entity flags the record; an already-flagged record stays flagged; no missed entities and an unavailable coverage result leave the flag unchanged. Each case asserts the boolean dtype and untouched run() flags. The first case fails without the fix.
  • The coverage workflow normalizes its output to Python lists before the interface, including through the Arrow-backed dataset reader, so the list check is sound.

For reviewers

🤖 Generated with Claude Code

@binaryaaron
binaryaaron requested a review from a team as a code owner November 2, 2026 21:15
@greptile-apps

greptile-apps Bot commented Nov 2, 2026 •

Copy link
Copy Markdown
Contributor

RetriggerView in GreptileConfidence Score: 5/5

[Medium impact] The PR appears safe to merge; no actionable issues were found.

Summary

Rewrite-mode evaluate() now raises needs_human_review when the coverage judge reports missed entities.

  • Rewrite evaluation flags rows when the coverage judge finds missed entities.

Reviews (5) · Last reviewed commit: "docs(evaluation): note that an unflagged..." · Reviewed by Greptile

@lipikaramaswamy

Copy link
Copy Markdown
Collaborator

cc @memadi-nv could you review?

@memadi-nv memadi-nv left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for catching this edge case Aaron, LGTM! Just added some clarification note to the docs as a suggestion.

binaryaaron and others added 3 commits November 5, 2026 16:14
In Rewrite mode, Anonymizer.evaluate() now sets needs_human_review=True
on any row whose entity coverage judge reports non-empty missed_entities.
Rows with no missed entities or unavailable coverage keep their flag, and
the run() output is unchanged.

🤖 Generated with Claude Code

Co-Authored-By: Claude <noreply@anthropic.com>
Signed-off-by: Aaron Gonzales <aagonzales@nvidia.com>
Size each missed_entities cell with .str.len() and set the review flag
with mask() instead of a per-cell isinstance check and a copy/.loc
update. Coverage cells are always Python lists by this point, so the
flags and the needs_human_review dtype are unchanged.

🤖 Generated with Claude Code

Co-Authored-By: Claude <noreply@anthropic.com>
Signed-off-by: Aaron Gonzales <aagonzales@nvidia.com>
needs_human_review=False is not a guarantee: coverage feeds the flag
only when evaluate() runs, and detection and the coverage judge can
both miss entities.

🤖 Generated with Claude Code

Co-Authored-By: Claude <noreply@anthropic.com>
Signed-off-by: Aaron Gonzales <aagonzales@nvidia.com>
@binaryaaron
binaryaaron force-pushed the aagonzales/bugfix/evaluate-coverage-review-flag branch from ad5b287 to 9436fee Compare November 5, 2026 16:16
@binaryaaron
binaryaaron merged commit b29cb69 into main Nov 5, 2026
16 checks passed
@binaryaaron
binaryaaron deleted the aagonzales/bugfix/evaluate-coverage-review-flag branch November 5, 2026 16:21
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants