Post

Replies

Boosts

Views

Activity

Sign in with Apple: Better Auth token exchange returns invalid_client while equivalent direct request returns invalid_grant
Hi, Feedback ID - FB24176019 I am investigating a Sign in with Apple issue affecting my production application and would appreciate guidance on what Apple may be rejecting during the token exchange. The authorization stage succeeds and Apple returns an authorization code to our callback. The failure occurs when the authorization code is exchanged at: https://appleid.apple.com/auth/token The production OAuth implementation uses Better Auth 1.6.13. Apple configuration: Primary App ID / Bundle ID: com.whatsupplier.uk Services ID / client_id: com.whatsupplier.uk.signin Registered return URL: https://www.whatsupp.uk/api/auth/callback/apple We have checked the client secret JWT and confirmed: alg = ES256 kid matches the active Apple key iss matches our Apple Team ID sub = com.whatsupplier.uk.signin aud = https://appleid.apple.com iat/exp are valid the JWT signature verifies locally against the configured Apple private key the signature is P1363/raw r||s rather than ASN.1 DER the private key is EC / prime256v1 the redirect_uri exactly matches the registered return URL the token request uses application/x-www-form-urlencoded The unusual behaviour is reproducible: The real Better Auth token exchange reaches Apple's /auth/token endpoint but Apple responds: HTTP 400 error: invalid_client We created a diagnostic request directly to the same Apple token endpoint using the same configured credentials and a deliberately invalid authorization code. Apple responds: HTTP 400 error: invalid_grant "The code has expired or has been revoked." This indicates Apple accepts the client credentials/JWT in the direct request and proceeds as far as validating the authorization code. We also performed an A/B test using the exact same generated client-secret JWT: Test A: grant_type code redirect_uri client_id client_secret Result: invalid_grant Test B: grant_type code redirect_uri client_id client_secret code_verifier Result: invalid_grant Therefore code_verifier alone does not change Apple's classification. We then captured the observable shape of the real Better Auth token request and compared it with a direct request. The client_id, redirect_uri, grant_type, client-secret JWT claims, URLSearchParams/form encoding and absence of an Authorization header were consistent. Despite this, the real framework-generated exchange returns invalid_client while the direct diagnostic request is accepted at the client-authentication stage and returns invalid_grant. Could Apple advise what additional property of the token request could cause this difference in classification? In particular, is there any server-side state or request characteristic used by Sign in with Apple that could cause an otherwise valid client_secret to be classified as invalid_client only during the real authorization-code exchange? I have also prepared detailed diagnostic evidence and can submit the requested sensitive request information through Feedback Assistant rather than posting JWTs, authorization codes, or other credentials publicly. Thank you.
0
0
106
16h
Sign in with Apple: Better Auth token exchange returns invalid_client while equivalent direct request returns invalid_grant
Hi, Feedback ID - FB24176019 I am investigating a Sign in with Apple issue affecting my production application and would appreciate guidance on what Apple may be rejecting during the token exchange. The authorization stage succeeds and Apple returns an authorization code to our callback. The failure occurs when the authorization code is exchanged at: https://appleid.apple.com/auth/token The production OAuth implementation uses Better Auth 1.6.13. Apple configuration: Primary App ID / Bundle ID: com.whatsupplier.uk Services ID / client_id: com.whatsupplier.uk.signin Registered return URL: https://www.whatsupp.uk/api/auth/callback/apple We have checked the client secret JWT and confirmed: alg = ES256 kid matches the active Apple key iss matches our Apple Team ID sub = com.whatsupplier.uk.signin aud = https://appleid.apple.com iat/exp are valid the JWT signature verifies locally against the configured Apple private key the signature is P1363/raw r||s rather than ASN.1 DER the private key is EC / prime256v1 the redirect_uri exactly matches the registered return URL the token request uses application/x-www-form-urlencoded The unusual behaviour is reproducible: The real Better Auth token exchange reaches Apple's /auth/token endpoint but Apple responds: HTTP 400 error: invalid_client We created a diagnostic request directly to the same Apple token endpoint using the same configured credentials and a deliberately invalid authorization code. Apple responds: HTTP 400 error: invalid_grant "The code has expired or has been revoked." This indicates Apple accepts the client credentials/JWT in the direct request and proceeds as far as validating the authorization code. We also performed an A/B test using the exact same generated client-secret JWT: Test A: grant_type code redirect_uri client_id client_secret Result: invalid_grant Test B: grant_type code redirect_uri client_id client_secret code_verifier Result: invalid_grant Therefore code_verifier alone does not change Apple's classification. We then captured the observable shape of the real Better Auth token request and compared it with a direct request. The client_id, redirect_uri, grant_type, client-secret JWT claims, URLSearchParams/form encoding and absence of an Authorization header were consistent. Despite this, the real framework-generated exchange returns invalid_client while the direct diagnostic request is accepted at the client-authentication stage and returns invalid_grant. Could Apple advise what additional property of the token request could cause this difference in classification? In particular, is there any server-side state or request characteristic used by Sign in with Apple that could cause an otherwise valid client_secret to be classified as invalid_client only during the real authorization-code exchange? I have also prepared detailed diagnostic evidence and can submit the requested sensitive request information through Feedback Assistant rather than posting JWTs, authorization codes, or other credentials publicly. Thank you.
Replies
0
Boosts
0
Views
106
Activity
16h