hack/tls-gen.sh
#!/usr/bin/env bash

# Usage:
#   KUBE_NS=default \
#   SERVER_SECRET=vault-server-tls \
#   CLIENT_SECRET=vault-client-tls \
#   tls-gen.sh
# Additional params:
#   SAN_HOSTS="a.b.c,x.y.z"
#   SERVER_CERT="tls.crt"
#   SERVER_KEY="tls.key"


: ${KUBE_NS:?"Need to set KUBE_NS"}

SERVER_CERT=${SERVER_CERT:-"server.crt"}
SERVER_KEY=${SERVER_KEY:-"server.key"}

# Create temporary output directory
OUTPUT_DIR=$(mktemp -d)

# Deletes the temp directory
function cleanup {      
  rm -rf "$OUTPUT_DIR"
}
trap cleanup EXIT


if ! which cfssl > /dev/null; then
	echo "cfssl needs to be installed"
	exit 1
fi

if ! which cfssljson > /dev/null; then
	echo "cfssljson needs to be installed"
	exit 1
fi

if ! which jq > /dev/null; then
	echo "jq needs to be installed"
	exit 1
fi

if ! kubectl version 1> /dev/null ; then
    echo "kubectl with kubeconfig needs to be setup"
	exit 1
fi

rm -rf $OUTPUT_DIR/config
mkdir -p $OUTPUT_DIR/config
rm -rf $OUTPUT_DIR/certs/tmp
mkdir -p $OUTPUT_DIR/certs/tmp

# Generate ca-config.json and ca-csr.json
cfssl print-defaults config | \
  jq 'del(.signing.profiles) | .signing.default.expiry="8760h" | .signing.default.usages=["signing", "key encipherment", "server auth"] | .key = {"algo":"rsa","size":2048}' \
  > $OUTPUT_DIR/config/ca-config.json
cfssl print-defaults csr | \
  jq 'del(.hosts) | .CN = "Autogenerated CA" | .names[0].O="Autogen CA for Vault-Operator" | .key = {"algo":"rsa","size":2048}' \
	> $OUTPUT_DIR/config/ca-csr.json

# add additional hosts to SAN:
#   SAN_HOSTS="a.b.c,x.y.z"
HOSTS="\"localhost\", \"*.${KUBE_NS}.pod\", \"*.${KUBE_NS}.svc\""
for i in $(echo ${SAN_HOSTS} | sed "s/,/ /g")
do
    HOSTS="\"$i\",${HOSTS}"
done

echo "SAN HOSTS: ${HOSTS}"
# Generate vault-server-csr.json with the SANs according to the namespace and name of the vault cluster
cfssl print-defaults csr | jq ".hosts = [$HOSTS]" | \
	jq '.CN = "vault-server" | .key = {"algo":"rsa","size":2048}' > $OUTPUT_DIR/config/vault-csr.json

# Generate ca cert and key
cfssl gencert -initca $OUTPUT_DIR/config/ca-csr.json | cfssljson -bare $OUTPUT_DIR/certs/tmp/ca

# Generate server cert and key
cfssl gencert \
    -ca $OUTPUT_DIR/certs/tmp/ca.pem \
    -ca-key $OUTPUT_DIR/certs/tmp/ca-key.pem \
    -config $OUTPUT_DIR/config/ca-config.json \
    $OUTPUT_DIR/config/vault-csr.json | cfssljson -bare $OUTPUT_DIR/certs/tmp/server

# Rename certs for vault-operator consumption
mv $OUTPUT_DIR/certs/tmp/ca.pem $OUTPUT_DIR/certs/vault-client-ca.crt
mv $OUTPUT_DIR/certs/tmp/server.pem $OUTPUT_DIR/certs/${SERVER_CERT}
mv $OUTPUT_DIR/certs/tmp/server-key.pem $OUTPUT_DIR/certs/${SERVER_KEY}

# Create server secret
if [ -n "${SERVER_SECRET}" ]; then
	echo "creating server secret: ${SERVER_SECRET}"
	kubectl -n $KUBE_NS create secret generic $SERVER_SECRET --from-file=$OUTPUT_DIR/certs/${SERVER_CERT} --from-file=$OUTPUT_DIR/certs/${SERVER_KEY}
fi

# Create client secret
if [ -n "${CLIENT_SECRET}" ]; then
  echo "creating client secret: ${CLIENT_SECRET}"
	kubectl -n $KUBE_NS create secret generic $CLIENT_SECRET --from-file=$OUTPUT_DIR/certs/vault-client-ca.crt
fi
