Split GetKeyPair method into two methods

This commit is contained in:
James Munnelly 2017-09-10 22:54:55 +01:00
parent 6e1b4c8533
commit 89588bb281
5 changed files with 80 additions and 67 deletions

View File

@ -92,7 +92,7 @@ func (c *Controller) Sync(crt *v1alpha1.Certificate) (err error) {
}
// grab existing certificate and validate private key
cert, _, err := kube.GetKeyPair(c.client, crt.Namespace, crt.Spec.SecretName)
cert, err := kube.SecretTLSCert(c.secretLister, crt.Namespace, crt.Spec.SecretName)
if err != nil {
s := messageErrorCheckCertificate + err.Error()
@ -155,7 +155,7 @@ func (c *Controller) scheduleRenewal(crt *v1alpha1.Certificate) {
return
}
cert, _, err := kube.GetKeyPair(c.client, crt.Namespace, crt.Spec.SecretName)
cert, err := kube.SecretTLSCert(c.secretLister, crt.Namespace, crt.Spec.SecretName)
if err != nil {
runtime.HandleError(fmt.Errorf("[%s/%s] Error getting certificate '%s': %s", crt.Namespace, crt.Name, crt.Spec.SecretName, err.Error()))

View File

@ -27,9 +27,9 @@ func (a *Acme) obtainCertificate(crt *v1alpha1.Certificate) ([]byte, []byte, err
return nil, nil, fmt.Errorf("no domains specified")
}
_, acmePrivKey, err := kube.GetKeyPair(a.client, a.issuer.Namespace, a.issuer.Spec.ACME.PrivateKey)
acmePrivKey, err := kube.SecretTLSKey(a.secretsLister, a.issuer.Namespace, a.issuer.Spec.ACME.PrivateKey)
if acmePrivKey == nil {
if err != nil {
return nil, nil, fmt.Errorf("error getting acme account private key: %s", err.Error())
}
@ -38,7 +38,7 @@ func (a *Acme) obtainCertificate(crt *v1alpha1.Certificate) ([]byte, []byte, err
DirectoryURL: a.issuer.Spec.ACME.Server,
}
_, key, err := kube.GetKeyPair(a.client, crt.Namespace, crt.Spec.SecretName)
key, err := kube.SecretTLSKey(a.secretsLister, crt.Namespace, crt.Spec.SecretName)
if k8sErrors.IsNotFound(err) {
key, err = pki.GenerateRSAPrivateKey(2048)
@ -47,7 +47,7 @@ func (a *Acme) obtainCertificate(crt *v1alpha1.Certificate) ([]byte, []byte, err
}
}
if key == nil {
if err != nil {
return nil, nil, fmt.Errorf("error getting certificate private key: %s", err.Error())
}

View File

@ -7,6 +7,7 @@ import (
"sync"
"golang.org/x/crypto/acme"
k8sErrors "k8s.io/apimachinery/pkg/api/errors"
utilerrors "k8s.io/apimachinery/pkg/util/errors"
"github.com/jetstack-experimental/cert-manager/pkg/apis/certmanager/v1alpha1"
@ -27,9 +28,13 @@ func (a *Acme) Prepare(crt *v1alpha1.Certificate) (v1alpha1.CertificateStatus, e
}
log.Printf("getting private key for acme issuer %s/%s", a.issuer.Namespace, a.issuer.Name)
_, accountPrivKey, err := kube.GetKeyPair(a.client, a.issuer.Namespace, a.issuer.Spec.ACME.PrivateKey)
accountPrivKey, err := kube.SecretTLSKey(a.secretsLister, a.issuer.Namespace, a.issuer.Spec.ACME.PrivateKey)
if accountPrivKey == nil {
if k8sErrors.IsNotFound(err) {
return updateStatus, err
}
if err != nil {
return updateStatus, fmt.Errorf("error getting acme account private key: %s", err.Error())
}

View File

@ -2,6 +2,7 @@ package acme
import (
"context"
"crypto/rsa"
"fmt"
"strings"
@ -32,39 +33,13 @@ const (
func (a *Acme) Setup() (v1alpha1.IssuerStatus, error) {
update := a.issuer.DeepCopy()
_, accountPrivKey, err := kube.GetKeyPair(a.client, a.issuer.Namespace, a.issuer.Spec.ACME.PrivateKey)
accountPrivKey, err := kube.SecretTLSKey(a.secretsLister, a.issuer.Namespace, a.issuer.Spec.ACME.PrivateKey)
if k8sErrors.IsNotFound(err) {
accountPrivKey, err = pki.GenerateRSAPrivateKey(2048)
if err != nil {
s := messageAccountRegistrationFailed + "error generating private key " + err.Error()
glog.Info(s)
a.recorder.Event(a.issuer, v1.EventTypeWarning, errorAccountRegistrationFailed, s)
v1alpha1.UpdateIssuerStatusCondition(update, v1alpha1.IssuerConditionReady, v1alpha1.ConditionFalse, errorAccountRegistrationFailed, s)
return update.Status, fmt.Errorf(s)
}
_, err = kube.EnsureSecret(a.client, &v1.Secret{
ObjectMeta: metav1.ObjectMeta{
Name: a.issuer.Spec.ACME.PrivateKey,
Namespace: a.issuer.Namespace,
},
Data: map[string][]byte{
v1.TLSPrivateKeyKey: pki.EncodePKCS1PrivateKey(accountPrivKey),
},
})
if err != nil {
s := messageAccountRegistrationFailed + "error saving private key " + err.Error()
glog.Info(s)
a.recorder.Event(a.issuer, v1.EventTypeWarning, errorAccountRegistrationFailed, s)
v1alpha1.UpdateIssuerStatusCondition(update, v1alpha1.IssuerConditionReady, v1alpha1.ConditionFalse, errorAccountRegistrationFailed, s)
return update.Status, fmt.Errorf(s)
}
accountPrivKey, err = a.createAccountPrivateKey()
}
if accountPrivKey == nil {
if err != nil {
s := messageAccountRegistrationFailed + err.Error()
glog.Info(s)
a.recorder.Event(a.issuer, v1.EventTypeWarning, errorAccountRegistrationFailed, s)
@ -77,7 +52,7 @@ func (a *Acme) Setup() (v1alpha1.IssuerStatus, error) {
DirectoryURL: a.issuer.Spec.ACME.Server,
}
_, err = cl.GetReg(context.Background(), a.issuer.Status.ACME.URI)
_, err = cl.GetReg(context.Background(), a.issuer.Status.ACMEStatus().URI)
if err == nil {
glog.Info(messageAccountVerified)
@ -112,3 +87,27 @@ func (a *Acme) Setup() (v1alpha1.IssuerStatus, error) {
return update.Status, nil
}
func (a *Acme) createAccountPrivateKey() (*rsa.PrivateKey, error) {
accountPrivKey, err := pki.GenerateRSAPrivateKey(2048)
if err != nil {
return nil, err
}
_, err = kube.EnsureSecret(a.client, &v1.Secret{
ObjectMeta: metav1.ObjectMeta{
Name: a.issuer.Spec.ACME.PrivateKey,
Namespace: a.issuer.Namespace,
},
Data: map[string][]byte{
v1.TLSPrivateKeyKey: pki.EncodePKCS1PrivateKey(accountPrivKey),
},
})
if err != nil {
return nil, err
}
return accountPrivKey, err
}

View File

@ -3,45 +3,54 @@ package kube
import (
"crypto/rsa"
"crypto/x509"
"fmt"
"github.com/jetstack-experimental/cert-manager/pkg/util/errors"
"github.com/jetstack-experimental/cert-manager/pkg/util/pki"
api "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
utilerrors "k8s.io/apimachinery/pkg/util/errors"
"k8s.io/client-go/kubernetes"
corelisters "k8s.io/client-go/listers/core/v1"
)
func GetKeyPair(cl kubernetes.Interface, namespace, name string) (*x509.Certificate, *rsa.PrivateKey, error) {
secret, err := cl.CoreV1().Secrets(namespace).Get(name, metav1.GetOptions{})
func GetKeyPair(secretLister corelisters.SecretLister, namespace, name string) (certBytes []byte, keyBytes []byte, err error) {
secret, err := secretLister.Secrets(namespace).Get(name)
if err != nil {
return nil, nil, err
}
certBytes, okcert := secret.Data[api.TLSCertKey]
keyBytes, okkey := secret.Data[api.TLSPrivateKeyKey]
certBytes = secret.Data[api.TLSCertKey]
keyBytes = secret.Data[api.TLSPrivateKeyKey]
// check if the certificate and private key exist, we stop so as to not
// destroy a secret potentially used for something else
if !okcert || !okkey {
return nil, nil, fmt.Errorf("Secret does not contain TLS fields")
}
key, keyErr := pki.DecodePKCS1PrivateKeyBytes(keyBytes)
cert, certErr := pki.DecodeX509CertificateBytes(certBytes)
var errs []error
if keyErr != nil {
errs = append(errs, keyErr)
}
if certErr != nil {
errs = append(errs, certErr)
}
if len(errs) > 0 {
err = errors.NewInvalidData(utilerrors.NewAggregate(errs).Error())
}
return cert, key, err
return certBytes, keyBytes, err
}
func SecretTLSKey(secretLister corelisters.SecretLister, namespace, name string) (*rsa.PrivateKey, error) {
secret, err := secretLister.Secrets(namespace).Get(name)
if err != nil {
return nil, err
}
keyBytes := secret.Data[api.TLSPrivateKeyKey]
key, err := pki.DecodePKCS1PrivateKeyBytes(keyBytes)
if err != nil {
return key, errors.NewInvalidData(err.Error())
}
return key, nil
}
func SecretTLSCert(secretLister corelisters.SecretLister, namespace, name string) (*x509.Certificate, error) {
secret, err := secretLister.Secrets(namespace).Get(name)
if err != nil {
return nil, err
}
certBytes := secret.Data[api.TLSCertKey]
cert, err := pki.DecodeX509CertificateBytes(certBytes)
if err != nil {
return cert, errors.NewInvalidData(err.Error())
}
return cert, nil
}