我正在尝试在 Kubernetes 集群中部署的 Vault 中启用 TLS 身份验证。我的目标是能够使用 cert 方法登录到保险库,如下所示:
vault login \
-method=cert \
-ca-cert=vault-ca.pem \
-client-cert=cert.pem \
-client-key=key.pem \
name=web
我首先在此页面之后针对 minikube 集群部署了保管库。此页面创建 Vault 服务器的公钥、私钥和证书。有了这三个文件,我假设到服务器的任何连接都是安全的。我遵循的步骤如下:
创建独立的 TLS 保险库服务器
1. 创建环境变量
# SERVICE is the name of the Vault service in Kubernetes.
# It does not have to match the actual running service, though it may help for consistency.
SERVICE=vault-server-tls
# NAMESPACE where the Vault service is running.
NAMESPACE=vault-namespace
# SECRET_NAME to create in the Kubernetes secrets store.
SECRET_NAME=vault-server-tls
# TMPDIR is a temporary working directory.
TMPDIR=/tmp
2. 为保管库服务器创建私钥
openssl genrsa -out ${TMPDIR}/vault.key 2048
3. 创建和部署证书签名请求
- 3.1) 创建文件
csr.conf
$ cat <<EOF >${TMPDIR}/csr.conf
[req]
req_extensions = v3_req
distinguished_name = req_distinguished_name
[req_distinguished_name]
[ v3_req ]
basicConstraints = CA:FALSE
keyUsage = nonRepudiation, digitalSignature, keyEncipherment
extendedKeyUsage = serverAuth
subjectAltName = @alt_names
[alt_names]
DNS.1 = ${SERVICE}
DNS.2 = ${SERVICE}.${NAMESPACE}
DNS.3 = ${SERVICE}.${NAMESPACE}.svc
DNS.4 = ${SERVICE}.${NAMESPACE}.svc.cluster.local
IP.1 = 127.0.0.1
EOF
- 3.2) 使用中的配置创建证书签名请求
csr.conf
openssl req -new -key ${TMPDIR}/vault.key -subj "/CN=${SERVICE}.${NAMESPACE}.svc" -out ${TMPDIR}/server.csr -config ${TMPDIR}/csr.conf
- 3.3) 将证书签名请求放入 Kubernetes 的 CertificateSigningRequest yaml
$ export CSR_NAME=vault-csr
$ cat <<EOF >${TMPDIR}/csr.yaml
apiVersion: certificates.k8s.io/v1beta1
kind: CertificateSigningRequest
metadata:
name: ${CSR_NAME}
spec:
groups:
- system:authenticated
request: $(cat ${TMPDIR}/server.csr | base64 | tr -d '\n')
usages:
- digital signature
- key encipherment
- server auth
EOF
并将其应用到 Kubernetes
kubectl create -f ${TMPDIR}/csr.yaml
- 3.4) 批准证书签名请求
kubectl certificate approve ${CSR_NAME}
4. 获取 Vault 服务器的证书
serverCert=$(kubectl get csr ${CSR_NAME} -o jsonpath='{.status.certificate}')
并将其放入文件中
echo "${serverCert}" | openssl base64 -d -A -out ${TMPDIR}/vault.crt
5. 获取证书颁发机构的证书
kubectl config view --raw --minify --flatten -o jsonpath='{.clusters[].cluster.certificate-authority-data}' | base64 -d > ${TMPDIR}/vault.ca
在这个阶段,我有保险库服务器的私钥vault.key
、它的证书vault.crt
和 CA 证书vault.ca
6. 我可以将这些文件放入 Kubernetes 机密中,以供 Vault 服务器部署使用。
kubectl create secret generic ${SECRET_NAME} \
--namespace ${NAMESPACE} \
--from-file=vault.key=${TMPDIR}/vault.key \
--from-file=vault.crt=${TMPDIR}/vault.crt \
--from-file=vault.ca=${TMPDIR}/vault.ca
7. 最后使用 Helm 图表和以下自定义值部署 Vault 服务器
global:
enabled: true
tlsDisable: false
server:
extraEnvironmentVars:
VAULT_CACERT: /vault/userconfig/vault-server-tls/vault.ca
extraVolumes:
- type: secret
name: vault-server-tls # Matches the ${SECRET_NAME} from above
standalone:
enabled: true
config: |
listener "tcp" {
address = "[::]:8200"
cluster_address = "[::]:8201"
tls_cert_file = "/vault/userconfig/vault-server-tls/vault.crt"
tls_key_file = "/vault/userconfig/vault-server-tls/vault.key"
tls_client_ca_file = "/vault/userconfig/vault-server-tls/vault.ca"
}
storage "file" {
path = "/vault/data"
}
$ helm repo add hashicorp https://helm.releases.hashicorp.com
$ helm install vault hashicorp/vault --values values.yml
使用证书进行身份验证
我kubectl exec
进入吊舱vault-0
,然后启动并打开保险库。
然后我尝试使用我创建的文件登录。我知道它们与服务器的文件相同。但是,由于它们是配对和签名的,我希望它们能够工作。此外,我确实进入了 Vault 的 UI 并添加了 vault.ca 作为要在 TLS Acess 中使用的证书。
$ vault login -method=cert -ca-cert=/vault/userconfig/vault-server-tls/vault.ca -client-cert=/vault/userconfig/vault-server-tls/vault.cr
t -client-key=/vault/userconfig/vault-server-tls/vault.key
但是,我收到此错误:
Error authenticating: Error making API request.
URL: PUT https://127.0.0.1:8200/v1/auth/cert/login
Code: 500. Errors:
* failed to verify client's certificate: x509: certificate specifies an incompatible key usage
我对 TLS 的理解有限。谁能指出我正确的方向?