Keycloak Token exchange Error - Client is not within the token audience

442 views
Skip to first unread message

Vinod Louis

unread,
Aug 1, 2024, 3:21:19 AM8/1/24
to Keycloak User

Hi,

I'm working on a token-exchange request of keycloak wherein trying to get the access token of client2 while being authenticated with client1.

Have enabled token_exchange and admin_fine_grained_authz on keycloak instance.

Followed the documentation from https://www.keycloak.org/docs/latest/securing_apps/index.html#_internal-token-to-internal-token-exchange and followed as per instructions for permissions & policies

When I hit the API for token exchange as

curl --location 'http://<URL>/realms/Genting/protocol/openid-connect/token' \ --header 'Content-Type: application/x-www-form-urlencoded' \ --data-urlencode 'client_id=client2' \ --data-urlencode 'client_secret=<client2 secret>' \ --data-urlencode 'subject_token=<client1 token> \ --data-urlencode 'audience=client2' \ --data-urlencode 'grant_type=urn:ietf:params:oauth:grant-type:token-exchange' \ --data-urlencode 'requested_token_type=urn:ietf:params:oauth:token-type:access_token' 

In response, I'm getting

{ "error": "access_denied", "error_description": "Client is not within the token audience" }

Is there some setting I missed here that prevented me from receiving the token correctly?

Thanks in Advance

Jayson Helseth

unread,
Aug 2, 2024, 2:10:09 AM8/2/24
to Keycloak User
If you want to login with client1, I believe that you want to use the client_id and client_secret of client1. The audience of client2 is where I believe the exchange happens. Can you give that a try?

Thanks,

Jayson
Aatrix Software, LLC - 2617 S Columbia Rd. - Grand Forks, ND 58201 - www.aatrix.com

The content of this message may be confidential and is intended only for the recipient specified in the message.  If you have received this message by mistake, please inform us so we can ensure this mistake does not occur in the future, then delete the message.  The integrity and security of this email cannot be guaranteed over the Internet; therefore, the sender will not be held liable for any damage caused by the message.

Aldino Aulia Aurunisbi

unread,
Aug 2, 2024, 2:33:09 AM8/2/24
to Vinod Louis, Keycloak User
Heres my full function to exchange token between clients.
const exchangeToken = (publicToken: any, clientId: any, clientSecret: any): Promise<string> => {
return new Promise((resolve, reject) => {
let params = 'grant_type=urn:ietf:params:oauth:grant-type:uma-ticket';
params += `&audience=${clientId}`;
const req = new XMLHttpRequest();
req.onreadystatechange = () => {
if (req.readyState === 4) {
if (req.status === 200) {
try {
const response = JSON.parse(req.responseText);
resolve(response.access_token);
} catch (error) {
console.error('Error parsing response:', error);
reject(new Error('Token exchange failed: Invalid JSON response'));
}
} else {
console.error('Token exchange error:', req.responseText);
reject(new Error('Token exchange failed: ' + req.statusText));
}
}
};

req.open('POST', `${process.env.REACT_APP_KEYCLOAK_BASE_URL}/realms/${process.env.REACT_APP_KEYCLOAK_REALM}/protocol/openid-connect/token`, true);
req.setRequestHeader('Content-type', 'application/x-www-form-urlencoded');
req.setRequestHeader('Authorization', 'Bearer ' + String(publicToken));
req.send(params.toString());
});
};


const onTokens = async (tokens: KeycloakTokens) => {
if (tokens.token && tokens.refreshToken) {
console.log(`Keycloak tokens: ${JSON.stringify(tokens)}`);
try {
const exchangeTokenPromises = confidentialClientIds.map(async (clientId) => {
try {
const clientSecret = process.env[`REACT_APP_${clientId!.toUpperCase()}_CLIENT_SECRET`];
console.log("onTokens:clientId, ",clientId, "onTokens:clientSecret, ",clientSecret);
if (!clientSecret) {
console.error(`Client secret for ${clientId} not found`);
return;
}
localStorage.removeItem(`${clientId}_token`);
const confToken = await exchangeToken(tokens.token, clientId, clientSecret);
localStorage.setItem(`${clientId}_token`, confToken);

} catch (error) {
console.error(`Token exchange error for ${clientId}:`, error);
}
});
await Promise.all(exchangeTokenPromises);

const leadsTokens = localStorage.getItem('arsi_leads_token') ?? "";
const operationTokens = localStorage.getItem('arsi_operation_token') ?? "";
const communicationTokens= localStorage.getItem('arsi_communication_token')?? "";
const reportingTokens = localStorage.getItem('arsi_reporting_token')?? "";
const systemTokens = localStorage.getItem('arsi_system_token')?? "";
const mediaServerTokens = localStorage.getItem('arsi_mediaserver_token')?? "";
const utilityTokens = localStorage.getItem('arsi_utility_token')?? "";

await store.dispatch(loginWithToken({ token: tokens.token, refreshToken: tokens.refreshToken, channelToken:"",
leadsToken: leadsTokens,operationToken:operationTokens,communicationToken:communicationTokens,reportingToken:reportingTokens,
systemToken:systemTokens,mediaServerToken:mediaServerTokens,utilityToken:utilityTokens}));

console.log("Login with token successful");
} catch (error) {
console.error("Error during login with token", error);
}
}
};

--
You received this message because you are subscribed to the Google Groups "Keycloak User" group.
To unsubscribe from this group and stop receiving emails from it, send an email to keycloak-use...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/keycloak-user/b8a1fb0f-7539-4e98-b6f1-51181bf3ab3en%40googlegroups.com.


--
Salam,

Aldino Aulia Aurunisbi


Reply all
Reply to author
Forward
0 new messages