diff --git a/cmd/controller/main.go b/cmd/controller/main.go index 95408d6..8152ec2 100644 --- a/cmd/controller/main.go +++ b/cmd/controller/main.go @@ -12,6 +12,7 @@ var ( ) func init() { + flag.StringVar(&cfg.PVProvisioner, "pv-provisioner", "kubernetes.io/gce-pd", "persistent volume provisioner type") flag.StringVar(&cfg.MasterHost, "master", "", "API Server addr, e.g. ' - NOT RECOMMENDED FOR PRODUCTION - http://127.0.0.1:8080'. Omit parameter to run in on-cluster mode and utilize the service account token.") flag.StringVar(&cfg.TLSConfig.CertFile, "cert-file", "", " - NOT RECOMMENDED FOR PRODUCTION - Path to public TLS certificate file.") flag.StringVar(&cfg.TLSConfig.KeyFile, "key-file", "", "- NOT RECOMMENDED FOR PRODUCTION - Path to private TLS certificate file.") diff --git a/pkg/controller/controller.go b/pkg/controller/controller.go index 06c0778..b5cf799 100644 --- a/pkg/controller/controller.go +++ b/pkg/controller/controller.go @@ -3,6 +3,7 @@ package controller import ( "encoding/json" "errors" + "fmt" "io" "net/http" "time" @@ -20,36 +21,59 @@ const ( tprName = "etcd-cluster.coreos.com" ) +var ( + supportedPVProvisioners = map[string]struct{}{ + "kubernetes.io/gce-pd": {}, + "kubernetes.io/aws-ebs": {}, + } +) + type Event struct { Type string Object cluster.EtcdCluster } type Controller struct { - masterHost string - namespace string - kclient *unversioned.Client - clusters map[string]*cluster.Cluster + masterHost string + namespace string + kclient *unversioned.Client + clusters map[string]*cluster.Cluster + pvProvisioner string } type Config struct { - Namespace string - MasterHost string - TLSInsecure bool - TLSConfig restclient.TLSClientConfig + Namespace string + MasterHost string + TLSInsecure bool + TLSConfig restclient.TLSClientConfig + PVProvisioner string +} + +func (c *Config) validate() error { + if _, ok := supportedPVProvisioners[c.PVProvisioner]; !ok { + return fmt.Errorf( + "persistent volume provisioner %s is not supported: options = %v", + c.PVProvisioner, supportedPVProvisioners, + ) + } + return nil } func New(cfg Config) *Controller { + if err := cfg.validate(); err != nil { + panic(err) + } kclient := k8sutil.MustCreateClient(cfg.MasterHost, cfg.TLSInsecure, &cfg.TLSConfig) host := cfg.MasterHost if len(host) == 0 { host = k8sutil.MustGetInClusterMasterHost() } return &Controller{ - masterHost: host, - kclient: kclient, - clusters: make(map[string]*cluster.Cluster), - namespace: cfg.Namespace, + masterHost: host, + kclient: kclient, + clusters: make(map[string]*cluster.Cluster), + namespace: cfg.Namespace, + pvProvisioner: cfg.PVProvisioner, } } @@ -133,7 +157,7 @@ func (c *Controller) initResource() (string, error) { return "", err } } - err = k8sutil.CreateStorageClass(c.kclient) + err = k8sutil.CreateStorageClass(c.kclient, c.pvProvisioner) if err != nil { log.Errorf("fail to create storage class: %v", err) return "", err diff --git a/pkg/util/k8sutil/k8sutil.go b/pkg/util/k8sutil/k8sutil.go index c5e2b5d..0dd4abf 100644 --- a/pkg/util/k8sutil/k8sutil.go +++ b/pkg/util/k8sutil/k8sutil.go @@ -158,13 +158,12 @@ func GetNodePortString(srv *api.Service) string { return fmt.Sprint(srv.Spec.Ports[0].NodePort) } -func CreateStorageClass(kubecli *unversioned.Client) error { +func CreateStorageClass(kubecli *unversioned.Client, pvProvisioner string) error { class := &storage.StorageClass{ ObjectMeta: api.ObjectMeta{ Name: storageClassName, }, - // TODO: add aws - Provisioner: "kubernetes.io/gce-pd", + Provisioner: pvProvisioner, } _, err := kubecli.StorageClasses().Create(class) return err