Skip to content

fix(inference): stop dumping raw JSON into description on parse failure#66

Merged
Liuhaai merged 1 commit into
mainfrom
fix/crop-describe-json-fallback
May 8, 2026
Merged

fix(inference): stop dumping raw JSON into description on parse failure#66
Liuhaai merged 1 commit into
mainfrom
fix/crop-describe-json-fallback

Conversation

@Liuhaai

@Liuhaai Liuhaai commented May 8, 2026

Copy link
Copy Markdown
Collaborator

Summary

When the VLM emits a SCENE_SCHEMA-shaped JSON but json.loads fails (truncation, no closing brace, or malformed), _crop_describe_inner was leaking a 300-char raw JSON slice into description — observable as DB rows like:

{
  "activity_level": "moderate",
  "people_count": 0,
  ...
  "is_know

(ending mid-token at exactly 300 chars). The downstream substring-match fallback then guessed activity_level from random words inside the JSON dump, producing rows where the structured columns were inferred from JSON literals rather than the model's actual output.

Changes

  • Recognize lowercase summary (the SCENE_SCHEMA contract) in the entities branch so schema-mode outputs produce a clean description instead of the "0 people, N vehicles: parked, …" parts template. summary is read without pop so callers re-parsing entities still see it.
  • Stop dumping raw JSON in the final fallback. When json.loads fails, or when text starts with { but has no closing } (truncation), return desc = "" instead of clean[:300].
  • Add diagnostic warnings with text length + head/tail bytes so the truncation-vs-malformed root cause is observable from logs once deployed.
  • Plain prose (no leading {) keeps the existing 300-char slice behavior unchanged.

Test plan

  • All 6 existing tests in test_inference_router.py pass unchanged.
  • New: SCENE_SCHEMA summary populates description, summary preserved in entities.
  • New: truncated JSON (no closing brace) → desc="", warning logged with truncation suspected.
  • New: malformed JSON (trailing comma) → desc="", warning logged with JSON parse failed.
  • New: plain prose still uses the 300-char slice.
  • After deploy: confirm crop_describe: JSON parse failed / truncation suspected warnings appear in /tmp/vlm.log and pin the root cause (likely max_tokens=512 default for SCENE_SCHEMA payloads with multi-vehicle arrays).

Notes

This addresses the symptom only. The next step is using the new diagnostic logs to determine the failure mode and either bump max_tokens (currently engine.config.max_tokens=512 and not overridden in _crop_describe_inner) or fix the specific malformation. ~500 existing JSON-string description rows in prod are not backfilled by this change.

🤖 Generated with Claude Code

When the VLM emitted a SCENE_SCHEMA-shaped JSON but trio-core's
json.loads failed (truncation, no closing brace, malformed), the
fallback `desc = clean[:300]` was leaking 300-char raw JSON slices
into observations.description, ending mid-token. The downstream
substring-match fallback then guessed activity_level from random
words inside the JSON dump (e.g. "moderate" appearing as a value).

- Recognize lowercase `summary` (SCENE_SCHEMA) in the entities
  branch so schema-mode outputs produce a clean description instead
  of the "0 people, N vehicles: parked, …" parts template.
- On JSON parse failure (or JSON-shaped text with no closing brace),
  return empty desc rather than raw garbage and emit a warning that
  includes text length plus head/tail bytes so the truncation-vs-
  malformed root cause is observable.
- Plain prose (no leading `{`) keeps the existing 300-char slice
  behavior unchanged.

Tests cover: SCENE_SCHEMA summary path, truncated JSON, malformed
JSON, and plain prose.
@Liuhaai Liuhaai force-pushed the fix/crop-describe-json-fallback branch from 0911a42 to 3d1c063 Compare May 8, 2026 22:25
@Liuhaai Liuhaai merged commit 43e0a1a into main May 8, 2026
7 checks passed
@Liuhaai Liuhaai deleted the fix/crop-describe-json-fallback branch May 8, 2026 22:28
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.

1 participant