fix(auth): report the status when a request is rejected without a body - #43
Open
ExtraToast wants to merge 1 commit into
Open
ExtraToast wants to merge 1 commit into
ExtraToast wants to merge 1 commit into
Conversation
A request rejected by a servlet filter carries no ProblemDetail body, so
unwrap threw Error('Missing response body') and the form fell back to a
generic "Login failed" — hiding a 401 from the resource-server filter.
A non-ok response is now treated as a rejection even with no error
payload, and the status is reported in a synthesized ProblemDetail.
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.
Summary
A request rejected by a servlet filter carries no
ProblemDetailbody.unwrapreaderror === undefined, fell through todata == nulland threwError('Missing response body'); the store'sisProblemDetailcheck then failed and the form showed "Login failed" — a message that names neither the status nor the fact that the server refused the request before reading it.That message cost a full investigation. A sign-in failure reported as a 401 turned out to be
/api/oauth2/authorizeanswering 401 to a non-HTMLAccept(JorisJonkers-dev/auth-api#59), and thesession-loginattempts that followed were 400invalid-credentials— wrong credentials, which the form also reports as "Login failed" whenever the body cannot be read. The status is the one fact that separates "your password is wrong" from "a filter refused this", and the SPA discarded it.Fix
ClientResultnow carries theResponse.isRejectedtreats a non-okresponse as a rejection even when the client reports no error payload, andrejectionOfsynthesizes aProblemDetailfrom the status when there is no body to read:An error response that does carry a
ProblemDetailis passed through untouched, so every existing message — including the 400invalid-credentialsdetail the API does return — is unchanged.Verification
authService.test.tsdrives a bodyless401throughsessionLoginand asserts the thrown value carriesstatusand the status-bearingdetail. Proven to fail before the fix by reverting theisRejectedresponse check — it threwError('Missing response body').pnpm test— 124 tests passed across 13 files, onmainat release 0.4.4.pnpm lint(--max-warnings 0) andpnpm typecheck— clean.Risk
detail.detailnames a status rather than a cause, which is deliberate — it is the only thing known about a rejection that never reached a controller.Links