mirror of
				https://github.com/optim-enterprises-bv/kubernetes.git
				synced 2025-11-04 04:08:16 +00:00 
			
		
		
		
	[Mitigate KCM CrashLooping] Add unittests for controllers' Init function.
This commit is contained in:
		@@ -36,6 +36,7 @@ import (
 | 
				
			|||||||
	cacheddiscovery "k8s.io/client-go/discovery/cached"
 | 
						cacheddiscovery "k8s.io/client-go/discovery/cached"
 | 
				
			||||||
	"k8s.io/client-go/dynamic"
 | 
						"k8s.io/client-go/dynamic"
 | 
				
			||||||
	clientset "k8s.io/client-go/kubernetes"
 | 
						clientset "k8s.io/client-go/kubernetes"
 | 
				
			||||||
 | 
						restclient "k8s.io/client-go/rest"
 | 
				
			||||||
	csiclientset "k8s.io/csi-api/pkg/client/clientset/versioned"
 | 
						csiclientset "k8s.io/csi-api/pkg/client/clientset/versioned"
 | 
				
			||||||
	"k8s.io/kubernetes/pkg/controller"
 | 
						"k8s.io/kubernetes/pkg/controller"
 | 
				
			||||||
	cloudcontroller "k8s.io/kubernetes/pkg/controller/cloud"
 | 
						cloudcontroller "k8s.io/kubernetes/pkg/controller/cloud"
 | 
				
			||||||
@@ -331,6 +332,10 @@ func startNamespaceController(ctx ControllerContext) (http.Handler, bool, error)
 | 
				
			|||||||
	nsKubeconfig.QPS *= 20
 | 
						nsKubeconfig.QPS *= 20
 | 
				
			||||||
	nsKubeconfig.Burst *= 100
 | 
						nsKubeconfig.Burst *= 100
 | 
				
			||||||
	namespaceKubeClient := clientset.NewForConfigOrDie(nsKubeconfig)
 | 
						namespaceKubeClient := clientset.NewForConfigOrDie(nsKubeconfig)
 | 
				
			||||||
 | 
						return startModifiedNamespaceController(ctx, namespaceKubeClient, nsKubeconfig)
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func startModifiedNamespaceController(ctx ControllerContext, namespaceKubeClient clientset.Interface, nsKubeconfig *restclient.Config) (http.Handler, bool, error) {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	dynamicClient, err := dynamic.NewForConfig(nsKubeconfig)
 | 
						dynamicClient, err := dynamic.NewForConfig(nsKubeconfig)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -17,6 +17,7 @@ limitations under the License.
 | 
				
			|||||||
package app
 | 
					package app
 | 
				
			||||||
 | 
					
 | 
				
			||||||
import (
 | 
					import (
 | 
				
			||||||
 | 
						"net/http"
 | 
				
			||||||
	"testing"
 | 
						"testing"
 | 
				
			||||||
	"time"
 | 
						"time"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@@ -35,7 +36,10 @@ type TestClientBuilder struct {
 | 
				
			|||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func (TestClientBuilder) Config(name string) (*restclient.Config, error) { return nil, nil }
 | 
					func (TestClientBuilder) Config(name string) (*restclient.Config, error) { return nil, nil }
 | 
				
			||||||
func (TestClientBuilder) ConfigOrDie(name string) *restclient.Config      { return nil }
 | 
					func (TestClientBuilder) ConfigOrDie(name string) *restclient.Config {
 | 
				
			||||||
 | 
						return &restclient.Config{}
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func (TestClientBuilder) Client(name string) (clientset.Interface, error) { return nil, nil }
 | 
					func (TestClientBuilder) Client(name string) (clientset.Interface, error) { return nil, nil }
 | 
				
			||||||
func (m TestClientBuilder) ClientOrDie(name string) clientset.Interface {
 | 
					func (m TestClientBuilder) ClientOrDie(name string) clientset.Interface {
 | 
				
			||||||
	return m.clientset
 | 
						return m.clientset
 | 
				
			||||||
@@ -62,6 +66,10 @@ func (c *FakeClientSet) Discovery() discovery.DiscoveryInterface {
 | 
				
			|||||||
	return c.DiscoveryObj
 | 
						return c.DiscoveryObj
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func (c *FakeClientSet) GetPossibleResources() []*metav1.APIResourceList {
 | 
				
			||||||
 | 
						return c.DiscoveryObj.PossibleResources
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// Create a fake Clientset with its Discovery method overridden.
 | 
					// Create a fake Clientset with its Discovery method overridden.
 | 
				
			||||||
func NewFakeClientset(fakeDiscovery FakeDiscoveryWithError) *FakeClientSet {
 | 
					func NewFakeClientset(fakeDiscovery FakeDiscoveryWithError) *FakeClientSet {
 | 
				
			||||||
	cs := &FakeClientSet{}
 | 
						cs := &FakeClientSet{}
 | 
				
			||||||
@@ -69,20 +77,8 @@ func NewFakeClientset(fakeDiscovery FakeDiscoveryWithError) *FakeClientSet {
 | 
				
			|||||||
	return cs
 | 
						return cs
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func TestStartResourceQuotaController_DiscoveryError(t *testing.T) {
 | 
					func possibleDiscoveryResource() []*metav1.APIResourceList {
 | 
				
			||||||
	tcs := map[string]struct {
 | 
						return []*metav1.APIResourceList{
 | 
				
			||||||
		discoveryError    error
 | 
					 | 
				
			||||||
		expectedErr       bool
 | 
					 | 
				
			||||||
		possibleResources []*metav1.APIResourceList
 | 
					 | 
				
			||||||
	}{
 | 
					 | 
				
			||||||
		"No Discovery Error": {
 | 
					 | 
				
			||||||
			discoveryError:    nil,
 | 
					 | 
				
			||||||
			possibleResources: nil,
 | 
					 | 
				
			||||||
			expectedErr:       false,
 | 
					 | 
				
			||||||
		},
 | 
					 | 
				
			||||||
		"Discovery Calls Partially Failed": {
 | 
					 | 
				
			||||||
			discoveryError: new(discovery.ErrGroupDiscoveryFailed),
 | 
					 | 
				
			||||||
			possibleResources: []*metav1.APIResourceList{
 | 
					 | 
				
			||||||
		{
 | 
							{
 | 
				
			||||||
			GroupVersion: "create/v1",
 | 
								GroupVersion: "create/v1",
 | 
				
			||||||
			APIResources: []metav1.APIResource{
 | 
								APIResources: []metav1.APIResource{
 | 
				
			||||||
@@ -94,7 +90,30 @@ func TestStartResourceQuotaController_DiscoveryError(t *testing.T) {
 | 
				
			|||||||
				},
 | 
									},
 | 
				
			||||||
			},
 | 
								},
 | 
				
			||||||
		},
 | 
							},
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					type controllerInitFunc func(ControllerContext) (http.Handler, bool, error)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func TestController_DiscoveryError(t *testing.T) {
 | 
				
			||||||
 | 
						controllerInitFuncMap := map[string]controllerInitFunc{
 | 
				
			||||||
 | 
							"ResourceQuotaController":    startResourceQuotaController,
 | 
				
			||||||
 | 
							"GarbageCollectorController": startGarbageCollectorController,
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						tcs := map[string]struct {
 | 
				
			||||||
 | 
							discoveryError    error
 | 
				
			||||||
 | 
							expectedErr       bool
 | 
				
			||||||
 | 
							possibleResources []*metav1.APIResourceList
 | 
				
			||||||
 | 
						}{
 | 
				
			||||||
 | 
							"No Discovery Error": {
 | 
				
			||||||
 | 
								discoveryError:    nil,
 | 
				
			||||||
 | 
								possibleResources: possibleDiscoveryResource(),
 | 
				
			||||||
 | 
								expectedErr:       false,
 | 
				
			||||||
		},
 | 
							},
 | 
				
			||||||
 | 
							"Discovery Calls Partially Failed": {
 | 
				
			||||||
 | 
								discoveryError:    new(discovery.ErrGroupDiscoveryFailed),
 | 
				
			||||||
 | 
								possibleResources: possibleDiscoveryResource(),
 | 
				
			||||||
			expectedErr:       false,
 | 
								expectedErr:       false,
 | 
				
			||||||
		},
 | 
							},
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
@@ -107,9 +126,16 @@ func TestStartResourceQuotaController_DiscoveryError(t *testing.T) {
 | 
				
			|||||||
			InformerFactory:  informers.NewSharedInformerFactoryWithOptions(testClientset, time.Duration(1)),
 | 
								InformerFactory:  informers.NewSharedInformerFactoryWithOptions(testClientset, time.Duration(1)),
 | 
				
			||||||
			InformersStarted: make(chan struct{}),
 | 
								InformersStarted: make(chan struct{}),
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
		_, _, err := startResourceQuotaController(ctx)
 | 
							for funcName, controllerInit := range controllerInitFuncMap {
 | 
				
			||||||
 | 
								_, _, err := controllerInit(ctx)
 | 
				
			||||||
			if test.expectedErr != (err != nil) {
 | 
								if test.expectedErr != (err != nil) {
 | 
				
			||||||
			t.Errorf("test failed for use case: %v", name)
 | 
									t.Errorf("%v test failed for use case: %v", funcName, name)
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							_, _, err := startModifiedNamespaceController(
 | 
				
			||||||
 | 
								ctx, testClientset, testClientBuilder.ConfigOrDie("namespace-controller"))
 | 
				
			||||||
 | 
							if test.expectedErr != (err != nil) {
 | 
				
			||||||
 | 
								t.Errorf("Namespace Controller test failed for use case: %v", name)
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user