Содержание

TLS сертификаты для сайтов (cert-manager)

Cert-manager — это дополнение Kubernetes для автоматизации управления и выдачи сертификатов TLS из различных источников.

Устанавливаем

Устанавливаем из манифеста:

kubectl apply -f https://github.com/cert-manager/cert-manager/releases/download/<version>/cert-manager.yaml

Актуальную версию релиза можно посмотреть тут: https://github.com/cert-manager/cert-manager

Проверяем

Например, создадим самоподписанный сертификат. Создадим файл self-s.yaml

---
apiVersion: v1
kind: Namespace
metadata:
  name: cert-manager-test

---
apiVersion: cert-manager.io/v1
kind: Issuer
metadata:
  name: test-selfsigned
  namespace: cert-manager-test
spec:
  selfSigned: {}

---
apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
  name: selfsigned-cert
  namespace: cert-manager-test
spec:
  dnsNames:
    - myexample.com
  secretName: selfsigned-cert-tls
  issuerRef:
    name: test-selfsigned 

Применим файл:

kubectl apply -f self-s.yaml

Смотрим на результат:

kubectl -n cert-manager-test describe certificate
TypeReasonAgeFromMessage
Normal Issuing 14s cert-manager-certificates-issuing The certificate has been successfully issued

Смотрим на ключ и сертификат:

kubectl -n cert-manager-test get secret
NAMETYPEDATAAGE
selfsigned-cert-tls kubernetes.io/tls 3 47s

Сертификаты Let's Encrypt

Создаем тестового выпускающего (ClusterIssuer) обслуживающего весь кластер:

---
apiVersion: cert-manager.io/v1
kind: ClusterIssuer
metadata:
  name: letsencrypt-staging
spec:
  acme:
    # Test only
    server: https://acme-staging-v02.api.letsencrypt.org/directory 
    # Email address used for ACME registration
    email: [email protected]                           <- надо указать свой
    # Name of a secret used to store the ACME account private key
    privateKeySecretRef:
      name: cert-manager-staging-letsencrypt-private-key
    # Enable the HTTP-01 challenge provider
    solvers:
      # An empty 'selector' means that this solver matches all domains
    - selector: {}
      http01:
        ingress:
          class: nginx
          serviceType: ClusterIP

Создаем prod выпускающего (ClusterIssuer) обслуживающего весь кластер:

---
apiVersion: cert-manager.io/v1
kind: ClusterIssuer
metadata:
  name: letsencrypt-prod
spec:
  acme:
    # The ACME server URL
    server: https://acme-v02.api.letsencrypt.org/directory
    # Email address used for ACME registration
    email: [email protected]                           <- надо указать свой
    # Name of a secret used to store the ACME account private key
    privateKeySecretRef:
      name: cert-manager-prod-letsencrypt-private-key
    # Enable the HTTP-01 challenge provider
    solvers:
      # An empty 'selector' means that this solver matches all domains
    - selector: {}
      http01:
        ingress:
          class: nginx
          serviceType: ClusterIP

Проверяем выпуск сертификатов Let's Encrypt

Выпустим сертификат:

---
apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
  name: letsencrypt-cert-gen
  namespace: mynamespace
  labels:
    app: example
spec:
  secretName: cert-tls
  privateKey:
    rotationPolicy: Always
  issuerRef:
    name: letsencrypt-staging  <- Это тестовый. Для основного поменять staging на prod.
    kind: ClusterIssuer
  commonName: mysite.example.ru
  dnsNames:
    - mysite.example.ru

При этом, dns должен быть настроен, и mysite.examle.ru указывать в нужное место.

При через некоторое время, при успешном завершении процесса, в mynamespace появится secret с названием cert-tls который и будет содержать созданный сертификат.

И еще, если во всех вышеприведенных конфигурациях ClusterIssuer поменять на Issuer (и указать namespace), то в каждом namespace можно указать отдельных Issuer с разными настройками.

Приделаем сертификат к сайту.

Создадим тестовый сайт с использованием созданного сертификата:

 
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: test-deploy
  namespace: mynamespace
spec:
  replicas: 2
  selector:
    matchLabels:
      app: nginx-test
  template:
    metadata:
      name: nginx-test-temp
      labels:
        app: nginx-test
    spec:
      containers:
      - name: nginx-container
        image: nginxdemos/nginx-hello:plain-text
        ports:
        - name: http
          containerPort: 8080
          protocol: TCP

---
apiVersion: v1
kind: Service
metadata:
  name: ng-svc
  namespace: mynamespace
spec:
  type: ClusterIP
  ports:
  - name: name-np
    port: 80
    targetPort: 8080
  selector:
    app: nginx-test

---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: my-ingress
  namespace: mynamespace
spec:
  ingressClassName: nginx
  tls:
  - hosts:
    - mysite.example.ru
    secretName: cert-tls
  rules:
  - host: mysite.example.ru
    http:
      paths:
      - backend:
          service:
            name: ng-svc
            port:
              number: 80
        path: /
        pathType: Prefix

Недописано.
Приходите позже.