Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/tidy-pianos-shave.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'react-native-app-auth': patch
---

Fix iOS sending `NSNull` as the OAuth `state` when `additionalParameters.state` is null.
1 change: 1 addition & 0 deletions docs/docs/usage/config.md
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,7 @@ See specific example [configurations for your provider](/docs/category/providers
- **register** - (`{ [key: string]: value }`) headers to be passed during registration request.
- **additionalHeaders** - (`{ [key: string]: value }`) _IOS_ you can specify additional headers to be passed for all authorize, refresh, and register requests.
- **useNonce** - (`boolean`) (default: true) optionally allows not sending the nonce parameter, to support non-compliant providers. To specify custom nonce, provide it in `additionalParameters` under the `nonce` key.
- **state** - to specify a custom state, provide it in `additionalParameters` under the `state` key. A random state is generated when the key is absent. Pass `null` to omit the parameter entirely, to support providers that do not echo it back. Only omit it if you understand the CSRF tradeoff, and note that a provider returning a state you did not send will still fail validation.
- **usePKCE** - (`boolean`) (default: true) optionally allows not sending the code_challenge parameter and skipping PKCE code verification, to support non-compliant providers.
- **skipCodeExchange** - (`boolean`) (default: false) just return the authorization response, instead of automatically exchanging the authorization code. This is useful if this exchange needs to be done manually (not client-side)
- **iosCustomBrowser** - (`string`) (default: undefined) _IOS_ override the used browser for authorization, used to open an external browser. If no value is provided, the `ASWebAuthenticationSession` or `SFSafariViewController` are used by the `AppAuth-iOS` library.
Expand Down
2 changes: 2 additions & 0 deletions packages/react-native-app-auth/index.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,8 @@ interface BuiltInParameters {
display?: 'page' | 'popup' | 'touch' | 'wap';
login_prompt?: string;
prompt?: 'consent' | 'login' | 'none' | 'select_account';
/** Custom state. Pass null to omit the parameter, for providers that do not echo it back. */
state?: string | null;
}

export type BaseAuthConfiguration = BaseConfiguration & {
Expand Down
12 changes: 11 additions & 1 deletion packages/react-native-app-auth/ios/RNAppAuth.m
Original file line number Diff line number Diff line change
Expand Up @@ -344,6 +344,16 @@ - (void)authorizeWithConfiguration: (OIDServiceConfiguration *) configuration
[mutableDict removeObjectForKey:@"state"];
[mutableDict removeObjectForKey:@"nonce"];

// A null from JS bridges to NSNull, which is truthy in ObjC, so a plain
// ternary would send NSNull as the state. Absent generates, null omits.
id requestedState = additionalParameters[@"state"];
NSString *state = nil;
if (requestedState == nil) {
state = [[self class] generateState];
} else if (![requestedState isKindOfClass:[NSNull class]]) {
state = requestedState;
}

// builds authentication request
OIDAuthorizationRequest *request =
[[OIDAuthorizationRequest alloc] initWithConfiguration:configuration
Expand All @@ -353,7 +363,7 @@ - (void)authorizeWithConfiguration: (OIDServiceConfiguration *) configuration
scope:[OIDScopeUtilities scopesWithArray:scopes]
redirectURL:[NSURL URLWithString:redirectUrl]
responseType:OIDResponseTypeCode
state: additionalParameters[@"state"] ? additionalParameters[@"state"] : [[self class] generateState]
state:state
nonce:nonce
codeVerifier:codeVerifier
codeChallenge:codeChallenge
Expand Down