侧边栏壁纸
博主头像
小续的成长时光 博主等级

行动起来,活在当下

  • 累计撰写 21 篇文章
  • 累计创建 14 个标签
  • 累计收到 3 条评论

目 录CONTENT

文章目录

Cert-Manager入门

小续
2025-02-06 / 0 评论 / 0 点赞 / 82 阅读 / 0 字 / 正在检测是否收录...

Cert-Manager入门

GitHub 地址:Cert-Manager | GitHub

官方文档:Cert-Manager | Documentation

一、概述

Cert-Manager 是一款开源的云原生证书管理工具,适用于 Kubernetes 和 OpenShift 的 X.509 证书管理。

Cert-Manager 通过Kubernetes 的自定义资源定义(CRD)机制,将 TLS 证书看作是一种资源,可以使用 Kubernetes API 进行管理。

Cert-Manager 架构包括:

  • 控制层: 负责管理证书,包括证书的创建、更新、删除等。
  • 数据层: 负责存储证书的相关数据,包括证书私钥、证书请求、证书颁发机构等。

Cert-Manager 可以从各种证书颁发机构获取证书,包括自签名证书等;

使用 Cert-Manager 的证书资源,私钥和证书均保存在 Kubernetes Secret 中,然后由对应的 Pod 挂载或 Ingress 资源使用。

Cert-Manager 核心功能包括:

  • 自动管理证书: Cert-Manager 可以自动化管理证书,无需人工干预,自动签发证书以及证书过期前续期,避免了证书管理的复杂性和错误。
  • 支持多种供应商: Cert-Manager 支持从多个证书颁发机构申请证书,包括但不限于 Let's Encrypt、HashiCorp Vault、Venafi 等。
  • 支持多种验证方法: Cert-Manager 支持多种域验证方式,包括 HTTP-01、DNS-01、TLS-SNI 等。
  • 支持Webhook: Cert-Manager 允许通过webhook 扩展来支持额外的验证方法和颁发者类型。

High level overview diagram explaining cert-manager architecture

二、安装部署

1、使用配置文件部署

# 使用官方配置文件进行部署
kubectl apply -f https://github.com/cert-manager/cert-manager/releases/download/v1.17.0/cert-manager.yaml

# 部署完成后查看,可以再名称空间 cert-manager 中看到如下pods
[root@pve ~]# kubectl -n cert-manager get pods 
NAME                                       READY   STATUS    RESTARTS   AGE
cert-manager-6bf4d69c6-gtmrt               1/1     Running   0          5d12h
cert-manager-cainjector-6f96cbbcc7-8tc2w   1/1     Running   0          5d12h
cert-manager-webhook-5f6d4756f4-k22tj      1/1     Running   0          5d12h

三、基础资源

1、Issuer和ClusterIssuer

Issuer 是名称空间级别的资源,只能在指定的某个名称空间使用。

ClusterIssuer 是集群级别的资源,可以在集群的任意名称空间中使用。

2、Certificate

在 Cert-Manager 中,Certificate 资源表示证书请求的人类可读定义。Cert-Manager 使用此输入生产私钥和 CertificateRequest 资源,以便从 IssuerClusterIssuer处获取签名证书 。并将签名的证书和私钥保存在 Certificate 指定的 Secret 中。Cert-Manager 将会保证在证书过期前续订以及在需要时重新签发证书。

2.1、Certificate Yaml文件详解

apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
  name: example-com
  namespace: sandbox
spec:
  # Secret names are always required.
  secretName: example-com-tls

  # secret模板是可选的。如果设置了,这些注释和标签将被复制到名为 example-com-tls 的 Secret 中。如果证书的 secret 模板更改,这些标签和注释将重新协调。secret 模板也是强制执行的,因此 Cert-Manager 将重写第三方对 Secret 的相关标签和注释更改,以匹配secret模板。
  secretTemplate:
    annotations:
      my-secret-annotation-1: "foo"
      my-secret-annotation-2: "bar"
    labels:
      my-secret-label: foo

  privateKey:
    algorithm: RSA
    encoding: PKCS1
    size: 2048

  # keystores 允许添加额外的输出格式。此示例仅供参考。
  keystores:
    pkcs12:
      create: true
      passwordSecretRef:
        name: example-com-tls-keystore
        key: password
      profile: Modern2023
  
  # 这里的时间只能使用 s 、 m 和 h 后缀来指定这些值。不能用 d
  duration: 2160h # 90d
  renewBefore: 360h # 15d

  isCA: false
  usages:
    - server auth
    - client auth

  subject:
    organizations:
      - cert-manager

  # 避免在end-entity (leaf) 证书中使用 commonName 作为DNS名称。除非您的环境中有特定需求,否则请专门使用 dnsName 来避免commonName 出现问题。通常,commonName 用于为 CA 证书赋予人类可读的名称,并且可以避免用于其他证书。
  commonName: example.com

  # literalSubmit 字段与 subject  和 commonName 独占。它允许将主题直接指定为字符串。当主题字段的顺序很重要或主题包含可以由其收件箱指定的特殊类型时,这很有用。
  # literalSubject: "O=jetstack, CN=example.com, 2.5.4.42=John, 2.5.4.4=Doe"

  # commonName,DNSNAME,URIS,EmailAddresses,iPaddresses 或 otherNames 中需要至少有一个。
  dnsNames:
    - example.com
    - www.example.com
  uris:
    - spiffe://cluster.local/ns/sandbox/sa/example
  emailAddresses:
    - john.doe@cert-manager.io
  ipAddresses:
    - 192.168.0.5
  # Needs cert-manager 1.14+ and "OtherNames" feature flag
  otherNames:
    # Should only supply oid of ut8 valued types
    - oid: 1.3.6.1.4.1.311.20.2.3 # User Principal Name "OID"
      utf8Value: upn@example.local

  # Issuer references are always required.
  issuerRef:
    name: ca-issuer
    # We can reference ClusterIssuers by changing the kind here.
    # The default value is Issuer (i.e. a locally namespaced Issuer)
    kind: Issuer
    # 这是可选的,因为cert-manager将默认为此值,但如果您使用外部发行者,请将其更改为该发行者组。
    group: cert-manager.io

additionalOutputFormats是证书 spec上的一个字段,允许 指定已颁发证书的附加补充格式及其 私钥。目前有两种支持的附加输出格式: CombinedPEMDER 。可以在同一个证书上指定两种输出格式。

apiVersion: cert-manager.io/v1
kind: Certificate
spec:
  ...
  secretName: my-cert-tls
  additionalOutputFormats:
  - type: CombinedPEM
  - type: DER

# Results in:

apiVersion: v1
kind: Secret
metadata:
  name: my-cert-tls
type: kubernetes.io/tls
data:
  ca.crt: <PEM CA certificate>
  tls.key: <PEM private key>
  tls.crt: <PEM signed certificate chain>
  tls-combined.pem: <PEM private key + "\n" + PEM signed certificate chain>
  key.der: <DER binary format of private key>

默认情况下,私钥不会自动轮换。使用设置 rotationPolicy: Always ,与证书关联的私钥 Secret 可以将对象配置为在重新颁发证书后立即轮换(请参阅 发行触发器)。

在以下示例中,证书已设置为 rotationPolicy: Always

apiVersion: cert-manager.io/v1
kind: Certificate
spec:
  secretName: my-cert-tls
  privateKey:
    rotationPolicy: Always # 🔰 Here.

默认情况下,当删除相应的 Certificate资源时,cert-manager 不会删除包含签名证书的 Secret资源。这意味着删除 Certificate不会删除当前依赖该证书的任何服务,但该证书将不再续订。如果不再需要 Secret ,需要手动删除。

如果希望在删除 Certificate时自动删除 Secret ,则需要配置您的安装以通过 --enable-certificate-owner-ref 标志到控制器。

2.2、Certificate 工作流程

Certificate resource - cert-manager Documentation

  • 创建临时 secret,存储私钥
  • 创建 CertificateRequest,使用刚刚生成的私钥和指定的 Issuer 签发证书
  • Certificate 整合 CertificateRequest 以及临时 secret 中的私钥生成最终 secret 存放证书

四、简单使用

1、创建自签名证书

1.1、直接创建自签名证书

  • 创建集群级别的 ClusterIssuer:
---
apiVersion: cert-manager.io/v1
kind: ClusterIssuer
metadata:
  name: selfsigned-cluster-issuer
spec:
  selfSigned: {}
  • 使用Issuer颁发自签名证书:
---
apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
  name: syncthing-ca
  namespace: default
spec:
  commonName: syncthing.ctnrs.com
  dnsNames:
    - syncthing.ctnrs.com
  duration: 2160h # 定义证书有效期:90 days
  renewBefore: 240h # 定义到期前多久刷新证书:10 days
  secretName: syncthing-certs
  subject:
    countries:
      - CN
    localities:
      - XiAn
    organizationalUnits:
      - Home-XiAn-CA
    organizations:
      - ctnrs.com
    postalCodes:
      - "310000"
    provinces:
      - ShanXi
    streetAddresses:
      - xian
    serialNumber: SELF20230919
  isCA: false
  # 指定对应的 ClusterIssuer
  issuerRef:
    name: selfsigned-cluster-issuer
    kind: ClusterIssuer
    group: cert-manager.io

1.2、使用自签名证书创建Issuer

  • 使用自签名证书创建 ClusterIssuer 作为证书颁发机构
---
apiVersion: cert-manager.io/v1
kind: ClusterIssuer
metadata:
  name: selfsigned-cluster-issuer
spec:
  selfSigned: {}
---
apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
  name: selfsigned-ca
  namespace: cert-manager
spec:
  commonName: ca.ctnrs.com
  duration: 2160h # 90 days
  renewBefore: 240h # 10 days
  secretName: selfsigned-ca-certs
  subject:
    countries:
      - CN
    localities:
      - XiAn
    organizationalUnits:
      - Home-XiAn-CA
    organizations:
      - ctnrs.com
    postalCodes:
      - "310000"
    provinces:
      - ShanXi
    streetAddresses:
      - xian
    serialNumber: SELF20230919
  isCA: true
  privateKey:
    algorithm: ECDSA
    size: 256
  issuerRef:
    name: selfsigned-cluster-issuer
    kind: ClusterIssuer
    group: cert-manager.io
---
apiVersion: cert-manager.io/v1
kind: ClusterIssuer
metadata:
  name: cluster-ca-issuer
spec:
  ca:
    secretName: selfsigned-ca-certs
  • 通过 Certificate 使用 ClusterIssuer 签发证书
---
apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
  name: syncthing-ca
  namespace: default
spec:
  commonName: syncthing.ctnrs.com
  dnsNames:
    - syncthing.ctnrs.com
  duration: 2160h # 定义证书有效期:90 days
  renewBefore: 240h # 定义到期前多久刷新证书:10 days
  secretName: syncthing-certs
  subject:
    countries:
      - CN
    localities:
      - XiAn
    organizationalUnits:
      - Home-XiAn-CA
    organizations:
      - ctnrs.com
    postalCodes:
      - "310000"
    provinces:
      - ShanXi
    streetAddresses:
      - xian
    serialNumber: SELF20230919
  isCA: false
  # 指定对应的 ClusterIssuer
  issuerRef:
    name: cluster-ca-issuer
    kind: ClusterIssuer
    group: cert-manager.io
0

评论区