Skip to content

fix(toon): raise ToonDecodeError, not ValueError, on invalid escapes - #209

Open
rahul05ranjan wants to merge 1 commit into
Oaklight:masterfrom
rahul05ranjan:fix/toon-decode-error-type
Open

rahul05ranjan wants to merge 1 commit into
Oaklight:masterfrom
rahul05ranjan:fix/toon-decode-error-type

Conversation

@rahul05ranjan

Copy link
Copy Markdown

What

_unescape now raises ToonDecodeError instead of a bare ValueError for invalid escape sequences and a trailing backslash, and the conformance baseline shrinks by the nine IDs from #198.

Why

The module's contract — its docstrings and the Raises: sections, and what the conformance gate enforces on shouldError decode cases — is ToonDecodeError. A caller writing except ToonDecodeError did not catch these nine escapes; they leaked out as a generic ValueError:

decode/validation-errors[4]   raised ValueError (want ToonDecodeError)
decode/validation-errors[5]
decode/validation-errors[6]
decode/validation-errors[80]
decode/validation-errors[87]
decode/validation-errors[94]
decode/validation-errors[95]
decode/validation-errors[96]
decode/validation-errors[101]

All nine trace to the two raise ValueError sites in _unescape. That helper is decode-only — its only callers are _parse_primitive and _parse_key, which already raise ToonDecodeError for sibling malformed-string cases ("Unterminated string", "Unterminated quoted key"), so the raise sites simply move to the contract type. ToonDecodeError does not subclass ValueError, and no except ValueError handler in the module wraps these paths, so nothing else changes behaviour.

Changes

  • toon/toon.py: the two raise sites in _unescape move from ValueError to ToonDecodeError.
  • toon/conformance_baseline.json: --update-baseline removes the nine IDs; passing_total 350 → 359.
  • toon/test_toon_decode_errors.py: new no-dependency tests pinning the contract directly — parametrized invalid escapes (including the quoted-key and non-strict cases), the trailing-backslash case, and that ToonDecodeError is not a ValueError subclass.

Verification

  • Reproduced all nine failures on master; confirmed these are the only shouldError decode cases raising ValueError (scanned all 404 decode fixtures: exactly 9, no extras).
  • pytest toon/test_toon_conformance.py: 6 passed on the branch (the gate itself demanded the baseline shrink — test_baseline_entries_still_fail fails until the nine IDs are removed, then passes).
  • pytest toon/test_toon_decode_errors.py toon/test_toon_conformance.py: 14 passed.
  • toon/test_toon_correctness.py is skipped here (needs the toon_format reference package, not installed in this environment).
  • Note: make lint (ruff/ty/complexipy) was not runnable locally; the diff is two changed raise sites plus tests written to match the surrounding style.

Fixes #198

_unescape raised a bare ValueError for invalid escape sequences, so the
nine conformance cases in Oaklight#198 escaped callers writing except ToonDecodeError
— the type the module's own docstrings promise. _unescape is decode-only
(its two callers already raise ToonDecodeError for sibling failures), so the
raise sites move to the contract type and the baseline shrinks by those nine.

Co-authored-by: rahul05ranjan <11793455+rahul05ranjan@users.noreply.github.com>

This branch has not been deployed

No deployments
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.

toon: decode raises ValueError where the contract is ToonDecodeError

1 participant