[keycloak-user] Token exchange cross realm

Ravindra De Silva ravindra.desilva at gmail.com
Sun Mar 10 21:21:25 EDT 2019


Hi Pedro,

I saw this thread when about to inquire on cross realm token exchange.
My use case is quite similar. I have multiple realms (one per brand), and
all the staff users are in master realm federated from Free IPA (LDAP
integration). Staff users in master realm manage all other users in other
realms.
I tested staff (master realm) users impersonating the members (other
realms) using admin console. However, unfortunately, all our apps (browser,
native apps)  are using Resource Owner Password Credentials (ROPC) flow for
authentication. This decision is beyond my control due to legacy and
branding reasons. Anyhow, as a result, I cannot rely on Keycloak cookies
for anything and rely extensively on Keycloak APIs.

As mentioned in this thread, token exchange within the realm worked
perfectly. Then cross-realm token exchange did not work.
The first challenge I faced is in creating the token exchange policy. A
client (admin app1) from a master realm is not available to select from the
brand (member) realm. Only the clients from the same realm are available to
pick as the starting client. Therefore, a member realm client (member app1)
cannot allow a master realm client (admin app1) to exchange (at least to
create a token exchange policy).

Then I looked at ways how a staff member can authenticate against the
member realm so that both starting and target realms are the same.
I tried using identity federation. I configured member realm IDP to use
master realm broker. As a staff member, I was able to log in to member
realm through the federation, using Keycloak browser authentication
(redirects).
However, I could not figure out how to use identity brokering via API only,
since member realm OIDC endpoints are of the master realm.
So far, from what I understand identity brokering is a must for cross-realm
token exchange? However, identity brokering requires browser redirects?

I will debug Keycloak source code next week. However, please let me know if
the cross-realm token exchange is not possible when the original
authentication (starting realm) was performed using API only with ROPC flow.

Please note that I am aware that I can federate staff users to each realm
and get staff users to impersonate members in each realm. However, I would
like to avoid that duplication.
Once I am very clear about the intentions of token exchange, I can send a
PR request for the documentation.

I appreciate your help.

Thanks,
Ravindra





On Sun, Mar 10, 2019 at 9:55 AM Pedro Igor Silva <psilva at redhat.com> wrote:

> Nice ! Please, feel free to send a PR with improvements to docs.
>
> Regarding the app1 being able to exchange any token on R2 did you try to
> write a JS policy with your access constraints to the token-exchange
> permission ?
>
> On Fri, Mar 8, 2019 at 8:14 AM triton oidc <triton.oidc at gmail.com> wrote:
>
> > Hi,
> >
> > I tried giving the app1 the credentials of the R1_for_R2 (the client used
> > for the federation on the IDP2)
> > and i could exchange the token from the app1 to a token on the app2 !
> >
> > However that's far from what we wish
> > the app1 has now the power to exchange any token on R2 configured with
> the
> > Client R1_for_R2, so i can have only one application on each side with
> > token exchange activated without security issues.
> >
> > If it makes sense, i can propose an update on the documentation,
> specifying
> > the application needs the credentials of the second IDP to do the
> exchange.
> >
> > Cheers
> >
> >
> > On Wed, Mar 6, 2019 at 4:49 PM triton oidc <triton.oidc at gmail.com>
> wrote:
> >
> > > Hi Keycloak masters
> > >
> > > I've done the token exchange in the same realm,
> > > here is a link with my scenario
> > >
> > >
> >
> https://www.websequencediagrams.com/?lz=dGl0bGUgRGV0YWlsZWQgdG9rZW4gZXhjaGFuZ2UgKEtleWNsb2FrKQoKcGFydGljaXBhbnQgVXNlciBhcyBVAAkNQXBwMSBhcyAxAB8NSURQIGFzIElEUAAdEDIgYXMgMgoKbm90ZSBvdmVyIFU6VGhlIHUAWQVuZCBhbGwgdGhlIGFwcCBhcmUgaW4ACgVzYW1lIHJlYWxtADALMTp0aGlzIEFwcCBpcyBPSURDIHByb3RlY3RlZApVLT4xOgCBMAVnb2VzIHRvAFAHIHdpdGggYQCBcAdmcm9tIElEUFxuKHNpbXBsaWZpY2F0aW9uKQBSFndhbnQgdG8gZG8gYSBjYWxsIG8AgRsGYXBwMlxub24gYmVoYWxmIG9mAIFCBXVzZXIKMS0-SURQOnJlcXVlc3QAgmEQAH4FQVBQMSB0bwCBRwUyXG51c2luZwCCDwYAgxoFLACCNgZjbGllbnRJRACCJQUAgnYFY3JlZGVudGlhbHMKSURQLS0-MTpyZXR1cm4gYWNjZXNzAIFgCG9yAIJ6BQoxLT4yOmJhY2tlbmQAgTsGAGYGACIMAIMTCzI6T3B0aW9ubmFsCjIAgUEGZ2V0dXNlcmluZm8AKRMsXG4AgzcIaXMgc3VyZQCBfwwncyBpAIErBXR5AIFdCElEUCdzIHRydXN0AIE7BzIAgToIAF8LCjIAgU8MAIE0DAoxLS0-VQCBbQgKCg&s=rose
> > >
> > > I'm trying to do the same cross realm following this documentation
> > >
> > >
> >
> https://www.keycloak.org/docs/latest/securing_apps/index.html#external-token-to-internal-token-exchange
> > >
> > > Here is a link to my draft
> > >
> > >
> >
> https://www.websequencediagrams.com/?lz=dGl0bGUgRGV0YWlsZWQgdG9rZW4gZXhjaGFuZ2UgQ3Jvc3MgcmVhbG0gRHJhZnQgKEtleWNsb2FrKQoKcGFydGljaXBhbnQgVXNlciBhcyBVAAkNQXBwMSBhcyAxAB8NSURQABEFSURQAAgRMgASBzIAOBAAFAUyCgpub3RlIG92ZXIgVTpUaGUgdQB0BW5kIGFsbCB0aGUgYQBvBXJlIGluAAsFc2FtZQCBPQYAMQsxOnRoaXMgQXBwIGlzIE9JREMgcHJvdGVjdGVkClUtPjE6AIFMBWdvZXMgdG8AUQcgd2l0aCBJRABqBUFjY2VzcwCCKgdmcm9tIElEUFxuKHNpbXBsaWZpY2F0aW9uKQBeFndhbnQgdG8gZG8gYSBjYWxsIG8AgScGYXBwMlxub24gYmVoYWxmIG9mAIFPBXVzZXIKMS0-SURQMjpyZXF1ZXN0AIMcEACAfwVBUFAxIHRvAIJFBVxudXNpbmcAghwGAINUBQpJRFAyLS0-MTpyZXR1cm4gYQCBOA1vcgCCdAYxLT4yOmJhY2tlbmQAgRgGAEMGACIMAIJ9CzI6T3B0aW9ubmFsCjIAgR0HZ2V0dXNlcmluZm8AKhMsXG4AgyMHIGlzIHN1cmUAgV0MJ3MgaWRlbnRpdHkAgTsISURQJ3MgdHJ1c3QAgTwIMgCBPAgAYAsKAIFQDQCBNgwKMS0tPlUAgW8ICgo&s=rose
> > >
> > > However i don't know which client credentials put in the query.
> > > my app only knows it's own credentials (*app1_clientID* and
> > > *app1_clientSecret*)
> > > and wants to get an access token on the Realm2 (R2) on the clientID "
> > > *secured_R2*"
> > > The broker on the IDP2 is using the clientID "*R1_for_R2*" on the IDP1
> > > The alias of the broker is "*R2_for_R1_users*"
> > >
> > > curl -X POST \
> > >     -d "client_id=*app1_clientID*" \
> > >     -d "client_secret=*app1_clientSecret*" \
> > >     --data-urlencode
> > > "grant_type=urn:ietf:params:oauth:grant-type:token-exchange" \
> > >     -d "subject_token="*my_token_obtained_using_app1_clientID*" \
> > >     -d "subject_issuer=*R2_for_R1_users*" \
> > >     --data-urlencode
> > > "subject_token_type=urn:ietf:params:oauth:token-type:access_token" \
> > >     -d "audience=*secured_R2*" \
> > >     http://*IDP2*/auth/realms/*R2*/protocol/openid-connect/token
> > >
> > > I got an invalid credentials, which makes sense because the IDP2 can't
> > > verify the credentials of the App1 linked to the realm1 (IDP1)
> > > I know i missed something.
> > > If someone could give me a hint
> > >
> > > Once i understand, i'm willing to propose an update on the
> documentation
> > >
> > > Thanks for any help
> > >
> > > Amaury
> > >
> > >
> > >
> > >
> > >
> > _______________________________________________
> > keycloak-user mailing list
> > keycloak-user at lists.jboss.org
> > https://lists.jboss.org/mailman/listinfo/keycloak-user
> >
> _______________________________________________
> keycloak-user mailing list
> keycloak-user at lists.jboss.org
> https://lists.jboss.org/mailman/listinfo/keycloak-user
>


More information about the keycloak-user mailing list