- 网络
- 云原生
- 网络安全
【免费下载链接】calico
Cloud native networking and network security
本文围绕 Calico 仓库中 hack/test/certs/README.md 所描述的 FV(Feature Validation)测试证书目录展开,系统讲解这套仅用于测试环境的 Kubernetes PKI 证书体系——包括根 CA、admin 客户端证书、API Server 证书与 Service Account 密钥的生成逻辑(regenerate.sh)、cfssl 签名配置、两类 kubeconfig 的差异,以及证书最终如何被挂载进 Felix FV 测试中临时启动的 kube-apiserver 容器。读完本文,你将掌握 Calico FV 测试 TLS 基础设施的完整链路,并能在本地复现证书再生成流程。
FV 证书的作用与适用场景
根据 hack/test/certs/README.md 的说明,该目录下的全部密钥与证书仅在当前仓库的 FV 测试中使用,并且是按照开源社区广泛流传的 "Kubernetes the Hard Way" 教程的步骤生成的。这意味着它并非生产环境制品,而是一套为测试用例临时拉起真实 kube-apiserver 而准备的信任链。
FV 测试之所以需要完整 PKI,是因为 Felix 的数据面测试(见 felix/fv/infrastructure/infra_k8s.go)会在容器内启动一个真实的 kube-apiserver 与 kube-controller-manager,用于验证 Calico 与 Kubernetes 的集成行为。API Server 需要 TLS 证书对外提供 HTTPS 服务,控制器需要 Service Account 密钥完成 SA Token 签发,客户端则需要合法证书访问 API——目录中每一份材料都对应测试链路上的一个角色。
目录完整内容如下:
| 文件 | 角色 |
|---|---|
ca.pem/ca-key.pem | 根 CA 证书与私钥,签发链的信任锚点 |
ca-config.json/ca-csr.json | cfssl 的签名策略配置与 CA 证书签名请求 |
admin.pem/admin-key.pem | admin 客户端证书(O=system:masters) |
kubernetes.pem/kubernetes-key.pem | API Server 服务端证书(含 SAN) |
service-account.pem/service-account-key.pem | Service Account 签名密钥对 |
admin-csr.json/kubernetes-csr.json/service-account-csr.json | 各证书的 CSR 定义 |
kubeconfig | admin 用户访问测试 API Server 的客户端配置 |
kube-controller-manager.kubeconfig | 控制器访问 API Server 的配置(证书内嵌) |
regenerate.sh | 一键再生成全部密钥与证书的脚本 |
证书信任链架构:一个 CA 派生全部凭证
从目录中四组 CSR 与证书可以清晰看出,整套体系采用"单一根 CA + 多角色证书"的经典结构:
- 根 CA(
CN=Kubernetes):由ca-csr.json定义,regenerate.sh通过cfssl gencert -initca初始化,是所有下级证书的签发者; - admin 客户端证书(
CN=admin):admin-csr.json中O=system:masters使该证书具备集群管理员权限,用于 FV 测试中 kubectl 对 API Server 的读写操作; - kubernetes 服务端证书(
CN=kubernetes):同时充当 API Server 的服务端证书,其 SAN 覆盖10.96.0.1(集群 Service IP)、127.0.0.1及一组kubernetes.default域名,确保容器内外的多种访问方式都能通过 TLS 校验; - service-account 密钥对(
CN=service-accounts):用于 kube-controller-manager 签发/校验 ServiceAccount Token,是测试集群内 Pod 身份认证的基础。
其中kubernetes-csr.json的 CN 与 SAN 设计值得注意:KUBERNETES_HOSTNAMES变量(见 regenerate.sh)覆盖了kubernetes、kubernetes.default、kubernetes.default.svc、kubernetes.default.svc.cluster与kubernetes.svc.cluster.local五个主机名,这些正是 kube-apiserver 以 Service 形式暴露时客户端可能使用的 DNS 名称。
cfssl 签名策略与 CSR 配置逐项解析
签名策略ca-config.json
{ "signing": { "default": { "expiry": "87600h" }, "profiles": { "kubernetes": { "usages": ["signing", "key encipherment", "server auth", "client auth"], "expiry": "87600h" } } } }该配置定义了一个名为kubernetes的签名 profile,核心参数含义:
expiry: 87600h:证书有效期 10 年(87600 小时),测试证书无需频繁轮换;usages同时包含server auth与client auth,使同一把kubernetes证书既能充当服务端证书,也能作为客户端证书复用,这是测试环境的务实做法;signing与key encipherment允许证书用于签名与密钥封装,满足 API Server 的 TLS 握手需求。
CSR 公共字段
四份 CSR(ca-csr.json、admin-csr.json、kubernetes-csr.json、service-account-csr.json)的密钥参数一致:rsa算法、2048位长度,组织信息统一为C=US, L=Portland, ST=Oregon, O=Kubernetes, OU=CA(admin 证书的 OU 为Kubernetes The Hard Way)。差异集中在CN与O:
| CSR | CN | O(组织) | 用途 |
|---|---|---|---|
| ca-csr.json | Kubernetes | Kubernetes | 根 CA 自身 |
| admin-csr.json | admin | system:masters | 管理员客户端 |
| kubernetes-csr.json | kubernetes | Kubernetes | API Server 服务端 |
| service-account-csr.json | service-accounts | Kubernetes | SA Token 签名 |
admin证书的O=system:masters是关键设计:kube-apiserver 默认将system:masters组映射为超级管理员,测试中的 kubectl 操作因此无需额外 RBAC 配置。
一键再生成:regenerate.sh 完整流程
README 明确指出:要重新生成证书,运行./regenerate.sh,该脚本会彻底删除并重建全部密钥与证书(包括根 CA)。完整脚本内容如下(regenerate.sh):
#!/bin/bash set -xe rm -f *.pem *.key *.csr cfssl gencert -initca ca-csr.json | cfssljson -bare ca cfssl gencert \ -ca=ca.pem \ -ca-key=ca-key.pem \ -config=ca-config.json \ -profile=kubernetes \ admin-csr.json | cfssljson -bare admin KUBERNETES_HOSTNAMES=kubernetes,kubernetes.default,kubernetes.default.svc,kubernetes.default.svc.cluster,kubernetes.svc.cluster.local cfssl gencert \ -ca=ca.pem \ -ca-key=ca-key.pem \ -config=ca-config.json \ -hostname=10.96.0.1,127.0.0.1,${KUBERNETES_HOSTNAMES} \ -profile=kubernetes \ kubernetes-csr.json | cfssljson -bare kubernetes cfssl gencert \ -ca=ca.pem \ -ca-key=ca-key.pem \ -config=ca-config.json \ -profile=kubernetes \ service-account-csr.json | cfssljson -bare service-account kubectl config set-credentials system:kube-controller-manager \ --client-certificate=admin.pem \ --client-key=admin-key.pem \ --embed-certs=true \ --kubeconfig=kube-controller-manager.kubeconfig rm *.csr脚本执行顺序与关键点:
- 清场:
rm -f *.pem *.key *.csr删除当前目录全部旧制品,保证每次再生成都是全新信任链(根 CA 也会重建,因此旧证书立即全部失效); - 生成根 CA:
cfssl gencert -initca ca-csr.json | cfssljson -bare ca,产出ca.pem与ca-key.pem; - 签发 admin 证书:使用
-profile=kubernetes签名策略,产出admin.pem与admin-key.pem; - 签发 kubernetes 证书:这是唯一带
-hostname参数的一步,SAN 列表由10.96.0.1,127.0.0.1与KUBERNETES_HOSTNAMES拼接而成,10.96.0.1对应 kube-apiserver 的 ClusterIP 段,127.0.0.1对应本地回环访问; - 签发 service-account 证书:与 admin 相同,仅用 CSR 与 profile;
- 生成控制器 kubeconfig:用
kubectl config set-credentials将 admin 证书内嵌(--embed-certs=true)写入kube-controller-manager.kubeconfig,system:kube-controller-manager是 Kubernetes 内置的系统用户名; - 收尾:删除所有中间
.csr文件。
环境依赖方面,脚本依赖cfssl/cfssljson与kubectl两个命令行工具,且默认假设在hack/test/certs目录内执行(set -xe保证出错即停、输出执行过程)。执行后再生成时,只要测试基础设施按同一路径挂载新证书(见下文),FV 测试即可继续工作。
两类 kubeconfig 的差异与设计意图
目录中的两份 kubeconfig 形态完全不同,值得对比理解。
admin 版 kubeconfig(kubeconfig)
apiVersion: v1 clusters: - cluster: insecure-skip-tls-verify: true server: https://127.0.0.1:6443 name: test-apiserver contexts: - context: cluster: test-apiserver user: admin name: admin current-context: admin kind: Config users: - name: admin user: # The tests which use this kubeconfig are run in a container # and expect these files to be mounted at this location. client-certificate: /home/user/certs/admin.pem client-key: /home/user/certs/admin-key.pem要点:
server: https://127.0.0.1:6443指向测试容器内 kube-apiserver 的标准监听地址;- 证书以文件路径引用方式配置,且注释明确指出:使用该 kubeconfig 的测试运行在容器中,期望证书被挂载到
/home/user/certs这一固定位置; - 开启
insecure-skip-tls-verify: true,因为测试环境为临时集群,跳过对 API Server 证书链的校验可简化故障排查。
控制器版 kubeconfig(kube-controller-manager.kubeconfig)
与 admin 版不同,这份 kubeconfig 通过kubectl config set-credentials --embed-certs=true生成,client-certificate-data与client-key-data两个字段中直接内嵌了 Base64 编码的证书与私钥,无需外部文件;server字段为空字符串,实际访问地址由测试基础设施在启动控制器时另行指定。
两种形态对应两种使用环境:admin kubeconfig 供测试容器内手动执行的 kubectl 命令使用(文件挂载即可),控制器 kubeconfig 则因 kube-controller-manager 由测试框架以容器参数方式拉起,内嵌证书可避免额外的挂载编排。
证书在 FV 测试中的实际挂载链路
证书最终价值的体现点在 felix/fv/infrastructure/infra_k8s.go,该文件是 Felix FV 测试的 Kubernetes 基础设施封装,从源码结构可以看到完整的挂载与消费关系:
- 统一挂载点:通过
-v $CERTS_PATH:/home/user/certs(CERTS_PATH为环境变量)将证书目录整体挂载进 kube-apiserver、kube-controller-manager 与客户端容器,与 kubeconfig 中的/home/user/certs路径一一对应; - API Server 消费:
--service-account-key-file=/home/user/certs/service-account.pem、--service-account-signing-key-file=/home/user/certs/service-account-key.pem、--client-ca-file=/home/user/certs/ca.pem、--tls-cert-file=/home/user/certs/kubernetes.pem、--tls-private-key-file=/home/user/certs/kubernetes-key.pem——即用kubernetes.pem对外提供 TLS 服务、用ca.pem校验客户端证书、用service-account密钥对完成 SA Token 的签发; - kube-controller-manager 消费:
--kubeconfig=/home/user/certs/kube-controller-manager.kubeconfig与--root-ca-file=/home/user/certs/ca.pem、--service-account-private-key-file=/home/user/certs/service-account-key.pem,控制器据此访问 API Server 并签发 SA Token; - 客户端消费:测试中的 kubectl 通过
--kubeconfig=/home/user/certs/kubeconfig apply -f /crds/等命令应用 CRD 清单,其身份凭证正是admin.pem与admin-key.pem; - TLS 校验方向:
kubernetes.pem还会被复制进客户端容器(kubernetes.pem作为 CA 信任链上传),确保客户端到 API Server 的 HTTPS 连接可完成证书链验证。
由此可以完整还原测试链路:根 CA 签发三张证书 → 证书以目录挂载形式进入各测试容器 → kube-apiserver 用 kubernetes 证书对外服务、用 ca.pem 校验 admin 客户端 → admin 证书驱动 kubectl 操作 → service-account 密钥对支撑控制器签发 SA Token,四个角色各司其职、缺一不可。
再生成时的注意事项
- 运行
./regenerate.sh会连同根 CA 一起删除重建,因此这是"推倒重来"式的操作,而不是增量轮换;再生成后,所有依赖旧证书的已运行容器需重新拉起; - 脚本使用
set -xe,任何一步失败都会立即终止,可通过执行日志快速定位是 cfssl 配置问题还是工具缺失; - 再生成后需确保
$CERTS_PATH指向新证书目录,且挂载路径仍为/home/user/certs,否则 kubeconfig 中引用的绝对路径将失效; - 由于
ca-config.json中expiry长达 87600 小时(10 年),日常开发中该目录极少需要再生成,README 提供该脚本的意义更多在于保证证书来源可追溯、可重建,避免仓库内长期滞留无法再生的测试密钥。
综上,Calico 的 FV 证书目录是一个小而完整的 PKI 实践样本:它用 cfssl 完成"单 CA + 多角色证书"的标准化签发,用两种 kubeconfig 适配容器化测试的两种消费方式,并在infra_k8s.go中形成了"目录挂载 + 启动参数"的确定性交付链路。理解这套体系,不仅能看懂 Calico FV 测试的 TLS 握手过程,也能为其他需要自建测试集群 PKI 的项目提供直接可复用的参考模板。
- 网络
- 云原生
- 网络安全
【免费下载链接】calico
Cloud native networking and network security
相关推荐
EMQX 测试基础设施中的 TLS 证书体系:docker-compose 测试服务证书的生成、命名与维护
EMQX 测试基础设施中的 TLS 证书体系:docker compose 测试服务证书的生成、命名与维护 本篇技术指南聚焦 EMQX 开源仓库中为 docke
后端物联网消息队列通信Lore 服务端 mTLS 测试证书体系:test_data 目录与 QUIC 安全测试基础设施
Lore 服务端 mTLS 测试证书体系:test_data 目录与 QUIC 安全测试基础设施 本文围绕 Lore 仓库中的测试证书目录 lore serve
版本控制后端Recommenders 测试体系深度解析:从 PR Gate 到 Nightly Build 的 MLOps 测试基础设施
Recommenders 测试体系深度解析:从 PR Gate 到 Nightly Build 的 MLOps 测试基础设施 Recommenders 是微软开
人工智能机器学习深度学习
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考