Skip to content

fix: add fetch timeout to prevent indefinite hangs#118

Open
nicknisi wants to merge 1 commit into
mainfrom
fix/fetch-timeout
Open

fix: add fetch timeout to prevent indefinite hangs#118
nicknisi wants to merge 1 commit into
mainfrom
fix/fetch-timeout

Conversation

@nicknisi
Copy link
Copy Markdown
Member

Summary

  • Adds AbortSignal.timeout(30_000) to the HTTP client's #post method
  • Without this, a misconfigured or unreachable custom auth domain (e.g., after environment promotion before Cloudflare bootstrapping completes) causes fetch() to block indefinitely — initialize() never resolves and the React provider's isLoading stays true forever
  • 30 seconds is generous enough for post-sleep/high-latency scenarios but prevents infinite hangs

Surfaced by VectorShift after promoting their staging environment to production — identity.vectorshift.ai wasn't routing correctly and fetch hung with no timeout.

Related: #117 (post-sleep lock timeout), workos/authkit-react (createClient rejection handling PR)

Test plan

  • All 83 tests pass (npm test)
  • New test: createClient resolves (not hangs) when fetch rejects with a TimeoutError
  • npm run build passes
  • Verify in a browser: when apiHostname points to an unreachable domain, initialization times out after ~30s instead of hanging forever

Adds AbortSignal.timeout(30s) to the HTTP client's POST method so a
misconfigured or unreachable custom auth domain times out instead of
blocking initialization forever.
@nicknisi nicknisi requested review from cmatheson and gjtorikian May 15, 2026 18:30
Copy link
Copy Markdown

@devin-ai-integration devin-ai-integration Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

✅ Devin Review: No Issues Found

Devin Review analyzed this PR and found no potential bugs to report.

View in Devin Review to see 1 additional finding.

Open in Devin Review

Copy link
Copy Markdown
Collaborator

@cmatheson cmatheson left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍

Comment thread src/create-client.test.ts

it("does not hang when the API is unreachable and the fetch times out", async () => {
const originalFetch = global.fetch;
const timeoutError = new DOMException(
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

kind of think it would feel better if we wrapped this error (instead of passing the DOMException straight through), but i don't feel too strongly about it if you disagree.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Development

Successfully merging this pull request may close these issues.

2 participants