step-ca
step-ca
step-ca
in a Docker containerstep-ca
step-ca
step-ca
in a Docker containerAutocert exists to make it easy to use mutual TLS to improve security within a cluster and to secure communication into, out of, and between Kubernetes clusters.
To get a certificate you simply need to telll autocert your workload's name, using the autocert.step.sm/name
pod annotation.
Autocert will issue a cert to the pod, make it available in var/run/autocert.step.sm
, and keep it renewed.
It requires a certificate authority to issue certificates.
This guide shows how to configure autocert to use Certificate Manager as the upstream CA.
You will need:
Bootstrapping with your Authority configures your workstation to trust the authority's root certificate.
Run:
step ca bootstrap --ca-url [your CA URL] \
--fingerprint [your CA fingerprint] \
--install
Autocert requires a JWK provisioner (it's the default type).
Let's call it autocert
. Run:
step ca provisioner add autocert --create
You’ll be asked to provide a password to encrypt the provisioner private key.
In Kubernetes, create a namespace for autocert:
kubectl create ns step
Output:
namespace/step created
Use the same password you entered when creating the provisioner to create the Secret.
kubectl -n step create secret generic autocert-password --from-file=password=autocert-password.txt
Output:
secret/autocert-password created
Now create a ConfigMap
that includes your (bootstrapped) config dir:
kubectl -n step create configmap config --from-file $(step path)/config`
Output:
configmap/config created
We'll do the same thing for the certs
dir, which contains our CA's root certificate:
kubectl -n step create configmap certs --from-file $(step path)/certs
Output:
configmap/certs created
Download the yaml config:
curl -O https://raw.githubusercontent.com/smallstep/autocert/master/install/02-autocert.yaml
Edit the caUrl
in the autocert-config
ConfigMap in the 02-autocert.yaml
file you just downloaded. Change it from https://ca.step.svc.cluster.local
to your Certificate Manager authority URL, e.g. https://autocert.areed.ca.smallstep.com
.
Run:
kubectl apply -f https://raw.githubusercontent.com/smallstep/autocert/master/install/03-rbac.yaml
Output:
clusterrole.rbac.authorization.k8s.io/autocert-controller created
clusterrolebinding.rbac.authorization.k8s.io/autocert-controller created
Now let's deploy autocert. Run:
kubectl apply -f 02-autocert.yaml
Output:
service/autocert created
configmap/autocert-config created
deployment.apps/autocert created
And, let's deploy the admission webhook:
You can see in this block that we're including the root CA certificate (in base64) as part of the client configuration for autocert.
cat <<EOF | kubectl apply -f -
apiVersion: admissionregistration.k8s.io/v1
kind: MutatingWebhookConfiguration
metadata:
name: autocert-webhook-config
labels: {app: autocert}
webhooks:
- name: autocert.step.sm
sideEffects: None
admissionReviewVersions: ["v1beta1"]
clientConfig:
service:
name: autocert
namespace: step
path: "/mutate"
caBundle: $(cat $(step path)/certs/root_ca.crt | base64 | tr -d '\n')
rules:
- operations: ["CREATE"]
apiGroups: [""]
apiVersions: ["v1"]
resources: ["pods"]
namespaceSelector:
matchLabels:
autocert.step.sm: enabled
EOF
output:
mutatingwebhookconfiguration.admissionregistration.k8s.io/autocert-webhook-config created
Autocert is now added to the cluster and configured. You can run this command to verify the autocert pods are marked Ready.
kubectl -n step get deployment/autocert
Let’s create a test app that will use autocert. It’s a “Hello World” web server that uses mutual TLS authentication.
Since this deployment is in the default namespace, label it to tell autocert to issue and renew certificates for new pods with the autocert.step.sm/name
annotation:
kubectl label namespace default autocert.step.sm=enabled
Output:
namespace/default labeled
To test things out, we'll create a deployment with the autocert.step.sm/name
pod annotation.
This example uses the name localhost
, since we will be testing from our workstation.
cat <<EOF | kubectl apply -f -
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app: hello-mtls
name: hello-mtls
spec:
selector:
matchLabels:
app: hello-mtls
template:
metadata:
annotations:
autocert.step.sm/name: localhost
labels:
app: hello-mtls
spec:
containers:
- image: smallstep/hello-mtls-server-go:latest
name: hello-mtls
EOF
Output:
deployment.apps/hello-mtls created
For testing, forward localhost:8443
to port 443 on the pod.
kubectl port-forward deploy/hello-mtls 8443:443
Output:
Forwarding from 127.0.0.1:8443 -> 443
Forwarding from [::1]:8443 -> 443
Keep this running in the background during the next steps.
Now issue a client certificate signed by your CA. You’ll need this to authenticate to the “Hello mTLS” test server.
step ca certificate andrew@smallstep.com areed.crt areed.key
Finally, you should be able to verify it's all working:
curl --cacert $(step path)/certs/root_ca.crt \
--cert areed.crt --key areed.key \
https://localhost:8443
Output:
Hello andrew@smallstep.com!
Unsubscribe anytime. See our privacy policy.
© 2023 Smallstep Labs, Inc. All rights reserved.