From dec43289f6b66f05410002f0cd72c1c1dd114672 Mon Sep 17 00:00:00 2001 From: Ryan Richard Date: Wed, 20 Oct 2021 15:53:25 -0700 Subject: [PATCH] Lots of small updates based on PR feedback --- .../types_oidcidentityprovider.go.tmpl | 5 +- ...or.pinniped.dev_oidcidentityproviders.yaml | 56 ++++++++++--------- generated/1.17/README.adoc | 2 +- .../v1alpha1/types_oidcidentityprovider.go | 5 +- ...or.pinniped.dev_oidcidentityproviders.yaml | 56 ++++++++++--------- generated/1.18/README.adoc | 2 +- .../v1alpha1/types_oidcidentityprovider.go | 5 +- ...or.pinniped.dev_oidcidentityproviders.yaml | 56 ++++++++++--------- generated/1.19/README.adoc | 2 +- .../v1alpha1/types_oidcidentityprovider.go | 5 +- ...or.pinniped.dev_oidcidentityproviders.yaml | 56 ++++++++++--------- generated/1.20/README.adoc | 2 +- .../v1alpha1/types_oidcidentityprovider.go | 5 +- ...or.pinniped.dev_oidcidentityproviders.yaml | 56 ++++++++++--------- .../v1alpha1/types_oidcidentityprovider.go | 5 +- .../oidc_upstream_watcher.go | 19 +++---- .../fositestorage/accesstoken/accesstoken.go | 2 + .../authorizationcode/authorizationcode.go | 2 + .../openidconnect/openidconnect.go | 2 + internal/fositestorage/pkce/pkce.go | 2 + .../refreshtoken/refreshtoken.go | 2 + internal/oidc/auth/auth_handler.go | 3 +- internal/oidc/callback/callback_handler.go | 3 +- .../provider/dynamic_upstream_idp_provider.go | 2 +- pkg/oidcclient/login.go | 1 + pkg/oidcclient/login_test.go | 1 + .../howto/configure-supervisor-with-gitlab.md | 7 ++- .../howto/configure-supervisor-with-okta.md | 4 +- 28 files changed, 208 insertions(+), 160 deletions(-) diff --git a/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go.tmpl b/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go.tmpl index bae993d0..a53d6f53 100644 --- a/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go.tmpl +++ b/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go.tmpl @@ -45,8 +45,11 @@ type OIDCAuthorizationConfig struct { // the following scopes: "openid", "offline_access", "email", and "profile". See // https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" // scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the - // "offline_access" scope. By setting this list to anything other than an empty list, you are overriding the + // "offline_access" scope. This default value may change in future versions of Pinniped as the standard evolves, + // or as common patterns used by providers who implement the standard in the ecosystem evolve. + // By setting this list to anything other than an empty list, you are overriding the // default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. + // If you do not want any of these scopes to be requested, you may set this list to contain only "openid". // Some OIDC providers may also require a scope to get access to the user's group membership, in which case you // may wish to include it in this list. Sometimes the scope to request the user's group membership is called // "groups", but unfortunately this is not specified in the OIDC standard. diff --git a/deploy/supervisor/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml b/deploy/supervisor/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml index 14f6fd89..8ebd5eb5 100644 --- a/deploy/supervisor/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml +++ b/deploy/supervisor/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml @@ -114,32 +114,36 @@ spec: Supervisor will request the following scopes: "openid", "offline_access", "email", and "profile". See https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess - for a description of the "offline_access" scope. By setting - this list to anything other than an empty list, you are overriding - the default value, so you may wish to include some of "offline_access", - "email", and "profile" in your override list. Some OIDC providers - may also require a scope to get access to the user''s group - membership, in which case you may wish to include it in this - list. Sometimes the scope to request the user''s group membership - is called "groups", but unfortunately this is not specified - in the OIDC standard. Generally speaking, you should include - any scopes required to cause the appropriate claims to be the - returned by your OIDC provider in the ID token or userinfo endpoint - results for those claims which you would like to use in the - oidcClaims settings to determine the usernames and group memberships - of your Kubernetes users. See your OIDC provider''s documentation - for more information about what scopes are available to request - claims. Additionally, the Pinniped Supervisor requires that - your OIDC provider returns refresh tokens to the Supervisor - from these authorization flows. For most OIDC providers, the - scope required to receive refresh tokens will be "offline_access". - See the documentation of your OIDC provider''s authorization - and token endpoints for its requirements for what to include - in the request in order to receive a refresh token in the response, - if anything. Note that it may be safe to send "offline_access" - even to providers which do not require it, since the provider - may ignore scopes that it does not understand or require (see - https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). + for a description of the "offline_access" scope. This default + value may change in future versions of Pinniped as the standard + evolves, or as common patterns used by providers who implement + the standard in the ecosystem evolve. By setting this list to + anything other than an empty list, you are overriding the default + value, so you may wish to include some of "offline_access", + "email", and "profile" in your override list. If you do not + want any of these scopes to be requested, you may set this list + to contain only "openid". Some OIDC providers may also require + a scope to get access to the user''s group membership, in which + case you may wish to include it in this list. Sometimes the + scope to request the user''s group membership is called "groups", + but unfortunately this is not specified in the OIDC standard. + Generally speaking, you should include any scopes required to + cause the appropriate claims to be the returned by your OIDC + provider in the ID token or userinfo endpoint results for those + claims which you would like to use in the oidcClaims settings + to determine the usernames and group memberships of your Kubernetes + users. See your OIDC provider''s documentation for more information + about what scopes are available to request claims. Additionally, + the Pinniped Supervisor requires that your OIDC provider returns + refresh tokens to the Supervisor from these authorization flows. + For most OIDC providers, the scope required to receive refresh + tokens will be "offline_access". See the documentation of your + OIDC provider''s authorization and token endpoints for its requirements + for what to include in the request in order to receive a refresh + token in the response, if anything. Note that it may be safe + to send "offline_access" even to providers which do not require + it, since the provider may ignore scopes that it does not understand + or require (see https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). In the unusual case that you must avoid sending the "offline_access" scope, then you must override the default value of this setting. This is required if your OIDC provider will reject the request diff --git a/generated/1.17/README.adoc b/generated/1.17/README.adoc index 35b16323..d18e7610 100644 --- a/generated/1.17/README.adoc +++ b/generated/1.17/README.adoc @@ -1099,7 +1099,7 @@ OIDCAuthorizationConfig provides information about how to form the OAuth2 author [cols="25a,75a", options="header"] |=== | Field | Description -| *`additionalScopes`* __string array__ | additionalScopes are the additional scopes that will be requested from your OIDC provider in the authorization request during an OIDC Authorization Code Flow and in the token request during a Resource Owner Password Credentials Grant. Note that the "openid" scope will always be requested regardless of the value in this setting, since it is always required according to the OIDC spec. By default, when this field is not set, the Supervisor will request the following scopes: "openid", "offline_access", "email", and "profile". See https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the "offline_access" scope. By setting this list to anything other than an empty list, you are overriding the default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. Some OIDC providers may also require a scope to get access to the user's group membership, in which case you may wish to include it in this list. Sometimes the scope to request the user's group membership is called "groups", but unfortunately this is not specified in the OIDC standard. Generally speaking, you should include any scopes required to cause the appropriate claims to be the returned by your OIDC provider in the ID token or userinfo endpoint results for those claims which you would like to use in the oidcClaims settings to determine the usernames and group memberships of your Kubernetes users. See your OIDC provider's documentation for more information about what scopes are available to request claims. Additionally, the Pinniped Supervisor requires that your OIDC provider returns refresh tokens to the Supervisor from these authorization flows. For most OIDC providers, the scope required to receive refresh tokens will be "offline_access". See the documentation of your OIDC provider's authorization and token endpoints for its requirements for what to include in the request in order to receive a refresh token in the response, if anything. Note that it may be safe to send "offline_access" even to providers which do not require it, since the provider may ignore scopes that it does not understand or require (see https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). In the unusual case that you must avoid sending the "offline_access" scope, then you must override the default value of this setting. This is required if your OIDC provider will reject the request when it includes "offline_access" (e.g. GitLab's OIDC provider). +| *`additionalScopes`* __string array__ | additionalScopes are the additional scopes that will be requested from your OIDC provider in the authorization request during an OIDC Authorization Code Flow and in the token request during a Resource Owner Password Credentials Grant. Note that the "openid" scope will always be requested regardless of the value in this setting, since it is always required according to the OIDC spec. By default, when this field is not set, the Supervisor will request the following scopes: "openid", "offline_access", "email", and "profile". See https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the "offline_access" scope. This default value may change in future versions of Pinniped as the standard evolves, or as common patterns used by providers who implement the standard in the ecosystem evolve. By setting this list to anything other than an empty list, you are overriding the default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. If you do not want any of these scopes to be requested, you may set this list to contain only "openid". Some OIDC providers may also require a scope to get access to the user's group membership, in which case you may wish to include it in this list. Sometimes the scope to request the user's group membership is called "groups", but unfortunately this is not specified in the OIDC standard. Generally speaking, you should include any scopes required to cause the appropriate claims to be the returned by your OIDC provider in the ID token or userinfo endpoint results for those claims which you would like to use in the oidcClaims settings to determine the usernames and group memberships of your Kubernetes users. See your OIDC provider's documentation for more information about what scopes are available to request claims. Additionally, the Pinniped Supervisor requires that your OIDC provider returns refresh tokens to the Supervisor from these authorization flows. For most OIDC providers, the scope required to receive refresh tokens will be "offline_access". See the documentation of your OIDC provider's authorization and token endpoints for its requirements for what to include in the request in order to receive a refresh token in the response, if anything. Note that it may be safe to send "offline_access" even to providers which do not require it, since the provider may ignore scopes that it does not understand or require (see https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). In the unusual case that you must avoid sending the "offline_access" scope, then you must override the default value of this setting. This is required if your OIDC provider will reject the request when it includes "offline_access" (e.g. GitLab's OIDC provider). | *`additionalAuthorizeParameters`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-17-apis-supervisor-idp-v1alpha1-parameter[$$Parameter$$] array__ | additionalAuthorizeParameters are extra query parameters that should be included in the authorize request to your OIDC provider in the authorization request during an OIDC Authorization Code Flow. By default, no extra parameters are sent. The standard parameters that will be sent are "response_type", "scope", "client_id", "state", "nonce", "code_challenge", "code_challenge_method", and "redirect_uri". These parameters cannot be included in this setting. Additionally, the "hd" parameter cannot be included in this setting at this time. The "hd" parameter is used by Google's OIDC provider to provide a hint as to which "hosted domain" the user should use during login. However, Pinniped does not yet support validating the hosted domain in the resulting ID token, so it is not yet safe to use this feature of Google's OIDC provider with Pinniped. This setting does not influence the parameters sent to the token endpoint in the Resource Owner Password Credentials Grant. The Pinniped Supervisor requires that your OIDC provider returns refresh tokens to the Supervisor from the authorization flows. Some OIDC providers may require a certain value for the "prompt" parameter in order to properly request refresh tokens. See the documentation of your OIDC provider's authorization endpoint for its requirements for what to include in the request in order to receive a refresh token in the response, if anything. If your provider requires the prompt parameter to request a refresh token, then include it here. Also note that most providers also require a certain scope to be requested in order to receive refresh tokens. See the additionalScopes setting for more information about using scopes to request refresh tokens. | *`allowPasswordGrant`* __boolean__ | allowPasswordGrant, when true, will allow the use of OAuth 2.0's Resource Owner Password Credentials Grant (see https://datatracker.ietf.org/doc/html/rfc6749#section-4.3) to authenticate to the OIDC provider using a username and password without a web browser, in addition to the usual browser-based OIDC Authorization Code Flow. The Resource Owner Password Credentials Grant is not officially part of the OIDC specification, so it may not be supported by your OIDC provider. If your OIDC provider supports returning ID tokens from a Resource Owner Password Credentials Grant token request, then you can choose to set this field to true. This will allow end users to choose to present their username and password to the kubectl CLI (using the Pinniped plugin) to authenticate to the cluster, without using a web browser to log in as is customary in OIDC Authorization Code Flow. This may be convenient for users, especially for identities from your OIDC provider which are not intended to represent a human actor, such as service accounts performing actions in a CI/CD environment. Even if your OIDC provider supports it, you may wish to disable this behavior by setting this field to false when you prefer to only allow users of this OIDCIdentityProvider to log in via the browser-based OIDC Authorization Code Flow. Using the Resource Owner Password Credentials Grant means that the Pinniped CLI and Pinniped Supervisor will directly handle your end users' passwords (similar to LDAPIdentityProvider), and you will not be able to require multi-factor authentication or use the other web-based login features of your OIDC provider during Resource Owner Password Credentials Grant logins. allowPasswordGrant defaults to false. |=== diff --git a/generated/1.17/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go b/generated/1.17/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go index bae993d0..a53d6f53 100644 --- a/generated/1.17/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go +++ b/generated/1.17/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go @@ -45,8 +45,11 @@ type OIDCAuthorizationConfig struct { // the following scopes: "openid", "offline_access", "email", and "profile". See // https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" // scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the - // "offline_access" scope. By setting this list to anything other than an empty list, you are overriding the + // "offline_access" scope. This default value may change in future versions of Pinniped as the standard evolves, + // or as common patterns used by providers who implement the standard in the ecosystem evolve. + // By setting this list to anything other than an empty list, you are overriding the // default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. + // If you do not want any of these scopes to be requested, you may set this list to contain only "openid". // Some OIDC providers may also require a scope to get access to the user's group membership, in which case you // may wish to include it in this list. Sometimes the scope to request the user's group membership is called // "groups", but unfortunately this is not specified in the OIDC standard. diff --git a/generated/1.17/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml b/generated/1.17/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml index 14f6fd89..8ebd5eb5 100644 --- a/generated/1.17/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml +++ b/generated/1.17/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml @@ -114,32 +114,36 @@ spec: Supervisor will request the following scopes: "openid", "offline_access", "email", and "profile". See https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess - for a description of the "offline_access" scope. By setting - this list to anything other than an empty list, you are overriding - the default value, so you may wish to include some of "offline_access", - "email", and "profile" in your override list. Some OIDC providers - may also require a scope to get access to the user''s group - membership, in which case you may wish to include it in this - list. Sometimes the scope to request the user''s group membership - is called "groups", but unfortunately this is not specified - in the OIDC standard. Generally speaking, you should include - any scopes required to cause the appropriate claims to be the - returned by your OIDC provider in the ID token or userinfo endpoint - results for those claims which you would like to use in the - oidcClaims settings to determine the usernames and group memberships - of your Kubernetes users. See your OIDC provider''s documentation - for more information about what scopes are available to request - claims. Additionally, the Pinniped Supervisor requires that - your OIDC provider returns refresh tokens to the Supervisor - from these authorization flows. For most OIDC providers, the - scope required to receive refresh tokens will be "offline_access". - See the documentation of your OIDC provider''s authorization - and token endpoints for its requirements for what to include - in the request in order to receive a refresh token in the response, - if anything. Note that it may be safe to send "offline_access" - even to providers which do not require it, since the provider - may ignore scopes that it does not understand or require (see - https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). + for a description of the "offline_access" scope. This default + value may change in future versions of Pinniped as the standard + evolves, or as common patterns used by providers who implement + the standard in the ecosystem evolve. By setting this list to + anything other than an empty list, you are overriding the default + value, so you may wish to include some of "offline_access", + "email", and "profile" in your override list. If you do not + want any of these scopes to be requested, you may set this list + to contain only "openid". Some OIDC providers may also require + a scope to get access to the user''s group membership, in which + case you may wish to include it in this list. Sometimes the + scope to request the user''s group membership is called "groups", + but unfortunately this is not specified in the OIDC standard. + Generally speaking, you should include any scopes required to + cause the appropriate claims to be the returned by your OIDC + provider in the ID token or userinfo endpoint results for those + claims which you would like to use in the oidcClaims settings + to determine the usernames and group memberships of your Kubernetes + users. See your OIDC provider''s documentation for more information + about what scopes are available to request claims. Additionally, + the Pinniped Supervisor requires that your OIDC provider returns + refresh tokens to the Supervisor from these authorization flows. + For most OIDC providers, the scope required to receive refresh + tokens will be "offline_access". See the documentation of your + OIDC provider''s authorization and token endpoints for its requirements + for what to include in the request in order to receive a refresh + token in the response, if anything. Note that it may be safe + to send "offline_access" even to providers which do not require + it, since the provider may ignore scopes that it does not understand + or require (see https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). In the unusual case that you must avoid sending the "offline_access" scope, then you must override the default value of this setting. This is required if your OIDC provider will reject the request diff --git a/generated/1.18/README.adoc b/generated/1.18/README.adoc index 2f383af3..417b57ac 100644 --- a/generated/1.18/README.adoc +++ b/generated/1.18/README.adoc @@ -1099,7 +1099,7 @@ OIDCAuthorizationConfig provides information about how to form the OAuth2 author [cols="25a,75a", options="header"] |=== | Field | Description -| *`additionalScopes`* __string array__ | additionalScopes are the additional scopes that will be requested from your OIDC provider in the authorization request during an OIDC Authorization Code Flow and in the token request during a Resource Owner Password Credentials Grant. Note that the "openid" scope will always be requested regardless of the value in this setting, since it is always required according to the OIDC spec. By default, when this field is not set, the Supervisor will request the following scopes: "openid", "offline_access", "email", and "profile". See https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the "offline_access" scope. By setting this list to anything other than an empty list, you are overriding the default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. Some OIDC providers may also require a scope to get access to the user's group membership, in which case you may wish to include it in this list. Sometimes the scope to request the user's group membership is called "groups", but unfortunately this is not specified in the OIDC standard. Generally speaking, you should include any scopes required to cause the appropriate claims to be the returned by your OIDC provider in the ID token or userinfo endpoint results for those claims which you would like to use in the oidcClaims settings to determine the usernames and group memberships of your Kubernetes users. See your OIDC provider's documentation for more information about what scopes are available to request claims. Additionally, the Pinniped Supervisor requires that your OIDC provider returns refresh tokens to the Supervisor from these authorization flows. For most OIDC providers, the scope required to receive refresh tokens will be "offline_access". See the documentation of your OIDC provider's authorization and token endpoints for its requirements for what to include in the request in order to receive a refresh token in the response, if anything. Note that it may be safe to send "offline_access" even to providers which do not require it, since the provider may ignore scopes that it does not understand or require (see https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). In the unusual case that you must avoid sending the "offline_access" scope, then you must override the default value of this setting. This is required if your OIDC provider will reject the request when it includes "offline_access" (e.g. GitLab's OIDC provider). +| *`additionalScopes`* __string array__ | additionalScopes are the additional scopes that will be requested from your OIDC provider in the authorization request during an OIDC Authorization Code Flow and in the token request during a Resource Owner Password Credentials Grant. Note that the "openid" scope will always be requested regardless of the value in this setting, since it is always required according to the OIDC spec. By default, when this field is not set, the Supervisor will request the following scopes: "openid", "offline_access", "email", and "profile". See https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the "offline_access" scope. This default value may change in future versions of Pinniped as the standard evolves, or as common patterns used by providers who implement the standard in the ecosystem evolve. By setting this list to anything other than an empty list, you are overriding the default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. If you do not want any of these scopes to be requested, you may set this list to contain only "openid". Some OIDC providers may also require a scope to get access to the user's group membership, in which case you may wish to include it in this list. Sometimes the scope to request the user's group membership is called "groups", but unfortunately this is not specified in the OIDC standard. Generally speaking, you should include any scopes required to cause the appropriate claims to be the returned by your OIDC provider in the ID token or userinfo endpoint results for those claims which you would like to use in the oidcClaims settings to determine the usernames and group memberships of your Kubernetes users. See your OIDC provider's documentation for more information about what scopes are available to request claims. Additionally, the Pinniped Supervisor requires that your OIDC provider returns refresh tokens to the Supervisor from these authorization flows. For most OIDC providers, the scope required to receive refresh tokens will be "offline_access". See the documentation of your OIDC provider's authorization and token endpoints for its requirements for what to include in the request in order to receive a refresh token in the response, if anything. Note that it may be safe to send "offline_access" even to providers which do not require it, since the provider may ignore scopes that it does not understand or require (see https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). In the unusual case that you must avoid sending the "offline_access" scope, then you must override the default value of this setting. This is required if your OIDC provider will reject the request when it includes "offline_access" (e.g. GitLab's OIDC provider). | *`additionalAuthorizeParameters`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-18-apis-supervisor-idp-v1alpha1-parameter[$$Parameter$$] array__ | additionalAuthorizeParameters are extra query parameters that should be included in the authorize request to your OIDC provider in the authorization request during an OIDC Authorization Code Flow. By default, no extra parameters are sent. The standard parameters that will be sent are "response_type", "scope", "client_id", "state", "nonce", "code_challenge", "code_challenge_method", and "redirect_uri". These parameters cannot be included in this setting. Additionally, the "hd" parameter cannot be included in this setting at this time. The "hd" parameter is used by Google's OIDC provider to provide a hint as to which "hosted domain" the user should use during login. However, Pinniped does not yet support validating the hosted domain in the resulting ID token, so it is not yet safe to use this feature of Google's OIDC provider with Pinniped. This setting does not influence the parameters sent to the token endpoint in the Resource Owner Password Credentials Grant. The Pinniped Supervisor requires that your OIDC provider returns refresh tokens to the Supervisor from the authorization flows. Some OIDC providers may require a certain value for the "prompt" parameter in order to properly request refresh tokens. See the documentation of your OIDC provider's authorization endpoint for its requirements for what to include in the request in order to receive a refresh token in the response, if anything. If your provider requires the prompt parameter to request a refresh token, then include it here. Also note that most providers also require a certain scope to be requested in order to receive refresh tokens. See the additionalScopes setting for more information about using scopes to request refresh tokens. | *`allowPasswordGrant`* __boolean__ | allowPasswordGrant, when true, will allow the use of OAuth 2.0's Resource Owner Password Credentials Grant (see https://datatracker.ietf.org/doc/html/rfc6749#section-4.3) to authenticate to the OIDC provider using a username and password without a web browser, in addition to the usual browser-based OIDC Authorization Code Flow. The Resource Owner Password Credentials Grant is not officially part of the OIDC specification, so it may not be supported by your OIDC provider. If your OIDC provider supports returning ID tokens from a Resource Owner Password Credentials Grant token request, then you can choose to set this field to true. This will allow end users to choose to present their username and password to the kubectl CLI (using the Pinniped plugin) to authenticate to the cluster, without using a web browser to log in as is customary in OIDC Authorization Code Flow. This may be convenient for users, especially for identities from your OIDC provider which are not intended to represent a human actor, such as service accounts performing actions in a CI/CD environment. Even if your OIDC provider supports it, you may wish to disable this behavior by setting this field to false when you prefer to only allow users of this OIDCIdentityProvider to log in via the browser-based OIDC Authorization Code Flow. Using the Resource Owner Password Credentials Grant means that the Pinniped CLI and Pinniped Supervisor will directly handle your end users' passwords (similar to LDAPIdentityProvider), and you will not be able to require multi-factor authentication or use the other web-based login features of your OIDC provider during Resource Owner Password Credentials Grant logins. allowPasswordGrant defaults to false. |=== diff --git a/generated/1.18/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go b/generated/1.18/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go index bae993d0..a53d6f53 100644 --- a/generated/1.18/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go +++ b/generated/1.18/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go @@ -45,8 +45,11 @@ type OIDCAuthorizationConfig struct { // the following scopes: "openid", "offline_access", "email", and "profile". See // https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" // scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the - // "offline_access" scope. By setting this list to anything other than an empty list, you are overriding the + // "offline_access" scope. This default value may change in future versions of Pinniped as the standard evolves, + // or as common patterns used by providers who implement the standard in the ecosystem evolve. + // By setting this list to anything other than an empty list, you are overriding the // default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. + // If you do not want any of these scopes to be requested, you may set this list to contain only "openid". // Some OIDC providers may also require a scope to get access to the user's group membership, in which case you // may wish to include it in this list. Sometimes the scope to request the user's group membership is called // "groups", but unfortunately this is not specified in the OIDC standard. diff --git a/generated/1.18/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml b/generated/1.18/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml index 14f6fd89..8ebd5eb5 100644 --- a/generated/1.18/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml +++ b/generated/1.18/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml @@ -114,32 +114,36 @@ spec: Supervisor will request the following scopes: "openid", "offline_access", "email", and "profile". See https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess - for a description of the "offline_access" scope. By setting - this list to anything other than an empty list, you are overriding - the default value, so you may wish to include some of "offline_access", - "email", and "profile" in your override list. Some OIDC providers - may also require a scope to get access to the user''s group - membership, in which case you may wish to include it in this - list. Sometimes the scope to request the user''s group membership - is called "groups", but unfortunately this is not specified - in the OIDC standard. Generally speaking, you should include - any scopes required to cause the appropriate claims to be the - returned by your OIDC provider in the ID token or userinfo endpoint - results for those claims which you would like to use in the - oidcClaims settings to determine the usernames and group memberships - of your Kubernetes users. See your OIDC provider''s documentation - for more information about what scopes are available to request - claims. Additionally, the Pinniped Supervisor requires that - your OIDC provider returns refresh tokens to the Supervisor - from these authorization flows. For most OIDC providers, the - scope required to receive refresh tokens will be "offline_access". - See the documentation of your OIDC provider''s authorization - and token endpoints for its requirements for what to include - in the request in order to receive a refresh token in the response, - if anything. Note that it may be safe to send "offline_access" - even to providers which do not require it, since the provider - may ignore scopes that it does not understand or require (see - https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). + for a description of the "offline_access" scope. This default + value may change in future versions of Pinniped as the standard + evolves, or as common patterns used by providers who implement + the standard in the ecosystem evolve. By setting this list to + anything other than an empty list, you are overriding the default + value, so you may wish to include some of "offline_access", + "email", and "profile" in your override list. If you do not + want any of these scopes to be requested, you may set this list + to contain only "openid". Some OIDC providers may also require + a scope to get access to the user''s group membership, in which + case you may wish to include it in this list. Sometimes the + scope to request the user''s group membership is called "groups", + but unfortunately this is not specified in the OIDC standard. + Generally speaking, you should include any scopes required to + cause the appropriate claims to be the returned by your OIDC + provider in the ID token or userinfo endpoint results for those + claims which you would like to use in the oidcClaims settings + to determine the usernames and group memberships of your Kubernetes + users. See your OIDC provider''s documentation for more information + about what scopes are available to request claims. Additionally, + the Pinniped Supervisor requires that your OIDC provider returns + refresh tokens to the Supervisor from these authorization flows. + For most OIDC providers, the scope required to receive refresh + tokens will be "offline_access". See the documentation of your + OIDC provider''s authorization and token endpoints for its requirements + for what to include in the request in order to receive a refresh + token in the response, if anything. Note that it may be safe + to send "offline_access" even to providers which do not require + it, since the provider may ignore scopes that it does not understand + or require (see https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). In the unusual case that you must avoid sending the "offline_access" scope, then you must override the default value of this setting. This is required if your OIDC provider will reject the request diff --git a/generated/1.19/README.adoc b/generated/1.19/README.adoc index 0dace9e2..0317faed 100644 --- a/generated/1.19/README.adoc +++ b/generated/1.19/README.adoc @@ -1099,7 +1099,7 @@ OIDCAuthorizationConfig provides information about how to form the OAuth2 author [cols="25a,75a", options="header"] |=== | Field | Description -| *`additionalScopes`* __string array__ | additionalScopes are the additional scopes that will be requested from your OIDC provider in the authorization request during an OIDC Authorization Code Flow and in the token request during a Resource Owner Password Credentials Grant. Note that the "openid" scope will always be requested regardless of the value in this setting, since it is always required according to the OIDC spec. By default, when this field is not set, the Supervisor will request the following scopes: "openid", "offline_access", "email", and "profile". See https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the "offline_access" scope. By setting this list to anything other than an empty list, you are overriding the default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. Some OIDC providers may also require a scope to get access to the user's group membership, in which case you may wish to include it in this list. Sometimes the scope to request the user's group membership is called "groups", but unfortunately this is not specified in the OIDC standard. Generally speaking, you should include any scopes required to cause the appropriate claims to be the returned by your OIDC provider in the ID token or userinfo endpoint results for those claims which you would like to use in the oidcClaims settings to determine the usernames and group memberships of your Kubernetes users. See your OIDC provider's documentation for more information about what scopes are available to request claims. Additionally, the Pinniped Supervisor requires that your OIDC provider returns refresh tokens to the Supervisor from these authorization flows. For most OIDC providers, the scope required to receive refresh tokens will be "offline_access". See the documentation of your OIDC provider's authorization and token endpoints for its requirements for what to include in the request in order to receive a refresh token in the response, if anything. Note that it may be safe to send "offline_access" even to providers which do not require it, since the provider may ignore scopes that it does not understand or require (see https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). In the unusual case that you must avoid sending the "offline_access" scope, then you must override the default value of this setting. This is required if your OIDC provider will reject the request when it includes "offline_access" (e.g. GitLab's OIDC provider). +| *`additionalScopes`* __string array__ | additionalScopes are the additional scopes that will be requested from your OIDC provider in the authorization request during an OIDC Authorization Code Flow and in the token request during a Resource Owner Password Credentials Grant. Note that the "openid" scope will always be requested regardless of the value in this setting, since it is always required according to the OIDC spec. By default, when this field is not set, the Supervisor will request the following scopes: "openid", "offline_access", "email", and "profile". See https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the "offline_access" scope. This default value may change in future versions of Pinniped as the standard evolves, or as common patterns used by providers who implement the standard in the ecosystem evolve. By setting this list to anything other than an empty list, you are overriding the default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. If you do not want any of these scopes to be requested, you may set this list to contain only "openid". Some OIDC providers may also require a scope to get access to the user's group membership, in which case you may wish to include it in this list. Sometimes the scope to request the user's group membership is called "groups", but unfortunately this is not specified in the OIDC standard. Generally speaking, you should include any scopes required to cause the appropriate claims to be the returned by your OIDC provider in the ID token or userinfo endpoint results for those claims which you would like to use in the oidcClaims settings to determine the usernames and group memberships of your Kubernetes users. See your OIDC provider's documentation for more information about what scopes are available to request claims. Additionally, the Pinniped Supervisor requires that your OIDC provider returns refresh tokens to the Supervisor from these authorization flows. For most OIDC providers, the scope required to receive refresh tokens will be "offline_access". See the documentation of your OIDC provider's authorization and token endpoints for its requirements for what to include in the request in order to receive a refresh token in the response, if anything. Note that it may be safe to send "offline_access" even to providers which do not require it, since the provider may ignore scopes that it does not understand or require (see https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). In the unusual case that you must avoid sending the "offline_access" scope, then you must override the default value of this setting. This is required if your OIDC provider will reject the request when it includes "offline_access" (e.g. GitLab's OIDC provider). | *`additionalAuthorizeParameters`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-19-apis-supervisor-idp-v1alpha1-parameter[$$Parameter$$] array__ | additionalAuthorizeParameters are extra query parameters that should be included in the authorize request to your OIDC provider in the authorization request during an OIDC Authorization Code Flow. By default, no extra parameters are sent. The standard parameters that will be sent are "response_type", "scope", "client_id", "state", "nonce", "code_challenge", "code_challenge_method", and "redirect_uri". These parameters cannot be included in this setting. Additionally, the "hd" parameter cannot be included in this setting at this time. The "hd" parameter is used by Google's OIDC provider to provide a hint as to which "hosted domain" the user should use during login. However, Pinniped does not yet support validating the hosted domain in the resulting ID token, so it is not yet safe to use this feature of Google's OIDC provider with Pinniped. This setting does not influence the parameters sent to the token endpoint in the Resource Owner Password Credentials Grant. The Pinniped Supervisor requires that your OIDC provider returns refresh tokens to the Supervisor from the authorization flows. Some OIDC providers may require a certain value for the "prompt" parameter in order to properly request refresh tokens. See the documentation of your OIDC provider's authorization endpoint for its requirements for what to include in the request in order to receive a refresh token in the response, if anything. If your provider requires the prompt parameter to request a refresh token, then include it here. Also note that most providers also require a certain scope to be requested in order to receive refresh tokens. See the additionalScopes setting for more information about using scopes to request refresh tokens. | *`allowPasswordGrant`* __boolean__ | allowPasswordGrant, when true, will allow the use of OAuth 2.0's Resource Owner Password Credentials Grant (see https://datatracker.ietf.org/doc/html/rfc6749#section-4.3) to authenticate to the OIDC provider using a username and password without a web browser, in addition to the usual browser-based OIDC Authorization Code Flow. The Resource Owner Password Credentials Grant is not officially part of the OIDC specification, so it may not be supported by your OIDC provider. If your OIDC provider supports returning ID tokens from a Resource Owner Password Credentials Grant token request, then you can choose to set this field to true. This will allow end users to choose to present their username and password to the kubectl CLI (using the Pinniped plugin) to authenticate to the cluster, without using a web browser to log in as is customary in OIDC Authorization Code Flow. This may be convenient for users, especially for identities from your OIDC provider which are not intended to represent a human actor, such as service accounts performing actions in a CI/CD environment. Even if your OIDC provider supports it, you may wish to disable this behavior by setting this field to false when you prefer to only allow users of this OIDCIdentityProvider to log in via the browser-based OIDC Authorization Code Flow. Using the Resource Owner Password Credentials Grant means that the Pinniped CLI and Pinniped Supervisor will directly handle your end users' passwords (similar to LDAPIdentityProvider), and you will not be able to require multi-factor authentication or use the other web-based login features of your OIDC provider during Resource Owner Password Credentials Grant logins. allowPasswordGrant defaults to false. |=== diff --git a/generated/1.19/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go b/generated/1.19/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go index bae993d0..a53d6f53 100644 --- a/generated/1.19/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go +++ b/generated/1.19/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go @@ -45,8 +45,11 @@ type OIDCAuthorizationConfig struct { // the following scopes: "openid", "offline_access", "email", and "profile". See // https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" // scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the - // "offline_access" scope. By setting this list to anything other than an empty list, you are overriding the + // "offline_access" scope. This default value may change in future versions of Pinniped as the standard evolves, + // or as common patterns used by providers who implement the standard in the ecosystem evolve. + // By setting this list to anything other than an empty list, you are overriding the // default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. + // If you do not want any of these scopes to be requested, you may set this list to contain only "openid". // Some OIDC providers may also require a scope to get access to the user's group membership, in which case you // may wish to include it in this list. Sometimes the scope to request the user's group membership is called // "groups", but unfortunately this is not specified in the OIDC standard. diff --git a/generated/1.19/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml b/generated/1.19/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml index 14f6fd89..8ebd5eb5 100644 --- a/generated/1.19/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml +++ b/generated/1.19/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml @@ -114,32 +114,36 @@ spec: Supervisor will request the following scopes: "openid", "offline_access", "email", and "profile". See https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess - for a description of the "offline_access" scope. By setting - this list to anything other than an empty list, you are overriding - the default value, so you may wish to include some of "offline_access", - "email", and "profile" in your override list. Some OIDC providers - may also require a scope to get access to the user''s group - membership, in which case you may wish to include it in this - list. Sometimes the scope to request the user''s group membership - is called "groups", but unfortunately this is not specified - in the OIDC standard. Generally speaking, you should include - any scopes required to cause the appropriate claims to be the - returned by your OIDC provider in the ID token or userinfo endpoint - results for those claims which you would like to use in the - oidcClaims settings to determine the usernames and group memberships - of your Kubernetes users. See your OIDC provider''s documentation - for more information about what scopes are available to request - claims. Additionally, the Pinniped Supervisor requires that - your OIDC provider returns refresh tokens to the Supervisor - from these authorization flows. For most OIDC providers, the - scope required to receive refresh tokens will be "offline_access". - See the documentation of your OIDC provider''s authorization - and token endpoints for its requirements for what to include - in the request in order to receive a refresh token in the response, - if anything. Note that it may be safe to send "offline_access" - even to providers which do not require it, since the provider - may ignore scopes that it does not understand or require (see - https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). + for a description of the "offline_access" scope. This default + value may change in future versions of Pinniped as the standard + evolves, or as common patterns used by providers who implement + the standard in the ecosystem evolve. By setting this list to + anything other than an empty list, you are overriding the default + value, so you may wish to include some of "offline_access", + "email", and "profile" in your override list. If you do not + want any of these scopes to be requested, you may set this list + to contain only "openid". Some OIDC providers may also require + a scope to get access to the user''s group membership, in which + case you may wish to include it in this list. Sometimes the + scope to request the user''s group membership is called "groups", + but unfortunately this is not specified in the OIDC standard. + Generally speaking, you should include any scopes required to + cause the appropriate claims to be the returned by your OIDC + provider in the ID token or userinfo endpoint results for those + claims which you would like to use in the oidcClaims settings + to determine the usernames and group memberships of your Kubernetes + users. See your OIDC provider''s documentation for more information + about what scopes are available to request claims. Additionally, + the Pinniped Supervisor requires that your OIDC provider returns + refresh tokens to the Supervisor from these authorization flows. + For most OIDC providers, the scope required to receive refresh + tokens will be "offline_access". See the documentation of your + OIDC provider''s authorization and token endpoints for its requirements + for what to include in the request in order to receive a refresh + token in the response, if anything. Note that it may be safe + to send "offline_access" even to providers which do not require + it, since the provider may ignore scopes that it does not understand + or require (see https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). In the unusual case that you must avoid sending the "offline_access" scope, then you must override the default value of this setting. This is required if your OIDC provider will reject the request diff --git a/generated/1.20/README.adoc b/generated/1.20/README.adoc index cbdcb6fd..faf7ad54 100644 --- a/generated/1.20/README.adoc +++ b/generated/1.20/README.adoc @@ -1099,7 +1099,7 @@ OIDCAuthorizationConfig provides information about how to form the OAuth2 author [cols="25a,75a", options="header"] |=== | Field | Description -| *`additionalScopes`* __string array__ | additionalScopes are the additional scopes that will be requested from your OIDC provider in the authorization request during an OIDC Authorization Code Flow and in the token request during a Resource Owner Password Credentials Grant. Note that the "openid" scope will always be requested regardless of the value in this setting, since it is always required according to the OIDC spec. By default, when this field is not set, the Supervisor will request the following scopes: "openid", "offline_access", "email", and "profile". See https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the "offline_access" scope. By setting this list to anything other than an empty list, you are overriding the default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. Some OIDC providers may also require a scope to get access to the user's group membership, in which case you may wish to include it in this list. Sometimes the scope to request the user's group membership is called "groups", but unfortunately this is not specified in the OIDC standard. Generally speaking, you should include any scopes required to cause the appropriate claims to be the returned by your OIDC provider in the ID token or userinfo endpoint results for those claims which you would like to use in the oidcClaims settings to determine the usernames and group memberships of your Kubernetes users. See your OIDC provider's documentation for more information about what scopes are available to request claims. Additionally, the Pinniped Supervisor requires that your OIDC provider returns refresh tokens to the Supervisor from these authorization flows. For most OIDC providers, the scope required to receive refresh tokens will be "offline_access". See the documentation of your OIDC provider's authorization and token endpoints for its requirements for what to include in the request in order to receive a refresh token in the response, if anything. Note that it may be safe to send "offline_access" even to providers which do not require it, since the provider may ignore scopes that it does not understand or require (see https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). In the unusual case that you must avoid sending the "offline_access" scope, then you must override the default value of this setting. This is required if your OIDC provider will reject the request when it includes "offline_access" (e.g. GitLab's OIDC provider). +| *`additionalScopes`* __string array__ | additionalScopes are the additional scopes that will be requested from your OIDC provider in the authorization request during an OIDC Authorization Code Flow and in the token request during a Resource Owner Password Credentials Grant. Note that the "openid" scope will always be requested regardless of the value in this setting, since it is always required according to the OIDC spec. By default, when this field is not set, the Supervisor will request the following scopes: "openid", "offline_access", "email", and "profile". See https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the "offline_access" scope. This default value may change in future versions of Pinniped as the standard evolves, or as common patterns used by providers who implement the standard in the ecosystem evolve. By setting this list to anything other than an empty list, you are overriding the default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. If you do not want any of these scopes to be requested, you may set this list to contain only "openid". Some OIDC providers may also require a scope to get access to the user's group membership, in which case you may wish to include it in this list. Sometimes the scope to request the user's group membership is called "groups", but unfortunately this is not specified in the OIDC standard. Generally speaking, you should include any scopes required to cause the appropriate claims to be the returned by your OIDC provider in the ID token or userinfo endpoint results for those claims which you would like to use in the oidcClaims settings to determine the usernames and group memberships of your Kubernetes users. See your OIDC provider's documentation for more information about what scopes are available to request claims. Additionally, the Pinniped Supervisor requires that your OIDC provider returns refresh tokens to the Supervisor from these authorization flows. For most OIDC providers, the scope required to receive refresh tokens will be "offline_access". See the documentation of your OIDC provider's authorization and token endpoints for its requirements for what to include in the request in order to receive a refresh token in the response, if anything. Note that it may be safe to send "offline_access" even to providers which do not require it, since the provider may ignore scopes that it does not understand or require (see https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). In the unusual case that you must avoid sending the "offline_access" scope, then you must override the default value of this setting. This is required if your OIDC provider will reject the request when it includes "offline_access" (e.g. GitLab's OIDC provider). | *`additionalAuthorizeParameters`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-20-apis-supervisor-idp-v1alpha1-parameter[$$Parameter$$] array__ | additionalAuthorizeParameters are extra query parameters that should be included in the authorize request to your OIDC provider in the authorization request during an OIDC Authorization Code Flow. By default, no extra parameters are sent. The standard parameters that will be sent are "response_type", "scope", "client_id", "state", "nonce", "code_challenge", "code_challenge_method", and "redirect_uri". These parameters cannot be included in this setting. Additionally, the "hd" parameter cannot be included in this setting at this time. The "hd" parameter is used by Google's OIDC provider to provide a hint as to which "hosted domain" the user should use during login. However, Pinniped does not yet support validating the hosted domain in the resulting ID token, so it is not yet safe to use this feature of Google's OIDC provider with Pinniped. This setting does not influence the parameters sent to the token endpoint in the Resource Owner Password Credentials Grant. The Pinniped Supervisor requires that your OIDC provider returns refresh tokens to the Supervisor from the authorization flows. Some OIDC providers may require a certain value for the "prompt" parameter in order to properly request refresh tokens. See the documentation of your OIDC provider's authorization endpoint for its requirements for what to include in the request in order to receive a refresh token in the response, if anything. If your provider requires the prompt parameter to request a refresh token, then include it here. Also note that most providers also require a certain scope to be requested in order to receive refresh tokens. See the additionalScopes setting for more information about using scopes to request refresh tokens. | *`allowPasswordGrant`* __boolean__ | allowPasswordGrant, when true, will allow the use of OAuth 2.0's Resource Owner Password Credentials Grant (see https://datatracker.ietf.org/doc/html/rfc6749#section-4.3) to authenticate to the OIDC provider using a username and password without a web browser, in addition to the usual browser-based OIDC Authorization Code Flow. The Resource Owner Password Credentials Grant is not officially part of the OIDC specification, so it may not be supported by your OIDC provider. If your OIDC provider supports returning ID tokens from a Resource Owner Password Credentials Grant token request, then you can choose to set this field to true. This will allow end users to choose to present their username and password to the kubectl CLI (using the Pinniped plugin) to authenticate to the cluster, without using a web browser to log in as is customary in OIDC Authorization Code Flow. This may be convenient for users, especially for identities from your OIDC provider which are not intended to represent a human actor, such as service accounts performing actions in a CI/CD environment. Even if your OIDC provider supports it, you may wish to disable this behavior by setting this field to false when you prefer to only allow users of this OIDCIdentityProvider to log in via the browser-based OIDC Authorization Code Flow. Using the Resource Owner Password Credentials Grant means that the Pinniped CLI and Pinniped Supervisor will directly handle your end users' passwords (similar to LDAPIdentityProvider), and you will not be able to require multi-factor authentication or use the other web-based login features of your OIDC provider during Resource Owner Password Credentials Grant logins. allowPasswordGrant defaults to false. |=== diff --git a/generated/1.20/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go b/generated/1.20/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go index bae993d0..a53d6f53 100644 --- a/generated/1.20/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go +++ b/generated/1.20/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go @@ -45,8 +45,11 @@ type OIDCAuthorizationConfig struct { // the following scopes: "openid", "offline_access", "email", and "profile". See // https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" // scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the - // "offline_access" scope. By setting this list to anything other than an empty list, you are overriding the + // "offline_access" scope. This default value may change in future versions of Pinniped as the standard evolves, + // or as common patterns used by providers who implement the standard in the ecosystem evolve. + // By setting this list to anything other than an empty list, you are overriding the // default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. + // If you do not want any of these scopes to be requested, you may set this list to contain only "openid". // Some OIDC providers may also require a scope to get access to the user's group membership, in which case you // may wish to include it in this list. Sometimes the scope to request the user's group membership is called // "groups", but unfortunately this is not specified in the OIDC standard. diff --git a/generated/1.20/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml b/generated/1.20/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml index 14f6fd89..8ebd5eb5 100644 --- a/generated/1.20/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml +++ b/generated/1.20/crds/idp.supervisor.pinniped.dev_oidcidentityproviders.yaml @@ -114,32 +114,36 @@ spec: Supervisor will request the following scopes: "openid", "offline_access", "email", and "profile". See https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess - for a description of the "offline_access" scope. By setting - this list to anything other than an empty list, you are overriding - the default value, so you may wish to include some of "offline_access", - "email", and "profile" in your override list. Some OIDC providers - may also require a scope to get access to the user''s group - membership, in which case you may wish to include it in this - list. Sometimes the scope to request the user''s group membership - is called "groups", but unfortunately this is not specified - in the OIDC standard. Generally speaking, you should include - any scopes required to cause the appropriate claims to be the - returned by your OIDC provider in the ID token or userinfo endpoint - results for those claims which you would like to use in the - oidcClaims settings to determine the usernames and group memberships - of your Kubernetes users. See your OIDC provider''s documentation - for more information about what scopes are available to request - claims. Additionally, the Pinniped Supervisor requires that - your OIDC provider returns refresh tokens to the Supervisor - from these authorization flows. For most OIDC providers, the - scope required to receive refresh tokens will be "offline_access". - See the documentation of your OIDC provider''s authorization - and token endpoints for its requirements for what to include - in the request in order to receive a refresh token in the response, - if anything. Note that it may be safe to send "offline_access" - even to providers which do not require it, since the provider - may ignore scopes that it does not understand or require (see - https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). + for a description of the "offline_access" scope. This default + value may change in future versions of Pinniped as the standard + evolves, or as common patterns used by providers who implement + the standard in the ecosystem evolve. By setting this list to + anything other than an empty list, you are overriding the default + value, so you may wish to include some of "offline_access", + "email", and "profile" in your override list. If you do not + want any of these scopes to be requested, you may set this list + to contain only "openid". Some OIDC providers may also require + a scope to get access to the user''s group membership, in which + case you may wish to include it in this list. Sometimes the + scope to request the user''s group membership is called "groups", + but unfortunately this is not specified in the OIDC standard. + Generally speaking, you should include any scopes required to + cause the appropriate claims to be the returned by your OIDC + provider in the ID token or userinfo endpoint results for those + claims which you would like to use in the oidcClaims settings + to determine the usernames and group memberships of your Kubernetes + users. See your OIDC provider''s documentation for more information + about what scopes are available to request claims. Additionally, + the Pinniped Supervisor requires that your OIDC provider returns + refresh tokens to the Supervisor from these authorization flows. + For most OIDC providers, the scope required to receive refresh + tokens will be "offline_access". See the documentation of your + OIDC provider''s authorization and token endpoints for its requirements + for what to include in the request in order to receive a refresh + token in the response, if anything. Note that it may be safe + to send "offline_access" even to providers which do not require + it, since the provider may ignore scopes that it does not understand + or require (see https://datatracker.ietf.org/doc/html/rfc6749#section-3.3). In the unusual case that you must avoid sending the "offline_access" scope, then you must override the default value of this setting. This is required if your OIDC provider will reject the request diff --git a/generated/latest/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go b/generated/latest/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go index bae993d0..a53d6f53 100644 --- a/generated/latest/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go +++ b/generated/latest/apis/supervisor/idp/v1alpha1/types_oidcidentityprovider.go @@ -45,8 +45,11 @@ type OIDCAuthorizationConfig struct { // the following scopes: "openid", "offline_access", "email", and "profile". See // https://openid.net/specs/openid-connect-core-1_0.html#ScopeClaims for a description of the "profile" and "email" // scopes. See https://openid.net/specs/openid-connect-core-1_0.html#OfflineAccess for a description of the - // "offline_access" scope. By setting this list to anything other than an empty list, you are overriding the + // "offline_access" scope. This default value may change in future versions of Pinniped as the standard evolves, + // or as common patterns used by providers who implement the standard in the ecosystem evolve. + // By setting this list to anything other than an empty list, you are overriding the // default value, so you may wish to include some of "offline_access", "email", and "profile" in your override list. + // If you do not want any of these scopes to be requested, you may set this list to contain only "openid". // Some OIDC providers may also require a scope to get access to the user's group membership, in which case you // may wish to include it in this list. Sometimes the scope to request the user's group membership is called // "groups", but unfortunately this is not specified in the OIDC standard. diff --git a/internal/controller/supervisorconfig/oidcupstreamwatcher/oidc_upstream_watcher.go b/internal/controller/supervisorconfig/oidcupstreamwatcher/oidc_upstream_watcher.go index 9719be44..34e81631 100644 --- a/internal/controller/supervisorconfig/oidcupstreamwatcher/oidc_upstream_watcher.go +++ b/internal/controller/supervisorconfig/oidcupstreamwatcher/oidc_upstream_watcher.go @@ -12,10 +12,11 @@ import ( "fmt" "net/http" "net/url" - "sort" "strings" "time" + "k8s.io/apimachinery/pkg/util/sets" + "github.com/coreos/go-oidc/v3/oidc" "github.com/go-logr/logr" "golang.org/x/oauth2" @@ -427,20 +428,14 @@ func computeScopes(additionalScopes []string) []string { } // Otherwise, first compute the unique set of scopes, including "openid" (de-duplicate). - set := make(map[string]bool, len(additionalScopes)+1) - set["openid"] = true + set := sets.NewString() + set.Insert("openid") for _, s := range additionalScopes { - set[s] = true + set.Insert(s) } - // Then grab all the keys and sort them. - scopes := make([]string, 0, len(set)) - for s := range set { - scopes = append(scopes, s) - } - sort.Strings(scopes) - - return scopes + // Return the set as a sorted list. + return set.List() } func truncateMostLongErr(err error) string { diff --git a/internal/fositestorage/accesstoken/accesstoken.go b/internal/fositestorage/accesstoken/accesstoken.go index fc2427ad..dbd57fb3 100644 --- a/internal/fositestorage/accesstoken/accesstoken.go +++ b/internal/fositestorage/accesstoken/accesstoken.go @@ -26,6 +26,8 @@ const ( ErrInvalidAccessTokenRequestVersion = constable.Error("access token request data has wrong version") ErrInvalidAccessTokenRequestData = constable.Error("access token request data must be present") + // Version 1 was the initial release of storage. + // Version 2 is when we switched to storing psession.PinnipedSession inside the fosite request. accessTokenStorageVersion = "2" ) diff --git a/internal/fositestorage/authorizationcode/authorizationcode.go b/internal/fositestorage/authorizationcode/authorizationcode.go index a76f684f..b259e406 100644 --- a/internal/fositestorage/authorizationcode/authorizationcode.go +++ b/internal/fositestorage/authorizationcode/authorizationcode.go @@ -27,6 +27,8 @@ const ( ErrInvalidAuthorizeRequestData = constable.Error("authorization request data must be present") ErrInvalidAuthorizeRequestVersion = constable.Error("authorization request data has wrong version") + // Version 1 was the initial release of storage. + // Version 2 is when we switched to storing psession.PinnipedSession inside the fosite request. authorizeCodeStorageVersion = "2" ) diff --git a/internal/fositestorage/openidconnect/openidconnect.go b/internal/fositestorage/openidconnect/openidconnect.go index f1e2200f..81699410 100644 --- a/internal/fositestorage/openidconnect/openidconnect.go +++ b/internal/fositestorage/openidconnect/openidconnect.go @@ -28,6 +28,8 @@ const ( ErrInvalidOIDCRequestData = constable.Error("oidc request data must be present") ErrMalformedAuthorizationCode = constable.Error("malformed authorization code") + // Version 1 was the initial release of storage. + // Version 2 is when we switched to storing psession.PinnipedSession inside the fosite request. oidcStorageVersion = "2" ) diff --git a/internal/fositestorage/pkce/pkce.go b/internal/fositestorage/pkce/pkce.go index cf6cec69..cbe566bd 100644 --- a/internal/fositestorage/pkce/pkce.go +++ b/internal/fositestorage/pkce/pkce.go @@ -26,6 +26,8 @@ const ( ErrInvalidPKCERequestVersion = constable.Error("pkce request data has wrong version") ErrInvalidPKCERequestData = constable.Error("pkce request data must be present") + // Version 1 was the initial release of storage. + // Version 2 is when we switched to storing psession.PinnipedSession inside the fosite request. pkceStorageVersion = "2" ) diff --git a/internal/fositestorage/refreshtoken/refreshtoken.go b/internal/fositestorage/refreshtoken/refreshtoken.go index a456ed75..c2d4336c 100644 --- a/internal/fositestorage/refreshtoken/refreshtoken.go +++ b/internal/fositestorage/refreshtoken/refreshtoken.go @@ -26,6 +26,8 @@ const ( ErrInvalidRefreshTokenRequestVersion = constable.Error("refresh token request data has wrong version") ErrInvalidRefreshTokenRequestData = constable.Error("refresh token request data must be present") + // Version 1 was the initial release of storage. + // Version 2 is when we switched to storing psession.PinnipedSession inside the fosite request. refreshTokenStorageVersion = "2" ) diff --git a/internal/oidc/auth/auth_handler.go b/internal/oidc/auth/auth_handler.go index 270678bc..4c457faf 100644 --- a/internal/oidc/auth/auth_handler.go +++ b/internal/oidc/auth/auth_handler.go @@ -160,7 +160,8 @@ func handleAuthRequestForOIDCUpstreamPasswordGrant( } if token.RefreshToken == nil || token.RefreshToken.Token == "" { - plog.Warning("refresh token not returned by upstream provider during password grant", + plog.Warning("refresh token not returned by upstream provider during password grant, "+ + "please check configuration of OIDCIdentityProvider and the client in the upstream provider's API/UI", "upstreamName", oidcUpstream.GetName(), "scopes", oidcUpstream.GetScopes()) return writeAuthorizeError(w, oauthHelper, authorizeRequester, diff --git a/internal/oidc/callback/callback_handler.go b/internal/oidc/callback/callback_handler.go index e99d1678..22f37a55 100644 --- a/internal/oidc/callback/callback_handler.go +++ b/internal/oidc/callback/callback_handler.go @@ -70,7 +70,8 @@ func NewHandler( } if token.RefreshToken == nil || token.RefreshToken.Token == "" { - plog.Warning("refresh token not returned by upstream provider during authcode exchange", + plog.Warning("refresh token not returned by upstream provider during authcode exchange, "+ + "please check configuration of OIDCIdentityProvider and the client in the upstream provider's API/UI", "upstreamName", upstreamIDPConfig.GetName(), "scopes", upstreamIDPConfig.GetScopes(), "additionalParams", upstreamIDPConfig.GetAdditionalAuthcodeParams()) diff --git a/internal/oidc/provider/dynamic_upstream_idp_provider.go b/internal/oidc/provider/dynamic_upstream_idp_provider.go index 9ece5f4d..88710f00 100644 --- a/internal/oidc/provider/dynamic_upstream_idp_provider.go +++ b/internal/oidc/provider/dynamic_upstream_idp_provider.go @@ -64,7 +64,7 @@ type UpstreamOIDCIdentityProviderI interface { ) (*oidctypes.Token, error) // PerformRefresh will call the provider's token endpoint to perform a refresh grant. The provider may or may not - // return a new ID or refresh token in the response. If it returns an ID token, then use ValidateRefresh to + // return a new ID or refresh token in the response. If it returns an ID token, then use ValidateToken to // validate the ID token. PerformRefresh(ctx context.Context, refreshToken string) (*oauth2.Token, error) diff --git a/pkg/oidcclient/login.go b/pkg/oidcclient/login.go index 3d62e05d..46319490 100644 --- a/pkg/oidcclient/login.go +++ b/pkg/oidcclient/login.go @@ -813,6 +813,7 @@ func (h *handlerState) handleRefresh(ctx context.Context, refreshToken *oidctype refreshed, err := upstreamOIDCIdentityProvider.PerformRefresh(ctx, refreshToken.Token) if err != nil { // Ignore errors during refresh, but return nil which will trigger the full login flow. + h.logger.V(debugLogLevel).Info("Pinniped: Refresh failed.") return nil, nil } diff --git a/pkg/oidcclient/login_test.go b/pkg/oidcclient/login_test.go index 2c30ffb0..e2548ebd 100644 --- a/pkg/oidcclient/login_test.go +++ b/pkg/oidcclient/login_test.go @@ -513,6 +513,7 @@ func TestLogin(t *testing.T) { // nolint:gocyclo wantLogs: []string{ `"level"=4 "msg"="Pinniped: Performing OIDC discovery" "issuer"="` + successServer.URL + `"`, `"level"=4 "msg"="Pinniped: Refreshing cached token."`, + `"level"=4 "msg"="Pinniped: Refresh failed."`, `"msg"="could not open callback listener" "error"="some listen error"`, }, // Expect this to fall through to the authorization code flow, so it fails here. diff --git a/site/content/docs/howto/configure-supervisor-with-gitlab.md b/site/content/docs/howto/configure-supervisor-with-gitlab.md index 97058c16..c7998470 100644 --- a/site/content/docs/howto/configure-supervisor-with-gitlab.md +++ b/site/content/docs/howto/configure-supervisor-with-gitlab.md @@ -32,8 +32,7 @@ For example, to create a user-owned application: 1. Enter the redirect URI. This is the `spec.issuer` you configured in your `FederationDomain` appended with `/callback`. 1. Check the box saying that the application is _Confidential_. This is required and will cause GitLab to autogenerate a client ID and client secret for your application. - 1. Check the box saying to _Expire Access Tokens_ to cause refresh tokens to be returned to the Supervisor. This is - required starting in Pinniped v0.13.0. + 1. Check the box saying to _Expire Access Tokens_ to cause refresh tokens to be returned to the Supervisor. 1. Select scope `openid`. This is required to get ID tokens. Also, this provides access to the `nickname` (GitLab username) and `groups` (GitLab groups) claims in the ID tokens. 1. Optionally select other scopes which might provide access to other claims that you might want to use to determine @@ -69,7 +68,9 @@ spec: additionalScopes: [openid] # If you would also like to allow your end users to authenticate using - # a password grant, then change this to true. + # a password grant, then change this to true. See + # https://docs.gitlab.com/ee/api/oauth2.html#resource-owner-password-credentials-flow + # for more information about using the password grant with GitLab. allowPasswordGrant: false # Specify how GitLab claims are mapped to Kubernetes identities. diff --git a/site/content/docs/howto/configure-supervisor-with-okta.md b/site/content/docs/howto/configure-supervisor-with-okta.md index 62110444..d90c7d82 100644 --- a/site/content/docs/howto/configure-supervisor-with-okta.md +++ b/site/content/docs/howto/configure-supervisor-with-okta.md @@ -36,9 +36,9 @@ For example, to create an app: password grant flow to your end users, then choose `Native Application` instead. 1. Enter a name for your app, such as "My Kubernetes Clusters". 1. If you chose to create a `Web Application` then in the General Settings section, choose Grant Types - `Authorization Code` and `Refresh Token`. Starting in Pinniped v0.13.0, the `Refresh Token` grant is required. + `Authorization Code` and `Refresh Token`. 1. If you chose `Native Application` then in the General Settings section, choose Grant Types `Authorization Code`, - `Refresh Token`, and `Resource Owner Password`. Starting in Pinniped v0.13.0, the `Refresh Token` grant is required. + `Refresh Token`, and `Resource Owner Password`. 1. Enter the sign-in redirect URI. This is the `spec.issuer` you configured in your `FederationDomain` appended with `/callback`. 1. Optionally select `Limit access to selected groups` to restrict which Okta users can log in to Kubernetes using this integration. 1. Save the app and make note of the _Client ID_ and _Client secret_. If you chose to create a `Native Application`