vendor update for CSI 0.3.0

This commit is contained in:
gman
2018-07-18 16:47:22 +02:00
parent 6f484f92fc
commit 8ea659f0d5
6810 changed files with 438061 additions and 193861 deletions

View File

@ -2,7 +2,9 @@ approvers:
- thockin
- luxas
- wlan0
- andrewsykim
reviewers:
- thockin
- luxas
- wlan0
- andrewsykim

View File

@ -26,7 +26,6 @@ go_library(
"//vendor/k8s.io/client-go/rest:go_default_library",
"//vendor/k8s.io/client-go/tools/leaderelection:go_default_library",
"//vendor/k8s.io/client-go/tools/leaderelection/resourcelock:go_default_library",
"//vendor/k8s.io/client-go/tools/record:go_default_library",
],
)

View File

@ -5,7 +5,14 @@ go_library(
srcs = ["config.go"],
importpath = "k8s.io/kubernetes/cmd/cloud-controller-manager/app/config",
visibility = ["//visibility:public"],
deps = ["//cmd/controller-manager/app:go_default_library"],
deps = [
"//cmd/controller-manager/app:go_default_library",
"//pkg/apis/componentconfig:go_default_library",
"//vendor/k8s.io/apiserver/pkg/server:go_default_library",
"//vendor/k8s.io/client-go/kubernetes:go_default_library",
"//vendor/k8s.io/client-go/rest:go_default_library",
"//vendor/k8s.io/client-go/tools/record:go_default_library",
],
)
filegroup(

View File

@ -17,25 +17,39 @@ limitations under the License.
package app
import (
"time"
apiserver "k8s.io/apiserver/pkg/server"
clientset "k8s.io/client-go/kubernetes"
restclient "k8s.io/client-go/rest"
"k8s.io/client-go/tools/record"
genericcontrollermanager "k8s.io/kubernetes/cmd/controller-manager/app"
"k8s.io/kubernetes/pkg/apis/componentconfig"
)
// ExtraConfig are part of Config, also can place your custom config here.
type ExtraConfig struct {
NodeStatusUpdateFrequency time.Duration
}
// Config is the main context object for the cloud controller manager.
type Config struct {
Generic genericcontrollermanager.Config
Extra ExtraConfig
ComponentConfig componentconfig.CloudControllerManagerConfiguration
SecureServing *apiserver.SecureServingInfo
// TODO: remove deprecated insecure serving
InsecureServing *genericcontrollermanager.InsecureServingInfo
Authentication apiserver.AuthenticationInfo
Authorization apiserver.AuthorizationInfo
// the general kube client
Client *clientset.Clientset
// the client only used for leader election
LeaderElectionClient *clientset.Clientset
// the rest config for the master
Kubeconfig *restclient.Config
// the event sink
EventRecorder record.EventRecorder
}
type completedConfig struct {
Generic genericcontrollermanager.CompletedConfig
Extra *ExtraConfig
*Config
}
// CompletedConfig same as Config, just to swap private object.
@ -46,10 +60,6 @@ type CompletedConfig struct {
// Complete fills in any fields not set that are required to have valid data. It's mutating the receiver.
func (c *Config) Complete() *CompletedConfig {
cc := completedConfig{
c.Generic.Complete(),
&c.Extra,
}
cc := completedConfig{c}
return &CompletedConfig{&cc}
}

View File

@ -34,7 +34,6 @@ import (
restclient "k8s.io/client-go/rest"
"k8s.io/client-go/tools/leaderelection"
"k8s.io/client-go/tools/leaderelection/resourcelock"
"k8s.io/client-go/tools/record"
cloudcontrollerconfig "k8s.io/kubernetes/cmd/cloud-controller-manager/app/config"
"k8s.io/kubernetes/cmd/cloud-controller-manager/app/options"
genericcontrollermanager "k8s.io/kubernetes/cmd/controller-manager/app"
@ -55,7 +54,11 @@ const (
// NewCloudControllerManagerCommand creates a *cobra.Command object with default parameters
func NewCloudControllerManagerCommand() *cobra.Command {
s := options.NewCloudControllerManagerOptions()
s, err := options.NewCloudControllerManagerOptions()
if err != nil {
glog.Fatalf("unable to initialize command options: %v", err)
}
cmd := &cobra.Command{
Use: "cloud-controller-manager",
Long: `The Cloud controller manager is a daemon that embeds
@ -86,13 +89,13 @@ the cloud specific control loops shipped with Kubernetes.`,
func resyncPeriod(c *cloudcontrollerconfig.CompletedConfig) func() time.Duration {
return func() time.Duration {
factor := rand.Float64() + 1
return time.Duration(float64(c.Generic.ComponentConfig.MinResyncPeriod.Nanoseconds()) * factor)
return time.Duration(float64(c.ComponentConfig.GenericComponent.MinResyncPeriod.Nanoseconds()) * factor)
}
}
// Run runs the ExternalCMServer. This should never exit.
func Run(c *cloudcontrollerconfig.CompletedConfig) error {
cloud, err := cloudprovider.InitCloudProvider(c.Generic.ComponentConfig.CloudProvider, c.Generic.ComponentConfig.CloudConfigFile)
cloud, err := cloudprovider.InitCloudProvider(c.ComponentConfig.CloudProvider.Name, c.ComponentConfig.CloudProvider.CloudConfigFile)
if err != nil {
glog.Fatalf("Cloud provider could not be initialized: %v", err)
}
@ -101,7 +104,7 @@ func Run(c *cloudcontrollerconfig.CompletedConfig) error {
}
if cloud.HasClusterID() == false {
if c.Generic.ComponentConfig.AllowUntaggedCloud == true {
if c.ComponentConfig.KubeCloudShared.AllowUntaggedCloud == true {
glog.Warning("detected a cluster without a ClusterID. A ClusterID will be required in the future. Please tag your cluster to avoid any future issues")
} else {
glog.Fatalf("no ClusterID found. A ClusterID is required for the cloud provider to function properly. This check can be bypassed by setting the allow-untagged-cloud option")
@ -110,46 +113,50 @@ func Run(c *cloudcontrollerconfig.CompletedConfig) error {
// setup /configz endpoint
if cz, err := configz.New("componentconfig"); err == nil {
cz.Set(c.Generic.ComponentConfig)
cz.Set(c.ComponentConfig)
} else {
glog.Errorf("unable to register configz: %c", err)
}
// Start the controller manager HTTP server
stopCh := make(chan struct{})
if c.Generic.SecureServing != nil {
if err := genericcontrollermanager.Serve(&c.Generic, c.Generic.SecureServing.Serve, stopCh); err != nil {
if c.SecureServing != nil {
handler := genericcontrollermanager.NewBaseHandler(&c.ComponentConfig.Debugging)
handler = genericcontrollermanager.BuildHandlerChain(handler, &c.Authorization, &c.Authentication)
if err := c.SecureServing.Serve(handler, 0, stopCh); err != nil {
return err
}
}
if c.Generic.InsecureServing != nil {
if err := genericcontrollermanager.Serve(&c.Generic, c.Generic.InsecureServing.Serve, stopCh); err != nil {
if c.InsecureServing != nil {
handler := genericcontrollermanager.NewBaseHandler(&c.ComponentConfig.Debugging)
handler = genericcontrollermanager.BuildHandlerChain(handler, &c.Authorization, &c.Authentication)
if err := c.InsecureServing.Serve(handler, 0, stopCh); err != nil {
return err
}
}
run := func(stop <-chan struct{}) {
rootClientBuilder := controller.SimpleControllerClientBuilder{
ClientConfig: c.Generic.Kubeconfig,
ClientConfig: c.Kubeconfig,
}
var clientBuilder controller.ControllerClientBuilder
if c.Generic.ComponentConfig.UseServiceAccountCredentials {
if c.ComponentConfig.KubeCloudShared.UseServiceAccountCredentials {
clientBuilder = controller.SAControllerClientBuilder{
ClientConfig: restclient.AnonymousClientConfig(c.Generic.Kubeconfig),
CoreClient: c.Generic.Client.CoreV1(),
AuthenticationClient: c.Generic.Client.AuthenticationV1(),
ClientConfig: restclient.AnonymousClientConfig(c.Kubeconfig),
CoreClient: c.Client.CoreV1(),
AuthenticationClient: c.Client.AuthenticationV1(),
Namespace: "kube-system",
}
} else {
clientBuilder = rootClientBuilder
}
if err := startControllers(c, c.Generic.Kubeconfig, rootClientBuilder, clientBuilder, stop, c.Generic.EventRecorder, cloud); err != nil {
if err := startControllers(c, rootClientBuilder, clientBuilder, stop, cloud); err != nil {
glog.Fatalf("error running controllers: %v", err)
}
}
if !c.Generic.ComponentConfig.LeaderElection.LeaderElect {
if !c.ComponentConfig.GenericComponent.LeaderElection.LeaderElect {
run(nil)
panic("unreachable")
}
@ -163,13 +170,13 @@ func Run(c *cloudcontrollerconfig.CompletedConfig) error {
id = id + "_" + string(uuid.NewUUID())
// Lock required for leader election
rl, err := resourcelock.New(c.Generic.ComponentConfig.LeaderElection.ResourceLock,
rl, err := resourcelock.New(c.ComponentConfig.GenericComponent.LeaderElection.ResourceLock,
"kube-system",
"cloud-controller-manager",
c.Generic.LeaderElectionClient.CoreV1(),
c.LeaderElectionClient.CoreV1(),
resourcelock.ResourceLockConfig{
Identity: id,
EventRecorder: c.Generic.EventRecorder,
EventRecorder: c.EventRecorder,
})
if err != nil {
glog.Fatalf("error creating lock: %v", err)
@ -178,9 +185,9 @@ func Run(c *cloudcontrollerconfig.CompletedConfig) error {
// Try and become the leader and start cloud controller manager loops
leaderelection.RunOrDie(leaderelection.LeaderElectionConfig{
Lock: rl,
LeaseDuration: c.Generic.ComponentConfig.LeaderElection.LeaseDuration.Duration,
RenewDeadline: c.Generic.ComponentConfig.LeaderElection.RenewDeadline.Duration,
RetryPeriod: c.Generic.ComponentConfig.LeaderElection.RetryPeriod.Duration,
LeaseDuration: c.ComponentConfig.GenericComponent.LeaderElection.LeaseDuration.Duration,
RenewDeadline: c.ComponentConfig.GenericComponent.LeaderElection.RenewDeadline.Duration,
RetryPeriod: c.ComponentConfig.GenericComponent.LeaderElection.RetryPeriod.Duration,
Callbacks: leaderelection.LeaderCallbacks{
OnStartedLeading: run,
OnStoppedLeading: func() {
@ -192,7 +199,7 @@ func Run(c *cloudcontrollerconfig.CompletedConfig) error {
}
// startControllers starts the cloud specific controller loops.
func startControllers(c *cloudcontrollerconfig.CompletedConfig, kubeconfig *restclient.Config, rootClientBuilder, clientBuilder controller.ControllerClientBuilder, stop <-chan struct{}, recorder record.EventRecorder, cloud cloudprovider.Interface) error {
func startControllers(c *cloudcontrollerconfig.CompletedConfig, rootClientBuilder, clientBuilder controller.ControllerClientBuilder, stop <-chan struct{}, cloud cloudprovider.Interface) error {
// Function to build the kube client object
client := func(serviceAccountName string) kubernetes.Interface {
return clientBuilder.ClientOrDie(serviceAccountName)
@ -210,17 +217,16 @@ func startControllers(c *cloudcontrollerconfig.CompletedConfig, kubeconfig *rest
nodeController := cloudcontrollers.NewCloudNodeController(
sharedInformers.Core().V1().Nodes(),
client("cloud-node-controller"), cloud,
c.Generic.ComponentConfig.NodeMonitorPeriod.Duration,
c.Extra.NodeStatusUpdateFrequency)
c.ComponentConfig.KubeCloudShared.NodeMonitorPeriod.Duration,
c.ComponentConfig.NodeStatusUpdateFrequency.Duration)
nodeController.Run()
time.Sleep(wait.Jitter(c.Generic.ComponentConfig.ControllerStartInterval.Duration, ControllerStartJitter))
nodeController.Run(stop)
time.Sleep(wait.Jitter(c.ComponentConfig.GenericComponent.ControllerStartInterval.Duration, ControllerStartJitter))
// Start the PersistentVolumeLabelController
pvlController := cloudcontrollers.NewPersistentVolumeLabelController(client("pvl-controller"), cloud)
threads := 5
go pvlController.Run(threads, stop)
time.Sleep(wait.Jitter(c.Generic.ComponentConfig.ControllerStartInterval.Duration, ControllerStartJitter))
go pvlController.Run(5, stop)
time.Sleep(wait.Jitter(c.ComponentConfig.GenericComponent.ControllerStartInterval.Duration, ControllerStartJitter))
// Start the service controller
serviceController, err := servicecontroller.New(
@ -228,34 +234,34 @@ func startControllers(c *cloudcontrollerconfig.CompletedConfig, kubeconfig *rest
client("service-controller"),
sharedInformers.Core().V1().Services(),
sharedInformers.Core().V1().Nodes(),
c.Generic.ComponentConfig.ClusterName,
c.ComponentConfig.KubeCloudShared.ClusterName,
)
if err != nil {
glog.Errorf("Failed to start service controller: %v", err)
} else {
go serviceController.Run(stop, int(c.Generic.ComponentConfig.ConcurrentServiceSyncs))
time.Sleep(wait.Jitter(c.Generic.ComponentConfig.ControllerStartInterval.Duration, ControllerStartJitter))
go serviceController.Run(stop, int(c.ComponentConfig.ServiceController.ConcurrentServiceSyncs))
time.Sleep(wait.Jitter(c.ComponentConfig.GenericComponent.ControllerStartInterval.Duration, ControllerStartJitter))
}
// If CIDRs should be allocated for pods and set on the CloudProvider, then start the route controller
if c.Generic.ComponentConfig.AllocateNodeCIDRs && c.Generic.ComponentConfig.ConfigureCloudRoutes {
if c.ComponentConfig.KubeCloudShared.AllocateNodeCIDRs && c.ComponentConfig.KubeCloudShared.ConfigureCloudRoutes {
if routes, ok := cloud.Routes(); !ok {
glog.Warning("configure-cloud-routes is set, but cloud provider does not support routes. Will not configure cloud provider routes.")
} else {
var clusterCIDR *net.IPNet
if len(strings.TrimSpace(c.Generic.ComponentConfig.ClusterCIDR)) != 0 {
_, clusterCIDR, err = net.ParseCIDR(c.Generic.ComponentConfig.ClusterCIDR)
if len(strings.TrimSpace(c.ComponentConfig.KubeCloudShared.ClusterCIDR)) != 0 {
_, clusterCIDR, err = net.ParseCIDR(c.ComponentConfig.KubeCloudShared.ClusterCIDR)
if err != nil {
glog.Warningf("Unsuccessful parsing of cluster CIDR %v: %v", c.Generic.ComponentConfig.ClusterCIDR, err)
glog.Warningf("Unsuccessful parsing of cluster CIDR %v: %v", c.ComponentConfig.KubeCloudShared.ClusterCIDR, err)
}
}
routeController := routecontroller.New(routes, client("route-controller"), sharedInformers.Core().V1().Nodes(), c.Generic.ComponentConfig.ClusterName, clusterCIDR)
go routeController.Run(stop, c.Generic.ComponentConfig.RouteReconciliationPeriod.Duration)
time.Sleep(wait.Jitter(c.Generic.ComponentConfig.ControllerStartInterval.Duration, ControllerStartJitter))
routeController := routecontroller.New(routes, client("route-controller"), sharedInformers.Core().V1().Nodes(), c.ComponentConfig.KubeCloudShared.ClusterName, clusterCIDR)
go routeController.Run(stop, c.ComponentConfig.KubeCloudShared.RouteReconciliationPeriod.Duration)
time.Sleep(wait.Jitter(c.ComponentConfig.GenericComponent.ControllerStartInterval.Duration, ControllerStartJitter))
}
} else {
glog.Infof("Will not configure cloud provider routes for allocate-node-cidrs: %v, configure-cloud-routes: %v.", c.Generic.ComponentConfig.AllocateNodeCIDRs, c.Generic.ComponentConfig.ConfigureCloudRoutes)
glog.Infof("Will not configure cloud provider routes for allocate-node-cidrs: %v, configure-cloud-routes: %v.", c.ComponentConfig.KubeCloudShared.AllocateNodeCIDRs, c.ComponentConfig.KubeCloudShared.ConfigureCloudRoutes)
}
// If apiserver is not running we should wait for some time and fail only then. This is particularly

View File

@ -13,13 +13,24 @@ go_library(
deps = [
"//cmd/cloud-controller-manager/app/config:go_default_library",
"//cmd/controller-manager/app/options:go_default_library",
"//pkg/client/leaderelectionconfig:go_default_library",
"//pkg/api/legacyscheme:go_default_library",
"//pkg/apis/componentconfig:go_default_library",
"//pkg/apis/componentconfig/v1alpha1:go_default_library",
"//pkg/features:go_default_library",
"//pkg/master/ports:go_default_library",
"//vendor/github.com/golang/glog:go_default_library",
"//vendor/github.com/spf13/pflag:go_default_library",
"//vendor/k8s.io/api/core/v1:go_default_library",
"//vendor/k8s.io/apimachinery/pkg/apis/meta/v1:go_default_library",
"//vendor/k8s.io/apimachinery/pkg/runtime:go_default_library",
"//vendor/k8s.io/apimachinery/pkg/util/errors:go_default_library",
"//vendor/k8s.io/apiserver/pkg/server/options:go_default_library",
"//vendor/k8s.io/apiserver/pkg/util/feature:go_default_library",
"//vendor/k8s.io/client-go/kubernetes:go_default_library",
"//vendor/k8s.io/client-go/kubernetes/typed/core/v1:go_default_library",
"//vendor/k8s.io/client-go/rest:go_default_library",
"//vendor/k8s.io/client-go/tools/clientcmd:go_default_library",
"//vendor/k8s.io/client-go/tools/record:go_default_library",
],
)

View File

@ -18,71 +18,185 @@ package options
import (
"fmt"
"time"
"net"
"k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/runtime"
utilerrors "k8s.io/apimachinery/pkg/util/errors"
apiserveroptions "k8s.io/apiserver/pkg/server/options"
utilfeature "k8s.io/apiserver/pkg/util/feature"
"k8s.io/client-go/kubernetes"
clientset "k8s.io/client-go/kubernetes"
v1core "k8s.io/client-go/kubernetes/typed/core/v1"
restclient "k8s.io/client-go/rest"
"k8s.io/client-go/tools/clientcmd"
"k8s.io/client-go/tools/record"
cloudcontrollerconfig "k8s.io/kubernetes/cmd/cloud-controller-manager/app/config"
cmoptions "k8s.io/kubernetes/cmd/controller-manager/app/options"
"k8s.io/kubernetes/pkg/client/leaderelectionconfig"
"k8s.io/kubernetes/pkg/api/legacyscheme"
"k8s.io/kubernetes/pkg/apis/componentconfig"
componentconfigv1alpha1 "k8s.io/kubernetes/pkg/apis/componentconfig/v1alpha1"
"k8s.io/kubernetes/pkg/master/ports"
// add the kubernetes feature gates
_ "k8s.io/kubernetes/pkg/features"
"github.com/golang/glog"
"github.com/spf13/pflag"
)
const (
// CloudControllerManagerUserAgent is the userAgent name when starting cloud-controller managers.
CloudControllerManagerUserAgent = "cloud-controller-manager"
)
// CloudControllerManagerOptions is the main context object for the controller manager.
type CloudControllerManagerOptions struct {
Generic cmoptions.GenericControllerManagerOptions
CloudProvider *cmoptions.CloudProviderOptions
Debugging *cmoptions.DebuggingOptions
GenericComponent *cmoptions.GenericComponentConfigOptions
KubeCloudShared *cmoptions.KubeCloudSharedOptions
ServiceController *cmoptions.ServiceControllerOptions
SecureServing *apiserveroptions.SecureServingOptions
// TODO: remove insecure serving mode
InsecureServing *cmoptions.InsecureServingOptions
Authentication *apiserveroptions.DelegatingAuthenticationOptions
Authorization *apiserveroptions.DelegatingAuthorizationOptions
Master string
Kubeconfig string
// NodeStatusUpdateFrequency is the frequency at which the controller updates nodes' status
NodeStatusUpdateFrequency metav1.Duration
}
// NewCloudControllerManagerOptions creates a new ExternalCMServer with a default config.
func NewCloudControllerManagerOptions() *CloudControllerManagerOptions {
componentConfig := cmoptions.NewDefaultControllerManagerComponentConfig(ports.InsecureCloudControllerManagerPort)
func NewCloudControllerManagerOptions() (*CloudControllerManagerOptions, error) {
componentConfig, err := NewDefaultComponentConfig(ports.InsecureCloudControllerManagerPort)
if err != nil {
return nil, err
}
s := CloudControllerManagerOptions{
// The common/default are kept in 'cmd/kube-controller-manager/app/options/util.go'.
// Please make common changes there and put anything cloud specific here.
Generic: cmoptions.NewGenericControllerManagerOptions(componentConfig),
NodeStatusUpdateFrequency: metav1.Duration{Duration: 5 * time.Minute},
CloudProvider: &cmoptions.CloudProviderOptions{},
Debugging: &cmoptions.DebuggingOptions{},
GenericComponent: cmoptions.NewGenericComponentConfigOptions(componentConfig.GenericComponent),
KubeCloudShared: cmoptions.NewKubeCloudSharedOptions(componentConfig.KubeCloudShared),
ServiceController: &cmoptions.ServiceControllerOptions{
ConcurrentServiceSyncs: componentConfig.ServiceController.ConcurrentServiceSyncs,
},
SecureServing: apiserveroptions.NewSecureServingOptions(),
InsecureServing: &cmoptions.InsecureServingOptions{
BindAddress: net.ParseIP(componentConfig.KubeCloudShared.Address),
BindPort: int(componentConfig.KubeCloudShared.Port),
BindNetwork: "tcp",
},
Authentication: nil, // TODO: enable with apiserveroptions.NewDelegatingAuthenticationOptions()
Authorization: nil, // TODO: enable with apiserveroptions.NewDelegatingAuthorizationOptions()
NodeStatusUpdateFrequency: componentConfig.NodeStatusUpdateFrequency,
}
s.Generic.ComponentConfig.LeaderElection.LeaderElect = true
s.Generic.SecureServing.ServerCert.CertDirectory = "/var/run/kubernetes"
s.Generic.SecureServing.ServerCert.PairName = "cloud-controller-manager"
s.SecureServing.ServerCert.CertDirectory = "/var/run/kubernetes"
s.SecureServing.ServerCert.PairName = "cloud-controller-manager"
return &s
// disable secure serving for now
// TODO: enable HTTPS by default
s.SecureServing.BindPort = 0
return &s, nil
}
// NewDefaultComponentConfig returns cloud-controller manager configuration object.
func NewDefaultComponentConfig(insecurePort int32) (componentconfig.CloudControllerManagerConfiguration, error) {
scheme := runtime.NewScheme()
componentconfigv1alpha1.AddToScheme(scheme)
componentconfig.AddToScheme(scheme)
versioned := componentconfigv1alpha1.CloudControllerManagerConfiguration{}
scheme.Default(&versioned)
internal := componentconfig.CloudControllerManagerConfiguration{}
if err := scheme.Convert(&versioned, &internal, nil); err != nil {
return internal, err
}
internal.KubeCloudShared.Port = insecurePort
return internal, nil
}
// AddFlags adds flags for a specific ExternalCMServer to the specified FlagSet
func (o *CloudControllerManagerOptions) AddFlags(fs *pflag.FlagSet) {
o.Generic.AddFlags(fs)
o.CloudProvider.AddFlags(fs)
o.Debugging.AddFlags(fs)
o.GenericComponent.AddFlags(fs)
o.KubeCloudShared.AddFlags(fs)
o.ServiceController.AddFlags(fs)
fs.StringVar(&o.Generic.ComponentConfig.CloudProvider, "cloud-provider", o.Generic.ComponentConfig.CloudProvider, "The provider of cloud services. Cannot be empty.")
o.SecureServing.AddFlags(fs)
o.InsecureServing.AddFlags(fs)
o.Authentication.AddFlags(fs)
o.Authorization.AddFlags(fs)
fs.StringVar(&o.Master, "master", o.Master, "The address of the Kubernetes API server (overrides any value in kubeconfig).")
fs.StringVar(&o.Kubeconfig, "kubeconfig", o.Kubeconfig, "Path to kubeconfig file with authorization and master location information.")
fs.DurationVar(&o.NodeStatusUpdateFrequency.Duration, "node-status-update-frequency", o.NodeStatusUpdateFrequency.Duration, "Specifies how often the controller updates nodes' status.")
// TODO: remove --service-account-private-key-file 6 months after 1.8 is released (~1.10)
fs.StringVar(&o.Generic.ComponentConfig.ServiceAccountKeyFile, "service-account-private-key-file", o.Generic.ComponentConfig.ServiceAccountKeyFile, "Filename containing a PEM-encoded private RSA or ECDSA key used to sign service account tokens.")
fs.MarkDeprecated("service-account-private-key-file", "This flag is currently no-op and will be deleted.")
fs.Int32Var(&o.Generic.ComponentConfig.ConcurrentServiceSyncs, "concurrent-service-syncs", o.Generic.ComponentConfig.ConcurrentServiceSyncs, "The number of services that are allowed to sync concurrently. Larger number = more responsive service management, but more CPU (and network) load")
leaderelectionconfig.BindFlags(&o.Generic.ComponentConfig.LeaderElection, fs)
utilfeature.DefaultFeatureGate.AddFlag(fs)
}
// ApplyTo fills up cloud controller manager config with options.
func (o *CloudControllerManagerOptions) ApplyTo(c *cloudcontrollerconfig.Config) error {
if err := o.Generic.ApplyTo(&c.Generic, "cloud-controller-manager"); err != nil {
func (o *CloudControllerManagerOptions) ApplyTo(c *cloudcontrollerconfig.Config, userAgent string) error {
if err := o.CloudProvider.ApplyTo(&c.ComponentConfig.CloudProvider); err != nil {
return err
}
if err := o.Debugging.ApplyTo(&c.ComponentConfig.Debugging); err != nil {
return err
}
if err := o.GenericComponent.ApplyTo(&c.ComponentConfig.GenericComponent); err != nil {
return err
}
if err := o.KubeCloudShared.ApplyTo(&c.ComponentConfig.KubeCloudShared); err != nil {
return err
}
if err := o.ServiceController.ApplyTo(&c.ComponentConfig.ServiceController); err != nil {
return err
}
if err := o.SecureServing.ApplyTo(&c.SecureServing); err != nil {
return err
}
if err := o.InsecureServing.ApplyTo(&c.InsecureServing); err != nil {
return err
}
if err := o.Authentication.ApplyTo(&c.Authentication, c.SecureServing, nil); err != nil {
return err
}
if err := o.Authorization.ApplyTo(&c.Authorization); err != nil {
return err
}
c.Extra.NodeStatusUpdateFrequency = o.NodeStatusUpdateFrequency.Duration
// sync back to component config
// TODO: find more elegant way than syncing back the values.
c.ComponentConfig.KubeCloudShared.Port = int32(o.InsecureServing.BindPort)
c.ComponentConfig.KubeCloudShared.Address = o.InsecureServing.BindAddress.String()
var err error
c.Kubeconfig, err = clientcmd.BuildConfigFromFlags(o.Master, o.Kubeconfig)
if err != nil {
return err
}
c.Kubeconfig.ContentConfig.ContentType = o.GenericComponent.ContentType
c.Kubeconfig.QPS = o.GenericComponent.KubeAPIQPS
c.Kubeconfig.Burst = int(o.GenericComponent.KubeAPIBurst)
c.Client, err = clientset.NewForConfig(restclient.AddUserAgent(c.Kubeconfig, userAgent))
if err != nil {
return err
}
c.LeaderElectionClient = clientset.NewForConfigOrDie(restclient.AddUserAgent(c.Kubeconfig, "leader-election"))
c.EventRecorder = createRecorder(c.Client, userAgent)
c.ComponentConfig.NodeStatusUpdateFrequency = o.NodeStatusUpdateFrequency
return nil
}
@ -90,9 +204,18 @@ func (o *CloudControllerManagerOptions) ApplyTo(c *cloudcontrollerconfig.Config)
// Validate is used to validate config before launching the cloud controller manager
func (o *CloudControllerManagerOptions) Validate() error {
errors := []error{}
errors = append(errors, o.Generic.Validate()...)
if len(o.Generic.ComponentConfig.CloudProvider) == 0 {
errors = append(errors, o.CloudProvider.Validate()...)
errors = append(errors, o.Debugging.Validate()...)
errors = append(errors, o.GenericComponent.Validate()...)
errors = append(errors, o.KubeCloudShared.Validate()...)
errors = append(errors, o.ServiceController.Validate()...)
errors = append(errors, o.SecureServing.Validate()...)
errors = append(errors, o.InsecureServing.Validate()...)
errors = append(errors, o.Authentication.Validate()...)
errors = append(errors, o.Authorization.Validate()...)
if len(o.CloudProvider.Name) == 0 {
errors = append(errors, fmt.Errorf("--cloud-provider cannot be empty"))
}
@ -100,15 +223,23 @@ func (o *CloudControllerManagerOptions) Validate() error {
}
// Config return a cloud controller manager config objective
func (o CloudControllerManagerOptions) Config() (*cloudcontrollerconfig.Config, error) {
func (o *CloudControllerManagerOptions) Config() (*cloudcontrollerconfig.Config, error) {
if err := o.Validate(); err != nil {
return nil, err
}
c := &cloudcontrollerconfig.Config{}
if err := o.ApplyTo(c); err != nil {
if err := o.ApplyTo(c, CloudControllerManagerUserAgent); err != nil {
return nil, err
}
return c, nil
}
func createRecorder(kubeClient kubernetes.Interface, userAgent string) record.EventRecorder {
eventBroadcaster := record.NewBroadcaster()
eventBroadcaster.StartLogging(glog.Infof)
eventBroadcaster.StartRecordingToSink(&v1core.EventSinkImpl{Interface: kubeClient.CoreV1().Events("")})
// TODO: remove dependence on the legacyscheme
return eventBroadcaster.NewRecorder(legacyscheme.Scheme, v1.EventSource{Component: userAgent})
}

View File

@ -31,14 +31,78 @@ import (
"k8s.io/kubernetes/pkg/apis/componentconfig"
)
func TestDefaultFlags(t *testing.T) {
s, _ := NewCloudControllerManagerOptions()
expected := &CloudControllerManagerOptions{
CloudProvider: &cmoptions.CloudProviderOptions{
Name: "",
CloudConfigFile: "",
},
Debugging: &cmoptions.DebuggingOptions{
EnableContentionProfiling: false,
},
GenericComponent: &cmoptions.GenericComponentConfigOptions{
MinResyncPeriod: metav1.Duration{Duration: 12 * time.Hour},
ContentType: "application/vnd.kubernetes.protobuf",
KubeAPIQPS: 20.0,
KubeAPIBurst: 30,
ControllerStartInterval: metav1.Duration{Duration: 0},
LeaderElection: componentconfig.LeaderElectionConfiguration{
ResourceLock: "endpoints",
LeaderElect: true,
LeaseDuration: metav1.Duration{Duration: 15 * time.Second},
RenewDeadline: metav1.Duration{Duration: 10 * time.Second},
RetryPeriod: metav1.Duration{Duration: 2 * time.Second},
},
},
KubeCloudShared: &cmoptions.KubeCloudSharedOptions{
Port: 10253, // Note: InsecureServingOptions.ApplyTo will write the flag value back into the component config
Address: "0.0.0.0", // Note: InsecureServingOptions.ApplyTo will write the flag value back into the component config
RouteReconciliationPeriod: metav1.Duration{Duration: 10 * time.Second},
NodeMonitorPeriod: metav1.Duration{Duration: 5 * time.Second},
ClusterName: "kubernetes",
ClusterCIDR: "",
AllocateNodeCIDRs: false,
CIDRAllocatorType: "",
ConfigureCloudRoutes: true,
},
ServiceController: &cmoptions.ServiceControllerOptions{
ConcurrentServiceSyncs: 1,
},
SecureServing: &apiserveroptions.SecureServingOptions{
BindPort: 0,
BindAddress: net.ParseIP("0.0.0.0"),
ServerCert: apiserveroptions.GeneratableKeyCert{
CertDirectory: "/var/run/kubernetes",
PairName: "cloud-controller-manager",
},
HTTP2MaxStreamsPerConnection: 0,
},
InsecureServing: &cmoptions.InsecureServingOptions{
BindAddress: net.ParseIP("0.0.0.0"),
BindPort: int(10253),
BindNetwork: "tcp",
},
Kubeconfig: "",
Master: "",
NodeStatusUpdateFrequency: metav1.Duration{Duration: 5 * time.Minute},
}
if !reflect.DeepEqual(expected, s) {
t.Errorf("Got different run options than expected.\nDifference detected on:\n%s", diff.ObjectReflectDiff(expected, s))
}
}
func TestAddFlags(t *testing.T) {
f := pflag.NewFlagSet("addflagstest", pflag.ContinueOnError)
s := NewCloudControllerManagerOptions()
s, _ := NewCloudControllerManagerOptions()
s.AddFlags(f)
args := []string{
"--address=192.168.4.10",
"--allocate-node-cidrs=true",
"--bind-address=192.168.4.21",
"--cert-dir=/a/b/c",
"--cloud-config=/cloud-config",
"--cloud-provider=gce",
"--cluster-cidr=1.2.3.4/24",
@ -47,7 +111,6 @@ func TestAddFlags(t *testing.T) {
"--contention-profiling=true",
"--controller-start-interval=2m",
"--http2-max-streams-per-connection=47",
"--min-resync-period=5m",
"--kube-api-burst=100",
"--kube-api-content-type=application/vnd.kubernetes.protobuf",
"--kube-api-qps=50.0",
@ -58,109 +121,68 @@ func TestAddFlags(t *testing.T) {
"--leader-elect-resource-lock=configmap",
"--leader-elect-retry-period=5s",
"--master=192.168.4.20",
"--min-resync-period=8h",
"--min-resync-period=100m",
"--node-status-update-frequency=10m",
"--port=10000",
"--profiling=false",
"--node-status-update-frequency=10m",
"--route-reconciliation-period=30s",
"--min-resync-period=100m",
"--use-service-account-credentials=false",
"--cert-dir=/a/b/c",
"--bind-address=192.168.4.21",
"--secure-port=10001",
"--use-service-account-credentials=false",
}
f.Parse(args)
expected := &CloudControllerManagerOptions{
Generic: cmoptions.GenericControllerManagerOptions{
ComponentConfig: componentconfig.KubeControllerManagerConfiguration{
CloudProvider: "gce",
CloudConfigFile: "/cloud-config",
Port: 10253, // Note: InsecureServingOptions.ApplyTo will write the flag value back into the component config
Address: "0.0.0.0", // Note: InsecureServingOptions.ApplyTo will write the flag value back into the component config
ConcurrentEndpointSyncs: 5,
ConcurrentRSSyncs: 5,
ConcurrentResourceQuotaSyncs: 5,
ConcurrentDeploymentSyncs: 5,
ConcurrentDaemonSetSyncs: 2,
ConcurrentJobSyncs: 5,
ConcurrentNamespaceSyncs: 10,
ConcurrentSATokenSyncs: 5,
ConcurrentServiceSyncs: 1,
ConcurrentGCSyncs: 20,
ConcurrentRCSyncs: 5,
MinResyncPeriod: metav1.Duration{Duration: 100 * time.Minute},
NodeMonitorPeriod: metav1.Duration{Duration: 5 * time.Second},
ResourceQuotaSyncPeriod: metav1.Duration{Duration: 5 * time.Minute},
NamespaceSyncPeriod: metav1.Duration{Duration: 5 * time.Minute},
PVClaimBinderSyncPeriod: metav1.Duration{Duration: 15 * time.Second},
HorizontalPodAutoscalerSyncPeriod: metav1.Duration{Duration: 30 * time.Second},
HorizontalPodAutoscalerUpscaleForbiddenWindow: metav1.Duration{Duration: 3 * time.Minute},
HorizontalPodAutoscalerDownscaleForbiddenWindow: metav1.Duration{Duration: 5 * time.Minute},
HorizontalPodAutoscalerTolerance: 0.1,
DeploymentControllerSyncPeriod: metav1.Duration{Duration: 30 * time.Second},
PodEvictionTimeout: metav1.Duration{Duration: 5 * time.Minute},
NodeMonitorGracePeriod: metav1.Duration{Duration: 40 * time.Second},
NodeStartupGracePeriod: metav1.Duration{Duration: 1 * time.Minute},
ClusterSigningDuration: metav1.Duration{Duration: 8760 * time.Hour},
ReconcilerSyncLoopPeriod: metav1.Duration{Duration: 1 * time.Minute},
TerminatedPodGCThreshold: 12500,
RegisterRetryCount: 10,
ClusterName: "k8s",
ConfigureCloudRoutes: false,
AllocateNodeCIDRs: true,
EnableGarbageCollector: true,
EnableTaintManager: true,
HorizontalPodAutoscalerUseRESTClients: true,
VolumeConfiguration: componentconfig.VolumeConfiguration{
EnableDynamicProvisioning: true,
EnableHostPathProvisioning: false,
FlexVolumePluginDir: "/usr/libexec/kubernetes/kubelet-plugins/volume/exec/",
PersistentVolumeRecyclerConfiguration: componentconfig.PersistentVolumeRecyclerConfiguration{
MaximumRetry: 3,
MinimumTimeoutNFS: 300,
IncrementTimeoutNFS: 30,
MinimumTimeoutHostPath: 60,
IncrementTimeoutHostPath: 30,
},
},
ContentType: "application/vnd.kubernetes.protobuf",
ClusterSigningCertFile: "/etc/kubernetes/ca/ca.pem",
ClusterSigningKeyFile: "/etc/kubernetes/ca/ca.key",
EnableContentionProfiling: true,
KubeAPIQPS: 50.0,
KubeAPIBurst: 100,
LeaderElection: componentconfig.LeaderElectionConfiguration{
ResourceLock: "configmap",
LeaderElect: false,
LeaseDuration: metav1.Duration{Duration: 30 * time.Second},
RenewDeadline: metav1.Duration{Duration: 15 * time.Second},
RetryPeriod: metav1.Duration{Duration: 5 * time.Second},
},
ControllerStartInterval: metav1.Duration{Duration: 2 * time.Minute},
RouteReconciliationPeriod: metav1.Duration{Duration: 30 * time.Second},
ClusterCIDR: "1.2.3.4/24",
NodeCIDRMaskSize: 24,
CIDRAllocatorType: "RangeAllocator",
Controllers: []string{"*"},
},
SecureServing: &apiserveroptions.SecureServingOptions{
BindPort: 10001,
BindAddress: net.ParseIP("192.168.4.21"),
ServerCert: apiserveroptions.GeneratableKeyCert{
CertDirectory: "/a/b/c",
PairName: "cloud-controller-manager",
},
HTTP2MaxStreamsPerConnection: 47,
},
InsecureServing: &cmoptions.InsecureServingOptions{
BindAddress: net.ParseIP("192.168.4.10"),
BindPort: int(10000),
BindNetwork: "tcp",
},
Kubeconfig: "/kubeconfig",
Master: "192.168.4.20",
CloudProvider: &cmoptions.CloudProviderOptions{
Name: "gce",
CloudConfigFile: "/cloud-config",
},
Debugging: &cmoptions.DebuggingOptions{
EnableContentionProfiling: true,
},
GenericComponent: &cmoptions.GenericComponentConfigOptions{
MinResyncPeriod: metav1.Duration{Duration: 100 * time.Minute},
ContentType: "application/vnd.kubernetes.protobuf",
KubeAPIQPS: 50.0,
KubeAPIBurst: 100,
ControllerStartInterval: metav1.Duration{Duration: 2 * time.Minute},
LeaderElection: componentconfig.LeaderElectionConfiguration{
ResourceLock: "configmap",
LeaderElect: false,
LeaseDuration: metav1.Duration{Duration: 30 * time.Second},
RenewDeadline: metav1.Duration{Duration: 15 * time.Second},
RetryPeriod: metav1.Duration{Duration: 5 * time.Second},
},
},
KubeCloudShared: &cmoptions.KubeCloudSharedOptions{
Port: 10253, // Note: InsecureServingOptions.ApplyTo will write the flag value back into the component config
Address: "0.0.0.0", // Note: InsecureServingOptions.ApplyTo will write the flag value back into the component config
RouteReconciliationPeriod: metav1.Duration{Duration: 30 * time.Second},
NodeMonitorPeriod: metav1.Duration{Duration: 5 * time.Second},
ClusterName: "k8s",
ClusterCIDR: "1.2.3.4/24",
AllocateNodeCIDRs: true,
CIDRAllocatorType: "RangeAllocator",
ConfigureCloudRoutes: false,
},
ServiceController: &cmoptions.ServiceControllerOptions{
ConcurrentServiceSyncs: 1,
},
SecureServing: &apiserveroptions.SecureServingOptions{
BindPort: 10001,
BindAddress: net.ParseIP("192.168.4.21"),
ServerCert: apiserveroptions.GeneratableKeyCert{
CertDirectory: "/a/b/c",
PairName: "cloud-controller-manager",
},
HTTP2MaxStreamsPerConnection: 47,
},
InsecureServing: &cmoptions.InsecureServingOptions{
BindAddress: net.ParseIP("192.168.4.10"),
BindPort: int(10000),
BindNetwork: "tcp",
},
Kubeconfig: "/kubeconfig",
Master: "192.168.4.20",
NodeStatusUpdateFrequency: metav1.Duration{Duration: 10 * time.Minute},
}
if !reflect.DeepEqual(expected, s) {