Skip to content

[FEATURE] Extract Soroban capacity denominators and fix restore detection - #2

Merged
tmosleyIII merged 2 commits into
mainfrom
feature/tmosley/soroban-capacity-and-archival-facts
Aug 5, 2026
Merged

[FEATURE] Extract Soroban capacity denominators and fix restore detection#2
tmosleyIII merged 2 commits into
mainfrom
feature/tmosley/soroban-capacity-and-archival-facts

Conversation

@tmosleyIII

Copy link
Copy Markdown
Contributor

Summary

Three gaps in this library, each of which surfaces downstream as a silent zero rather than an error. Nothing consuming it could tell the data was missing.

parseConfigSettingFields was an empty stub. Every consumer received a config settings row with the limit columns NULL, and had to decode the XDR itself to find them — so in practice nobody did. A capacity meter had a numerator and no denominator. The settings that act as denominators are now promoted into their own fields.

Protocol 23 renamed the read-side limits to "disk read" under CAP-0062. They keep their existing column names here: the meaning consumers rely on — the ledger-wide ceiling on entries a transaction may read — is unchanged.

ExtractRestoredKeys scanned for a RestoreFootprint operation. CAP-0062 restores an archived entry named in a readWrite footprint during InvokeHostFunction, with no such operation present anywhere in the transaction. The detector returned nothing on protocol 23+ ledgers that plainly did restore entries — mainnet ledger 61,500,126 restored 22 entries with zero restore operations. It now reads LedgerEntryChangeTypeLedgerEntryRestored from the change stream.

The rewrite fixes three further defects in the same function:

  • Fee-bumped transactions resolved their operations but never their footprint, and were skipped entirely.
  • Every declared readWrite key was recorded as restored, whether or not it actually was. A footprint declares intent; only the change stream reports what happened.
  • Durability was hardcoded to "unknown". It now comes off the entry — which matters, because a temporary entry is deleted on expiry and can never be restored, so a restored entry reported as temporary would describe something that cannot happen.

TransactionData gains the declared footprint counts and the contract error. The protocol charges ledger capacity against what a transaction declares, not against the changes it turns out to make, so the declared counts are the correct numerators. Counting observed changes undercounts.

Type of Change

  • Feature (new functionality)
  • Bug fix (fixes an existing issue)

Breaking Changes

  • No

ConfigSettingData gains TxMaxFootprintEntries and TransactionData gains four fields. Consumers that select columns explicitly are unaffected; struct literals without field names would need updating, but none are used across these types.

Testing Performed

  • Unit tests added (10 new)
  • go build ./..., go vet ./... clean

Tests pin the field mapping specifically, because swapping read for write, or ledger-wide for per-transaction, yields a percentage that looks entirely reasonable and is wrong — nothing downstream can catch that. Also covered: unhandled settings leave every field nil rather than writing a zero that reads as a real limit of zero, durability derivation per entry type, and that only contract-defined errors carry a code.

Deployment Notes

Consumers must re-pin and rebuild. Restorations already ingested under the old detector are absent, not wrong — backfilling them is a separate decision.

🤖 Generated with Claude Code

Three gaps that each surface downstream as a silent zero rather than an
error, so nothing consuming this library could tell the data was absent.

parseConfigSettingFields was an empty stub. Every consumer got a
config_settings row with the limit columns NULL and had to decode the
XDR itself to find them, so in practice nobody did — a capacity meter
had a numerator and no denominator. The settings that act as denominators
are now promoted into their own fields. Protocol 23 renamed the read-side
limits to "disk read" under CAP-0062; they keep their existing column
names, since the meaning consumers rely on is unchanged.

ExtractRestoredKeys scanned for a RestoreFootprint operation. CAP-0062
restores an archived entry named in a readWrite footprint during
InvokeHostFunction, with no such operation present, so the detector
returned nothing on protocol 23+ ledgers that plainly did restore
entries: mainnet 61,500,126 restored 22 with no restore operation. It now
reads LedgerEntryChangeTypeLedgerEntryRestored from the change stream.
That also fixes three further defects in the same function — fee-bumped
transactions resolved their operations but never their footprint and were
skipped, every declared readWrite key was recorded as restored whether or
not it was, and durability was hardcoded to "unknown".

TransactionData gains the declared footprint entry counts and the
contract error. The protocol charges ledger capacity against what a
transaction declares rather than the changes it makes, so the declared
counts are the numerators; counting observed changes undercounts.

TxMaxFootprintEntries is new on ConfigSettingData. Consumers that select
columns explicitly are unaffected.
@tmosleyIII
tmosleyIII merged commit a2c4dbc into main Aug 5, 2026
2 checks passed
@tmosleyIII
tmosleyIII deleted the feature/tmosley/soroban-capacity-and-archival-facts branch August 5, 2026 02:25
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