Skip to content

fix(config): clamp max_chars to a minimum of 1#9

Open
YashManek1 wants to merge 1 commit into
traceroot-ai:mainfrom
YashManek1:fix/max-chars-bounds
Open

fix(config): clamp max_chars to a minimum of 1#9
YashManek1 wants to merge 1 commit into
traceroot-ai:mainfrom
YashManek1:fix/max-chars-bounds

Conversation

@YashManek1

@YashManek1 YashManek1 commented Jul 6, 2026

Copy link
Copy Markdown

Problem

TRACEROOT_PLUGIN_MAX_CHARS set to 0 or a negative value silently disables span-text truncation instead of erroring or falling back — oversized span attributes can then hit backend/OTLP size limits and get dropped, and negative values produce corrupted, overlapping text.

Root cause

load_config() only guards against non-integer input (except ValueError), not out-of-range integers — int("0") and int("-5") both succeed. Then in middle_truncate, max_chars=0 makes half=0, and s[-half:] evaluates to s[-0:], which in Python returns the entire string. So the "truncated" output is actually the full text with a misleading "middle elided" marker glued on. Negative max_chars produces overlapping, corrupted slices.

Change

Defense in depth, two layers:

  • config.py: clamp max_chars < 1 to the 20000 default, same as the non-integer fallback.
  • spans.py: guard middle_truncate against half <= 0 directly, so any bad value that reaches it still degrades safely (elision marker only, no full-string leak).

Validation

  • Added 5 regression tests in tests/test_spans.py: zero budget, negative budget, small positive budget (normal path), and two load_config clamp tests.
  • Verified by hand: max_chars=0 -> half=0 -> s[-0:] == full string (confirms the bug); max_chars=-5 -> half=-3 -> s[3:] (confirms overlap).
  • uv run pytest tests/test_spans.py -q -> 26 passed, 0 failed.
  • Confirmed the new tests fail without the fix and pass with it.

Risk / rollback

Additive-only change to a config-bounds check and a defensive guard; no behavior changes on the default/valid-range path. Revert is a straight git revert of this commit.

Closes #8


Summary by cubic

Clamp invalid TRACEROOT_PLUGIN_MAX_CHARS values and harden middle_truncate so truncation can’t be disabled or corrupt span text. This keeps span attributes within size limits and prevents OTLP drops.

  • Bug Fixes
    • Clamp max_chars < 1 to 20000 in load_config.
    • In middle_truncate, return only the elision marker when the budget is too small.
    • Added regression tests for zero/negative budgets and config clamping.

Written for commit e829633. Summary will update on new commits.

Review in cubic

TRACEROOT_PLUGIN_MAX_CHARS=0 or a negative value passed the int()
parse, so load_config() never fell back to the default. With
max_chars=0, middle_truncate's half=0 made s[-half:] evaluate to
s[-0:], which returns the whole string -- truncation silently
disabled while the output still claimed text was elided. Negative
values produced overlapping, corrupted slices instead. Clamp the
config value and guard the half<=0 case in middle_truncate as a
second line of defense.

Closes traceroot-ai#8

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

No issues found across 3 files

Re-trigger cubic

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.

bug: max_chars=0/negative silently disables truncation and corrupts middle_truncate output

1 participant