본문 바로가기
Kubernetes

[Kubernetes] Nginx Controller에 Let’s Encrypt 인증서 등록(DNS01)

by worldcenter 2025. 1. 20.

 

http01에서는 와일드카드 인증서 발급이 불가하기 때문에 dns01 방식을 사용합니다. 해당 테스트는 Azure의 Kubernetes를 사용하여 진행하였습니다.

 

사전 준비

1. Nginx Controller를 설치합니다.

2. 테스트 용도의 Pod 또는 Deployment와 Cluster IP 타입의 Service를 생성합니다.

3. DNS Zone Contributor 이상의 권한을 가진 Service Principal을 Azure Kubernetes에게 할당합니다.

 

 

Helm으로 Cert-Manager 설치하기

  • Cert-Manager는 Kubernetes 클러스터 내에서 SSL/TLS 인증서를 관리하는 도구 입니다(컨드롤러).
  • 사용자와 Provider(letsencrypt) 중간에서 중계해주는 역할을 합니다.
  • Kubernetes에 배포될 때 cert-manager는 자동으로 ingress controller에 필요한 인증서를 발급하고 인증서가 유효한지 최신 상태인지 확인합니다.
  • 인증서의 만료 날짜를 추적하고 구성된 시간 간격으로 갱신을 시도합니다.
  • 자세한 내용은 Helm 공식 링크에서 확인 가능합니다.

1. Helm Repository를 추가합니다.

helm repo add jetstack https://charts.jetstack.io

 

2. 로컬 helm chart repository 캐시를 업데이트 합니다.

helm repo update

 

3. CustomResourceDefinitions를 설치합니다.

kubectl apply -f https://github.com/cert-manager/cert-manager/releases/download/v1.12.0/cert-manager.crds.yaml

 

4. cert-manager를 설치합니다.

helm install \
  cert-manager jetstack/cert-manager \
  --namespace cert-manager \
  --create-namespace \
  --version v1.12.0 \
  # --set installCRDs=true

 

 

ClusterIssuer 생성

  • DNS01 인증 방식으로 ClusterIssuer를 생성할 경우 도메인을 보유하고 있는 DNS에 따라 달라집니다.
  • 본문에서는 Azure DNS 사용을 기준으로 설명합니다.
  • 참고로 Azure DNS로 cert-manager가 접근하기 위해서는 적합한 권한을 부여해 줘야 합니다.
  • Azure의 경우 크게 Managed identity 또는 Service Principal로 나뉘며 Managed identity 인증 방식은 cert-manager ≥ v1.11.0 에서만 사용 가능합니다.
  • 본문에서는 Service Principal 방식을 사용합니다.

1. Service Principal Secret값을 가진 Kubernetes Secret 생성합니다.

// Client Secret 값 저장용 Secret 생성
kubectl create secret generic azuredns-config --from-literal=client-secret=password-aaaa-bbbb-cccc-dddddddddddd -n cert-manager

 

2. ClusterIssuer를 생성합니다.

apiVersion: cert-manager.io/v1
kind: ClusterIssuer
metadata:
  name: letsencrypt-issuer
spec:
  acme:
    # You must replace this email address with your own.
    # Let's Encrypt will use this to contact you about expiring
    # certificates, and issues related to your account.
    email: <E-mail 주소>
    server: https://acme-v02.api.letsencrypt.org/directory
    privateKeySecretRef:
      # Secret resource that will be used to store the account's private key.
      name: letsencrypt-issuer-account-key
    # Add a single challenge solver, HTTP01 using nginx
    solvers:
    - dns01:
        azureDNS:
          clientID: <appId>
          clientSecretSecretRef: 
            name: azuredns-config
            key: client-secret
          subscriptionID: <subscriptionId>
          tenantID: <tenantId>
          resourceGroupName: <resourcegroupName>
          hostedZoneName: <DNS Zone Name>
          environment: AzurePublicCloud

 

3. Ingress를 배포합니다.

apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  annotations:
    cert-manager.io/cluster-issuer: letsencrypt-issuer
  name: nuri-ingress
  namespace: nuri
spec:
  ingressClassName: nginx
  rules:
  - host: "*.balance.gaonnuri.site"
    http:
      paths:
      - backend:
          service:
            name: nuri-service
            port:
              number: 80
        path: /
        pathType: Prefix
  tls:
  - hosts:
    - "*.balance.gaonnuri.site"
    secretName: letsencrypt-issuer-account-key

 

 

 

참고 자료

https://cert-manager.io/docs/tutorials/getting-started-aks-letsencrypt/#install-the-azure-workload-identity-features

 

Deploy cert-manager on Azure Kubernetes Service (AKS) and use Let's Encrypt to sign a certificate for an HTTPS website

Learn how to deploy cert-manager on Azure Kubernetes Service (AKS) and configure it to get a signed certificate from Let's Encrypt for an HTTPS web server, using the DNS-01 protocol and Azure DNS with workload identity federation.

cert-manager.io

https://cert-manager.io/docs/configuration/acme/dns01/azuredns/

 

AzureDNS

cert-manager configuration: ACME DNS-01 challenges using AzureDNS

cert-manager.io