-
Notifications
You must be signed in to change notification settings - Fork 7.9k
Description
Before reporting an issue
- I have read and understood the above terms for submitting issues, and I understand that my issue may be closed without action if I do not follow them.
Area
token-exchange
Describe the bug
When doing token exchange with audience = client_id aud claim is no longer present in issued token. It worked as expected in keycloak 25.0.4.
When audience != client_id aud claim is added to issued token as expected
Version
26.1.0
Regression
- The issue is a regression
Expected behavior
audience, supplied as parameter to exchange should be added as aud claim to issued token, even if target audience is equal to client, that is doing exchange.
Actual behavior
When target audience is equal to client, that is doing token exchange, aud claim is omitted.
How to Reproduce?
- Create client-a, client-b
- Issue token with client credentials grant for client-a
- Exchange token of client-a with audience = client-b and client_id = client_b
Anything else?
Adding more verbose steps to reproduce. This is IntelliJ IDEA rest client format, but it should-be self-explanatory what is going on here.
It also has client-c to test exchange when audience != client_id.
Test "Exchange Token (self)" fails
Test "Exchange Token (client-c)" passes
### Get Client Credentials Token
POST https://iam.local.dev/auth/realms/my/protocol/openid-connect/token
Content-Type: application/x-www-form-urlencoded
Authorization: Basic client-a CLIENT_A_SECRET
grant_type = client_credentials
> {% client.global.set("client_a_token", response.body.access_token); %}
### Exchange Token (self)
POST https://iam.local.dev/auth/realms/my/protocol/openid-connect/token
Content-Type: application/x-www-form-urlencoded
grant_type = urn:ietf:params:oauth:grant-type:token-exchange &
audience = client-b &
client_id = client-b &
client_secret = CLIENT_B_SECRET &
subject_token = {{client_a_token}} &
requested_token_type = urn:ietf:params:oauth:token-type:refresh_token
> {%
client.test("Response token has aud", () => {
const { aud } = JSON.parse(Window.atob(response.body.access_token.split('.')[1]));
client.assert(aud == 'client-b', `Expected client-b as audience, but got ${aud}`)
})
%}
### Exchange Token (client-c)
POST https://iam.local.dev/auth/realms/my/protocol/openid-connect/token
Content-Type: application/x-www-form-urlencoded
grant_type = urn:ietf:params:oauth:grant-type:token-exchange &
audience = client-c &
client_id = client-b &
client_secret = CLIENT_B_SECRET &
subject_token = {{client_a_token}} &
requested_token_type = urn:ietf:params:oauth:token-type:refresh_token
> {%
client.test("Response token has aud", () => {
const { aud } = JSON.parse(Window.atob(response.body.access_token.split('.')[1]));
client.assert(aud == 'client-c')
})
%}