Traditionally in the OAuth’s Authorisation Code Grant flow user starts the journey through the front channel, requesting a resource from the authorisation server via a specifically crafted URL. We are passing all necessary details like client_id, scopes, response type, perhaps details for PKCE (Proof Key For Code Exchange), redirect_uri via the browser.
An example login URL would look something like this:
We are then redirected to the SSO login screen and after successful credential (or SSO session) validation we receive the code.
While this is secure and in fact has been designed with security in mind, there may be some aspects of it that may cause discomfort or even… technical problems. One could make a case that they don’t want to show all the details required to begin the flow or the specific scope names. I have also seen situations where those URLs became so long, they have exceeded browser’s limits.
Better security and more flexibility
When you’re trying to solve complex maths problems you sometimes substitute the variables, effectively making it more transparent. PAR is exactly that. We still need to pass the information to the authorisation server, but this time we’re doing it on the back channel. What happens is that the application is sending the authorisation parameters using the same channel that it uses to exchange the code for the token, this time in the body of the message.
POST /as/par.oauth2 HTTP/1.1
Host: myserver.com
Authorization: Basic someclientsecret
Content-Type: application/x-www-form-urlencoded
response_type=code
&scope=openid
&client_id=myapp
&state=xyzABC123
&redirect_uri=https://myapplication.com
The response from the authorisation server would look something like this:
{
“expires_in”: 60,
“request_uri”: “urn:ietf:params:oauth:request_uri:c1aATuhzXgq2LQa5EZiq8lt0m04v8DpF”
}
The next step follows the traditional flow, redirecting the user in the browser to the authorisation server, but instead of all parameters, we now pass the request_uri parameter. Server knows what to do with it, since it uses request_uri as reference.
Et voila, after successful login you get the code, no parameters were saved in the browser (URL) and you didn’t need to worry about the size of the request.
If you want to learn more about this OAuth2 extension – head here, where you can find the draft for RFC9126 .