Skip to content

Make CSRF token handling resilient to badtoken errors - #111

Merged
DaxServer merged 3 commits into
mainfrom
csrf-token-retry
Jul 5, 2026
Merged

DaxServer merged 3 commits into
mainfrom
csrf-token-retry

Conversation

@DaxServer

Copy link
Copy Markdown
Owner

MediaWiki API tokens can occasionally be rejected as invalid (error.code === 'badtoken'), and every mutating call in MediaWikiClient / WikidataClient previously failed outright when that happened — including mid-way through a chunked upload, discarding chunks already staged on the server.

  • Add a shared withCsrfTokenRetry helper: fetch/reuse a token, make the request, and on badtoken fetch a fresh token and retry exactly once.
  • Wire it into every mutating call site: createPage, applySdc, replaceCategoryInPage, nullEdit, both loops in uploadFile, and WikidataClient.editItem.
  • Fix a latent gap in nullEdit and editItem: neither previously inspected the API response body for an error field, so a badtoken failure was silently swallowed as success.
  • Log a warning with a per-call-site label (e.g. [mw] uploadFile chunk 2/3) whenever a retry actually fires.

DaxServer and others added 3 commits July 5, 2026 11:48
CSRF tokens fetched before mutating calls were never refreshed if
MediaWiki rejected them as invalid, failing the whole operation
(including mid-way through a chunked upload). Add a one-shot
fetch-fresh-token-and-retry helper to MediaWikiClient (for both
apiRequest-based and FormData-based chunk/commit calls) and an
analogous pair of private methods to WikidataClient, and wire every
mutating call site through it.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017ak8tpbsoWNcVsSAhxBygf
The previous commit added new describe blocks for createPage/applySdc/
replaceCategoryInPage/nullEdit without noticing equivalent blocks already
existed later in the file, creating duplicates. Merge the new badtoken-retry
tests into the pre-existing blocks instead.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017ak8tpbsoWNcVsSAhxBygf
MediaWikiClient had two near-identical private retry methods
(apiRequestWithTokenRetry, apiUploadChunkWithTokenRetry) and WikidataClient
had a third (editItemWithTokenRetry), all implementing the same
fetch/reuse-token -> request -> refetch-and-retry-once-on-badtoken algorithm,
differing only in how the underlying request was made. Extract this into a
single withCsrfTokenRetry(label, getToken, doRequest, token?) function shared
by both clients, and log a warning (with a per-call-site label, e.g.
"[mw] uploadFile chunk 2/3") whenever a retry is triggered so a badtoken event
is visible in logs instead of silent.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017ak8tpbsoWNcVsSAhxBygf
@greptile-apps

greptile-apps Bot commented Jul 5, 2026

Copy link
Copy Markdown
Contributor

Confidence Score: 5/5

This looks safe to merge.

  • No blocking issues found in the changed code.

Important Files Changed

Filename Overview
backend/src/mediawiki/tokenRetry.ts Adds the shared CSRF retry helper that retries once on badtoken and returns the final result and token.
backend/src/mediawiki/client.ts Uses the shared retry helper across MediaWiki mutating calls and preserves upload token propagation.
backend/src/mediawiki/wikidata.ts Uses the shared retry helper for Wikidata edits while keeping the same request body and signing inputs.
backend/src/tests/tokenRetry.test.ts Adds direct tests for retry success, retry exhaustion, token reuse, and first-attempt success.
backend/src/tests/uploadClient.test.ts Adds MediaWiki mutation and upload tests for badtoken retry behavior.
backend/src/tests/wikidataClient.test.ts Adds Wikidata edit tests for retry success and retry exhaustion.

Reviews (1): Last reviewed commit: "refactor: unify badtoken retry logic int..." | Re-trigger Greptile

@DaxServer
DaxServer merged commit c55892d into main Jul 5, 2026
5 checks passed
@DaxServer
DaxServer deleted the csrf-token-retry branch July 5, 2026 10:06
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