Skip to content

Commit

Permalink
Split directControllerParentGetter and controllerFetcher
Browse files Browse the repository at this point in the history
  • Loading branch information
jbartosik committed Oct 8, 2020
1 parent 08a7fe0 commit 0f669ca
Show file tree
Hide file tree
Showing 3 changed files with 30 additions and 17 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,8 @@ func NewClusterStateFeeder(config *rest.Config, clusterState *model.ClusterState
kubeClient := kube_client.NewForConfigOrDie(config)
podLister, oomObserver := NewPodListerAndOOMObserver(kubeClient, namespace)
factory := informers.NewSharedInformerFactoryWithOptions(kubeClient, defaultResyncPeriod, informers.WithNamespace(namespace))
controllerFetcher := controllerfetcher.NewControllerFetcher(config, kubeClient, factory)
dirtectControllerParentGetter := controllerfetcher.NewDirectControllerParentGetter(config, kubeClient, factory)
controllerFetcher := controllerfetcher.NewControllerFetcher(dirtectControllerParentGetter)
return ClusterStateFeederFactory{
PodLister: podLister,
OOMObserver: oomObserver,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -78,14 +78,18 @@ type ControllerFetcher interface {
FindTopMostWellKnownOrScalable(controller *ControllerKeyWithAPIVersion) (*ControllerKeyWithAPIVersion, error)
}

type controllerFetcher struct {
type directControllerParentGetter struct {
scaleNamespacer scale.ScalesGetter
mapper apimeta.RESTMapper
informersMap map[wellKnownController]cache.SharedIndexInformer
}

// NewControllerFetcher returns a new instance of controllerFetcher
func NewControllerFetcher(config *rest.Config, kubeClient kube_client.Interface, factory informers.SharedInformerFactory) ControllerFetcher {
type controllerFetcher struct {
parentGetter controllerParentGetter
}

// NewDirectControllerParentGetter returns a new instance of directControllerParentGetter
func NewDirectControllerParentGetter(config *rest.Config, kubeClient kube_client.Interface, factory informers.SharedInformerFactory) *directControllerParentGetter {
discoveryClient, err := discovery.NewDiscoveryClientForConfig(config)
if err != nil {
klog.Fatalf("Could not create discoveryClient: %v", err)
Expand Down Expand Up @@ -120,13 +124,20 @@ func NewControllerFetcher(config *rest.Config, kubeClient kube_client.Interface,
}

scaleNamespacer := scale.New(restClient, mapper, dynamic.LegacyAPIPathResolverFunc, resolver)
return &controllerFetcher{
return &directControllerParentGetter{
scaleNamespacer: scaleNamespacer,
mapper: mapper,
informersMap: informersMap,
}
}

// NewControllerFetcher returns a new instance of controllerFetcher
func NewControllerFetcher(parentGetter controllerParentGetter) ControllerFetcher {
return &controllerFetcher{
parentGetter: parentGetter,
}
}

func getOwnerController(owners []metav1.OwnerReference, namespace string) *ControllerKeyWithAPIVersion {
for _, owner := range owners {
if owner.Controller != nil && *owner.Controller {
Expand Down Expand Up @@ -203,11 +214,11 @@ func getParentOfWellKnownController(informer cache.SharedIndexInformer, controll
return nil, fmt.Errorf("Don't know how to read owner controller")
}

func (f *controllerFetcher) getParentOfController(controllerKey ControllerKeyWithAPIVersion) (*ControllerKeyWithAPIVersion, error) {
func (f *directControllerParentGetter) GetParentOfController(controllerKey *ControllerKeyWithAPIVersion) (*ControllerKeyWithAPIVersion, error) {
kind := wellKnownController(controllerKey.Kind)
informer, exists := f.informersMap[kind]
if exists {
return getParentOfWellKnownController(informer, controllerKey)
return getParentOfWellKnownController(informer, *controllerKey)
}

groupKind, err := controllerKey.groupKind()
Expand Down Expand Up @@ -242,13 +253,13 @@ func (c *ControllerKeyWithAPIVersion) groupKind() (schema.GroupKind, error) {
return groupKind, nil
}

func (f *controllerFetcher) isWellKnown(key *ControllerKeyWithAPIVersion) bool {
func (f *directControllerParentGetter) isWellKnown(key *ControllerKeyWithAPIVersion) bool {
kind := wellKnownController(key.ControllerKey.Kind)
_, exists := f.informersMap[kind]
return exists
}

func (f *controllerFetcher) isWellKnownOrScalable(key *ControllerKeyWithAPIVersion) bool {
func (f *directControllerParentGetter) IsWellKnownOrScalable(key *ControllerKeyWithAPIVersion) bool {
if f.isWellKnown(key) {
return true
}
Expand Down Expand Up @@ -279,7 +290,7 @@ func (f *controllerFetcher) isWellKnownOrScalable(key *ControllerKeyWithAPIVersi
return false
}

func (f *controllerFetcher) getOwnerForScaleResource(groupKind schema.GroupKind, namespace, name string) (*ControllerKeyWithAPIVersion, error) {
func (f *directControllerParentGetter) getOwnerForScaleResource(groupKind schema.GroupKind, namespace, name string) (*ControllerKeyWithAPIVersion, error) {
if wellKnownController(groupKind.Kind) == node {
// Some pods specify nods as their owners. This causes performance problems
// in big clusters when VPA tries to get all nodes. We know nodes aren't
Expand Down Expand Up @@ -311,15 +322,15 @@ func (f *controllerFetcher) FindTopMostWellKnownOrScalable(key *ControllerKeyWit

var topMostWellKnownOrScalable *ControllerKeyWithAPIVersion

wellKnownOrScalable := f.isWellKnownOrScalable(key)
wellKnownOrScalable := f.parentGetter.IsWellKnownOrScalable(key)
if wellKnownOrScalable {
topMostWellKnownOrScalable = key
}

visited := make(map[ControllerKeyWithAPIVersion]bool)
visited[*key] = true
for {
owner, err := f.getParentOfController(*key)
owner, err := f.parentGetter.GetParentOfController(key)
if err != nil {
return nil, err
}
Expand All @@ -328,7 +339,7 @@ func (f *controllerFetcher) FindTopMostWellKnownOrScalable(key *ControllerKeyWit
return topMostWellKnownOrScalable, nil
}

wellKnownOrScalable = f.isWellKnownOrScalable(owner)
wellKnownOrScalable = f.parentGetter.IsWellKnownOrScalable(owner)
if wellKnownOrScalable {
topMostWellKnownOrScalable = owner
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,8 +41,8 @@ import (
var wellKnownControllers = []wellKnownController{daemonSet, deployment, replicaSet, statefulSet, replicationController, job, cronJob}
var trueVar = true

func simpleControllerFetcher() *controllerFetcher {
f := controllerFetcher{}
func simpleControllerFetcher() *directControllerParentGetter {
f := directControllerParentGetter{}
f.informersMap = make(map[wellKnownController]cache.SharedIndexInformer)
versioned := map[string][]metav1.APIResource{
"Foo": {{Kind: "Foo", Name: "bah", Group: "foo"}, {Kind: "Scale", Name: "iCanScale", Group: "foo"}},
Expand Down Expand Up @@ -97,7 +97,7 @@ func simpleControllerFetcher() *controllerFetcher {
return &f
}

func addController(controller *controllerFetcher, obj runtime.Object) {
func addController(controller *directControllerParentGetter, obj runtime.Object) {
kind := wellKnownController(obj.GetObjectKind().GroupVersionKind().Kind)
_, ok := controller.informersMap[kind]
if ok {
Expand Down Expand Up @@ -381,10 +381,11 @@ func TestControllerFetcher(t *testing.T) {
} {
t.Run(tc.name, func(t *testing.T) {
f := simpleControllerFetcher()
ff := NewControllerFetcher(f)
for _, obj := range tc.objects {
addController(f, obj)
}
topMostWellKnownOrScalableController, err := f.FindTopMostWellKnownOrScalable(tc.key)
topMostWellKnownOrScalableController, err := ff.FindTopMostWellKnownOrScalable(tc.key)
if tc.expectedKey == nil {
assert.Nil(t, topMostWellKnownOrScalableController)
} else {
Expand Down

0 comments on commit 0f669ca

Please sign in to comment.