我正在为驻留在AKS中的应用程序设置入口。但是在将证书绑定到入口时遇到了问题。
正如你在下面看到的,我试图从KV引用ingress-cert
,并通过SecretProviderClass
在入口中使用它
apiVersion: secrets-store.csi.x-k8s.io/v1
kind: SecretProviderClass
metadata:
name: {{ include "secretProvider.name" . }}
spec:
provider: azure
secretObjects:
- secretName: ingress-tls-csi
type: kubernetes.io/tls
data:
- objectName: ingress-cert
key: tls.key
- objectName: ingress-cert
key: tls.crt
parameters:
usePodIdentity: "false"
useVMManagedIdentity: "true"
userAssignedIdentityID: {{ .Values.keyVault.identity }}
keyvaultName: {{ .Values.keyVault.name }}
objects: |
array:
- |
objectName: ingress-cert
objectType: secret
tenantId: {{ .Values.keyVault.tenant }}
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: {{ include "ingress.name" . }}
annotations:
kubernetes.io/ingress.class: azure/application-gateway
kubernetes.io/ingress.allow-http: "false"
appgw.ingress.kubernetes.io/override-frontend-port: "443"
spec:
tls:
- hosts:
- {{ .Values.ingress.host }}
secretName: ingress-tls-csi
# Property `rules` is omitted
当通过env从pod访问其他机密时,它工作得很好,但对于入口,这是描述它的输出:
Name: my-ingress
Namespace: my-namespace
Address: x.x.x.x
Default backend: default-http-backend:80
TLS:
ingress-tls-csi terminates my.example.com
Rules:
Host Path Backends
---- ---- --------
Annotations: appgw.ingress.kubernetes.io/override-frontend-port: 443
kubernetes.io/ingress.allow-http: false
kubernetes.io/ingress.class: azure/application-gateway
Events:
Type Reason Age From Message
---- ------ ---- ---- -------
Warning SecretNotFound 3m3s (x2 over 3m10s) azure/application-gateway Unable to find the secret associated to secretId: [my-namespace/ingress-tls-csi]
我已经按照AKS集群文档中的Use the Azure Key Vault Provider for Secrets Store CSI Driver设置了KV集成。
但是,在遵循Set up Secrets Store CSI Driver启用具有TLS的NGINX入口控制器后,可以提示如何使用AGIC实现同样的功能。我注意到证书被添加为AKS中的一个秘密,然后在入口中使用secretName: ingress-tls-csi
引用。
kubectl get secret -n $NAMESPACE
NAME TYPE DATA AGE
ingress-tls-csi kubernetes.io/tls 2 1m34s
我假设ingress不能直接引用SecretProviderClass
中的秘密,因为文档中的示例需要使用ingress-tls-csi
作为秘密对象,我假设它(再次(由ingress-nginx
图表创建。
我的问题是,如何使用AGIC实现与ingress-nginx
示例相同的功能?
附加信息:
- 我在Azure CNI网络中使用了AGIC
- Ingress当前正在使用
kubectl
命令手动添加的证书。我需要使用KV的原因是AKS也会被部署在同一域但不同命名空间下的其他人使用,我认为直接访问证书的私钥是个坏主意
由于我找不到将Ingress与Azure密钥库集成的方法,我使用GitHub Actions实现了一个变通方法,以检索证书并将其添加到AKS。因为大多数都是bash命令,所以解决方法并不是GitHub Actions独有的。
name: Assign Cerfiticate from KV to AKS
on:
workflow_dispatch:
jobs:
build-push:
name: Assign Cerfiticate from KV to AKS
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
# Azure Authentication
- uses: azure/login@v1
with:
creds: ${{ secrets.AZURE_CREDENTIALS }}
- name: Authenticate and set context to AKS cluster
run: az aks get-credentials --name "my-aks-cluster" --resource-group "my-rg" --admin
- uses: azure/setup-helm@v3
with:
token: ${{ secrets.PAT }}
# Retrieve certificate and private key from Azure Key Vault
- name: Download certificate and private key in PKCS#12 format
run: |
az keyvault secret download --name my-certificate
--vault-name my-kv
--encoding base64
-f certificate.pfx
- name: Extract private key in RSA format
run: |
openssl pkcs12 -in certificate.pfx -nocerts -nodes -passin pass: | openssl rsa -out private.key
- name: Extract certificate
run: |
openssl pkcs12 -in certificate.pfx -clcerts -nokeys -passin pass: -out certificate.crt
- name: Deploy Kubernetes Configuration
run: |
helm upgrade --install release-name chart-name
-n my-namespace
--set-file mychart.ingress.key=private.key
--set-file mychart.ingress.certificate=certificate.crt
以上内容的简要说明:
- 下载
.pfx
格式的证书和私钥 - 使用OpenSSL提取到
.crt
和.key
- 使用
--set-file
将提取的文件传递到helm install/upgrade
这里是秘密和入口配置:
apiVersion: v1
kind: Secret
metadata:
name: ingress-tls
type: kubernetes.io/tls
data:
tls.crt: {{ .Values.ingress.certificate | b64enc }}
tls.key: {{ .Values.ingress.key | b64enc }}
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: {{ include "ingress.name" . }}
annotations:
kubernetes.io/ingress.class: azure/application-gateway
kubernetes.io/ingress.allow-http: "false"
appgw.ingress.kubernetes.io/override-frontend-port: "443"
spec:
tls:
- hosts:
- {{ .Values.ingress.host }}
secretName: ingress-tls
# Property `rules` is omitted
无需对SecretProviderClass
进行额外修改。
我希望这只是一个变通办法,因为如果Ingress可以直接与Azure密钥库集成会更好。