@@ -5,44 +5,48 @@ import (
5
5
"fmt"
6
6
"time"
7
7
8
- apierrors "k8s.io/apimachinery/pkg/api/errors"
9
- metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
10
- "k8s.io/client-go/tools/cache"
11
8
"k8s.io/client-go/util/workqueue"
12
9
"k8s.io/klog/v2"
13
10
14
11
operatorv1 "github.com/openshift/api/operator/v1"
15
- operatorv1alpha1 "github.com/openshift/api/operator/v1alpha1"
16
12
operatorclientset "github.com/openshift/client-go/operator/clientset/versioned"
17
- cvoclientv1alpha1 "github.com/openshift/client-go/operator/clientset/versioned/typed/operator/v1alpha1"
18
13
operatorexternalversions "github.com/openshift/client-go/operator/informers/externalversions"
19
- operatorlistersv1alpha1 "github.com/openshift/client-go/operator/listers/operator/v1alpha1"
20
14
"github.com/openshift/library-go/pkg/operator/loglevel"
21
15
22
16
i "github.com/openshift/cluster-version-operator/pkg/internal"
23
17
)
24
18
25
19
const ClusterVersionOperatorConfigurationName = "cluster"
26
20
21
+ const defaultQueueKey = "ClusterVersionOperator/" + ClusterVersionOperatorConfigurationName
22
+
27
23
type configuration struct {
28
24
lastObservedGeneration int64
29
25
desiredLogLevel operatorv1.LogLevel
30
26
}
31
27
28
+ func defaultConfiguration () configuration {
29
+ return configuration {
30
+ lastObservedGeneration : 0 ,
31
+ desiredLogLevel : operatorv1 .Normal ,
32
+ }
33
+ }
34
+
35
+ type ConfigProvider interface {
36
+ start (ctx context.Context ) error
37
+ get (context.Context ) (configuration , error )
38
+ }
39
+
32
40
type ClusterVersionOperatorConfiguration struct {
33
- queueKey string
34
41
// queue tracks checking for the CVO configuration.
35
42
//
36
43
// The type any is used to comply with the worker method of the cvo.Operator struct.
37
44
queue workqueue.TypedRateLimitingInterface [any ]
38
45
39
- client cvoclientv1alpha1.ClusterVersionOperatorInterface
40
- lister operatorlistersv1alpha1.ClusterVersionOperatorLister
41
- factory operatorexternalversions.SharedInformerFactory
42
-
43
46
started bool
44
47
45
48
configuration configuration
49
+ provider ConfigProvider
46
50
47
51
// Function to handle an update to the internal configuration.
48
52
//
@@ -57,28 +61,9 @@ func (config *ClusterVersionOperatorConfiguration) Queue() workqueue.TypedRateLi
57
61
return config .queue
58
62
}
59
63
60
- // clusterVersionOperatorEventHandler queues an update for the cluster version operator on any change to the given object.
61
- // Callers should use this with an informer.
62
- func (config * ClusterVersionOperatorConfiguration ) clusterVersionOperatorEventHandler () cache.ResourceEventHandler {
63
- return cache.ResourceEventHandlerFuncs {
64
- AddFunc : func (_ interface {}) {
65
- config .queue .Add (config .queueKey )
66
- klog .V (i .Debug ).Infof ("ClusterVersionOperator resource was added; queuing a sync" )
67
- },
68
- UpdateFunc : func (_ , _ interface {}) {
69
- config .queue .Add (config .queueKey )
70
- klog .V (i .Debug ).Infof ("ClusterVersionOperator resource was modified or resync period has passed; queuing a sync" )
71
- },
72
- DeleteFunc : func (_ interface {}) {
73
- config .queue .Add (config .queueKey )
74
- klog .V (i .Debug ).Infof ("ClusterVersionOperator resource was deleted; queuing a sync" )
75
- },
76
- }
77
- }
78
-
79
64
// NewClusterVersionOperatorConfiguration returns ClusterVersionOperatorConfiguration, which might be used
80
65
// to synchronize with the ClusterVersionOperator resource.
81
- func NewClusterVersionOperatorConfiguration (client operatorclientset. Interface , factory operatorexternalversions. SharedInformerFactory ) * ClusterVersionOperatorConfiguration {
66
+ func NewClusterVersionOperatorConfiguration () * ClusterVersionOperatorConfiguration {
82
67
var desiredLogLevel operatorv1.LogLevel
83
68
if currentLogLevel , notFound := loglevel .GetLogLevel (); notFound {
84
69
klog .Warningf ("The current log level could not be found; assuming the 'Normal' level is the currently desired" )
@@ -88,34 +73,28 @@ func NewClusterVersionOperatorConfiguration(client operatorclientset.Interface,
88
73
}
89
74
90
75
return & ClusterVersionOperatorConfiguration {
91
- queueKey : fmt .Sprintf ("ClusterVersionOperator/%s" , ClusterVersionOperatorConfigurationName ),
92
76
queue : workqueue .NewTypedRateLimitingQueueWithConfig [any ](
93
77
workqueue .DefaultTypedControllerRateLimiter [any ](),
94
78
workqueue.TypedRateLimitingQueueConfig [any ]{Name : "configuration" }),
95
- client : client .OperatorV1alpha1 ().ClusterVersionOperators (),
96
- factory : factory ,
97
79
configuration : configuration {desiredLogLevel : desiredLogLevel },
98
80
handler : func (c configuration ) error { return applyLogLevel (c .desiredLogLevel ) },
99
81
}
100
82
}
101
83
84
+ func (config * ClusterVersionOperatorConfiguration ) UsingKubeAPIServer (client operatorclientset.Interface , factory operatorexternalversions.SharedInformerFactory ) * ClusterVersionOperatorConfiguration {
85
+ config .provider = newConfigProviderKubeAPIServer (client , factory , config .queue )
86
+ return config
87
+ }
88
+
102
89
// Start initializes and starts the configuration's informers. Must be run before Sync is called.
103
90
// Blocks until informers caches are synchronized or the context is cancelled.
104
91
func (config * ClusterVersionOperatorConfiguration ) Start (ctx context.Context ) error {
105
- informer := config .factory .Operator ().V1alpha1 ().ClusterVersionOperators ()
106
- if _ , err := informer .Informer ().AddEventHandler (config .clusterVersionOperatorEventHandler ()); err != nil {
107
- return err
92
+ if config .provider == nil {
93
+ return fmt .Errorf ("the configuration provider must be initialized" )
108
94
}
109
- config .lister = informer .Lister ()
110
-
111
- config .factory .Start (ctx .Done ())
112
- synced := config .factory .WaitForCacheSync (ctx .Done ())
113
- for _ , ok := range synced {
114
- if ! ok {
115
- return fmt .Errorf ("caches failed to sync: %w" , ctx .Err ())
116
- }
95
+ if err := config .provider .start (ctx ); err != nil {
96
+ return err
117
97
}
118
-
119
98
config .started = true
120
99
return nil
121
100
}
@@ -130,36 +109,14 @@ func (config *ClusterVersionOperatorConfiguration) Sync(ctx context.Context, key
130
109
klog .V (i .Normal ).Infof ("Finished syncing CVO configuration (%v)" , time .Since (startTime ))
131
110
}()
132
111
133
- desiredConfig , err := config .lister .Get (ClusterVersionOperatorConfigurationName )
134
- if apierrors .IsNotFound (err ) {
135
- // TODO: Set default values
136
- return nil
137
- }
112
+ desiredConfig , err := config .provider .get (ctx )
138
113
if err != nil {
139
114
return err
140
115
}
141
- return config .sync (ctx , desiredConfig )
142
- }
143
-
144
- // sync synchronizes the local configuration based on the desired configuration
145
- // and updates the status of the Kubernetes resource if needed.
146
- //
147
- // desiredConfig is a read-only representation of the desired configuration.
148
- func (config * ClusterVersionOperatorConfiguration ) sync (ctx context.Context , desiredConfig * operatorv1alpha1.ClusterVersionOperator ) error {
149
- if desiredConfig .Status .ObservedGeneration != desiredConfig .Generation {
150
- newConfig := desiredConfig .DeepCopy ()
151
- newConfig .Status .ObservedGeneration = desiredConfig .Generation
152
- _ , err := config .client .UpdateStatus (ctx , newConfig , metav1.UpdateOptions {})
153
- if err != nil {
154
- return fmt .Errorf ("failed to update the ClusterVersionOperator resource: %w" , err )
155
- }
156
- }
157
-
158
- config .configuration .lastObservedGeneration = desiredConfig .Generation
159
- config .configuration .desiredLogLevel = desiredConfig .Spec .OperatorLogLevel
160
- if config .configuration .desiredLogLevel == "" {
161
- config .configuration .desiredLogLevel = operatorv1 .Normal
116
+ if desiredConfig .desiredLogLevel == "" {
117
+ desiredConfig .desiredLogLevel = operatorv1 .Normal
162
118
}
119
+ config .configuration = desiredConfig
163
120
164
121
if config .handler != nil {
165
122
return config .handler (config .configuration )
0 commit comments