fix: classify future-version ledgers with changed record shape correctly, not as corrupt
Version-check now runs on the parseLedger failure path too, so a v3 blob whose record shape actually changed reports FutureVersion instead of Unreadable, avoiding the corrupt-blob "clear it" advice. Also closes the six minor findings.
This commit is contained in:
@@ -141,6 +141,8 @@ bool parseRecordArray(json::Reader& r, OriginLedger& out) {
|
||||
|
||||
// `versionOut` stays 0 when no "v" key was present — the legacy path-only shape, or
|
||||
// an empty object. Read regardless of key order, so it is validated after the close.
|
||||
// A duplicate "v" key (never emitted by serialize()) is last-wins, same as every
|
||||
// other duplicate key here — not reachable except by hand-editing the blob.
|
||||
bool parseLedger(json::Reader& r, OriginLedger& out, int& versionOut) {
|
||||
if (!r.consume('{')) return false;
|
||||
r.skipWs();
|
||||
@@ -174,7 +176,14 @@ ParseOutcome parseStored(const std::string& text, OriginLedger& out) {
|
||||
OriginLedger parsed;
|
||||
int version = 0;
|
||||
::reasampler::json::Reader r(text);
|
||||
if (!parseLedger(r, parsed, version)) return ParseOutcome::Malformed;
|
||||
if (!parseLedger(r, parsed, version)) {
|
||||
// A future record shape (e.g. v3 retyping "kind" or "records") fails these v2
|
||||
// parse rules on the very field the version bump changed. "v" is read before
|
||||
// any record parsing in our own writer's key order, so `version` already holds
|
||||
// it here: report FutureVersion, not Malformed, or the operator gets the
|
||||
// corrupt-blob "clear it" advice against a newer build's ledger.
|
||||
return version > kLedgerVersion ? ParseOutcome::FutureVersion : ParseOutcome::Malformed;
|
||||
}
|
||||
// Trailing garbage means the blob is not what it claims; accepting it would turn
|
||||
// a detectably-corrupt value into a silently-partial ledger.
|
||||
r.skipWs();
|
||||
|
||||
Reference in New Issue
Block a user