๊ธฐ๋ณธ ์ง์
8482 ๋จ์ด certificatetech
cert-manager๋?
kubernetes ํด๋ฌ์คํฐ์์ SSL/TLS ์ธ์ฆ์๋ฅผ ๊ฐ๋จํ๊ฒ ์ฒ๋ฆฌํ๋ ๋๊ตฌ์ ๋๋ค.
์ธ์ฆ์์ ์ทจ๋, ๊ฐฑ์ , ์ฌ์ฉ์ด ๊ฐ๋จํด์ก๋ค.
๊ณต์ ๋ฌธ์
์ด ๊ธ์ ๋ด์ฉ
์ด ๊ธ์์๋ cert-Manager๋ฅผ ์ฌ์ฉํ๋ฉด์ ์ต์ํ ํต์ ํด์ผ ํ '์ฆ๋ช ์ ๋ฐํยทํ์ฉ ํ๋ก์ธ์ค'์'๋ฑ์ฅ์ธ๋ฌผ'๋ง ๊ฐ๋จํ ์ ๋ฆฌํ๋ค.
์ฆ๋ช ์ ์ฃผ๋ณ์์๋ ์ฌ๊ณ ๊ฐ ๋๋ฉด ๊ท์ฐฎ์์ ๋ง์ง๊ณ ์ถ์ง ์์ ์๋ ์์ง๋ง ๊ธฐ์ด ์ง์์ ๋จผ์ ์๊ณ ์ถ์ ๊ฒ์ด ์ต์ด์ ๋ฐํ์ด๋ค.
cert-manager v1.์ด์ด์ 6.1์ ์ด์ผ๊ธฐ๋ฅผ ํ๊ฒ ์ต๋๋ค.
๋ํ Let's Encerypt๋ฅผ Issuer์ ํ๋ก์ธ์ค๋ก ์ค๋ช ํ๊ธฐ ๋๋ฌธ์ ๋ค๋ฅธ Issuer Type์๋ ๋ค๋ฅธ ๋ด์ฉ์ด ์์ต๋๋ค.
์ธ์ฆ์ ๋ฐํ ๋ฐ ์ฌ์ฉ์ ๊ฐ๋จํ ์ ์ฐจ
์ฐ์ ๋๋ต์ ์ธ ์ ์ฐจ๋ฅผ ํ๋ ์จ๋ผ.
์ค์ ์ค์น ๋ฐฉ๋ฒ๊ณผ ์กฐ์ ๋ฑ ์์ธํ ๋ด์ฉ์ ๊ณต์ ๋ฌธ์์ ๋๊ธธ ๊ฒ์ด๋ค.
Issuer
์ด์
๋ธ๋ฆฌ๋ฅผ ์์ฑํฉ๋๋ค.Certificate
์ด์
๋ธ๋ฆฌ๋ฅผ ์์ฑํฉ๋๋ค.Issuer
, Certificate
๊ตฌ์ฑ ์์์ ์ค์ ์ ๋ฐ๋ผ ์ง์ ํ ์ธ์ฆ์ ๋ฐํ์ธ์๊ฒ ์ง์ ํ ์์ญ์ ์ธ์ฆ์๋ฅผ ์์ฒญํฉ๋๋ค.ใใฃใฌใณใธ
.ใใฃใฌใณใธ
๊ฐ ์๋ฃ๋๋ฉด ๋ฐํ๋ ์ธ์ฆ์์ ํค๋ Secret ์์์ ์ ์ฅ๋ฉ๋๋ค.์ธ์ฆ์์ ํค๊ฐ ์ ์ฅ๋ ์ํฌ๋ฆฟ์ ์ฐธ์กฐ
Ingress
๋ฑ์ ํตํด ์ธ์ฆ์๋ก ์ํธ ํต์ ์ ํ ์ ์์ต๋๋ค.๋ฑ์ฅ์ธ๋ฌผ
cert-Manager๋ ์ธ์ฆ์๋ฅผ ์ทจ๋ํ๊ณ ์ด์ฉํ ๋ ๊ด๋ จ ๋ฑ์ฅ์ธ๋ฌผ์ ์๊ฐํ๋ค.
Issuer
Issuer
๊ตฌ์ฑ ์์๋ Custom Resource Definition(CRD)์ ์ํด ์ ์๋ ์์์
๋๋ค.Issuer
๊ตฌ์ฑ ์์๋ ๊ฐ์namespace์์๋ง ๋ฐํํ ์ ์์ต๋๋คCertificate
.ClusterIssuer
๊ตฌ์ฑ ์์๋ฅผ ์ฌ์ฉํฉ๋๋ค.Certificate
์ฌ๊ธฐ ๊ธฐ์ฌ.์ ํต์์ ์ด๊ณ ์๊ธฐ ์ฝ๊ฒ ์ผ๋ค.
ACME Orders and Challenges
ใใฃใฌใณใธ
๋ผ๊ณ ๋ถ๋ฆฌ๋ ๋ฉ์ปค๋์ฆ์ด๋ค.ใใฃใฌใณใธ
์ ์์ฑํ๊ธฐ ์ํดcert-Manager๋ ๋ค์ ๋ ๊ฐ์ CRD๋ฅผ ๊ฐ์ ธ์ต๋๋ค.Order
Challenge
Order
ใใฃใฌใณใธ
๋ ์คํ ์์ฒญ์ ๋ํ๋ธ๋ค.ใใฃใฌใณใธ
์ ์์ธํ ๋ด์ฉ์ ์ฌ๊ธฐ.์ด๋ค.Challenge
ํ์
ใใฃใฌใณใธ
.Order
ํ๋์ ๋ํด ์ฌ๋ฌ ๋๋ฉ์ธChallenge
์ ์์ฑํฉ๋๋ค.Challenge
๋๊ธฐ์ด์์ ์์๋๋ก ์ฒ๋ฆฌํฉ๋๋ค.ใใฃใฌใณใธ
์์ฑ ํChallenge
์์์ด Kubernetes ๊ทธ๋ฃน์์ ์ฌ๋ผ์ง๋๋ค.Ingress
Ingress
์์ ์ฐธ๊ณ ํ๊ณ ์ฌ์ฉํฉ๋๋ค.Ingress
cert-Manager๊ฐ CRD๋ก ์ ์ํ๋ ๋ฆฌ์์ค๊ฐ ์๋๋๋ค.๋ฑ์ฅ์ธ๋ฌผ๋ณ manfest ํ์ผ ์ํ
์์์ ๋งํ ๋ฐ์ ๊ฐ์ด ๋ค์ ์ธ ๊ฐ์ง ์์์ ์ฌ์ฉ์๊ฐ manfest ํ์ผ์ ์ ์ํ๊ณ ๊ด๋ฆฌํด์ผ ํ๋ค.
Issuer
Certificate
Ingress
๋ฌธ์ ๊ฒฌ๋ณธ
apiVersion: cert-manager.io/v1
kind: Issuer
metadata:
name: YOUR_ISSUER_NAME
spec:
acme:
email: "hoge@example.com"
server: https://acme-staging-v02.api.letsencrypt.org/directory
privateKeySecretRef:
name: lets-encrypt
solvers:
- dns01:
cloudDNS:
project: example-com
serviceAccountSecretRef:
name: prod-clouddns-svc-acct-secret
key: service-account.json
Issuer
์ manfest ์ค ๊ฐ์ฅ ์ค์ํ ๊ฒ์ metadata.name
์specไปฅไธ
์ด๋ค.metadata.name
๊ฐ ๋ฐ๋ก ์ด ์์์ ๋ช
์นญ์ด๋ค.์ค์ํ ๊ฒ์ ๋ค๋ฅธ ์์์์ ์ด ์์์ ์ธ์ฉํ๋ ๊ฒ์ด๋ค.specไปฅไธ
ํ์
์ ๋ฐ๋ผ ๋ค๋ฆ
๋๋ค.์ด๋ฒ์๋ Let's Encerypt๋ฅผ ์ฌ์ฉํ๋ ์ ์ ์กฐ๊ฑด์ด๊ธฐ ๋๋ฌธ์Issuer
.์ด manfest๋ Staging ํ๊ฒฝ์ Let's Encerypt ์๋ฒ์ ๋ํ ์คํ
spec.acme
์
๋๋ค. GCP์ ํด๋ผ์ฐ๋ DNS๋ฅผ ์ฌ์ฉํ์ธ์. DNS01ใใฃใฌใณใธ
๋ผ๋ GCP ํ๋ก์ ํธ์ ํด๋ผ์ฐ๋ DNS๋ฅผ ์ฌ์ฉํ๊ธฐ ์ํดexample-com
์ด ์ํฌ๋ฆฟ ์์์ ์๋น์ค ๊ณ์ ์ ์ ์ฉ๋๋ฅผ ๋์์ต๋๋ค.๋ค๋ฅธ IssuerType ๋๋ ACME๋ฅผ ์ฌ์ฉํ์ฌ ๋ค๋ฅธ ์ค์ ์ ์ ํํ ๋๋ ๊ณต์ ๋ฌธ์๋ฅผ ์ฐธ์กฐํ์ญ์์ค.
๋ฌธ์ ๊ฒฌ๋ณธ
apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
name: YOUR_CERTIFICATE_NAME
spec:
secretName: YOUR_SECRET_NAME
dnsNames:
- example.com
issuerRef:
name: YOUR_ISSUER_NAME
kind: Issuer
prod-clouddns-svc-acct-secret
๊ตฌ์ฑ ์์์ manfest ํ์ผ์ Certificate
,secretName
,dnsNames
์ ํ๋๊ฐ ์กด์ฌํฉ๋๋ค.issuerRef
์์ ์ง์ ํ dnsNames
์์ ์ง์ ํ issuerRef
์์ Issuer
์์ ์ง์ ํ ์์ญ์ ์ธ์ฆ์๋ฅผ ๋ฐ์ต๋๋ค.secretName
Kubernetes์ Secret ์์ ์ด๋ฆ์ ์ง์ ํฉ๋๋ค.์ด Secret์ ์ค์ ํค์ ์ธ์ฆ์๋ฅผ ์ ์ฅํฉ๋๋ค.manfest ํ์ผ์ ์ค์ ํ๋ฉด
example.com
์ธ์ฆ์๋ YOUR_ISSUER_NAME
๋ผ๋ Issueer
์์ ๊ฐ์ ธ์ค๊ณ ์ธ์ฆ์์ ํค๋ YOUR_SECRET_NAME
๋ผ๋ Secret ์์์ ์ ์ฅ๋ฉ๋๋ค.์ค์ ์ํฌ๋ฆฟ์ ์ ์ฅ๋ ์๋ ๋ค์๊ณผ ๊ฐ์ต๋๋ค.
$ kubectl get secret ${YOUR_SECRET_NAME}
apiVersion: v1
kind: Secret
data:
tls.crt: LS0tLaa.....
tls.key: LS0tLOU....
creationTimestamp: "2022-00-00T00:00:00Z"
labels:
certmanager.k8s.io/certificate-name: YOUR_SECRET_NAME
name: YOUR_SECRET_NAME
namespace: YOUR_NAMESPACE_NAME
...
...
์ธ์ฆ์data.tls.crt
๋ ์ธ์ฆ์ ๊ฐ์ ํฌํจํ๊ณ data.tls.key
๋ ํค ๊ฐ์ ํฌํจํ๋ค.์ด ๊ฐ์ ์ฌ์ฉํ์ฌ ์ํธ ํต์ ์ ์คํํฉ๋๋ค.
์ฐธ๊ณ ๋ก ์ค์ ์ธ์ฆ์์ ๊ฐ์ Secret์๋ง ์กด์ฌํฉ๋๋ค.
ํท๊ฐ๋ฆฌ๊ธฐ ์ฝ์ต๋๋ค.
Certificate
์์์ ์ธ์ฆ์ ๊ฐ์ด ์กด์ฌํ์ง ์์ต๋๋ค.๋์ ์ธ์ฆ์ ์คํจ, ์์ ์ผ ๊ฐฑ์ ๋ฑ์ ์ ๋ณด๋ฅผ ํฌํจํ๋ค.
$ kubectl get Certificate ${YOUR_CERTIFICATE_NAME}
apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
creationTimestamp: "2022-01-13T12:19:50Z"
generation: 1
name: YOUR_CERTIFICATE_NAME
namespace: YOUR_NAMESPACE_NAME
spec:
commonName: example.com
dnsNames:
- example.com
issuerRef:
kind: Issuer
name: YOUR_ISSUER_NAME
secretName: YOUR_SECRET_NAME
status:
conditions:
- lastTransitionTime: "2022-01-13T12:19:50Z" # 2022/1/13ใซไฝๆ
message: Certificate is up to date and has not expired
observedGeneration: 1
reason: Ready
status: "True"
type: Ready
notAfter: "2022-04-13T11:21:25Z" # 90ๆฅๅพใฎ2022/4/13ใซๅคฑๅน
notBefore: "2022-01-13T11:21:26Z"
renewalTime: "2022-03-14T11:21:25Z" # 60ๆฅๅพใฎ2022/3/14ใซๆดๆฐไบๅฎ
revision: 1
๋ฌธ์ ๊ฒฌ๋ณธ
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
annotations:
cert-manager.io/issuer: YOUR_ISSUER_NAME
name: YOUR_INGRESS_NAME
namespace: YOUR_INGRESS_NAME
spec:
rules:
- host: example.com
http:
paths:
- pathType: Prefix
path: /
backend:
service:
name: YOUR_SERVICE_NAME
port:
number: 80
tls:
- hosts:
- example.com
secretName: YOUR_SECRET_NAME
tls.hosts[0].secretName
์ ์ธ์ฆ์์ ํค๋ฅผ ๊ฐ์ง ์ํฌ๋ฆฟ์ ์ด๋ฆ์ ์
๋ ฅํจ์ผ๋ก์จ Ingress๋ ์ธ์ฆ์๋ฅผ ์ฐธ์กฐํ์ฌ ์ํธ ํต์ ์ ์คํํ๋ค.์ฆ
Certificate
์manfest ๋ดspec.secretName
๊ฐ๊ณผ ๊ฐ์ผ๋ฉด OK๋ผ๋ ๊ฒ์ด๋ค.์ด๊ฒฐ์ฐ
๊ฐ๋จํ๊ฒ ๋งํ๋ฉด manfest ํ์ผ์ ์ํ์ ํฌํจํ์ฌcert-๊ด๋ฆฌ์๊ฐ ์ธ์ฆ์๋ฅผ ์ทจ๋ํ๊ณ ์ฌ์ฉํ๋ ์ ์ฐจ๋ฅผ ์๊ฐํ๋ค.
cert-Manager์ ๊ณต์ ๋ฌธ์๊ฐ ๋น๊ต์ ์ถฉ์คํด์ ๋๋ ๋ฐฐ์ธ ๋งํ๋ค๊ณ ์๊ฐํ๋ค.
๊ด์ฌ ์๋ ์ฌ๋์ด ์์ธํ ์ฝ์ด๋ณด๋ฉด ์ฌ๋ฏธ์์ ๊ฑฐ์์.
Reference
์ด ๋ฌธ์ ์ ๊ดํ์ฌ(๊ธฐ๋ณธ ์ง์), ์ฐ๋ฆฌ๋ ์ด๊ณณ์์ ๋ ๋ง์ ์๋ฃ๋ฅผ ๋ฐ๊ฒฌํ๊ณ ๋งํฌ๋ฅผ ํด๋ฆญํ์ฌ ๋ณด์๋ค https://zenn.dev/masaaania/articles/e54119948bbaa2ํ ์คํธ๋ฅผ ์์ ๋กญ๊ฒ ๊ณต์ ํ๊ฑฐ๋ ๋ณต์ฌํ ์ ์์ต๋๋ค.ํ์ง๋ง ์ด ๋ฌธ์์ URL์ ์ฐธ์กฐ URL๋ก ๋จ๊ฒจ ๋์ญ์์ค.
์ฐ์ํ ๊ฐ๋ฐ์ ์ฝํ
์ธ ๋ฐ๊ฒฌ์ ์ ๋
(Collection and Share based on the CC Protocol.)
์ข์ ์นํ์ด์ง ์ฆ๊ฒจ์ฐพ๊ธฐ
๊ฐ๋ฐ์ ์ฐ์ ์ฌ์ดํธ ์์ง
๊ฐ๋ฐ์๊ฐ ์์์ผ ํ ํ์ ์ฌ์ดํธ 100์ ์ถ์ฒ ์ฐ๋ฆฌ๋ ๋น์ ์ ์ํด 100๊ฐ์ ์์ฃผ ์ฌ์ฉํ๋ ๊ฐ๋ฐ์ ํ์ต ์ฌ์ดํธ๋ฅผ ์ ๋ฆฌํ์ต๋๋ค