Skip to content

Only create the dex TLS key pair when dex is enabled - #5141

Open
tmjd wants to merge 1 commit into
tigera:masterfrom
tmjd:tsla-11722-dex-keypair-only-when-enabled
Open

Only create the dex TLS key pair when dex is enabled#5141
tmjd wants to merge 1 commit into
tigera:masterfrom
tmjd:tsla-11722-dex-keypair-only-when-enabled

Conversation

@tmjd

@tmjd tmjd commented Aug 5, 2026

Copy link
Copy Markdown
Member

Description

Bug fix. utils.DexEnabled() returns false when Authentication.spec.oidc.type is Tigera, and dex is not deployed in that case. The authentication controller nonetheless calls GetOrCreateKeyPair() for tigera-dex-tls unconditionally (authentication_controller.go:282), which generates a new key pair whenever the existing secret is missing, expired or otherwise unusable.

The component that persists that key pair — rcertificatemanagement.CertificateManagement(...) — is only appended to components when enableDex is true. So on a cluster that does not run dex, nothing ever writes the newly generated secret. The result is that every reconcile generates and immediately discards an RSA key pair, and an expired tigera-dex-tls secret is re-detected forever:

{"level":"info","logger":"tls","msg":"KeyPair is an expired legacy operator cert, make a new one","name":"tigera-dex-tls"}

This never converges: while dex is disabled nothing can replace the expired secret, so the same log line repeats on every reconcile indefinitely. The cost is wasted key generation and signing on a hot controller, plus permanent log noise.

What changed

  • pkg/controller/authentication/authentication_controller.go — hoist enableDex (it only depends on the already-fetched Authentication) above the point where the key pair is built, and only call GetOrCreateKeyPair() when dex is enabled. CheckKeyPairWarnings() is guarded the same way, since it dereferences the key pair.
  • pkg/render/dex.goObjects() built c.deployment() and c.configMap() before checking DeleteDex, and both dereference c.cfg.TLSKeyPair, so a nil key pair would panic on the teardown path. Those two objects are only ever deleted on that path, so they are now identified by name and GVK instead of being fully rendered.

Not changed: when dex is enabled the behaviour is identical, and this does not alter the contents of any rendered object.

Testing

  • New unit test in pkg/render/dex_test.go covering DeleteDex: true with a nil TLSKeyPair, asserting nothing is rendered for creation and that the Deployment and ConfigMap are in the delete list. This test panics without the dex.go change.
  • go test ./pkg/render — 516 specs pass.
  • go test ./pkg/controller/authentication/... — passes.
  • gofmt clean; go vet clean on both changed packages.

Components affected

The authentication controller and the dex renderer only. Clusters using oidc.type other than Tigera (i.e. those that actually deploy dex) are unaffected.

Release Note

Stop generating a new tigera-dex-tls key pair on every reconcile when dex is not deployed.

For PR author

  • Tests for change.
  • If changing pkg/apis/, run make gen-files
  • If changing versions, run make gen-versions

For PR reviewers

A note for code reviewers - all pull requests must have the following:

  • Milestone set according to targeted release.
  • Appropriate labels:
    • kind/bug if this is a bugfix.
    • kind/enhancement if this is a a new feature.
    • enterprise if this PR applies to Calico Enterprise only.

Comment thread pkg/render/dex.go
utils.DexEnabled() returns false when Authentication.spec.oidc.type is
Tigera, and dex is not deployed in that case. The authentication
controller nonetheless called GetOrCreateKeyPair() for tigera-dex-tls
unconditionally, which generates a new key pair whenever the existing
secret is missing, expired or otherwise unusable.

The component that persists that key pair is only rendered when dex is
enabled, so on those clusters nothing ever writes the new secret. Every
reconcile therefore generated and discarded a key pair, and an expired
tigera-dex-tls secret was re-detected indefinitely, producing a steady
stream of "KeyPair is an expired legacy operator cert, make a new one"
log lines plus wasted RSA key generation on a hot controller.

Compute enableDex before the key pair is needed and only build it when
dex is enabled. render.Dex() previously required a key pair even on the
DeleteDex path, because Objects() builds the Deployment and the ConfigMap
before checking DeleteDex and both dereference TLSKeyPair. Those two are
only ever deleted on that path, so identify them by name instead.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
@tmjd
tmjd force-pushed the tsla-11722-dex-keypair-only-when-enabled branch from b98bd91 to ea82a7d Compare August 5, 2026 15:22
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants