React OIDC Client Quickstart
This guide walks you through how to integrate Descope into your React app as an OIDC client, using redirect-based login with Federated Apps.
Install the SDK
Install the Descope SDK for React using your preferred package manager:
npm install @descope/react-sdkWrap Your App with AuthProvider
In your root component (e.g., App.tsx), wrap your app in AuthProvider and configure OIDC by enabling oidcConfig.
import { AuthProvider } from '@descope/react-sdk';
import AppRoutes from './AppRoutes';
export default function AppRoot() {
return (
<AuthProvider
projectId="__ProjectID__" // Replace with your Project ID
oidcConfig={true} // Enables OIDC redirect behavior
>
<AppRoutes />
</AuthProvider>
);
}You may also pass a full oidcConfig object to customize settings such as redirectUri, scope, and applicationId. Read more in our Client SDK docs section.
Trigger Login with Redirect
Use the useDescope() hook and call sdk.oidc.loginWithRedirect() to start the login process.
import { useDescope } from '@descope/react-sdk';
export default function LoginButton() {
const sdk = useDescope();
return (
<button
onClick={() => {
sdk.oidc.loginWithRedirect({
redirect_uri: window.location.origin, // Optional: defaults to current URL
login_hint: 'user@example.com', // Optional: pre-fill the form.externalId context key
});
}}
>
Login with OIDC
</button>
);
}loginWithRedirect Parameters
You can pass any of the following parameters into the loginWithRedirect function to provide additional info to the OIDC provider:
redirect_uri: A custom URI that overrides the default redirect after login. This will default to being the current URL.login_hint: A hint to Descope of the user identifier (e.g., email address). This will pre-fill theform.externalIdcontext key in the flow you're redirected to.
Redirect Back and Automatic Session Handling
After a successful login, the OIDC provider will redirect the user to your app. The AuthProvider will automatically process the returned tokens and establish a session.
No additional code is needed on the redirect page — just ensure the app is wrapped with AuthProvider.
Access User and Session Info
You can use useSession() and useUser() to access authentication state and user info.
import { useSession, useUser } from '@descope/react-sdk';
export default function Dashboard() {
const { isAuthenticated, isSessionLoading } = useSession();
const { user, isUserLoading } = useUser();
if (isSessionLoading || isUserLoading) return <p>Loading...</p>;
if (isAuthenticated) {
return <p>Welcome, {user.name}</p>;
}
return <p>You are not logged in</p>;
}Logout the User
To log out, you can call sdk.logout() for local session clearing, or sdk.oidc.logout() for a full OIDC-compliant logout with redirect:
import { useDescope } from '@descope/react-sdk';
export default function LogoutButton() {
const sdk = useDescope();
return (
<>
<button onClick={() => sdk.logout()}>Logout</button>
<button
onClick={() =>
sdk.oidc.logout({
post_logout_redirect_uri: window.location.origin + '/after-logout',
})
}
>
Logout and Redirect
</button>
</>
);
}You're All Set!
Your React app now uses Descope as an OIDC provider with redirect-based login, logout, and session management.
Signing In with an Inbound App
The steps above use a Federated App, whose tokens sign the user in to your app. When your React app also needs an access token for your own API, with the API in aud, it signs in through a public Inbound App instead. See Choosing an App Type for when you need this.
You can point oidcConfig at the Inbound App with its issuer and client ID. The SDK then requests only the openid scope by default, so pass scope if you need more:
<AuthProvider
projectId="__ProjectID__"
oidcConfig={{
issuer: '__BaseURL__/v1/apps/__ProjectID__',
clientId: '<INBOUND_APP_CLIENT_ID>',
scope: 'openid profile email',
}}
>
<AppRoutes />
</AuthProvider>To get a token for one of your Resources, pass the Resource identifier as resource when you start the sign-in. The SDK hands the parameters of loginWithRedirect to oidc-client-ts, which sends resource on the authorize request:
sdk.oidc.loginWithRedirect({
resource: 'https://api.example.com',
skipUserInfo: true,
});The SDK always calls the UserInfo endpoint after the redirect back, and oidcConfig has no option to turn that off. If UserInfo rejects the access token, the sign-in fails even though Descope issued the tokens. Passing skipUserInfo: true to loginWithRedirect skips that call for this sign-in, and the SDK reads the user's claims from the ID token only.
Checkpoint
Your application is now integrated with Descope. Please test with sign-up or sign-in use case.