feat: implements svm controller
Signed-off-by: Nilekh Chaudhari <1626598+nilekhc@users.noreply.github.com>
This commit is contained in:
@@ -22,6 +22,7 @@ package app
|
||||
import (
|
||||
"context"
|
||||
"fmt"
|
||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||
"math/rand"
|
||||
"net/http"
|
||||
"os"
|
||||
@@ -74,6 +75,7 @@ import (
|
||||
"k8s.io/kubernetes/cmd/kube-controller-manager/app/options"
|
||||
"k8s.io/kubernetes/cmd/kube-controller-manager/names"
|
||||
kubectrlmgrconfig "k8s.io/kubernetes/pkg/controller/apis/config"
|
||||
garbagecollector "k8s.io/kubernetes/pkg/controller/garbagecollector"
|
||||
serviceaccountcontroller "k8s.io/kubernetes/pkg/controller/serviceaccount"
|
||||
"k8s.io/kubernetes/pkg/serviceaccount"
|
||||
)
|
||||
@@ -227,7 +229,7 @@ func Run(ctx context.Context, c *config.CompletedConfig) error {
|
||||
saTokenControllerDescriptor := newServiceAccountTokenControllerDescriptor(rootClientBuilder)
|
||||
|
||||
run := func(ctx context.Context, controllerDescriptors map[string]*ControllerDescriptor) {
|
||||
controllerContext, err := CreateControllerContext(logger, c, rootClientBuilder, clientBuilder, ctx.Done())
|
||||
controllerContext, err := CreateControllerContext(ctx, c, rootClientBuilder, clientBuilder)
|
||||
if err != nil {
|
||||
logger.Error(err, "Error building controller context")
|
||||
klog.FlushAndExit(klog.ExitFlushTimeout, 1)
|
||||
@@ -378,6 +380,9 @@ type ControllerContext struct {
|
||||
|
||||
// ControllerManagerMetrics provides a proxy to set controller manager specific metrics.
|
||||
ControllerManagerMetrics *controllersmetrics.ControllerManagerMetrics
|
||||
|
||||
// GraphBuilder gives an access to dependencyGraphBuilder which keeps tracks of resources in the cluster
|
||||
GraphBuilder *garbagecollector.GraphBuilder
|
||||
}
|
||||
|
||||
// IsControllerEnabled checks if the context's controllers enabled or not
|
||||
@@ -558,6 +563,7 @@ func NewControllerDescriptors() map[string]*ControllerDescriptor {
|
||||
register(newValidatingAdmissionPolicyStatusControllerDescriptor())
|
||||
register(newTaintEvictionControllerDescriptor())
|
||||
register(newServiceCIDRsControllerDescriptor())
|
||||
register(newStorageVersionMigratorControllerDescriptor())
|
||||
|
||||
for _, alias := range aliases.UnsortedList() {
|
||||
if _, ok := controllers[alias]; ok {
|
||||
@@ -571,7 +577,7 @@ func NewControllerDescriptors() map[string]*ControllerDescriptor {
|
||||
// CreateControllerContext creates a context struct containing references to resources needed by the
|
||||
// controllers such as the cloud provider and clientBuilder. rootClientBuilder is only used for
|
||||
// the shared-informers client and token controller.
|
||||
func CreateControllerContext(logger klog.Logger, s *config.CompletedConfig, rootClientBuilder, clientBuilder clientbuilder.ControllerClientBuilder, stop <-chan struct{}) (ControllerContext, error) {
|
||||
func CreateControllerContext(ctx context.Context, s *config.CompletedConfig, rootClientBuilder, clientBuilder clientbuilder.ControllerClientBuilder) (ControllerContext, error) {
|
||||
// Informer transform to trim ManagedFields for memory efficiency.
|
||||
trim := func(obj interface{}) (interface{}, error) {
|
||||
if accessor, err := meta.Accessor(obj); err == nil {
|
||||
@@ -598,15 +604,15 @@ func CreateControllerContext(logger klog.Logger, s *config.CompletedConfig, root
|
||||
restMapper := restmapper.NewDeferredDiscoveryRESTMapper(cachedClient)
|
||||
go wait.Until(func() {
|
||||
restMapper.Reset()
|
||||
}, 30*time.Second, stop)
|
||||
}, 30*time.Second, ctx.Done())
|
||||
|
||||
cloud, loopMode, err := createCloudProvider(logger, s.ComponentConfig.KubeCloudShared.CloudProvider.Name, s.ComponentConfig.KubeCloudShared.ExternalCloudVolumePlugin,
|
||||
cloud, loopMode, err := createCloudProvider(klog.FromContext(ctx), s.ComponentConfig.KubeCloudShared.CloudProvider.Name, s.ComponentConfig.KubeCloudShared.ExternalCloudVolumePlugin,
|
||||
s.ComponentConfig.KubeCloudShared.CloudProvider.CloudConfigFile, s.ComponentConfig.KubeCloudShared.AllowUntaggedCloud, sharedInformers)
|
||||
if err != nil {
|
||||
return ControllerContext{}, err
|
||||
}
|
||||
|
||||
ctx := ControllerContext{
|
||||
controllerContext := ControllerContext{
|
||||
ClientBuilder: clientBuilder,
|
||||
InformerFactory: sharedInformers,
|
||||
ObjectOrMetadataInformerFactory: informerfactory.NewInformerFactory(sharedInformers, metadataInformers),
|
||||
@@ -618,8 +624,26 @@ func CreateControllerContext(logger klog.Logger, s *config.CompletedConfig, root
|
||||
ResyncPeriod: ResyncPeriod(s),
|
||||
ControllerManagerMetrics: controllersmetrics.NewControllerManagerMetrics("kube-controller-manager"),
|
||||
}
|
||||
|
||||
if controllerContext.ComponentConfig.GarbageCollectorController.EnableGarbageCollector &&
|
||||
controllerContext.IsControllerEnabled(NewControllerDescriptors()[names.GarbageCollectorController]) {
|
||||
ignoredResources := make(map[schema.GroupResource]struct{})
|
||||
for _, r := range controllerContext.ComponentConfig.GarbageCollectorController.GCIgnoredResources {
|
||||
ignoredResources[schema.GroupResource{Group: r.Group, Resource: r.Resource}] = struct{}{}
|
||||
}
|
||||
|
||||
controllerContext.GraphBuilder = garbagecollector.NewDependencyGraphBuilder(
|
||||
ctx,
|
||||
metadataClient,
|
||||
controllerContext.RESTMapper,
|
||||
ignoredResources,
|
||||
controllerContext.ObjectOrMetadataInformerFactory,
|
||||
controllerContext.InformersStarted,
|
||||
)
|
||||
}
|
||||
|
||||
controllersmetrics.Register()
|
||||
return ctx, nil
|
||||
return controllerContext, nil
|
||||
}
|
||||
|
||||
// StartControllers starts a set of controllers with a specified ControllerContext
|
||||
|
||||
@@ -94,6 +94,7 @@ func TestControllerNamesDeclaration(t *testing.T) {
|
||||
names.LegacyServiceAccountTokenCleanerController,
|
||||
names.ValidatingAdmissionPolicyStatusController,
|
||||
names.ServiceCIDRController,
|
||||
names.StorageVersionMigratorController,
|
||||
)
|
||||
|
||||
for _, name := range KnownControllers() {
|
||||
|
||||
@@ -688,17 +688,16 @@ func startGarbageCollectorController(ctx context.Context, controllerContext Cont
|
||||
for _, r := range controllerContext.ComponentConfig.GarbageCollectorController.GCIgnoredResources {
|
||||
ignoredResources[schema.GroupResource{Group: r.Group, Resource: r.Resource}] = struct{}{}
|
||||
}
|
||||
garbageCollector, err := garbagecollector.NewGarbageCollector(
|
||||
|
||||
garbageCollector, err := garbagecollector.NewComposedGarbageCollector(
|
||||
ctx,
|
||||
gcClientset,
|
||||
metadataClient,
|
||||
controllerContext.RESTMapper,
|
||||
ignoredResources,
|
||||
controllerContext.ObjectOrMetadataInformerFactory,
|
||||
controllerContext.InformersStarted,
|
||||
controllerContext.GraphBuilder,
|
||||
)
|
||||
if err != nil {
|
||||
return nil, true, fmt.Errorf("failed to start the generic garbage collector: %v", err)
|
||||
return nil, true, fmt.Errorf("failed to start the generic garbage collector: %w", err)
|
||||
}
|
||||
|
||||
// Start the garbage collector.
|
||||
|
||||
92
cmd/kube-controller-manager/app/storageversionmigrator.go
Normal file
92
cmd/kube-controller-manager/app/storageversionmigrator.go
Normal file
@@ -0,0 +1,92 @@
|
||||
/*
|
||||
Copyright 2024 The Kubernetes Authors.
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
*/
|
||||
|
||||
package app
|
||||
|
||||
import (
|
||||
"context"
|
||||
"fmt"
|
||||
|
||||
"k8s.io/client-go/discovery"
|
||||
"k8s.io/client-go/dynamic"
|
||||
"k8s.io/client-go/metadata"
|
||||
"k8s.io/controller-manager/controller"
|
||||
"k8s.io/kubernetes/cmd/kube-controller-manager/names"
|
||||
"k8s.io/kubernetes/pkg/features"
|
||||
|
||||
utilfeature "k8s.io/apiserver/pkg/util/feature"
|
||||
clientgofeaturegate "k8s.io/client-go/features"
|
||||
svm "k8s.io/kubernetes/pkg/controller/storageversionmigrator"
|
||||
)
|
||||
|
||||
func newStorageVersionMigratorControllerDescriptor() *ControllerDescriptor {
|
||||
return &ControllerDescriptor{
|
||||
name: names.StorageVersionMigratorController,
|
||||
aliases: []string{"svm"},
|
||||
initFunc: startSVMController,
|
||||
}
|
||||
}
|
||||
|
||||
func startSVMController(
|
||||
ctx context.Context,
|
||||
controllerContext ControllerContext,
|
||||
controllerName string,
|
||||
) (controller.Interface, bool, error) {
|
||||
if !utilfeature.DefaultFeatureGate.Enabled(features.StorageVersionMigrator) ||
|
||||
!clientgofeaturegate.FeatureGates().Enabled(clientgofeaturegate.InformerResourceVersion) {
|
||||
return nil, false, nil
|
||||
}
|
||||
|
||||
if !controllerContext.ComponentConfig.GarbageCollectorController.EnableGarbageCollector {
|
||||
return nil, true, fmt.Errorf("storage version migrator requires garbage collector")
|
||||
}
|
||||
|
||||
config := controllerContext.ClientBuilder.ConfigOrDie(controllerName)
|
||||
client := controllerContext.ClientBuilder.ClientOrDie(controllerName)
|
||||
informer := controllerContext.InformerFactory.Storagemigration().V1alpha1().StorageVersionMigrations()
|
||||
|
||||
dynamicClient, err := dynamic.NewForConfig(config)
|
||||
if err != nil {
|
||||
return nil, false, err
|
||||
}
|
||||
|
||||
discoveryClient, err := discovery.NewDiscoveryClientForConfig(config)
|
||||
if err != nil {
|
||||
return nil, false, err
|
||||
}
|
||||
|
||||
go svm.NewResourceVersionController(
|
||||
ctx,
|
||||
client,
|
||||
discoveryClient,
|
||||
metadata.NewForConfigOrDie(config),
|
||||
informer,
|
||||
controllerContext.RESTMapper,
|
||||
).Run(ctx)
|
||||
|
||||
svmController := svm.NewSVMController(
|
||||
ctx,
|
||||
client,
|
||||
dynamicClient,
|
||||
informer,
|
||||
controllerName,
|
||||
controllerContext.RESTMapper,
|
||||
controllerContext.GraphBuilder,
|
||||
)
|
||||
go svmController.Run(ctx)
|
||||
|
||||
return svmController, true, nil
|
||||
}
|
||||
@@ -83,4 +83,5 @@ const (
|
||||
LegacyServiceAccountTokenCleanerController = "legacy-serviceaccount-token-cleaner-controller"
|
||||
ValidatingAdmissionPolicyStatusController = "validatingadmissionpolicy-status-controller"
|
||||
ServiceCIDRController = "service-cidr-controller"
|
||||
StorageVersionMigratorController = "storage-version-migrator-controller"
|
||||
)
|
||||
|
||||
Reference in New Issue
Block a user