Skip to content

feat(oidc): support refresh token flow without id_token#3151

Open
appleboy wants to merge 1 commit into
vmware:mainfrom
appleboy:feature/skip-require-id-token-on-refresh
Open

feat(oidc): support refresh token flow without id_token#3151
appleboy wants to merge 1 commit into
vmware:mainfrom
appleboy:feature/skip-require-id-token-on-refresh

Conversation

@appleboy

@appleboy appleboy commented Jun 24, 2026

Copy link
Copy Markdown

Some OIDC providers (e.g. AuthGate) do not return an id_token in their refresh token response.
Pinniped's handleRefresh() previously required an id_token unconditionally, causing silent
refresh failures and triggering a browser-based re-login every time the token expired.

This PR adds an opt-in flag to allow the refresh flow to succeed without an id_token,
falling back to the access_token when building the ExecCredential response.

Changes:

  • Add --skip-require-id-token-on-refresh flag to pinniped login oidc: when set, the refresh
    flow calls ValidateTokenAndMergeWithUserInfo with requireIDToken=false and returns the
    access_token as the credential when id_token is absent
  • Add --oidc-skip-require-id-token-on-refresh flag to pinniped get kubeconfig: automatically
    embeds --skip-require-id-token-on-refresh into the generated kubeconfig exec args
  • Add WithRequireIDTokenOnRefresh(bool) Option to pkg/oidcclient; defaults to true to
    preserve existing behavior for all other providers
  • Extend tokenCredential() to accept *oidctypes.Token and fall back to AccessToken when
    IDToken is nil; extract applyTokenToStatus() helper to remove duplicated logic
  • Add nil guard with a clear error message when --skip-require-id-token-on-refresh is used
    together with --enable-concierge (incompatible combination)
  • Update OIDCClientOptions interface and its GoMock implementation
  • Add unit tests covering the new happy path, default behavior preservation, and refresh failure

Release note:

Add --skip-require-id-token-on-refresh flag to pinniped login oidc and
--oidc-skip-require-id-token-on-refresh flag to pinniped get kubeconfig.
When enabled, the OIDC refresh token flow no longer requires the provider to
return an id_token, and falls back to using the access_token as the cluster
credential. This is intended for use with non-Supervisor OIDC providers (such as
AuthGate) that omit id_token from their refresh token response. Default behavior
is unchanged. This flag is incompatible with --enable-concierge.

- add --skip-require-id-token-on-refresh flag to login oidc command
- add --oidc-skip-require-id-token-on-refresh flag to get kubeconfig, auto-embedded in exec args
- add WithRequireIDTokenOnRefresh(bool) Option; defaults to true for backward compatibility
- make handleRefresh() use the configurable requireIDToken value instead of hardcoded true
- extend tokenCredential() to accept *oidctypes.Token and fall back to AccessToken when IDToken is nil
- add nil guard with clear error when --enable-concierge is used without an id_token
- update OIDCClientOptions interface and mock with new method
- add unit tests covering happy path, default behavior, and error cases

Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>
@netlify

netlify Bot commented Jun 24, 2026

Copy link
Copy Markdown

Deploy Preview for pinniped-dev canceled.

Name Link
🔨 Latest commit 225ffe5
🔍 Latest deploy log https://app.netlify.com/projects/pinniped-dev/deploys/6a3b815618f7c50008486f88

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant