Auth code pkce with MFA for a SPA app

I have created a OIDC react app in Okta with auth code pkce and custom sign on policy (pwd + factor(email or phone)). I have configured global session policy for Okta session (sid/idx cookie), authenticator policy (pwd + factor(email or phone)) associated to user group, custom authorization server with access policy configured with auth code, interaction code, client creds and token exchange and the access and refresh token lifetime.

I am able to authenticate and authorize the user with login and pwd (idx.authenticate) and then with email/phone factors (idx.proceed) with okta sdk. I get the OIDC tokens as well as Okta session cookie.
However, when I tried making a call as below, I get session token associated to the users.

      username: this.state.username,
       password: this.state.password

I would like to call Okta based on sessionToken and get the pertaining factors for the user. Is there a way to do so ?


When using idx.authenticate() with the auth SDK you are using the new Interaction Code flow introduced with the OIE Okta Org.

Using signInWithCredentials() is using the Okta Classic authn pipeline. If this is returning a sessionToken, that means the user is authenticated and the sessionToken can be exchanged for a browser session cookie (sid), or OAuth tokens.

If you are not expecting to get a sessionToken, but rather a stateToken with status MFA_REQUIRED, there could be a couple of reason.

  • You are passing a deviceToken or DT cookie and your Okta policies are configured to not prompt for MFA from the same device.
  • Your Okta ‘Global Policy’ only requires password. The authn API can only authenticate against the global policy, not application level policies. When you use idx.authenticate() it can evaluate the global followed by the application authentication policy, but authn will only evaluate the global authentication policy.

Thank You,

1 Like

For idx.authenticate, I see the challenge, introspect, challenge/answer api for MFA flow. In the challenge/answer response I get stateHandle and interaction_code. The next call is v1/token with client_id, redirect_uri, grant_type (as interaction_code), interaction_code (value received from challenge/answer ) and code_verifier. How shall I get the code_verifier value ?

I was able to get the code_verifier and pass it to v1/token with the idx flow and receive OIDC tokens after successful MFA. In my case, we have two different UI’s. One is intended to authenticate and then after successful authentication redirect to another UI for MFA.
Since my sample UI was configured with idx sdk, I was able to trace the calls to Okta and then separate the api calls within those 2 different UI (UI_1 which does authentication and UI_2 which does MFA).

I will try with /authn as well and see why its still not returning me the state token.

what would your preference be classic authn call and pass state token from UI_1 to UI_2 for MFA or idx api calls between 2 UI’s ie pass state handle with authenticators from UI_1 to UI_2 for MFA?

I’m a little confused about what you are asking for. If you are trying to use Okta as a directory service then the SDKs are set up to use the old Authentication API for Classic Okta orgs, and the new Interaction code flow to Okta Identity Engine Orgs. It won’t be completely supported to use the Authentication API with an OIE org.

It sounds like you are trying to do something a little different than that though, because you want to get the Okta session cookie. Having the Okta session cookie is only necessary if you want Okta to provide SSO to multiple applications. The Authentication API could do this, you get back the session token which you can exchange for a first-party session cookie by redirecting the user’s browser through Okta. Look at the second topic on the Sessions API page: Sessions | Okta Developer. IDX cannot provide this, in fact it says it is only meant for stand-along applications in the last sentence of the first paragraph on the Interaction Code Flow concepts page: Interaction Code grant type | Okta Developer. Part of the problem is there is no Okta session cookie with IDX, the new flow introduces an “idx” state cookie.

So this is your application matrix:

  • If you want SSO between multiple applications, you have to use Okta’s hosted authentication widget and initiate the authentication with an OIDC request (the SDK can do that too). This widget is fully customizable in the org configuration, so it can be branded any way you want. The IDX cookie provides the session ID for Okta SSO.

  • If you want to collect the credentials and handle the MFA prompts in your own monolithic application, you can either host our embedded sign-in widget (GitHub - okta/okta-signin-widget: HTML/CSS/JS widget that provides out-of-the-box authentication UX for your organization's apps) or write your own application (which you apparently have been doing). But then there is no reason to get the Okta session cookie because you aren’t doing SSO with multiple applications.

1 Like