@@ -20,6 +20,7 @@ import (
2020 "crypto/tls"
2121 "flag"
2222 "os"
23+ "path/filepath"
2324
2425 // Import all Kubernetes client auth plugins (e.g. Azure, GCP, OIDC, etc.)
2526 // to ensure that exec-entrypoint and run can make use of them.
@@ -29,6 +30,7 @@ import (
2930 utilruntime "k8s.io/apimachinery/pkg/util/runtime"
3031 clientgoscheme "k8s.io/client-go/kubernetes/scheme"
3132 ctrl "sigs.k8s.io/controller-runtime"
33+ "sigs.k8s.io/controller-runtime/pkg/certwatcher"
3234 "sigs.k8s.io/controller-runtime/pkg/healthz"
3335 "sigs.k8s.io/controller-runtime/pkg/log/zap"
3436 "sigs.k8s.io/controller-runtime/pkg/metrics/filters"
@@ -57,6 +59,8 @@ func init() {
5759
5860func main () {
5961 var metricsAddr string
62+ var metricsCertPath , metricsCertName , metricsCertKey string
63+ var webhookCertPath , webhookCertName , webhookCertKey string
6064 var enableLeaderElection bool
6165 var probeAddr string
6266 var secureMetrics bool
@@ -70,6 +74,12 @@ func main() {
7074 "Enabling this will ensure there is only one active controller manager." )
7175 flag .BoolVar (& secureMetrics , "metrics-secure" , true ,
7276 "If set, the metrics endpoint is served securely via HTTPS. Use --metrics-secure=false to use HTTP instead." )
77+ flag .StringVar (& webhookCertPath , "webhook-cert-path" , "" , "The directory that contains the webhook certificate." )
78+ flag .StringVar (& webhookCertName , "webhook-cert-name" , "tls.crt" , "The name of the webhook certificate file." )
79+ flag .StringVar (& webhookCertKey , "webhook-cert-key" , "tls.key" , "The name of the webhook key file." )
80+ flag .StringVar (& metricsCertPath , "metrics-cert-path" , "" , "The directory that contains the metrics server certificate." ) //nolint:lll
81+ flag .StringVar (& metricsCertName , "metrics-cert-name" , "tls.crt" , "The name of the metrics server certificate file." )
82+ flag .StringVar (& metricsCertKey , "metrics-cert-key" , "tls.key" , "The name of the metrics server key file." )
7383 flag .BoolVar (& disableHTTP2 , "disable-http2" , false ,
7484 "If set, HTTP/2 will be disabled for the metrics and webhook servers" )
7585 opts := zap.Options {
@@ -88,8 +98,33 @@ func main() {
8898 tlsOpts = append (tlsOpts , forceHTTP11 )
8999 }
90100
101+ // Create watchers for metrics and webhooks certificates
102+ var metricsCertWatcher , webhookCertWatcher * certwatcher.CertWatcher
103+
104+ // Initial webhook TLS options
105+ webhookTLSOpts := tlsOpts
106+
107+ if len (webhookCertPath ) > 0 {
108+ setupLog .Info ("Initializing webhook certificate watcher using provided certificates" ,
109+ "webhook-cert-path" , webhookCertPath , "webhook-cert-name" , webhookCertName , "webhook-cert-key" , webhookCertKey )
110+
111+ var err error
112+ webhookCertWatcher , err = certwatcher .New (
113+ filepath .Join (webhookCertPath , webhookCertName ),
114+ filepath .Join (webhookCertPath , webhookCertKey ),
115+ )
116+ if err != nil {
117+ setupLog .Error (err , "Failed to initialize webhook certificate watcher" )
118+ os .Exit (1 )
119+ }
120+
121+ webhookTLSOpts = append (webhookTLSOpts , func (config * tls.Config ) {
122+ config .GetCertificate = webhookCertWatcher .GetCertificate
123+ })
124+ }
125+
91126 webhookServer := webhook .NewServer (webhook.Options {
92- TLSOpts : tlsOpts ,
127+ TLSOpts : webhookTLSOpts ,
93128 })
94129
95130 // Metrics endpoint is enabled in 'config/default/kustomization.yaml'. The Metrics options configure the server.
@@ -116,6 +151,25 @@ func main() {
116151 metricsServerOptions .FilterProvider = filters .WithAuthenticationAndAuthorization
117152 }
118153
154+ if len (metricsCertPath ) > 0 {
155+ setupLog .Info ("Initializing metrics certificate watcher using provided certificates" ,
156+ "metrics-cert-path" , metricsCertPath , "metrics-cert-name" , metricsCertName , "metrics-cert-key" , metricsCertKey )
157+
158+ var err error
159+ metricsCertWatcher , err = certwatcher .New (
160+ filepath .Join (metricsCertPath , metricsCertName ),
161+ filepath .Join (metricsCertPath , metricsCertKey ),
162+ )
163+ if err != nil {
164+ setupLog .Error (err , "Failed to initialize metrics certificate watcher" )
165+ os .Exit (1 )
166+ }
167+
168+ metricsServerOptions .TLSOpts = append (metricsServerOptions .TLSOpts , func (config * tls.Config ) {
169+ config .GetCertificate = metricsCertWatcher .GetCertificate
170+ })
171+ }
172+
119173 mgr , err := ctrl .NewManager (ctrl .GetConfigOrDie (), ctrl.Options {
120174 Scheme : scheme ,
121175 Metrics : metricsServerOptions ,
@@ -158,6 +212,22 @@ func main() {
158212 }
159213 // +kubebuilder:scaffold:builder
160214
215+ if metricsCertWatcher != nil {
216+ setupLog .Info ("Adding metrics certificate watcher to manager" )
217+ if err := mgr .Add (metricsCertWatcher ); err != nil {
218+ setupLog .Error (err , "Unable to add metrics certificate watcher to manager" )
219+ os .Exit (1 )
220+ }
221+ }
222+
223+ if webhookCertWatcher != nil {
224+ setupLog .Info ("Adding webhook certificate watcher to manager" )
225+ if err := mgr .Add (webhookCertWatcher ); err != nil {
226+ setupLog .Error (err , "Unable to add webhook certificate watcher to manager" )
227+ os .Exit (1 )
228+ }
229+ }
230+
161231 if err := mgr .AddHealthzCheck ("healthz" , healthz .Ping ); err != nil {
162232 setupLog .Error (err , "unable to set up health check" )
163233 os .Exit (1 )
0 commit comments