[keycloak-dev] Offline tokens - step 1
Marek Posolda
mposolda at redhat.com
Mon Sep 21 08:58:38 EDT 2015
On 21/09/15 14:25, Stian Thorgersen wrote:
> What you've listed there doesn't sound correct to me. Each client that
> requires consent (consentRequired=true) has to prompt the user for all
> roles including realm roles. So each client requiring consent would
> need to ask user for consent.
Indeed you're right :-)
>
> How I think it would work is:
>
> * Add a 'offline_access' realm role - in the future we can move this
> to a OpenID Connect specific namespace
> * If a client has 'full access' on the scope tab it can obtain an
> offline token - no need for a separate offline enable toggle for this
> * The user has a role mapping for this (should be added by default as
> you said)
>
> A client that doesn't require consent (consentRequired=false) will
> automatically be provided with an offline token as long as the client
> either has full access or a scope on the realm offline_access role.
> For a client that requires consent the consent screen will first be
> shown, including all requested roles/scopes which includes the realm
> level 'offline_access' role. One given the consent is saved for that
> specific client. When another client that requires consent asks for
> offline token the consent screen is yet again shown.
There is one thing, that if client has scope and requires consent, the
consent screen with "Has Offline Access" will be displayed even if
offline token wasn't requested . The offline_access role will be also
always available in access token even with "classic" login without
offline token. Is this acceptable? Or should we add the flag on
RoleModel that role will be included just if available in scope parameter?
Marek
>
> On 21 September 2015 at 14:06, Marek Posolda <mposolda at redhat.com
> <mailto:mposolda at redhat.com>> wrote:
>
> On 21/09/15 12:33, Stian Thorgersen wrote:
>>
>>
>> On 21 September 2015 at 12:06, Marek Posolda <mposolda at redhat.com
>> <mailto:mposolda at redhat.com>> wrote:
>>
>> I've sent the PR . Right now it works like this:
>>
>> - ClientModel has flag "offlineTokensEnabled" . It's possible to
>> retrieve offline tokens just if flag is enabled
>>
>> - Offline token is classic refresh token with 2 differences.
>> It has type
>> "OFFLINE" when normal refresh token has type "REFRESH" . And
>> for offline
>> token, the expiration value is 0, so it never expires.
>>
>> - Offline token is generated by auth-server when client sends
>> "scope=offline_access" . It's supported for classic browser
>> flow, but
>> also for Direct Grant flow or Service account flow.
>>
>> - I've added OfflineClientSessionModel and
>> OfflineUserSessionModel with
>> CRUD methods on UserModel. So when new offline token is
>> generated by
>> Keycloak, some info about current UserSession and
>> ClientSession is
>> persisted on UserModel. This means that offline token can be
>> used to
>> create new access token even if "normal" UserSession and
>> ClientSession
>> are already invalid or logged out.
>>
>> - When refreshing access token with offline token, the
>> auth-server won't
>> send back another refresh token. It will send just accessToken +
>> IDToken. This is to avoid writes to user database for each
>> token refresh.
>>
>> - In account management applications tab, there is new table
>> column
>> "Additional grants" where is shown if client has offline
>> token for user.
>> The click on "Revoke" button will remove offline tokens and
>> granted
>> consents as well - no separate actions for revoke consents
>> and offline
>> tokens.
>>
>>
>> Still TODO:
>> - Properly handle consents (see "Questions" below)
>>
>> - More tests, example, export/import , docs
>>
>> - More things/refactoring based on your feedback
>>
>>
>> Questions:
>> - The specs mentions that consent should be displayed when
>> offline token
>> is requested. See
>> http://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess
>> .
>> Right now, I am not doing that. So when Client has
>> "isConsentRequired"
>> as false, the consent screen is not displayed. Now we also
>> don't have
>> support for "prompt=consent" (not sure if we need this) . Is
>> it ok to
>> keep it like this?
>>
>>
>> Wording is "MUST explicitly receive or have consent" - as the
>> client does not require consent (isConsentRequired=false) that
>> implies the client already has been given consent by the admin.
>>
>>
>> - I am thinking about adding new builtin client role
>> "offline_access",
>> which will be created for client when admin enables "offline
>> tokens"
>> switch. It will be used also as default role. This will allow
>> that just
>> some users are allowed to obtain offline-token (those which
>> have this
>> role). The role will be also displayed on consent screen for the
>> clients, which needs consent.
>> But that raises another question. IMO it will be good if role is
>> requested and displayed on consent screen just if offline
>> token is
>> requested, but not when classic refresh token is requested.
>>
>>
>> Hence I was thinking about adding the flag "scopeParamMode" to
>> RoleModel. The value true means that role will be requested
>> and used in
>> accessToken/refreshToken just if scope parameter contains
>> it's value.
>> This will be the setup for "offline_access" role, so it's
>> used just for
>> the offline token requests. Another thing is format of scope
>> parameter
>> with respect to realm roles and application roles. We can use
>> "//" as
>> delimiter, so realm role will have just "my-role" but client
>> role will
>> have "my-client//my-role" . The disadvantage is that for
>> requesting
>> offline_access you will then need to use scope like:
>> "scope=customer-portal//offline_access" as it's client role.
>>
>>
>> Spec says scope should be "offline_access", so if we use a
>> different name for it won't comply with the spec.
>>
>> Shouldn't the offline_access role be a realm role rather than a
>> role per-client?
> The issue with realm role is, that user needs to confirm
> offline_access consent just once per all clients, which doesn't
> look correct to me.
>
> For example there would be 2 clients "foo" and "bar":
> - User john wants offline_access for client "foo"
> - Consent screen is displayed with "offline_access" role and he
> confirms it
> - Then user john wants offline_access for client "bar"
> - There is no "offline_access" anymore on consent screen because
> john already has consent for realm role "offline_access" .
>
>
> IMO it should be "offline_access" displayed again as it's
> different client. Also logically offline_access is granted per
> client, so the text on the grant screen is:
>
> "has Offline Access in foo"
>
> or
>
> "has Offline Access in bar"
>
> which will be with client roles.
>
>>
>> Another thing to consider is that we'll be moving to role
>> namespaces instead of realm/client roles soon. In that case we
>> might want a OpenID Connect namespace that can hold these scopes.
>> So role could be "openid/offline_access".
> Ok. Maybe for now I won't do anything tricky but just limit the
> scope param support to client roles of current client. So scope
> "offline_access" is "offline_access" role of current client. We
> can improve it later once we add role namespaces support. WDYT?
>
> Marek
>>
>>
>> WDYT? Any better idea?
>>
>> Marek
>> _______________________________________________
>> keycloak-dev mailing list
>> keycloak-dev at lists.jboss.org
>> <mailto:keycloak-dev at lists.jboss.org>
>> https://lists.jboss.org/mailman/listinfo/keycloak-dev
>>
>>
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://lists.jboss.org/pipermail/keycloak-dev/attachments/20150921/6567567c/attachment.html
More information about the keycloak-dev
mailing list