diff --git a/cmd/kube-controller-manager/app/controllermanager.go b/cmd/kube-controller-manager/app/controllermanager.go index 7b65678637..1ee9d03dab 100644 --- a/cmd/kube-controller-manager/app/controllermanager.go +++ b/cmd/kube-controller-manager/app/controllermanager.go @@ -191,13 +191,16 @@ func Run(s *options.CMServer) error { return err } - rlc := resourcelock.ResourceLockConfig{ - Identity: id, - EventRecorder: recorder, - } - rl, err := leaderelection.GetLock(s.LeaderElection, *leaderElectionClient, rlc) + rl, err := resourcelock.New(s.LeaderElection.ResourceLock, + "kube-system", + "kube-controller-manager", + leaderElectionClient, + resourcelock.ResourceLockConfig{ + Identity: id, + EventRecorder: recorder, + }) if err != nil { - return err + glog.Fatalf("error creating lock: %v", err) } leaderelection.RunOrDie(leaderelection.LeaderElectionConfig{ diff --git a/hack/verify-flags/known-flags.txt b/hack/verify-flags/known-flags.txt index 7ea167c421..43ce0a7bbc 100644 --- a/hack/verify-flags/known-flags.txt +++ b/hack/verify-flags/known-flags.txt @@ -426,6 +426,7 @@ last-release-pr leader-elect leader-elect-lease-duration leader-elect-renew-deadline +leader-elect-resource-lock leader-elect-retry-period lease-duration leave-stdin-open diff --git a/pkg/apis/componentconfig/types.go b/pkg/apis/componentconfig/types.go index 3c4b8db98a..ce5c98c528 100644 --- a/pkg/apis/componentconfig/types.go +++ b/pkg/apis/componentconfig/types.go @@ -685,9 +685,9 @@ type LeaderElectionConfiguration struct { // acquisition and renewal of a leadership. This is only applicable if // leader election is enabled. RetryPeriod metav1.Duration - // LockType indicates the type of locking to use for leadership election. - // Supported options are `endpoints` (default) and `configmap`. - LockType string + // resourceLock indicates the resource object type that will be used to lock + // during leader election cycles. + ResourceLock string } type KubeControllerManagerConfiguration struct { diff --git a/pkg/apis/componentconfig/v1alpha1/defaults.go b/pkg/apis/componentconfig/v1alpha1/defaults.go index 06b01c0df4..0421118fad 100644 --- a/pkg/apis/componentconfig/v1alpha1/defaults.go +++ b/pkg/apis/componentconfig/v1alpha1/defaults.go @@ -26,6 +26,7 @@ import ( metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" kruntime "k8s.io/apimachinery/pkg/runtime" "k8s.io/kubernetes/pkg/api" + rl "k8s.io/kubernetes/pkg/client/leaderelection/resourcelock" "k8s.io/kubernetes/pkg/kubelet/qos" kubetypes "k8s.io/kubernetes/pkg/kubelet/types" "k8s.io/kubernetes/pkg/master/ports" @@ -193,6 +194,9 @@ func SetDefaults_LeaderElectionConfiguration(obj *LeaderElectionConfiguration) { if obj.RetryPeriod == zero { obj.RetryPeriod = metav1.Duration{Duration: 2 * time.Second} } + if obj.ResourceLock == "" { + obj.ResourceLock = rl.EndpointsResourceLock + } } func SetDefaults_KubeletConfiguration(obj *KubeletConfiguration) { diff --git a/pkg/apis/componentconfig/v1alpha1/types.go b/pkg/apis/componentconfig/v1alpha1/types.go index 02bb13e6b5..4be7d2df72 100644 --- a/pkg/apis/componentconfig/v1alpha1/types.go +++ b/pkg/apis/componentconfig/v1alpha1/types.go @@ -233,9 +233,9 @@ type LeaderElectionConfiguration struct { // acquisition and renewal of a leadership. This is only applicable if // leader election is enabled. RetryPeriod metav1.Duration `json:"retryPeriod"` - // LockType indicates the type of locking to use for leadership election. - // Supported options are `endpoints` (default) and `configmap`. - LockType string + // resourceLock indicates the resource object type that will be used to lock + // during leader election cycles. + ResourceLock string `json:"resourceLock"` } // A configuration field should go in KubeletFlags instead of KubeletConfiguration if any of these are true: diff --git a/pkg/apis/componentconfig/v1alpha1/zz_generated.conversion.go b/pkg/apis/componentconfig/v1alpha1/zz_generated.conversion.go index e73e7bfc06..f607ea6174 100644 --- a/pkg/apis/componentconfig/v1alpha1/zz_generated.conversion.go +++ b/pkg/apis/componentconfig/v1alpha1/zz_generated.conversion.go @@ -814,7 +814,6 @@ func autoConvert_v1alpha1_LeaderElectionConfiguration_To_componentconfig_LeaderE out.LeaseDuration = in.LeaseDuration out.RenewDeadline = in.RenewDeadline out.RetryPeriod = in.RetryPeriod - out.LockType = in.LockType return nil } @@ -830,7 +829,6 @@ func autoConvert_componentconfig_LeaderElectionConfiguration_To_v1alpha1_LeaderE out.LeaseDuration = in.LeaseDuration out.RenewDeadline = in.RenewDeadline out.RetryPeriod = in.RetryPeriod - out.LockType = in.LockType return nil } diff --git a/pkg/client/leaderelection/BUILD b/pkg/client/leaderelection/BUILD index a3b352b239..796151b02f 100644 --- a/pkg/client/leaderelection/BUILD +++ b/pkg/client/leaderelection/BUILD @@ -14,7 +14,6 @@ go_library( tags = ["automanaged"], deps = [ "//pkg/apis/componentconfig:go_default_library", - "//pkg/client/clientset_generated/clientset:go_default_library", "//pkg/client/leaderelection/resourcelock:go_default_library", "//vendor/github.com/golang/glog:go_default_library", "//vendor/github.com/spf13/pflag:go_default_library", diff --git a/pkg/client/leaderelection/leaderelection.go b/pkg/client/leaderelection/leaderelection.go index 01818db83e..936bc4e366 100644 --- a/pkg/client/leaderelection/leaderelection.go +++ b/pkg/client/leaderelection/leaderelection.go @@ -53,12 +53,11 @@ import ( "reflect" "time" - apierrors "k8s.io/apimachinery/pkg/api/errors" + "k8s.io/apimachinery/pkg/api/errors" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/util/runtime" "k8s.io/apimachinery/pkg/util/wait" "k8s.io/kubernetes/pkg/apis/componentconfig" - cs "k8s.io/kubernetes/pkg/client/clientset_generated/clientset" rl "k8s.io/kubernetes/pkg/client/leaderelection/resourcelock" "github.com/golang/glog" @@ -70,9 +69,6 @@ const ( DefaultLeaseDuration = 15 * time.Second DefaultRenewDeadline = 10 * time.Second DefaultRetryPeriod = 2 * time.Second - - LockTypeEndpoints = "endpoints" - LockTypeConfigMaps = "configmaps" ) // NewLeadereElector creates a LeaderElector from a LeaderElecitionConfig @@ -229,7 +225,7 @@ func (le *LeaderElector) tryAcquireOrRenew() bool { // 1. obtain or create the ElectionRecord oldLeaderElectionRecord, err := le.config.Lock.Get() if err != nil { - if !apierrors.IsNotFound(err) { + if !errors.IsNotFound(err) { glog.Errorf("error retrieving resource lock %v: %v", le.config.Lock.Describe(), err) return false } @@ -288,7 +284,7 @@ func DefaultLeaderElectionConfiguration() componentconfig.LeaderElectionConfigur LeaseDuration: metav1.Duration{Duration: DefaultLeaseDuration}, RenewDeadline: metav1.Duration{Duration: DefaultRenewDeadline}, RetryPeriod: metav1.Duration{Duration: DefaultRetryPeriod}, - LockType: LockTypeEndpoints, + ResourceLock: rl.EndpointsResourceLock, } } @@ -311,33 +307,7 @@ func BindFlags(l *componentconfig.LeaderElectionConfiguration, fs *pflag.FlagSet fs.DurationVar(&l.RetryPeriod.Duration, "leader-elect-retry-period", l.RetryPeriod.Duration, ""+ "The duration the clients should wait between attempting acquisition and renewal "+ "of a leadership. This is only applicable if leader election is enabled.") - fs.StringVar(&l.LockType, "leader-elect-lock-type", l.LockType, fmt.Sprintf(""+ - "Indicates the type of locking to use for leadership election. Supported options "+ - "are `%s` (default) and `%s`.", LockTypeConfigMaps, LockTypeEndpoints)) -} - -func GetLock(l componentconfig.LeaderElectionConfiguration, client cs.Clientset, rlc rl.ResourceLockConfig) (rl.Interface, error) { - name := "kube-controller-manager" - switch l.LockType { - case LockTypeEndpoints: - return &rl.EndpointsLock{ - EndpointsMeta: metav1.ObjectMeta{ - Namespace: metav1.NamespaceSystem, - Name: name, - }, - Client: client, - LockConfig: rlc, - }, nil - case LockTypeConfigMaps: - return &rl.ConfigMapLock{ - ConfigMapMeta: metav1.ObjectMeta{ - Namespace: metav1.NamespaceSystem, - Name: name, - }, - Client: client, - LockConfig: rlc, - }, nil - default: - return nil, fmt.Errorf("Invalid lock-type provided: %s. Supported types are `%s` and `%s`", l.LockType, LockTypeConfigMaps, LockTypeEndpoints) - } + fs.StringVar(&l.ResourceLock, "leader-elect-resource-lock", l.ResourceLock, ""+ + "The type of resource resource object that is used for locking during"+ + "leader election. Supported options are `endpoints` (default) and `configmap`.") } diff --git a/pkg/client/leaderelection/resourcelock/interface.go b/pkg/client/leaderelection/resourcelock/interface.go index 7b3775b9b2..6e9d5ce54e 100644 --- a/pkg/client/leaderelection/resourcelock/interface.go +++ b/pkg/client/leaderelection/resourcelock/interface.go @@ -17,12 +17,17 @@ limitations under the License. package resourcelock import ( + "fmt" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/client-go/tools/record" + cs "k8s.io/kubernetes/pkg/client/clientset_generated/clientset" ) const ( LeaderElectionRecordAnnotationKey = "control-plane.alpha.kubernetes.io/leader" + EndpointsResourceLock = "endpoints" + ConfigMapsResourceLock = "configmaps" ) // LeaderElectionRecord is the record that is stored in the leader election annotation. @@ -69,3 +74,29 @@ type Interface interface { // into a string Describe() string } + +// Manufacture will create a lock of a given type according to the input parameters +func New(lockType string, ns string, name string, client *cs.Clientset, rlc ResourceLockConfig) (Interface, error) { + switch lockType { + case EndpointsResourceLock: + return &EndpointsLock{ + EndpointsMeta: metav1.ObjectMeta{ + Namespace: ns, + Name: name, + }, + Client: client, + LockConfig: rlc, + }, nil + case ConfigMapsResourceLock: + return &ConfigMapLock{ + ConfigMapMeta: metav1.ObjectMeta{ + Namespace: ns, + Name: name, + }, + Client: client, + LockConfig: rlc, + }, nil + default: + return nil, fmt.Errorf("Invalid lock-type %s", lockType) + } +} diff --git a/plugin/cmd/kube-scheduler/app/server.go b/plugin/cmd/kube-scheduler/app/server.go index 00aa3166c9..c4ddae780c 100644 --- a/plugin/cmd/kube-scheduler/app/server.go +++ b/plugin/cmd/kube-scheduler/app/server.go @@ -26,7 +26,6 @@ import ( goruntime "runtime" "strconv" - metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apiserver/pkg/server/healthz" informers "k8s.io/kubernetes/pkg/client/informers/informers_generated/externalversions" @@ -112,17 +111,16 @@ func Run(s *options.SchedulerServer) error { return fmt.Errorf("unable to get hostname: %v", err) } - // TODO: enable other lock types - rl := &resourcelock.EndpointsLock{ - EndpointsMeta: metav1.ObjectMeta{ - Namespace: s.LockObjectNamespace, - Name: s.LockObjectName, - }, - Client: kubecli, - LockConfig: resourcelock.ResourceLockConfig{ + rl, err := resourcelock.New(s.LeaderElection.ResourceLock, + s.LockObjectNamespace, + s.LockObjectName, + kubecli, + resourcelock.ResourceLockConfig{ Identity: id, EventRecorder: recorder, - }, + }) + if err != nil { + glog.Fatalf("error creating lock: %v", err) } leaderelection.RunOrDie(leaderelection.LeaderElectionConfig{