Order the Docs batch back to front, not merely reversed - #55
Merged
Conversation
Google applies a batch sequentially: each request sees the document as the previous ones left it. Operations are generated in document order and a replacement emits its deletes before its insert, so reversing the list put the insert first -- at the same index those deletes start from. The insert then shifted every delete after it by its own length. On a wholesale rewrite that is thousands of characters: the deletes ate the text just inserted, missed the text they were meant to remove, and past the end of the body Google refused the range. Sorted explicitly instead: descending by index, deletes before inserts at the same index, so a position is cleared before anything is written to it. Closes #54 Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
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.
Pushing a markdown file that differs wholesale from the Doc failed with
Invalid deletion range. Cannot delete the requested range.The batchbegan with a ~1,900-character
insertTextat index 1, followed by threedeletes at descending indices.
Root cause. Google applies a batch sequentially — each request sees
the document as the previous ones left it.
diffOpsToRequestsorderedthe batch by reversing the generated list, which is not the same as
ordering it back-to-front: operations are generated in document order and
an N:M replacement pushes its deletes before its insert, so the reversal
put the insert first, at the same index those deletes start from. Every
delete after it then landed ~1,900 characters late.
Fix. Sort explicitly — descending by index, deletes before inserts at
the same index, so a position is cleared before anything is written to it.
Verification
The new test applies the emitted batch the way Google does, sequentially,
and refuses an out-of-range delete as the API would. Against the shape of
the failing document — three paragraph runs split by two tables, replaced
wholesale — it failed with:
Every original paragraph had survived and the new content was destroyed.
It passes after the sort, with both tables untouched.
The existing "reverse order for index stability" test passed throughout —
it asserts indices are non-increasing, which an insert tied with a delete
satisfies. That is why this survived: the ordering was checked, the
outcome of applying it was not.
Known artefact, not fixed here. A paragraph delete stops one
character short of its run, so each replaced run leaves a trailing
newline behind as an empty paragraph. The short stop is deliberate —
taking the newline before a table is itself invalid — and removing the
leftovers needs the delete to know whether a table follows. Filed in the
issue rather than bundled in.
pnpm test1034 passed / 62 files · typecheck clean · lint clean.Closes #54
🤖 Generated with Claude Code