Skip to content
This repository has been archived by the owner on Mar 28, 2020. It is now read-only.

[WIP] Etcd tls #218

Closed
wants to merge 3 commits into from
Closed

[WIP] Etcd tls #218

wants to merge 3 commits into from

Conversation

colhom
Copy link
Contributor

@colhom colhom commented Oct 12, 2016

The first commit is from #217, disregard for this review.

Here is the overview for kube-etcd-controller TLS flow, which should set us up well for integrating with pre-existing external PKI.

Trust delegation model:

kube-etcd-controller CA (self-signed or externally signed via CSR on startup)
    |
    |
    |-------->  etcd-cluster-A CA  (tpr object)
    |                  --------> etcd-cluster-A-0000 cert (pod)
    |                  --------> etcd-cluster-A-0001 cert 
    |                  --------> etcd-cluster-A-0002 cert 
    |           
    | ---------> etcd-cluster-B CA
                      --------> etcd-cluster-B-0000 cert
                      --------> etcd-cluster-B-0001 cert
                      --------> etcd-cluster-B-0002 cert

Here are the steps in order:

  1. kube-etcd-controller pod startup:
    • generate controller CA private key
    • generate controller CA certificate
      • generate self-signed cert (default for now, useful for development mode)
      • generate CSR, wait for external entity to sign it and return cert via Kubernetes API (production mode, allows integration with arbitrary external PKI systems)
  2. etcd cluster creation (in controller pod):
    • generate private key
    • generate controller CA as a subordinate CA of cluster CA using parameter from cluster spec
  3. etcd node pod startup (in the etcd pod, prior to etcd application starting):
    • generate private key
    • generate a CSR for CN=etcd-cluster-xxxx, submit for signing via annotation
  4. etcd node enrollment (in controller pod)
    • observe new CSR annotation on pod/etcd-cluster-xxxx
    • sign CSR with the cluster CA for pod/etcd-cluster-xxxx
      • --> return certificate via annotation to pod/etcd-cluster-xxxx
  5. etcd node startup (in etcd pod)
    • observe new signed certificate in annotation on pod/etcd-cluster-xxxx
    • bring up etcd application with private key, cert and cluster CA certificate

So far I have implemented up through step 2

\cc @hongchaodeng @brianredbeard

also tear down backup replicaset before etcd pods.

fixes #216
only support self-signed mode for now, appropriate hook in place for remote signing complete with todo's.

This will involve exchanging a CSR for a Certificate via the Kubernetes API, allowing the delegating CA's private key material to remain private.
@colhom
Copy link
Contributor Author

colhom commented Oct 12, 2016

fixes #12

)

// Parse from file if exists, else create new and write to file
func InitializePrivateKeyFile(keyPath string) (*rsa.PrivateKey, error) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why is it called "InitializePrivateKeyFile"? Is it gonna initialize private key or initialize a file?

return rsa.GenerateKey(rand.Reader, RSAKeySize)
}

func writePrivateKeyToFile(keyPath string, key *rsa.PrivateKey) error {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These two funcs aren't used in this file. Could you move them to where they are used?

@hongchaodeng
Copy link
Member

@colhom
The description of this PR is very good.
Could you write them as a design doc under design/ and submit in another PR?
For feature, we usually have design go in first and then implementation.

@@ -16,17 +17,26 @@ var (
func init() {
flag.StringVar(&cfg.PVProvisioner, "pv-provisioner", "kubernetes.io/gce-pd", "persistent volume provisioner type")
flag.BoolVar(&analyticsEnabled, "analytics", true, "Send analytical event (Cluster Created/Deleted etc.) to Google Analytics")
flag.StringVar(&cfg.EtcdTLSConfig.Dir, "etcd-tls-dir", "/etc/kube-etcd-controller/tls/", "directory to store etcd tls files. in most cases, this path will be mounted in a secret.")
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you move these under "masterhost" flag?
It'd better group all TLS flags together, and more specifically all etcd TLS together

flag.Parse()

cfg.Namespace = os.Getenv("MY_POD_NAMESPACE")
if len(cfg.Namespace) == 0 {
cfg.Namespace = "default"
}
if err := os.MkdirAll(cfg.EtcdTLSConfig.Dir, 0600); err != nil {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why we create the dir?
Why not let user create the dir because they pass in.

idCounter int
eventCh chan *clusterEvent
stopCh chan struct{}
kclient *unversioned.Client
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

don't group them together.
And group ca stuff together.

}
}

func (c *Controller) initializeClusterTLS(clusterName string, clusterSpec *spec.ClusterSpec) (*rsa.PrivateKey, *x509.Certificate, error) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could you put TLS methods into another file "controller/tls.go"?

@@ -40,6 +42,16 @@ type ClusterSpec struct {
// If there is no seed member, a completely new cluster will be created.
// There is no seed member by default.
Seed *SeedPolicy `json:"seed,omitempty"`
// Common name for the cluster CA
// Defaults to the cluster name
CACommonName string `json:"caCommonName,omitempty"`
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could you abstract another struct "TLSPolicy"?

@colhom
Copy link
Contributor Author

colhom commented Oct 12, 2016

@hongchaodeng I'm going to pause on this implementation and produce a design document before continuing (as you suggest). A few of your questions on this PR will hopefully be answered by the design doc.

@hongchaodeng
Copy link
Member

@colhom Thanks!

@colhom colhom mentioned this pull request Oct 13, 2016
@dhawal55
Copy link

Any update on this?

@hongchaodeng
Copy link
Member

@dhawal55

We have decided to go with #409

@philips
Copy link
Contributor

philips commented Jan 19, 2017

Closing this PR for now. We can revisit once #409 is in place and build on top of #409.

@philips philips closed this Jan 19, 2017
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants