SSL 证书验证文件部署到 K8s
🏷️ Kubernetes
申请免费证书时需要验证域名,一般有两种验证方式:
- DNS 验证
- 文件验证
一般使用 DNS 验证的方式,配置起来比较方便而且时效快。不过由于新网修改 DNS 解析时需要手机验证码,而手机号又不在我这,每次要验证码都比较麻烦,所以今天尝试了下使用文件的方式验证。
由于域名所在的服务是部署在 K8s 上的,所以需要部署一个专门用于访问校验文件的 Nginx 服务。
而为了避免每次添加或修改验证文件时需要重新制作镜像,这里使用在 Deployment 中挂载 ConfigMap 卷的方式来加载这些验证文件。
ConfigMap
apiVersion: v1
data:
0EMPE2QCKR.txt: 8bnj57lz2twd1kll0rac53ei5kot1xdu
CAFD2E57275C38A416EA308E168B234E.txt: |-
RUJLV3GQLSOZYNL4TMQ5K9ODKPLA313YQJ6R5H5HZEWW7GQ1K3R5PE7ZJQ4QQF12
trust-provider.com
cmcdtcsuoolffg
kind: ConfigMap
metadata:
name: domain-config
namespace: prod
这里的 CAFD2E57275C38A416EA308E168B234E.txt 对应的值就是腾讯云 SSL 证书验证文件的内容。需要注意的是这里有换行符,默认是 Linux 格式的换行符( \n
)。
直接从腾讯云的门户上下载的 txt 文件中使用的是 Windows 默认换行符( \r\n
),但是验证时使用 Linux 默认换行符的文件才能通过验证,而且这个验证感觉有延迟(可以请求到文件后隔一段时间才能验证通过),没有 DNS 验证的时效快(添加好 DNS 解析后很快就可以通过验证了)。
如果需要在配置文件中使用 Windows 默认换行符时可以采用如下写法:
apiVersion: v1
data:
0EMPE2QCKR.txt: 8bnj57lz2twd1kll0rac53ei5kot1xdu
CAFD2E57275C38A416EA308E168B234E.txt: "RUJLV3GQLSOZYNL4TMQ5K9ODKPLA313YQJ6R5H5HZEWW7GQ1K3R5PE7ZJQ4QQF12\r\ntrust-provider.com\r\ncmcdtcsuoolffg"
kind: ConfigMap
metadata:
name: domain-config
namespace: prod
Deployment
部署中挂载 ConfigMap 卷可以参考如下写法:
apiVersion: apps/v1
kind: Deployment
metadata:
name: ui-domain-txt-deploy
namespace: prod
spec:
replicas: 1
revisionHistoryLimit: 3
selector:
matchLabels:
app: ui-domain-txt
template:
metadata:
labels:
app: ui-domain-txt
spec:
containers:
- image: nginx:1.19.4
imagePullPolicy: IfNotPresent
name: ui-domain-txt
ports:
- containerPort: 80
volumeMounts:
- mountPath: /usr/share/nginx/html/
name: txt-files
readOnly: true
volumes:
- configMap:
defaultMode: 420
items:
- key: 0EMPE2QCKR.txt
path: 0EMPE2QCKR.txt
- key: LE2K8S6JNHIA8RM8HQ9XC53TJYFQHY7U.txt
path: .well-known/pki-validation/LE2K8S6JNHIA8RM8HQ9XC53TJYFQHY7U.txt
name: domain-config
name: txt-files
有一点需要注意的是配置中的 path: .well-known/pki-validation/LE2K8S6JNHIA8RM8HQ9XC53TJYFQHY7U.txt
在门户界面修改时会提示路径中有特殊字符,但是直接编辑 YAML 是可以这么写的。
Ingress
由于是新创建的一个服务,为了不影响其它的路由,这里使用的是 Exact
类型的路由匹配策略(只有当请求的路径完全匹配时才会将请求转发到后端的服务)。
apiVersion: networking.k8s.io/v1beta1
kind: Ingress
metadata:
annotations:
kubernetes.io/ingress.class: nginx-controller-blog
kubernetes.io/ingress.rule-mix: "true"
nginx.ingress.kubernetes.io/use-regex: "true"
generation: 3
name: ingress-domain-txt
namespace: prod
spec:
rules:
- host: www.liujiajia.me
http:
paths:
- backend:
serviceName: svc-ui-domain-txt
servicePort: 80
path: /0EMPE2QCKR.txt
pathType: Exact
- host: www.liujiajia.me
http:
paths:
- backend:
serviceName: svc-ui-domain-txt
servicePort: 80
path: /.well-known/pki-validation/LE2K8S6JNHIA8RM8HQ9XC53TJYFQHY7U.txt
pathType: Exact
tls:
- hosts:
- www.liujiajia.me
secretName: tls-www-liujiajia-me