Skip to content

Commit 26a6d8a

Browse files
feat: Add PAR (Pushed Authorization Request) section to examples documentation
1 parent e7638de commit 26a6d8a

File tree

1 file changed

+68
-0
lines changed

1 file changed

+68
-0
lines changed

EXAMPLES.md

Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
- [Specify a Custom Logout URL](#specify-a-custom-logout-url)
1313
- [Trusted Web Activity](#trusted-web-activity)
1414
- [DPoP [EA]](#dpop-ea)
15+
- [PAR (Pushed Authorization Request)](#par-pushed-authorization-request)
1516
- [Authentication API](#authentication-api)
1617
- [Login with database connection](#login-with-database-connection)
1718
- [Login using MFA with One Time Password code](#login-using-mfa-with-one-time-password-code)
@@ -290,6 +291,73 @@ WebAuthProvider.logout(account)
290291
> [!NOTE]
291292
> DPoP is supported only on Android version 6.0 (API level 23) and above. Trying to use DPoP in any older versions will result in an exception.
292293
294+
## PAR (Pushed Authorization Request)
295+
296+
PAR (Pushed Authorization Request) enables a Backend-for-Frontend (BFF) pattern where your backend server handles the `/par` and `/token` endpoints while the SDK manages the browser-based authorization flow.
297+
298+
This is useful when:
299+
- You need to use a confidential client with a `client_secret`
300+
- You want to keep sensitive parameters server-side
301+
- You're implementing a BFF architecture
302+
303+
### Usage
304+
305+
The PAR flow requires coordination between your backend (BFF) and the mobile app:
306+
307+
1. **Backend calls `/par` endpoint** - Your backend initiates the PAR request with the `client_secret` and receives a `request_uri`
308+
2. **SDK opens `/authorize`** - The mobile app uses the `request_uri` to open the browser for user authentication
309+
3. **SDK returns authorization code** - After authentication, the SDK returns the authorization code to the app
310+
4. **Backend exchanges code for tokens** - Your backend exchanges the code for tokens using the `client_secret`
311+
312+
```kotlin
313+
// Step 1: Your BFF calls /par and returns request_uri to the app
314+
val requestUri = yourBffClient.initiatePAR(scope, audience)
315+
316+
// Step 2 & 3: SDK opens browser and returns authorization code
317+
WebAuthProvider.par(account)
318+
.start(context, requestUri, object : Callback<AuthorizationCode, AuthenticationException> {
319+
override fun onSuccess(result: AuthorizationCode) {
320+
// Step 4: Send code to BFF to exchange for tokens
321+
yourBffClient.exchangeCode(result.code)
322+
}
323+
324+
override fun onFailure(error: AuthenticationException) {
325+
if (error.isCanceled) {
326+
// User closed the browser
327+
} else {
328+
// Handle error
329+
}
330+
}
331+
})
332+
```
333+
334+
<details>
335+
<summary>Using coroutines</summary>
336+
337+
```kotlin
338+
try {
339+
// Step 1: Your BFF calls /par and returns request_uri
340+
val requestUri = yourBffClient.initiatePAR(scope, audience)
341+
342+
// Step 2 & 3: SDK opens browser and returns authorization code
343+
val authCode = WebAuthProvider.par(account)
344+
.await(context, requestUri)
345+
346+
// Step 4: Send code to BFF to exchange for tokens
347+
val credentials = yourBffClient.exchangeCode(authCode.code)
348+
} catch (e: AuthenticationException) {
349+
if (e.isCanceled) {
350+
// User closed the browser
351+
} else {
352+
// Handle error
353+
}
354+
}
355+
```
356+
</details>
357+
358+
> [!NOTE]
359+
> The SDK only handles opening the browser with the `request_uri` and returning the authorization code. Token exchange must be performed by your backend server which holds the `client_secret`.
360+
293361
## Authentication API
294362

295363
The client provides methods to authenticate the user against the Auth0 server.

0 commit comments

Comments
 (0)