I have generated a very small spring boot application in heroku with an Okta add on. I can go to localhost:8080 and get directed to Okta login screen, login and everything works as expected. I now want to test the other apis with postman and have spent a long time reading the documentation and forum posts but still not getting it.
I downloaded the Okta APIs : Authentication and OpenID Connect. I run the primary authentication api with the username and password and get the session token. Now my understanding, from a previous forum post, is that I can pass that session token to the authorize endpoint which which will authenticate and authorize the user sending the details to the spring boot application.
The problem I’m having is sending this session token to the authorize endpoint. I see this example in the documentation:
I can follow all of this except the state parameter. Is the state the same as the state token? I found this on the forum:
It (the state token) is generated during the authentication (AuthN) process, and gets converted to a session token once the user has been authenticated
But my previous api call gave me the session token, has the state token already been converted, if so what do I set the state token in the api to?
No, the state parameter is not the same as the stateToken. In applicable Okta orgs, Okta uses the stateToken internally as a way of keeping track of the primary authentication transaction.
The state parameter for your authorize request is completely separate and is an optional parameter for the /authorize request in OIDC, supported by Okta, that is used to mitigate XSRF. More details in the spec: 188.8.131.52 Authentication Request | OpenID Connect Core 1.0 and in Okta’s documentation for this endpoint: OpenID Connect & OAuth 2.0 API | Okta Developer
- Okta requires the OAuth 2.0
state parameter on all requests to the
/authorize endpoint to prevent cross-site request forgery (CSRF). The OAuth 2.0 specification requires (opens new window)that clients protect their redirect URIs against CSRF by sending a value in the authorize request that binds the request to the user-agent’s authenticated state. Using the
state parameter is also a countermeasure to several other known attacks as outlined in OAuth 2.0 Threat Model and Security Considerations (opens new window).
Thanks, that helped to get me further. From the links I see state is an ‘opaque value’ which I guess means some string I put in. The other thing that helped was I was using response_type=token_id but one of the links indicated that it should be code. So now the postman request looks like (using the session token I got from the primary authentication api):
As you can see the response is html (the OKTA login page) but according to the docs I was expecting:
This request authenticates the user and returns tokens along with an authorization grant to the client application as a part of the callback response.
I have tried several things including adding prompt=none but that reverted to the 401.
Is it possible to see what I am doing wrong or point me in the right direction.
I am still stumped trying to execute apis in my okta protected app. Any pointers would be greatly appreciated.
I had thought that the following procedures would be the way to go:
use the Okta authentication api to get the session token
use the Okta authorize token using the session token to get access tokens (per OpenID Connect & OAuth 2.0 API | Okta Developer)
use the access tokens to be able to execute apis on my endpoints.
As stated in my previous posted question the second step is returning me html content instead of the expected access token or authorization grant. Am I wrong in thinking that it should return me the tokens or should I be using one of the other apis
As a follow up, if I do get the access tokens, am I correct in assuming that that is what I need to use to access my app endpoints.
So many choices… So there are four ways that you can have a user login, and several types of application architectures you can use. I’ll explain more about this if you ask.
I’m looking at your last post here. You can get a session cookie either via the Okta hosted sign-in widget or by using the API via /authn (I would use the SDK) and getting a session token which you exchange for a session cookie by redirecting the browser through Okta to an application landing page. If you look at the sessions API docs there are three ways to send the user there. The key is once you have the session cookie Okta sees the browser as an authenticated user.
Normally to get an access token for your application to talk to your API you need to call a custom authorization server as a separate step. No user interaction here because all authorization servers see the user as logged in (session cookie).
This subsequent call is to /authorize for the URL of your custom server is similar to what you had in an earlier post, except that your asking for an access token only. The state is just your choice of value echoed back so the application knows what it was doing (remember the browser redirect interrupts it) and the nonce is just another value to confirm it was you you sent the original request because it matches.
I know that you are doing this on the server side, but the flow is almost identical for a client-side app (you don’t need PKCE). Take a look at this example of the REST API I have that does exactly what you want including your API, using the default sign-in widget for the log in: GitHub - jmussman/pirates.
Thanks so much for your detailed explanation. This did get me further but I still cannot get the session cookie from postman.
I will spend some time looking at the example in your pirates repo.
There must be a redirect with the browser to pick up the session cookie, Postman can’t do that itself. You need to have the Postman Interceptor plugin installed in the browser, and then turned on in the browser and Postman so that Postman can read the cookies set in the browser.
Great, thanks Joel, I’ll look into that