본문 바로가기
MLOps/Doker & Kubernetes

Udemy CKA 강의 정리 145: TLS in Kubernetes - Certificate Creation

by 공부하는 무니 2023. 1. 17.
반응형

해당 내용은 Udemy의 Certified Kubernetes Administrator (CKA) with Practice Tests 강의를 공부한 내용입니다. 내용을 그대로 번역하기보다는, 제가 이해하기 쉬운 대로 수정한 부분들이 있습니다.

⚠️ 영어 독해가 많이 부족합니다. 틀린 내용이 있으면 알려주시면 감사하겠습니다.


이번 강의에서는 클러스터에 대한 인증서를 생성하는 방법에 대해 알아보겠습니다.

Generate Certificates

인증서를 생성하기 위해서는, Easy-RSA, OpenSSL 또는 CFSSL 등과 같은 다양한 tool을 사용할 수 있습니다. 이 강의에서는 OpenSSL tool을 사용하여 인증서를 생성하겠습니다. 

Certificate Authority (CA)

CA 인증서부터 시작하겠습니다. 먼저 OpenSSL 커맨드인 openssl genrsa -out ca.key를 사용하여 private key를 만듭니다.

$ openssl genrsa -out ca.key 2048

그런 다음 방금 만든 키와 함께 OpenSSL 요청 커맨드를 사용하여 인증서 서명 요청(CSR)을 생성합니다.

$ openssl req -new -key ca.key -subj "/CN=KUBERNETES-CA" -out ca.csr

인증서 서명 요청은 모든 세부 정보가 포함된 인증서와 같지만 서명은 없습니다. 인증서 서명 요청에서 Common Name 또는 CN 필드에 인증서의 컴포넌트 이름을 지정합니다. 이번에는 Kubernetes CA에 대한 인증서를 생성하므로 이름을 Kubernetes-CA로 지정합니다. 마지막으로 openssl x509 커맨드를 사용하고 이전 커맨드에서 생성한 인증서 서명 요청을 지정하여 인증서에 서명합니다.

$ openssl x509 -req -in ca.csr -signkey ca.key -out ca.crt

이것은 CA 자체를 위한 것이므로 CA가 첫 번째 단계에서 생성한 자체 private key를 사용하여 자체 서명됩니다. 앞으로 다른 모든 인증서에 대해 CA 키 쌍을 사용하여 서명합니다. 이제 CA에는 private key와 route certificate file이 있습니다. 

Generating Client Certificates

이제 클라이언트 인증서 생성을 살펴보겠습니다.

Admin User Certificates

admin user부터 시작합니다. OpenSSL 커맨드를 사용하여 관리자용 private key를 생성하는 동일한 프로세스를 따릅니다.

$ openssl genrsa -out admin.key 2048

그런 다음 CSR을 생성하고 여기에서 admin user의 이름을 지정합니다. 여기서는 kube-admin으로 지정했습니다.

$ openssl req -new -key admin.key -subj "/CN=kube-admin" -out admin.csr

이름에 대한 간단히 말씀드리자면, 실제로 kube-admin일 필요는 없습니다. 무엇이든 될 수 있지만 kubectl 커맨드를 실행할 때 kubectl 클라이언트가 인증하는 이름이어야 합니다. 이 이름은 audit logs 및 다른 곳에서 볼 수 있는 이름입니다. 

마지막으로 openssl x509 커맨드를 사용하여 서명된 인증서를 생성합니다.

$ openssl x509 -req -in admin.csr -CA ca.crt -CAkey ca.key -out admin.crt

그런데 이번에는 CA 인증서와 CA 키를 지정하여 CA 키 쌍으로 인증서에 서명하고 있습니다. 이렇게 하면 클러스터 내에서 유효한 인증서가 됩니다. 서명된 인증서는 admin.crt 파일로 출력됩니다. 이는 관리 사용자가 Kubernetes 클러스터에 인증하는 데 사용할 인증서입니다.

키와 인증서 쌍을 생성하는 이 전체 프로세스는 새 사용자를 위한 사용자 계정을 만드는 것과 비슷합니다. 인증서는 검증된 사용자 ID이고 키는 password와 같습니다. 단순한 username과 password보다는 훨씬 안전합니다.

이는 udmin user를 위한 것입니다. 이 사용자를 다른 사용자와 어떻게 구별할까요? 사용자 계정이 다른 기본 사용자가 아닌 admin 사용자로 식별되어야 합니다. 인증서에 사용자에 대한 그룹 세부 정보를 추가하면 됩니다. 지금 경우에는, system:masters라는 그룹이 관리 권한이 있는 Kubernetes에 존재합니다. 나중에 그룹에 대해 논의하겠지만 지금은 인증서 서명 요청에 이 정보를 언급해야 한다는 점에 유의해주세요. 인증서 서명 요청을 생성하는 동안 O 파라미터로 그룹 세부 정보를 추가하여 이를 수행할 수 있습니다.

$ openssl req -new -key admin.key -subj "/CN=kube-admin/O=system:masters" -out admin.csr

서명이 완료되면 관리자 권한이 있는 admin user에 대한 인증서가 생성됩니다.

동일한 프로세스에 따라 Kube API 서버에 액세스하는 다른 모든 컴포넌트에 대한 클라이언트 인증서를 생성합니다. 

kube-scheduler는 Kubernetes control plane의 일부인 시스템 컴포넌트이므로, 해당 이름 앞에 키워드 system을 붙여야 합니다.

kube-controller-manager도 동일합니다. 이것도 시스템 컴포넌트이므로 해당 이름 앞에 system이라는 키워드가 붙어야 합니다.

마지막으로 kube-proxy입니다.

지금까지 CA 인증서를 생성한 다음 admin user, scheduler, controller-manager 및 kube-proxy를 포함한 모든 클라이언트 인증서를 생성했습니다. API 서버 및 kubelet에 대한 서버 인증서를 생성할 때 동일한 절차에 따라 나머지 3개의 클라이언트 인증서를 생성합니다.

이제 이 인증서로 무엇을 합니까? 예를 들어 클러스터를 관리하려면 admin certificate를 가져옵니다. Kube API 서버에 대한 REST API 호출에서 username과 password 대신 이 인증서를 사용할 수 있습니다. key, certificate 및 CA 인증서를 옵션으로 지정하는 것은 간단한 방법입니다. 다른 방법은 이러한 모든 파라미터를 kubeconfig라는 configuration 파일로 옮기는 것입니다. 그 안에 API 서버 endpoint details, 사용할 인증서 등을 지정합니다. 이것이 대부분의 Kubernetes 클라이언트가 사용하는 것입니다. 다가오는 강의 중 하나에서 kubeconfig를 자세히 살펴보겠습니다.

이제 server site certificates가 남았지만 계속 진행하기 전에 한 가지 더 해야 합니다. prerequisite 강의에서 클라이언트가 서버에서 보낸 인증서의 유효성을 검사하거나 그 반대의 경우 모두 인증 기관 public certificate의 사본이 필요하다고 언급한 것을 기억하세요. 웹 애플리케이션의 경우에는 사용자의 브라우저에 이미 설치되어 있습니다.

마찬가지로 Kubernetes에서 이러한 다양한 컴포넌트가 서로를 확인하려면 모두 CA의 루트 인증서 사본이 필요합니다. 따라서 인증서가 있는 서버나 클라이언트를 구성할 때마다 CA 루트 인증서도 지정해야 합니다.

Generating Server Certificates

이제 서버측 인증서를 살펴보겠습니다.

ETCD Server certificate

ETCD 서버부터 시작하겠습니다. ETCD에 대한 인증서를 생성하기 위해 이전과 동일한 절차를 따릅니다. 이름을 etcd-server로 지정합니다. ETCD 서버는 고가용성 환경에서와 같이 여러 서버에 걸쳐 클러스터로 배포할 수 있습니다. 이 경우 클러스터의 다른 멤버 간의 통신을 보호하려면 추가 피어 인증서를 생성해야 합니다. 인증서가 생성되면 ETCD 서버를 시작하는 동안 인증서를 지정합니다. ETCD 서버 키를 지정하는 키 및 인증서 파일 옵션이 있습니다. 피어 인증서를 지정하는 데 사용할 수 있는 다른 옵션이 있습니다. 마지막으로 앞에서 설명한 것처럼 ETCD 서버에 연결하는 클라이언트가 유효한지 확인하려면 CA 루트 인증서가 필요합니다.

이제 Kube API 서버에 대해 이야기해 보겠습니다. 이전과 같이 API 서버에 대한 인증서를 생성합니다. 그런데 API 서버는 클러스터 내의 모든 컴포넌트 중에서 가장 많이 사용됩니다. 모든 작업이 Kube API 서버를 거칩니다. 클러스터 내에서 이동하는 모든 항목은 API 서버가 알고 있습니다. 정보가 필요하면 API 서버와 대화하면 됩니다. 따라서 클러스터 내에서 다양한 이름과 aliases으로 사용됩니다. 실제 이름은 Kube API server이지만 일부는 이를 Kubernetes라고 부릅니다. Kubernetes 내부에 무엇이 있는지 모르는 많은 사람들에게 Kube API 서버는 Kubernetes이기 때문입니다. 어떤 사람들은 이것을 Kubernetes.default라고 부르기를 좋아합니다. 일부는 이를 Kubernetes.default.svc라고 부르고 어떤 이들은 전체 이름 Kubernetes.default.svc.cluster.local로 부르기를 좋아합니다. 어떤 곳에서는 단순히 IP address로 불리기도 합니다. Kube API 서버를 실행하는 호스트 또는 이를 실행하는 파드의 IP 주소라고 볼 수 있습니다. 이러한 모든 이름은 Kube API 서버용으로 생성된 인증서에 있어야 합니다. 그런 다음 이러한 이름으로 Kube API 서버를 참조하는 사용자만이 유효한 연결을 설정할 수 있습니다.

이전과 동일한 커맨드 세트를 사용하여 키를 생성합니다. 인증서 서명 요청에서 Kube API 서버 이름을 지정합니다. 그러나 모든 alternate names을 어떻게 지정합니까? 이를 위해서는 OpenSSL config 파일을 만들어야 합니다. openssl.cnf 파일을 생성하고 파일의 alternate names 섹션에 alternate names을 지정합니다. API 서버가 통과하는 모든 DNS 이름과 IP 주소를 포함합니다. 인증서 서명 요청을 생성하는 동안 이 configuration 파일을 옵션으로 전달합니다. 마지막으로 CA certificate end key를 사용하여 인증서에 서명합니다. 그러면 이제 Kube API 서버 인증서가 있는 것을 확인할 수 있습니다.

이 키들을 지정할 위치를 살펴볼 때입니다. 클라이언트가 ETCD 및 kubelet 서버와 통신하는 동안 API 서버에서 사용하는 API 클라이언트 인증서를 고려해야 합니다. 이러한 인증서의 위치는 Kube API servers executable 또는 service configuration file에 전달됩니다.

- 먼저 CA 파일을 전달해야 모든 컴포넌트가 해당 클라이언트를 확인하기 위해 CA 인증서가 필요하다는 것을 기억할 수 있습니다.

- 그런 다음 TLS 인증서 옵션에서 API 서버 인증서를 제공합니다.

- 그런 다음 Kube API 서버에서 사용하는 클라이언트 인증서를 지정하여 CA 파일을 사용하여 ETCD 서버에 다시 연결합니다.

- 마지막으로 Kube API 서버 클라이언트 인증서는 kubelet에 연결합니다.

다음은 kubelets 서버입니다. kubelets 서버는 노드 관리를 담당하는 각 노드에서 실행되는 서버입니다. 이는 API 서버가 노드를 모니터링하고 이 노드에서 스케쥴링할 파드에 대한 정보를 보내기 위해 대화하는 서버입니다. 따라서 클러스터의 각 노드에 대한 키 인증서 쌍이 필요합니다. 이제 이 인증서의 이름은 무엇일까요? 그것들은 모두 kubelets로 명명될까요? 아니요. 노드의 이름을 따서 이름이 지정됩니다. node01, node02, node03 처럼요.

인증서가 생성되면 kubelet config 파일에서 사용합니다. 항상 그렇듯이 루트 CS 인증서를 지정한 다음 kubelet 노드 인증서를 제공합니다. 클러스터의 각 노드에 대해 이 작업을 수행해야 합니다.

Kube API 서버와 통신하기 위해 kubelet에서 사용할 클라이언트 인증서 세트에 대해서도 이야기했습니다. 이는 kubelet에서 Kube API 서버에 인증하는 데 사용되며, 생성해야 합니다. 이 인증서의 이름은 무엇일까요? API 서버는 인증 중인 노드를 알고 올바른 권한 세트를 부여해야 하므로 노드가 올바른 형식의 이름을 갖도록 해야 합니다. 노드는 앞에서 언급한 kube-scheduler 및 controller-manager와 같은 시스템 컴포넌트이므로 형식은 system 키워드, node, 노드 이름 순입니다. 지금의 경우에는 node01에서 node03까지입니다. 그리고 API 서버는 어떻게 올바른 권한 집합을 부여할까요? admin user가 administrative privileges을 얻도록 admin user의 그룹 이름을 지정했던 것을 기억하시나요? 마찬가지로 시스템 노드라는 그룹에 노드를 추가해야 합니다. 인증서가 생성되면 앞에서 설명한 대로 kubeconfig 파일로 이동합니다. 

반응형

댓글