test: compare the two storage layouts by replaying one corpus through both #1870 - #1891
Open
DmytroZaichenkoDev wants to merge 3 commits into
Open
DmytroZaichenkoDev wants to merge 3 commits into
DmytroZaichenkoDev wants to merge 3 commits into
Conversation
DmytroZaichenkoDev
force-pushed
the
feat/issue-1870-1-replay-diff
branch
5 times, most recently
from
September 3, 2026 11:58
df8b721 to
acbc1b9
Compare
DmytroZaichenkoDev
marked this pull request as ready for review
September 3, 2026 15:05
DmytroZaichenkoDev
requested review from
Oleksii-Klimov,
alexey-ban,
astsiapanay,
nepalevov and
tataranovich
as code owners
September 3, 2026 15:05
astsiapanay
approved these changes
Sep 4, 2026
… both #1870 Boots the full stack twice, once on each layout, replays a checked-in corpus through both and fails on any difference a caller could observe: status, body, response headers and etag. Etag is what makes this work - it is derived from content, so matching etags say the stored bytes agree without comparing a single path, which is the point when the paths are supposed to differ. Runs as its own Gradle task and its own CI job rather than inside :server:test. The layout is process-wide static state and this suite exists to flip it, which is what makes unrelated classes fail elsewhere in the same JVM; a separate job also means its minute runs alongside the main suite instead of after it. Differences are governed by a checked-in expectations file. Anything not listed fails, and an entry that stops matching fails too, so the file cannot quietly become a place where divergences go to be forgotten. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Three ways the differ could report green while behaviour differed: - Normalisation replaces a captured value with its role name wherever it appears, so the value's own divergence was invisible — including the etag, the one signal that checks content without comparing paths. Captures both runs derive from shared inputs (etag, publication url) are now compared by value. - Pagination continuation was never replayed; the one accepted-divergence entry swallowed the whole first-page body. The corpus now walks all three pages, each layout consuming its own tokens, and the entry is gone — the token is compared by role instead. - The HTTP client decoded compressed responses transparently, hiding exactly the divergence a migration that drops blob metadata produces; and repeated response headers collapsed last-wins. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
DmytroZaichenkoDev
force-pushed
the
feat/issue-1870-1-replay-diff
branch
from
September 7, 2026 11:50
72d016c to
722a89c
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Stacked on #1889.
Boots the full stack twice — once on each layout — replays a checked-in corpus through both, and fails on any difference a caller could observe: status, body, response headers and etag.
Etag is what makes it work. It is derived from content, so matching etags say the stored bytes agree without comparing a single path — which is the point, because the paths are supposed to differ:
Corpus covers conversation CRUD with etag preconditions, prompts with nested and escaped names, paginated listings, file upload through multipart, move and copy, the share lifecycle, and publication through approval.
Runs as its own Gradle task and its own CI job rather than inside
:server:test: the layout is process-wide static state and this suite exists to flip it, which is what makes unrelated classes fail elsewhere in the same JVM. A separate job also means its ~1 minute runs alongside the main suite instead of after it.Divergences are governed by
expected-divergences.json— anything unlisted fails, and an entry that stops matching fails too, so the file cannot quietly become where divergences go to be forgotten. One entry today:nextTokencarries the blob store's marker verbatim, so it changes shape with the layout.Found the invitation-id defect fixed in #1889.
Access differ and bucket verifier follow.
🤖 Generated with Claude Code