Vault PKI Intermediate CAs for ALL SERVICES Kubernetes the hard way v2: различия между версиями

Материал из noname.com.ua
Перейти к навигацииПерейти к поиску
 
(не показано 185 промежуточных версий этого же участника)
Строка 9: Строка 9:
   
   
  +
=Прежде чем начать читать=
=Некоторые термины=
 
  +
Эта часть описывает какие именно сертификаты и СА для чего используются разными сервисами - ее можно прочитать перед тем как настаивать <code>Vault</code> для понимания того что и зачем настраивается или после.
  +
<br>
  +
[[Vault_PKI_Intermediate_SETUP_CAs_for_ALL_SERVICES_Kubernetes_the_hard_way_v2|Описание настойки <code>Vault</code> для выпуска сертификатов]]
  +
  +
=Некоторые термины и замечания=
 
* <code>CA</code>: '''certificate authority''' или '''certification authority''' ( на русском это звучит как Центр Сертефикации)
 
* <code>CA</code>: '''certificate authority''' или '''certification authority''' ( на русском это звучит как Центр Сертефикации)
 
В контексте документа может иметь несколько возможных значений - как собственно центр выпуска сертификатов, так и сам корневой (или промежуточный сертификат) этого центра. По сути, сертификат СА, который используется для подписания клиентских и серверных сертификатом не только не является секретным, но наоборот должен быть доступен для доступа так как именно он используется для проверки валидности выпущенных сертификатов
 
В контексте документа может иметь несколько возможных значений - как собственно центр выпуска сертификатов, так и сам корневой (или промежуточный сертификат) этого центра. По сути, сертификат СА, который используется для подписания клиентских и серверных сертификатом не только не является секретным, но наоборот должен быть доступен для доступа так как именно он используется для проверки валидности выпущенных сертификатов
Строка 21: Строка 26:
 
* <code>client_auth</code> - этот суффикс у СА используется в значении "сертификаты используются для авторизации" (другими словами - не используются для организации <code>http</code>)
 
* <code>client_auth</code> - этот суффикс у СА используется в значении "сертификаты используются для авторизации" (другими словами - не используются для организации <code>http</code>)
 
* <code>tls</code> - этот суффикс у СА используется в значении "сертификаты используются для организации <code>https/TLS</code>"
 
* <code>tls</code> - этот суффикс у СА используется в значении "сертификаты используются для организации <code>https/TLS</code>"
  +
  +
  +
* В целом, если не использовать <code>Vault</code> а использовать другой PKI, будь то на основе <code>OpenSSL</code> или чего-то другого ничего принципиально не меняется, и ничего специфичного для PKI <code>Vault</code> в документе нет
  +
  +
* В этом разделе нет команд по получению сертификатов или настройке PKI, а только описание параметров сервисов, их назначения и свойства сертификатов которые используются.
  +
  +
В целом для лучшего понимания можно держать в голове такую схему
  +
  +
<PRE>
  +
  +
  +
+-------------+ +---------------------------------------------+ +-------------------------------------------------+
  +
| Корневой CA | --------> им подписан -------> |Промежуточный CA для сервиса X и пользования | -------------> им подписан ----------> | Конечный сертификат которым пользуется сервис Y |
  +
+-------------+ (процедура подписания ) +---------------------------------------------+ (процедура подписания скрыта ) +-------------------------------------------------+
  +
(скрыта внутри Vault и ) (внутри Vault и требует авторизации )
  +
(требует рутовый токен от Vault) (с логином и паролем, который выдается )
  +
(тому сервису которому нужен сертификат)
  +
</PRE>
  +
  +
Пример 1
  +
<BR>
  +
* Сервису <code>kubelet </code> нужен сертификат для того что бы авторизоваться у <code>kube-apiserver</code>
  +
* Создается промежуточный CA (внутри Vault) который будет иметь возможность выписывать такие сертификаты, в этом пример это будет СА <code>k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth/</code>
  +
* Сертификат этого промежуточного СА подписывается (или иногда говорят "заверяется", что в контексте SSL синонимы) Корневым СА (на схеме)
  +
** <code>k8s_pki_intermediate_ca_for_service_</code> - префикс общий для всех СA которые используются для K8s (в случае <code>Vault</code> используется например для более чем одного кластера, или еще зачем-то)
  +
** <code>kube_apiserver</code> - имя сервиса, который будет пользоваться сертификатами, в данном контексте "пользоваться" означает то что <code>kube-apiserver</code>будет проверять эти сертификаты, а не то что они будут непосредственно указаны в его конфигурационных файлах.
  +
** <code>client_auth</code> - назначение сертификатов которые будут создаваться с помощью этого CA
  +
** Создаются правила пользования этим СА - какие пользователи и с какими параметрами могут получать сертификаты для авторизации у <code>kube-apiserver</code>, ограничения касаются CN (подробнее об этом - о настройке PKI для <code>Vault</code>, как например [[Vault_PKI_Intermediate_ca_etcd_Roles_and_permissions_for_real_cluster_Kubernetes_the_hard_way_v2|настроено получение сертификатов для <code>Etcd</code>]]
  +
** Данные для авторизации выдаются сервису, которому нужен сертификат (в примере - <code>kubelet</code>) который используя API <code>Vault</code> может сам выпустить сертификат (с учетом ограничений CN) и при необходимости перевыпустить его.
  +
** Автоматизация перевыпуска сертификатов - дело будущей настройки сервисов и будет описана в других разделах
  +
  +
<BR>
  +
<BR>
  +
Пример 2
  +
<BR>
  +
* Сервису <code>kube-apiserver</code> нужно открыть порт и принимать <code>HTTPS/TLS</code> подключения (авторизация после подключения в этом примере пропущена)
  +
* Для этого требуется серверный сертификат
  +
* Для выпуска таких сертификатов создается СА <code>k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/</code>, промежуточный сертификат заверяется корневым
  +
* отличие - в том что он предназначен для <code>HTTPS/TLS</code> и имеет другой суффикс
  +
* для сервиса <code>kube-apiserver</code> создается пользователь и пароль в <code>Vault</code> (с ограничениями на CN)
  +
* имея доступ к API <code>Vault</code>, сервис <code>kube-apiserver</code> может выписать себе сертификат с нужным CN (в пределах ограничений) а так же перевыпустить просроченный сертификат
  +
<BR>
  +
<BR>
  +
Отличие между примерами в том, что хотя в обоих случаях СА имеют в имени <code>kube-apiserver</code>
  +
* k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth
  +
* k8s_pki_intermediate_ca_for_service_kube_apiserver_tls
  +
В первом пример сертификаты выписанные CA с пометкой '''client_auth''' используются для того что бы подключиться к <code>kube-apiserver</code> и не фигурируют в его конфигах
  +
Во втором же примере сертификаты выписанные СА с пометкой '''tls''' используются самим <code>kube-apiserver</code>
   
 
=Создание СА для работы кластера K8s=
 
=Создание СА для работы кластера K8s=
  +
==Соглашение о путях к файлам==
  +
* Путь к СА: <code>/etc/k8s/shared/certs/CA</code>
  +
* Все файлы СА (далее по тексту просто СА) можно загрузить из <code>Vault</code> в любой момент, без авторизации. Эти файлы СА (БЕЗ ключа!) не являются секретными, и могут использоваться только для проверки сертификатов (что бы проверить требуется вся цепочка - Корневой CA -- Промежуточный СА -- Сертификат
  +
* Скрипт загрузки проходится по списку сервисов и загружает с соответствующих endpoints СA в файлы :
  +
#kube_apiserver
  +
#kube_controller_manager
  +
#kube_scheduler
  +
#kubelet
  +
  +
в <code>Vault</code> и загружает промежуточные сертификаты в директорию<code>/etc/k8s/shared/certs/CA</code>
  +
{{#spoiler:show=Скрипт загрузки промежуточных CA|
  +
  +
<PRE>
  +
#!/bin/bash
  +
  +
set -eu${DEBUG:+x}
  +
  +
VAULT_ADDRESS="http://vault.home:8200"
  +
  +
SERVICE_NAMES="kubelet kube-apiserver kube-controller-manager kube-scheduler"
  +
USAGES="TLS CLIENT_AUTH"
  +
PKI_PATH_PREFIX="k8s_pki_intermediate_ca_for_service"
  +
CA_PATH="/etc/k8s/shared/certs/CA"
  +
mkdir -p "${CA_PATH}"
  +
  +
for SERVICE_NAME in ${SERVICE_NAMES};
  +
do
  +
for USAGE in ${USAGES};
  +
do
  +
SERVICE_NAME_UNDERSCORE=$(echo ${SERVICE_NAME} | sed 's/-/_/g')
  +
USAGE_LOWERCASE=$(echo "${USAGE,,}")
  +
USAGE_LOWERCASE=$(echo $USAGE_LOWERCASE | sed 's/-/_/g')
  +
  +
PKI_PATH="${PKI_PATH_PREFIX}_${SERVICE_NAME_UNDERSCORE}_${USAGE_LOWERCASE}"
  +
echo curl "${VAULT_ADDRESS}/v1/${PKI_PATH}/ca"
  +
echo "-----BEGIN CERTIFICATE-----" > "${CA_PATH}/${PKI_PATH}.pem" && \
  +
curl "${VAULT_ADDRESS}/v1/${PKI_PATH}/ca" | base64 >> "${CA_PATH}/${PKI_PATH}.pem" && \
  +
echo "-----END CERTIFICATE-----" >> "${CA_PATH}/${PKI_PATH}.pem"
  +
done
  +
done
  +
</PRE>
  +
}}
   
   
Строка 45: Строка 140:
 
=Полный список <code>СА</code> (промежуточных СА!)=
 
=Полный список <code>СА</code> (промежуточных СА!)=
   
Всего существует 8 СА которые используются в этой инсталляции (один из них - корневой СА). <br>
+
* Всего существует 8 СА которые используются в этой инсталляции (один из них - корневой СА). <br>
  +
<br>
 
Если верить документации, то это не предел - каждый файл с CA в настройках сервисов может содержать <br>
 
Если верить документации, то это не предел - каждый файл с CA в настройках сервисов может содержать <br>
 
более одного сертификата, другими словами 2 процесса <code>kube-apiserver</code> вполне могут использовать разные CA<br>
 
более одного сертификата, другими словами 2 процесса <code>kube-apiserver</code> вполне могут использовать разные CA<br>
   
 
В частных случаях можно упростить настройку, и вообще использовать 1 СА<br>
 
В частных случаях можно упростить настройку, и вообще использовать 1 СА<br>
Эта инсталляция подразумевает настойку PKI средней сложности, что бы не переусложнять.
+
Эта инсталляция подразумевает настойку PKI средней сложности.
 
<br>
 
<br>
  +
 
=<code>k8s_pki_intermediate_ca_for_service_etcd/</code>=
 
=<code>k8s_pki_intermediate_ca_for_service_etcd/</code>=
   
Строка 58: Строка 155:
 
* для авторизации клиентов
 
* для авторизации клиентов
   
=<code>k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth/</code> <code>k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/</code>=
+
=<code>k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth/</code><BR><BR><code>k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/</code>=
   
 
* <code>k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth/</code> - используется для клиентских сертефикатов <code>kube-apiserver</code>, по которым API проверяет права пользователей.
 
* <code>k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth/</code> - используется для клиентских сертефикатов <code>kube-apiserver</code>, по которым API проверяет права пользователей.
 
* <code>k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/</code> Используется для обеспечения https при подключении к <code>kube-apiserver</code>. При этом происходит двухсторонняя проверка
 
* <code>k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/</code> Используется для обеспечения https при подключении к <code>kube-apiserver</code>. При этом происходит двухсторонняя проверка
** Все клиенты (как сервисы, часть k8s, например kube-controller-manager, kube-scheduler так и kubectl для администрирования) должны обладать CA (который как и прочие СА не является секретным), для того что бы иметь возможность проверить кластер, другими словами быть уверенным в том что подключаются туда куда ожидают. <br>
+
** Все клиенты (как сервисы, часть k8s, например <code>kube-controller-manager</code>, <code>kube-scheduler</code>, <code>kubectl</code> так и для администрирования) должны обладать CA (который как и прочие СА не является секретным), для того что бы иметь возможность проверить кластер, другими словами быть уверенным в том что подключаются туда куда ожидают. <br>
 
Часть <code>kubeconfig</code> отвечающая за этот сертификат:
 
Часть <code>kubeconfig</code> отвечающая за этот сертификат:
 
<PRE>
 
<PRE>
Строка 73: Строка 170:
   
 
=<code>k8s_pki_intermediate_ca_for_service_kube_controller_manager_tls/</code>=
 
=<code>k8s_pki_intermediate_ca_for_service_kube_controller_manager_tls/</code>=
* <code>k8s_pki_intermediate_ca_for_service_kube_controller_manager_tls/</code> - используется для обеспечения https, серверные сетефикаты
+
* <code>k8s_pki_intermediate_ca_for_service_kube_controller_manager_tls/</code> - используется для обеспечения https, серверные сетефикаты для <code>kube-controller-manager</code> (Серверные сертификаты нужны для API)
   
 
=<code>k8s_pki_intermediate_ca_for_service_kube_scheduler_tls/</code>=
 
=<code>k8s_pki_intermediate_ca_for_service_kube_scheduler_tls/</code>=
* <code>k8s_pki_intermediate_ca_for_service_kube_scheduler_tls/</code> - используется для обеспечения https, серверные сетефикаты
+
* <code>k8s_pki_intermediate_ca_for_service_kube_scheduler_tls/</code> - используется для обеспечения https, серверные сетефикаты для <code>kube-scheduler</code> (Серверные сертификаты нужны для API)
   
=<code>k8s_pki_intermediate_ca_for_service_kubelet_client_auth/</code> <code>k8s_pki_intermediate_ca_for_service_kubelet_tls/</code>=
+
=<code>k8s_pki_intermediate_ca_for_service_kubelet_client_auth/<BR></BR></code> <code>k8s_pki_intermediate_ca_for_service_kubelet_tls/</code>=
  +
* <code>k8s_pki_intermediate_ca_for_service_kubelet_client_auth/</code> kubelet в целом устроен аналогично kube-api серверу, и использует 2 СА - один для авторизации клиентов (в случае с kubelet клиентом выступает kube-apiserver), а второй используется для обеспечения https
 
  +
** У <code>kube-apiserver</code> есть настройка <code>--kubelet-certificate-authority</code> - это файлс СА для <code>k8s_pki_intermediate_ca_for_service_kubelet_tls/</code>, таким образом <code>kube-apiserver</code> может точно знать что он обращается к нужному <code>kubelet</code>, так как его серверный сертефикат подписан этим СА
 
  +
<code>k8s_pki_intermediate_ca_for_service_kubelet_client_auth/</code> kubelet в целом устроен аналогично <code>kube-apiserver</code>, и использует 2 СА - один для авторизации клиентов (в случае с <code>kubelet</code> клиентом выступает <code>kube-apiserver</code>), а второй CA используется для обеспечения https
** <code>--kubelet-client-certificate</code><code>--kubelet-client-key</code> содрежат сертификат, выписанный помощью СА <code>k8s_pki_intermediate_ca_for_service_kubelet_client_auth/</code> и содержат имя пользователя и группу с которыми <code>kube-apiserver авторизуется</code> у <code>kubelet</code><br>
 
  +
  +
* У <code>kube-apiserver</code> есть настройка <code>--kubelet-certificate-authority</code> - это файл СА <code>k8s_pki_intermediate_ca_for_service_kubelet_tls/</code> (другими словами, это тот СА который выписал '''серверный''' сертификат для обеспечения <code>HTTPS/TLS</code> API <code>kubelet</code> ( Порт 10250). <br>
  +
Просмотреть содержимое можно например командой
  +
<PRE>
  +
openssl s_client -connect 127.0.0.1:10250
  +
</PRE>
  +
Используя СА <code>k8s_pki_intermediate_ca_for_service_kubelet_tls</code> <code>kube-apiserver</code> может
  +
точно знать что он обращается к нужному <code>kubelet</code>, так как его серверный сертефикат подписан этим СА
  +
  +
  +
* <code>--kubelet-client-certificate</code><code>--kubelet-client-key</code> содрежат сертификат, выписанный помощью СА <code>k8s_pki_intermediate_ca_for_service_kubelet_client_auth/</code> и содержат имя пользователя и группу с которыми <code>kube-apiserver авторизуется</code> у <code>kubelet</code><br>
 
<br>
 
<br>
 
Например: <code>O = system:masters</code>, <code>OU = system</code>, <code>CN = kube-apiserver-to-kubelet</code>
 
Например: <code>O = system:masters</code>, <code>OU = system</code>, <code>CN = kube-apiserver-to-kubelet</code>
 
<br>
 
<br>
<br>При этом по-умолчанию соответствующие <code>ClustetRoleBinding</code> отсутствуют, и перед подключением <code>kubele</code> их требуется создать дополнительно. (эта часть настройки выполняется при конфигурировании <code>kube-apiserver</code>
+
<br>При этом по-умолчанию соответствующие <code>ClustetRoleBinding</code> отсутствуют, и перед подключением <code>kubelet</code> их требуется создать дополнительно. (эта часть настройки выполняется при конфигурировании <code>kube-apiserver</code>
   
   
 
* <code>k8s_pki_intermediate_ca_for_service_kubelet_tls/</code> - используется для обеспечения https, серверные сетефикаты
 
* <code>k8s_pki_intermediate_ca_for_service_kubelet_tls/</code> - используется для обеспечения https, серверные сетефикаты
* <code>k8s_pki_root_ca/</code>
 
   
  +
=<code>k8s_pki_root_ca/</code>=
=TLS CA=
 
  +
* <code>k8s_pki_root_ca/</code> - это корневой СА которым подписаны все промежуточные СА, и его сертификат СА обязательно требуется распространить по всем хостам так как он является полностью доверенным (в пределах этой инсталляции, конечно)
Для того что бы предоставлять API по https нужны следующие СА
 
==<code>kube-apiserver</code> TLS CA==
 
--tls-cert-fil
 
--tls-private-key-file
 
   
  +
=Полный список сертификатов с кратким описанием=
==<code>kube-controller-manager</code> TLS CA==
 
  +
Это CA (в <code>VAULT</code>, c именами и описаниями) которые используются для выпуска сертификатов для k8s)
--tls-cert-file
 
  +
<PRE>
--tls-private-key-file
 
  +
k8s_pki_intermediate_ca_for_service_etcd/ pki pki_13a87e77 PKI Intermediate CA for ETCd service
  +
k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth/ pki pki_622072da PKI Intermediate CA for K8S: kube-apiserver CLIENT_AUTH
  +
k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/ pki pki_d8737474 PKI Intermediate CA for K8S: kube-apiserver TLS
  +
k8s_pki_intermediate_ca_for_service_kube_controller_manager_tls/ pki pki_34a63553 PKI Intermediate CA for K8S: kube-controller-manager TLS
  +
k8s_pki_intermediate_ca_for_service_kube_scheduler_tls/ pki pki_5b5f53f5 PKI Intermediate CA for K8S: kube-scheduler TLS
  +
k8s_pki_intermediate_ca_for_service_kubelet_client_auth/ pki pki_4f1df8fd PKI Intermediate CA for K8S: kubelet CLIENT_AUTH
  +
k8s_pki_intermediate_ca_for_service_kubelet_tls/ pki pki_47e7182a PKI Intermediate CA for K8S: kubelet TLS
  +
</PRE>
   
  +
Note: так как префикс <code>k8s_pki_intermediate_ca_for_service_</code> в именовании CA общий, то в таблице для удобства форматирования он опущен
==<code>kube-scheduler</code>TLS CA==
 
--tls-cert-file
 
--tls-private-key-file
 
   
==<code>kubelet</code> TLS CA==
 
--tls-cert-file
 
--tls-private-key-file
 
   
  +
==<code>kube-apiserver</code>==
This parameter should be set via the config file specified by the Kubelet's --config
 
  +
{| class="wikitable sortable"
<PRE>
 
  +
|+ Сертификаты K8s <code> kube-apiserver</code>
kind: KubeletConfiguration
 
  +
|-
apiVersion: kubelet.config.k8s.io/v1beta1
 
  +
! Сервис который использует этот сертификат !! Параметр сервиса !! СА выпустивший сертификат !! Тип сертификата (серверный/клиентский/CA) !! Назначение !! Subject и подробности
...
 
  +
|-
tlsCertFile: "/etc/k8s/kubelet/tls/kubelet.az1.k8s.home.pem"
 
  +
| <code>kube-apiserver</code>
tlsPrivateKeyFile: "/etc/k8s/kubelet/tls/kubelet.az1.k8s.home.key"
 
  +
|| <code>--etcd-certfile</code><br><code>--etcd-keyfile</code>
authorizationMode: Node,RBAC
 
  +
|| <code>etcd</code>
  +
|| Клиентский <br>TLS Web Client <br>Authentication
  +
|| Авторизация в <code>etcd</code>. В зависимости от настроек содержит имя пользователя <br> если etcd настроен на такой тип авторизации, используется именно такой способ: ([[Kubernetes_the_hard_way_etcd_setup#.D0.90.D0.B2.D1.82.D0.BE.D1.80.D0.B8.D0.B7.D0.B0.D1.86.D0.B8.D1.8F_.D0.BD.D0.B0_.D0.BE.D1.81.D0.BD.D0.BE.D0.B2.D0.B5_.D1.81.D0.B5.D1.80.D1.82.D0.B8.D1.84.D0.B8.D0.BA.D0.B0.D1.82.D0.BE.D0.B2|<code>etcd</code>: авторизация с использованием сертификатов]])
  +
||<PRE>
  +
openssl x509 -noout -text -in /etc/k8s/kube-apiserver/certs/etcd/kube-apiserver.pem
 
</PRE>
 
</PRE>
  +
<PRE>
  +
Certificate:
  +
Data:
  +
Version: 3 (0x2)
  +
Serial Number:
  +
56:ce:57:67:7d:9b:54:76:6d:60:51:4a:0c:09:c7:11:ac:f1:95:3b
  +
Signature Algorithm: sha256WithRSAEncryption
  +
Issuer: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, postalCode = 61172, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service ETCd
  +
Validity
  +
Not Before: Oct 17 15:23:37 2022 GMT
  +
Not After : Oct 16 15:24:04 2027 GMT
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st 322 app. 311, postalCode = 61172, O = Home Network, OU = IT, CN = kube-apiserver-1
  +
X509v3 extensions:
  +
X509v3 Key Usage: critical
  +
Digital Signature, Key Encipherment
  +
X509v3 Extended Key Usage:
  +
TLS Web Client Authentication
  +
X509v3 Subject Key Identifier:
  +
F8:E5:28:79:2F:4E:99:EA:BE:43:B7:CA:6C:1B:20:65:E6:0B:B3:72
  +
X509v3 Authority Key Identifier:
  +
60:41:31:79:58:90:A9:63:62:C2:26:FD:8F:02:B6:07:1A:1D:5C:50
  +
Authority Information Access:
  +
CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_etcd/ca
  +
X509v3 Subject Alternative Name:
  +
DNS:kube-apiserver-1
  +
X509v3 CRL Distribution Points:
  +
Full Name:
  +
URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_etcd/crl
   
  +
</PRE>
=Client CA=
 
  +
|-
* https://kubernetes.io/docs/setup/best-practices/certificates/
 
==<code></code>==
 
==<code></code>==
 
==<code></code>==
 
==<code></code>==
 
   
  +
=СА для TLS=
 
  +
Отдельный СА (промежуточный СА!)
 
  +
<br>
 
  +
Переменные вынесены в отдельный файл
 
  +
  +
  +
  +
  +
  +
  +
  +
  +
| <code>kube-apiserver</code>
  +
|| <code>--tls-cert-file</code><br> <code>--tls-private-key-file</code><br>
  +
|| <code>kube_apiserver_tls/</code>
  +
|| Серверный<br>TLS Web Server<br>Authentication
  +
|| <code>HTTPS</code> для API
  +
|| Можно получить <PRE>netstat -ntpl | grep kube-api </PRE>
 
<PRE>
 
<PRE>
  +
tcp 0 0 10.0.12.1:6443 0.0.0.0:* LISTEN 85224/kube-apiserve
env
 
 
</PRE>
 
</PRE>
  +
Или взять из параметров <code>kube-apiserver</code><br>
  +
Обратить внимание - в Alt Names прописан как основной домен ('''kube-apiserver.az1.k8s.cluster.home'''), так и домен балансера ('''kube-apiserver.k8s.cluster.home''') а так же адреса по которым может быть доступен сервис. Адрес '''10.80.0.1''' указывается в настройках <code>kube-apiserver</code>
  +
* DNS:kube-apiserver.az1.k8s.cluster.home
  +
* DNS:kube-apiserver.k8s.cluster.home
  +
* DNS:kubernetes
  +
* DNS:kubernetes.cluster.home
  +
* IP Address:10.0.12.1
  +
* IP Address:10.80.0.1
  +
* IP Address:127.0.0.1
  +
 
<PRE>
 
<PRE>
  +
openssl x509 -noout -text -in /etc/k8s/kube-apiserver/certs/tls/kube-apiserver-tls.pem
export VAULT_ADDR=http://127.0.0.1:8200
 
export VAULT_TOKEN="s.Yb1J2VamFyYoav3VVE2YQQ88"
 
export PKI_PATH="k8s_pki_intermediate_ca_for_service_kube_apiserver_tls"
 
export N='kube-apiserver'
 
 
</PRE>
 
</PRE>
 
==Настройка СА==
 
 
<PRE>
 
<PRE>
  +
Certificate:
#!/bin/bash
 
  +
Data:
  +
Version: 3 (0x2)
  +
Serial Number:
  +
71:a8:93:84:83:df:af:ba:78:df:63:3d:fe:4d:7f:f4:22:26:23:24
  +
Signature Algorithm: sha256WithRSAEncryption
  +
Issuer: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kube-apiserver TLS
  +
Validity
  +
Not Before: Nov 14 08:59:08 2022 GMT
  +
Not After : Nov 13 08:59:35 2027 GMT
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = kube-apiserver.az1.k8s.cluster.home
  +
Subject Public Key Info:
  +
X509v3 extensions:
  +
X509v3 Key Usage: critical
  +
Digital Signature, Key Encipherment
  +
X509v3 Extended Key Usage:
  +
TLS Web Server Authentication
  +
X509v3 Subject Key Identifier:
  +
E0:69:16:9A:99:A8:E6:95:AB:2B:2D:BC:58:CF:5C:E0:61:BF:10:51
  +
X509v3 Authority Key Identifier:
  +
22:7D:70:47:DB:79:ED:91:79:B3:51:0E:23:5F:32:B9:37:01:8D:C1
  +
Authority Information Access:
  +
CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/ca
  +
X509v3 Subject Alternative Name:
  +
DNS:kube-apiserver.az1.k8s.cluster.home, DNS:kube-apiserver.k8s.cluster.home, DNS:kubernetes, DNS:kubernetes.cluster.home, IP Address:10.0.12.1, IP Address:10.80.0.1, IP Address:127.0.0.1
  +
X509v3 CRL Distribution Points:
  +
Full Name:
  +
URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/crl
   
source ../env
 
 
vault \
 
secrets \
 
enable \
 
-path=${PKI_PATH} \
 
-description="PKI Intermediate CA for K8S kube-apiserver API endpoints" \
 
-max-lease-ttl="175200h" \
 
pki
 
 
</PRE>
 
</PRE>
  +
|-
   
<PRE>
 
#!/bin/bash
 
   
source ../env
 
   
vault \
 
write \
 
-format=json \
 
${PKI_PATH}/intermediate/generate/exported \
 
common_name="Intermediate CA for service kube-api-server API endpoints" \
 
country="Ukraine" \
 
locality="Kharkov" \
 
street_address="Lui Pastera st. 322 app. 131" \
 
postal_code="61172" \
 
organization="K8s The Hardest Way Labs" \
 
ou="IT" \
 
ttl="175200h" > ${PKI_PATH}.json
 
   
   
cat ${PKI_PATH}.json | jq -r '.data.csr' > ${PKI_PATH}_intermediate_ca.csr
 
cat ${PKI_PATH}.json | jq -r '.data.private_key' > ${PKI_PATH}_intermediate_ca.key
 
</PRE>
 
   
<PRE>
 
#!/bin/bash
 
   
source ../env
 
   
vault \
 
write \
 
-format=json \
 
k8s_pki_root_ca/root/sign-intermediate \
 
csr=@${PKI_PATH}_intermediate_ca.csr \
 
country="Ukraine" \
 
locality="Kharkov" \
 
street_address="Lui Pastera st. 322 app. 131" \
 
postal_code="61172" \
 
organization="K8s The Hardest Way Labs" \
 
ou="IT" \
 
format=pem_bundle \
 
ttl="175200h" > ${PKI_PATH}_intermediate_ca_pem_bundle.json
 
   
   
cat ${PKI_PATH}_intermediate_ca_pem_bundle.json | jq -r '.data.certificate' > ${PKI_PATH}_intermediate_ca_pem.crt
 
cat ${PKI_PATH}_intermediate_ca_pem_bundle.json | jq -r '.data.issuing_ca' > k8s_root_certificate.pem
 
</PRE>
 
   
<PRE>
 
#!/bin/bash
 
   
source ../env
 
   
openssl \
 
verify \
 
-verbose \
 
-CAfile k8s_root_certificate.pem \
 
${PKI_PATH}_intermediate_ca_pem.crt
 
</PRE>
 
   
  +
  +
  +
| <code>kube-apiserver</code>
  +
|| <code>--client-ca-file</code>
  +
|| <code>CA</code> <code>kube_apiserver_client_auth/</code>
  +
|| Не серверный<BR>Не клиентский<BR>'''CA'''
  +
|| Это СА который используется для проверки сертификатов, с которыми клиенты (другие сервисы или пользователи) подключаются к <code>kube-apiserver</code>. <BR>
  +
Важно, что ключ от этого сертификата в настройках <code>kube-apiserver</code> не участвует. <BR>Это означает что <code>kube-apiserver</code> может проверять сертификаты клиентов но не может выписывать новые сертификаты, эта часть - за администратором системы.
  +
  +
<BR>
  +
'''Именно с пмощью этого СА проверяются сертификаты как пользователей (если пользователи используют сертификаты) так и сервисов <code>kube-controller-manager</code>, <code>kube-proxy</code>, <code>kube-scheduler</code>, <code>kubelet</code>'''
  +
<BR>В случае PKI на основе <code>Vault</code> CA в любой момент можно скачать.
  +
||
 
<PRE>
 
<PRE>
  +
openssl x509 -noout -text -in /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth.pem
#!/bin/bash
 
  +
</PRE>
  +
<PRE>
  +
Certificate:
  +
Data:
  +
Version: 3 (0x2)
  +
Serial Number:
  +
1a:ba:2f:66:84:5f:65:d4:cf:65:e2:d8:86:6a:a5:22:fd:57:8c:2b
  +
Signature Algorithm: sha256WithRSAEncryption
  +
Issuer: C = Ukraine, L = Kharkov, street = app. 131 + street = Lui Pastera St. 322, postalCode = 61172, O = Home Network, OU = IT, CN = Root Certificate Authority for Home Network v2
  +
Validity
  +
Not Before: Nov 5 10:21:06 2022 GMT
  +
Not After : Oct 31 10:21:36 2042 GMT
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, CN = Intermediate CA for service kube-apiserver CLIENT_AUTH
  +
Subject Public Key Info:
  +
X509v3 extensions:
  +
X509v3 Key Usage: critical
  +
Certificate Sign, CRL Sign
  +
X509v3 Basic Constraints: critical
  +
CA:TRUE
  +
X509v3 Subject Key Identifier:
  +
2F:8E:7A:14:33:0D:E1:66:69:81:85:F5:C5:EC:09:3E:89:E1:B7:DF
  +
X509v3 Authority Key Identifier:
  +
02:F8:85:2B:75:F8:E1:1C:69:28:30:32:21:2D:86:71:AF:AB:EC:3C
  +
Authority Information Access:
  +
CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_root_ca/ca
  +
X509v3 CRL Distribution Points:
  +
Full Name:
  +
URI:http://vault.home:8200/v1/k8s_pki_root_ca/crl
  +
</PRE>
  +
|-
   
source ../env
 
   
  +
vault \
 
  +
write \
 
  +
${PKI_PATH}/intermediate/set-signed \
 
  +
certificate=@${PKI_PATH}_intermediate_ca_pem.crt \
 
  +
key=@${PKI_PATH}_intermediate_ca.key
 
  +
  +
  +
  +
  +
  +
  +
  +
  +
  +
  +
  +
| <code>kube-apiserver</code>
  +
|| <code>--kubelet-certificate-authority</code>
  +
|| <code>CA</code><BR><code>kubelet_tls</code>
  +
|| Не серверный<BR>Не клиентский<BR>'''CA'''
  +
|| Это <code>CA</code> используется для того, что бы проверить сертификат <code>kubelet</code>, и быть уверенным что подключение к правильному <code>kubelet</code><br>
  +
Этим же СА подписываются сертификаты <code>kubelet</code> для TLS <BR> (конфигурация <code>kubelet</code>)
  +
<code>/etc/k8s/kubelet/kubelet-config.yaml</code>
  +
<PRE>
  +
tlsCertFile: "/etc/k8s/kubelet/certs/tls/kubelet-tls.pem"
  +
tlsPrivateKeyFile: "/etc/k8s/kubelet/certs/tls/kubelet-tls.key"
 
</PRE>
 
</PRE>
  +
||
==Права, пользователи, роли==
 
Далее назначить права на пользователей для каждого экземпляра сервера
 
 
<PRE>
 
<PRE>
  +
openssl x509 -noout -text -in /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kubelet_tls.pem
#!/bin/bash
 
  +
</PRE>
  +
<PRE>
  +
Certificate:
  +
Data:
  +
Version: 3 (0x2)
  +
Serial Number:
  +
33:04:63:a1:86:f2:80:bd:96:5e:10:46:ae:d5:c8:28:89:d0:74:34
  +
Signature Algorithm: sha256WithRSAEncryption
  +
Issuer: C = Ukraine, L = Kharkov, street = app. 131 + street = Lui Pastera St. 322, postalCode = 61172, O = Home Network, OU = IT, CN = Root Certificate Authority for Home Network v2
  +
Validity
  +
Not Before: Nov 10 14:11:32 2022 GMT
  +
Not After : Nov 5 14:12:02 2042 GMT
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kubelet TLS
  +
Subject Public Key Info:
  +
Public Key Algorithm: rsaEncryption
  +
Public-Key: (2048 bit)
  +
Modulus:
  +
Exponent: 65537 (0x10001)
  +
X509v3 extensions:
  +
X509v3 Key Usage: critical
  +
Certificate Sign, CRL Sign
  +
X509v3 Basic Constraints: critical
  +
CA:TRUE
  +
X509v3 Subject Key Identifier:
  +
F1:9C:3B:FB:01:4E:9A:3F:F5:E8:28:CE:99:60:9F:E3:5E:51:DA:C8
  +
X509v3 Authority Key Identifier:
  +
02:F8:85:2B:75:F8:E1:1C:69:28:30:32:21:2D:86:71:AF:AB:EC:3C
  +
Authority Information Access:
  +
CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_root_ca/ca
  +
X509v3 CRL Distribution Points:
  +
Full Name:
  +
URI:http://vault.home:8200/v1/k8s_pki_root_ca/crl
  +
</PRE>
  +
|-
   
source ../env
 
   
N='kube-apiserver'
 
for AZ in $(seq 1 3);
 
do
 
DOMAIN="${N}.az${AZ}.k8s.cluster.home"
 
BALANCER_DOMAIN="${N}.k8s.cluster.home"
 
NAME_SERVER="${DOMAIN}-server"
 
NAME_CLIENT="${DOMAIN}-client"
 
   
   
vault \
 
write \
 
${PKI_PATH}/roles/${NAME_SERVER}-role \
 
country="Ukraine" \
 
locality="Kharkov" \
 
street_address="Lui Pastera st 322 app. 311"\
 
postal_code="61172" \
 
organization="Home Network" \
 
ou="IT" \
 
allowed_domains="${DOMAIN},${BALANCER_DOMAIN}" \
 
allow_subdomains=false \
 
max_ttl="87600h" \
 
key_bits="2048" \
 
key_type="rsa" \
 
allow_any_name=false \
 
allow_bare_domains=true \
 
allow_glob_domain=false \
 
allow_ip_sans=true \
 
allow_localhost=false \
 
client_flag=true \
 
server_flag=true \
 
enforce_hostnames=true \
 
key_usage="DigitalSignature,KeyEncipherment" \
 
ext_key_usage="ServerAuth" \
 
require_cn=true
 
   
  +
| <code>kube-apiserver</code>
vault \
 
  +
|| <code>--kubelet-client-certificate</code> <br> <code>--kubelet-client-key</code>
write \
 
  +
|| <code>kubelet_client_auth/</code>
${PKI_PATH}/roles/${NAME_CLIENT}-role \
 
  +
|| Клиентский <br>TLS Web Clien<br>Authentication
country="Ukraine" \
 
  +
|| Это сертификат используется <code>kube-apiserver</code> что бы авторизоваться у <code>kubelet</code><br>, это нужно что бы <code>kubelet</code> мог быть уверен что к нему пришел доверенный <code>kube-apiserver</code>
locality="Kharkov" \
 
  +
||
street_address="Lui Pastera st 322 app. 311"\
 
  +
Обратить внимание на <code>CN = kube-apiserver-to-kubelet</code> - для этого пользователя потребуется создать отдельный <code>ClusterRoleBinding</code>, по-умолчанию его нет. Естественно, что для своих ролей имена можно использовать любые, <code>kube-apiserver-to-kubelet</code> это текстовый идентификатор, который можно назначить по своему усмотрению, но, одинаковый как в сертификате так и в <code>ClusterRoleBinding</code>
postal_code="61172" \
 
  +
<PRE>
organization="Home Network" \
 
  +
openssl x509 -noout -text -in /etc/k8s/kube-apiserver/certs/client_auth/kubelet-client_auth.pem
ou="IT" \
 
  +
</PRE>
allow_subdomains=false \
 
  +
<PRE>
max_ttl="87600h" \
 
  +
Certificate:
key_bits="2048" \
 
  +
Data:
key_type="rsa" \
 
allow_any_name=true \
+
Version: 3 (0x2)
allow_bare_domains=true \
+
Serial Number:
  +
28:07:04:c7:ce:4a:6e:29:fc:f7:c9:60:00:57:2a:9c:16:ca:53:8f
allow_glob_domain=false \
 
  +
Signature Algorithm: sha256WithRSAEncryption
allow_ip_sans=true \
 
  +
Issuer: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, CN = Intermediate CA for service kubelet CLIENT_AUTH
allow_localhost=false \
 
client_flag=true \
+
Validity
server_flag=false \
+
Not Before: Nov 13 14:43:03 2022 GMT
  +
Not After : Nov 12 14:43:31 2027 GMT
enforce_hostnames=true \
 
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = system:masters, OU = system, CN = kube-apiserver-to-kubelet
key_usage="DigitalSignature,KeyEncipherment" \
 
  +
Subject Public Key Info:
ext_key_usage="ClientAuth" \
 
require_cn=true
+
Public Key Algorithm: rsaEncryption
  +
Public-Key: (2048 bit)
done
 
  +
Modulus:
  +
Exponent: 65537 (0x10001)
  +
X509v3 extensions:
  +
X509v3 Key Usage: critical
  +
Digital Signature, Key Encipherment
  +
X509v3 Extended Key Usage:
  +
TLS Web Client Authentication
  +
X509v3 Subject Key Identifier:
  +
22:7C:92:2B:A3:5F:53:0F:B5:7A:F2:84:FA:55:C9:51:DD:33:78:E8
  +
X509v3 Authority Key Identifier:
  +
50:35:A5:C5:B4:C6:FC:65:04:08:76:F7:FB:56:D3:76:6D:96:36:2F
  +
Authority Information Access:
  +
CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kubelet_client_auth/ca
  +
X509v3 Subject Alternative Name:
  +
DNS:kube-apiserver-to-kubelet
  +
X509v3 CRL Distribution Points:
  +
Full Name:
  +
URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kubelet_client_auth/crl
 
</PRE>
 
</PRE>
  +
|-
  +
|}
   
  +
==<code>kube-controller-manager</code>==
  +
  +
{| class="wikitable sortable"
  +
|+ Сертификаты K8s <code>kube-controller-manager</code>
  +
|-
  +
! Сервис который использует этот сертификат !! Параметр сервиса !! СА выпустивший сертификат !! Тип сертификата (серверный/клиентский/CA) !! Назначение !! Subject и подробности
  +
|-
  +
  +
| <code>kube-controller-manager</code>
  +
||
  +
<code>--tls-cert-file</code><BR>
  +
<code>--tls-private-key-file</code>
  +
||<code>kube_controller_manager_tls/</code>
  +
|| Серверный<BR>TLS Web Server<BR>Authentication
  +
||<code>kube-controller-manager</code> имеет свой API (по умолчанию - на порту 10257), в котором есть как минимум такие endpoints: /healthz, /readyz, /livez, /metrics.<BR>
  +
Этот сертификат служит для организации <code>TLS/HTTPS</code> для этого API
  +
<br>
  +
<br>
  +
Для разрешения доступа без авторизации служит параметр <code>--authorization-always-allow-paths=/healthz,/readyz,/livez,/metrics<code>, где перечислаются endpoints к которым можно получить доступ.
  +
|| Получить этот сертификат можно непосредственно подключившись к порту
 
<PRE>
 
<PRE>
  +
openssl s_client -connect kube-controller-manager.az1.k8s.cluster.home:10257
#!/bin/bash
 
  +
</PRE>
  +
<PRE>
  +
subject=C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = kube-controller-manager.az1.k8s.cluster.home
  +
issuer=C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kube-controller-manager TLS
  +
</PRE>
  +
Или в соответствующем файле (путь - в конфиге сервиса)
  +
<PRE>
  +
openssl x509 -noout -text -in kube-controller-manager-tls.pem
  +
</PRE>
  +
Certificate:
  +
Data:
  +
Version: 3 (0x2)
  +
Serial Number:
  +
68:35:c6:9e:d5:7d:c6:c8:ff:64:03:e7:fd:d8:c0:03:ff:ee:ec:50
  +
Signature Algorithm: sha256WithRSAEncryption
  +
Issuer: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kube-controller-manager TLS
  +
Validity
  +
Not Before: Nov 10 17:18:43 2022 GMT
  +
Not After : Nov 9 17:19:11 2027 GMT
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = kube-controller-manager.az1.k8s.cluster.home
  +
Subject Public Key Info:
  +
Public Key Algorithm: rsaEncryption
  +
Public-Key: (2048 bit)
  +
Modulus:
  +
...
  +
Exponent: 65537 (0x10001)
  +
X509v3 extensions:
  +
X509v3 Key Usage: critical
  +
Digital Signature, Key Encipherment
  +
X509v3 Extended Key Usage:
  +
TLS Web Server Authentication
  +
X509v3 Subject Key Identifier:
  +
7A:16:23:C5:0F:42:C2:D2:F2:FD:4C:2F:98:88:62:4D:C7:C6:E0:2A
  +
X509v3 Authority Key Identifier:
  +
3A:B0:CE:B4:3E:05:3F:7C:5F:87:24:BA:89:99:03:C6:9F:4C:2E:B1
  +
Authority Information Access:
  +
CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kube_controller_manager_tls/ca
  +
X509v3 Subject Alternative Name:
  +
DNS:kube-controller-manager.az1.k8s.cluster.home, DNS:kube-controller-manager.k8s.cluster.home, IP Address:10.0.12.1
  +
X509v3 CRL Distribution Points:
  +
Full Name:
  +
URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kube_controller_manager_tls/crl
  +
Signature Algorithm: sha256WithRSAEncryption
  +
Signature Value:
  +
...
  +
</PRE>
  +
|-
   
source ../env
 
   
N='kube-apiserver'
 
for AZ in $(seq 1 3);
 
do
 
DOMAIN="${N}.az${AZ}.k8s.cluster.home"
 
NAME_SERVER="${DOMAIN}-server"
 
NAME_CLIENT="${DOMAIN}-client"
 
   
cat << EOF > ${NAME_SERVER}-policy.hlc
 
path "${PKI_PATH}/issue/${NAME_SERVER}-role"
 
{
 
capabilities = ["read", "create", "list", "update"]
 
}
 
EOF
 
   
vault \
 
policy \
 
write \
 
${NAME_SERVER}-policy \
 
${NAME_SERVER}-policy.hlc
 
vault \
 
write \
 
auth/userpass/users/${NAME_SERVER}-user \
 
password=${NAME_SERVER}-password \
 
policies=" ${NAME_SERVER}-policy,default"
 
   
   
   
cat << EOF > ${NAME_CLIENT}-policy.hlc
 
path "${PKI_NAME}/issue/${NAME_CLIENT}-role"
 
{
 
capabilities = ["read", "create", "list", "update"]
 
}
 
EOF
 
   
vault \
 
policy \
 
write \
 
${NAME_CLIENT}-policy \
 
${NAME_CLIENT}-policy.hlc
 
vault \
 
write \
 
auth/userpass/users/${NAME_CLIENT}-user \
 
password=${NAME_CLIENT}-password \
 
policies=" ${NAME_CLIENT}-policy,default"
 
   
   
  +
done
 
  +
  +
| <code>kube-controller-manager</code>
  +
|| --root-ca-file
  +
||Root СА
  +
||Не Серверный<BR>Не Клиентский<BR>'''CA'''
  +
||Этот СА которым подписаны сертификаты для <code>HTTPS/TLS</code> для <code>kube-api-server</code> и он используется для проверки серверных сертификатов. Обладая этим CA можно проверить что подключение происходит к правильному <code>kube-apiserver</code>
  +
||
  +
<PRE>
  +
openssl x509 -noout -text -in /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem
  +
</PRE>
  +
<PRE>
  +
Certificate:
  +
Data:
  +
Version: 3 (0x2)
  +
Serial Number:
  +
0c:8b:42:a7:b4:5a:56:0e:b6:72:d0:40:03:70:5c:19:49:03:43:90
  +
Signature Algorithm: sha256WithRSAEncryption
  +
Issuer: C = Ukraine, L = Kharkov, street = app. 131 + street = Lui Pastera St. 322, postalCode = 61172, O = Home Network, OU = IT, CN = Root Certificate Authority for Home Network v2
  +
Validity
  +
Not Before: Nov 10 14:09:38 2022 GMT
  +
Not After : Nov 5 14:10:08 2042 GMT
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kube-apiserver TLS
 
</PRE>
 
</PRE>
   
  +
|-
  +
  +
  +
|}
  +
  +
==<code>kube-proxy</code>==
  +
Для <code>kube-proxy</code> за исключением <code>kubeconfig</code> сертификаты не используются
  +
  +
==<code>kube-scheduler</code>==
  +
  +
{| class="wikitable sortable"
  +
|+ Сертификаты K8s <code>kube-scheduler</code>
  +
|-
  +
! Сервис который использует этот сертификат !! Параметр сервиса !! СА выпустивший сертификат !! Тип сертификата (серверный/клиентский/CA) !! Назначение !! Subject и подробности
  +
  +
|-
  +
| <code>kube-scheduler</code>
  +
||<code>--tls-cert-file</code> <br> <code>--tls-private-key-file</code>
  +
||<code>kube_scheduler_tls</code>
  +
||Серверный<BR>TLS Web Server<BR>Authentication
  +
||
  +
<code>kube-scheduler</code> имеет свой API (по умолчанию - на порту 10259), в котором есть как минимум такие endpoints: /healthz, /readyz, /livez, /metrics.
  +
Этот сертификат служит для организации <code>TLS/HTTPS</code> для этого API<br><br>
  +
Для разрешения доступа без авторизации служит параметр <code>--authorization-always-allow-paths=/healthz,/readyz,/livez,/metrics<code>, где перечислаются endpoints к которым можно получить доступ.
  +
||
  +
Сертификат можно просмотреть:
  +
  +
<PRE> openssl s_client -connect kube-scheduler.az1.k8s.cluster.home:10259</PRE>
 
<PRE>
 
<PRE>
  +
subject=C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = kube-scheduler.az1.k8s.cluster.home
#!/bin/bash
 
  +
issuer=C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kube-scheduler TLS
  +
</PRE>
  +
Или посмотреть в файле (путь к файлу в параметрах сервиса)
  +
<PRE>openssl x509 -noout -text -in kube-scheduler-tls.pem
  +
</PRE>
  +
<PRE>
  +
Certificate:
  +
Data:
  +
Version: 3 (0x2)
  +
Serial Number:
  +
69:35:40:e1:3d:40:4f:f4:f4:0e:a7:a8:6b:cf:ab:5e:78:fd:76:e4
  +
Signature Algorithm: sha256WithRSAEncryption
  +
Issuer: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kube-scheduler TLS
  +
Validity
  +
Not Before: Nov 10 17:43:55 2022 GMT
  +
Not After : Nov 9 17:44:24 2027 GMT
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = kube-scheduler.az1.k8s.cluster.home
  +
Subject Public Key Info:
  +
Public Key Algorithm: rsaEncryption
  +
Public-Key: (2048 bit)
  +
Modulus:
  +
...
  +
Exponent: 65537 (0x10001)
  +
X509v3 extensions:
  +
X509v3 Key Usage: critical
  +
Digital Signature, Key Encipherment
  +
X509v3 Extended Key Usage:
  +
TLS Web Server Authentication
  +
X509v3 Subject Key Identifier:
  +
1E:54:7A:95:6C:DF:B4:99:1E:52:AC:33:42:E4:F0:FC:0C:64:55:A0
  +
X509v3 Authority Key Identifier:
  +
89:20:99:22:3A:5F:FB:50:26:01:42:BD:36:B6:F6:F3:B7:E4:51:A9
  +
Authority Information Access:
  +
CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kube_scheduler_tls/ca
  +
X509v3 Subject Alternative Name:
  +
DNS:kube-scheduler.az1.k8s.cluster.home, DNS:kube-scheduler.k8s.cluster.home, IP Address:10.0.12.1
  +
X509v3 CRL Distribution Points:
  +
Full Name:
  +
URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kube_scheduler_tls/crl
  +
Signature Algorithm: sha256WithRSAEncryption
  +
Signature Value:
  +
...
  +
</PRE>
  +
|-
  +
|}
   
  +
==<code>kubelet</code>==
source ../env
 
  +
Для <code>kubelet</code> сертификаты указываются в файле, определенном в параметре <code>--config=/etc/k8s/kubelet/kubelet-config.yaml</code>
  +
<PRE>
  +
kind: KubeletConfiguration
  +
apiVersion: kubelet.config.k8s.io/v1beta1
  +
authentication:
  +
anonymous:
  +
enabled: false
  +
webhook:
  +
enabled: true
  +
x509:
  +
clientCAFile: "/etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kubelet_client_auth.pem"
  +
authorization:
  +
mode: Webhook
  +
clusterDomain: "cluster.home"
  +
clusterDNS:
  +
- "10.80.0.10"
  +
resolvConf: "/run/systemd/resolve/resolv.conf"
  +
runtimeRequestTimeout: "15m"
  +
tlsCertFile: "/etc/k8s/kubelet/certs/tls/kubelet-tls.pem"
  +
tlsPrivateKeyFile: "/etc/k8s/kubelet/certs/tls/kubelet-tls.key"
  +
authorizationMode: Node,RBAC
  +
</PRE>
   
echo "---------ROLES---------------------"
 
vault \
 
list \
 
${PKI_PATH}/roles
 
echo "---------USERS---------------------"
 
vault \
 
list \
 
auth/userpass/users
 
echo "------------------------------"
 
   
   
for AZ in $(seq 1 3);
 
do
 
echo "------ AZ ${AZ} -----"
 
DOMAIN="${N}.az${AZ}.k8s.cluster.home"
 
NAME_SERVER="${DOMAIN}-server"
 
NAME_CLIENT="${DOMAIN}-client"
 
   
  +
{| class="wikitable sortable"
vault \
 
  +
|+ Сертификаты K8s <code>kubelet</code>
policy \
 
  +
|-
read \
 
  +
! Сервис который использует этот сертификат !! Параметр сервиса !! СА выпустивший сертификат !! Тип сертификата (серверный/клиентский/CA) !! Назначение !! Subject и подробности
${NAME_SERVER}-policy
 
   
  +
|-
vault \
 
  +
| <code>kubelet</code>
policy \
 
  +
||<code>clientCAFile</code>
read \
 
  +
||Root CA (другими словами этот СА подписан корневым СА, а сам является промежуточным СА)
${NAME_CLIENT}-policy
 
  +
|| Не серверный<BR>Не клиентский<BR>'''СА'''
  +
|| Предназначен для проверки сертификатов с которыми подключаются клиенты (насколько я знаю это только <code>kube-apiserver</code>, в его параметрах это <code>--kubelet-client-certificate</code> и
  +
<code>--kubelet-client-key</code>.
  +
||
   
  +
Сертификат можно просмотреть:
vault \
 
  +
<PRE>
read \
 
  +
openssl x509 -noout -text -in /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kubelet_client_auth.pem
auth/userpass/users/${NAME_SERVER}-user
 
  +
</PRE>
vault \
 
  +
<PRE>
read \
 
  +
Certificate:
auth/userpass/users/${NAME_SERVER}-user
 
  +
Data:
  +
Version: 3 (0x2)
  +
Serial Number:
  +
6e:c2:5c:3f:d0:0d:de:a9:bc:8c:2f:78:39:b9:ce:c6:c4:0f:ce:86
  +
Signature Algorithm: sha256WithRSAEncryption
  +
Issuer: C = Ukraine, L = Kharkov, street = app. 131 + street = Lui Pastera St. 322, postalCode = 61172, O = Home Network, OU = IT, CN = Root Certificate Authority for Home Network v2
  +
Validity
  +
Not Before: Nov 4 09:26:50 2022 GMT
  +
Not After : Oct 30 09:27:20 2042 GMT
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, CN = Intermediate CA for service kubelet CLIENT_AUTH
  +
Subject Public Key Info:
  +
Public Key Algorithm: rsaEncryption
  +
Public-Key: (2048 bit)
  +
Modulus:
  +
...
  +
Exponent: 65537 (0x10001)
  +
X509v3 extensions:
  +
X509v3 Key Usage: critical
  +
Certificate Sign, CRL Sign
  +
X509v3 Basic Constraints: critical
  +
CA:TRUE
  +
X509v3 Subject Key Identifier:
  +
50:35:A5:C5:B4:C6:FC:65:04:08:76:F7:FB:56:D3:76:6D:96:36:2F
  +
X509v3 Authority Key Identifier:
  +
02:F8:85:2B:75:F8:E1:1C:69:28:30:32:21:2D:86:71:AF:AB:EC:3C
  +
Authority Information Access:
  +
CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_root_ca/ca
  +
X509v3 CRL Distribution Points:
  +
Full Name:
  +
URI:http://vault.home:8200/v1/k8s_pki_root_ca/crl
  +
...
  +
</PRE>
  +
|-
   
  +
done
 
  +
  +
  +
| <code>kubelet</code>
  +
||<code>tlsCertFile</code>, <code>tlsPrivateKeyFile</code>
  +
||<code>kubelet_tls</code>
  +
||Серверный<BR>TLS Web Server<BR>Authentication
  +
|| Используется для <code>HTTP/TLS</CODE> для API <code>kubelet</code> (к которому подключается <code>kube-apiserver</code>, важный параметр - <code>kubelet</code>должен регистрироваться в <code>kube-apiserver</code> с одним из имен разрешенных для использования в сертификате.
  +
||
  +
Обратить внимание что в сертификате прописаны несколько возможных имен
  +
* DNS:kubelet.az1.k8s.cluster.home
  +
* DNS:worker01.az1.k8s.cluster.home - используется как основное, и указано в параметрах <code>kubelet</code>: <code>--hostname-override=${KUBELET_HOSTNAME_OVERRIDE}</code> В примере это '''worker01.az1.k8s.cluster.home'''
  +
* IP Address:10.0.12.1
  +
Сертификат можно просмотреть:
  +
<PRE>
  +
openssl x509 -noout -text -in /etc/k8s/kubelet/certs/tls/kubelet-tls.pem
 
</PRE>
 
</PRE>
  +
<PRE>
  +
Certificate:
  +
Data:
  +
Version: 3 (0x2)
  +
Serial Number:
  +
18:6e:c4:32:a9:b7:ba:44:55:0d:52:df:d3:fb:e4:75:f0:29:7b:72
  +
Signature Algorithm: sha256WithRSAEncryption
  +
Issuer: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kubelet TLS
  +
Validity
  +
Not Before: Nov 13 16:08:12 2022 GMT
  +
Not After : Nov 12 16:08:41 2027 GMT
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = kubelet.az1.k8s.cluster.home
  +
Subject Public Key Info:
  +
Public Key Algorithm: rsaEncryption
  +
Public-Key: (2048 bit)
  +
Modulus:
  +
...
  +
Exponent: 65537 (0x10001)
  +
X509v3 extensions:
  +
X509v3 Key Usage: critical
  +
Digital Signature, Key Encipherment
  +
X509v3 Extended Key Usage:
  +
TLS Web Server Authentication
  +
X509v3 Subject Key Identifier:
  +
42:97:B0:18:FC:0A:03:29:02:92:68:A5:F3:5B:A5:48:23:F1:14:DC
  +
X509v3 Authority Key Identifier:
  +
F1:9C:3B:FB:01:4E:9A:3F:F5:E8:28:CE:99:60:9F:E3:5E:51:DA:C8
  +
Authority Information Access:
  +
CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kubelet_tls/ca
  +
X509v3 Subject Alternative Name:
  +
DNS:kubelet.az1.k8s.cluster.home, DNS:worker01.az1.k8s.cluster.home, IP Address:10.0.12.1
  +
X509v3 CRL Distribution Points:
  +
Full Name:
  +
URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kubelet_tls/crl
  +
Signature Algorithm: sha256WithRSAEncryption
  +
Signature Value:
  +
...
  +
</PRE>
  +
|-
   
  +
|}
==Пример получения сертефикатов==
 
на конечных нодах используя имя пользователя и пароль а так же переменную AZ определнную на нодах индивидуально ([[Kubernetes_the_hard_way_kube_apiserver#--tls-cert-file_--tls-private-key-file|Сертефикаты для <code>kube-apiserver</code> <code>--tls-cert-file</code> и <code>--tls-private-key-file</code>]])
 
   
  +
=Файлы <code>kubeconfig</code>=
  +
Некоторые сервисы используют <code>kubeconfig</code> для авторизации у <code>kube-apiserver</code>, в том числе плюс-минус такой же конфиг используется для авторизации администратора
  +
<br>
  +
==Описание формата <code>kubeconfig</code>==
  +
Разберем пример файла (для примера взят конфиг от <code>kubelet</code>)
 
<PRE>
 
<PRE>
  +
apiVersion: v1
#!/bin/bash
 
  +
clusters:
  +
- cluster:
  +
certificate-authority: "/etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem"
  +
server: https://kube-apiserver.k8s.cluster.home:443
  +
name: kubernetes-the-hardest-way
  +
contexts:
  +
- context:
  +
cluster: kubernetes-the-hardest-way
  +
user: system:node:worker01.az1.k8s.cluster.home
  +
name: default
  +
current-context: default
  +
kind: Config
  +
preferences: {}
  +
users:
  +
- name: system:node:worker01.az1.k8s.cluster.home
  +
user:
  +
client-certificate: /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.pem
  +
client-key: /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.key
  +
</PRE>
   
  +
===clusters===
set -eu${DEBUG:+x}
 
  +
В этой секции описываются кластера, а именно
  +
* имя кластера
  +
<code> name: kubernetes-the-hardest-way</code>
  +
* Адрес по которому доступен <code>kube-apiserver</code>
  +
<code>server: https://kube-apiserver.k8s.cluster.home:443</code>
  +
* CA файл, с помощью которого можно проверить что подключение происходит к правильному кластеру
  +
<code>certificate-authority: /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem</code>
   
  +
Имя кластера можно выбрать произвольно, это имя служит только для связывания различных секций файла в единый контекст
PKI_NAME="k8s_pki_intermediate_ca_for_service_kube_apiserver_tls"
 
CERTS_PATH="/etc/k8s/kube-apiserver/certs/tls"
 
mkdir -p ${CERTS_PATH}
 
   
  +
===users===
N='kube-apiserver'
 
  +
В этой секции содержится описание пользователя, а именно:
#AZ=1
 
  +
* Имя пользователя
DOMAIN="${N}.az${AZ}.k8s.cluster.home"
 
  +
<code>- name: system:node:worker01.az1.k8s.cluster.home</code>
NAME_SERVER="${DOMAIN}-server"
 
  +
* Способ авторизации и параметры авторизации (в этом случае используются клиентские сертификаты
NAME_CLIENT="${DOMAIN}-client"
 
  +
** <code>client-certificate: /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.pem</code>
BALANCER_DOMAIN="${N}.k8s.cluster.home"
 
  +
** <code>client-key: /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.key</code>
IP="10.0.${AZ}2.1"
 
  +
<BR>
vault \
 
  +
'''Имя пользователя в этой секции - просто идентификатор и никак не участвует в процессе авторизации, а служит только для связывания различных секций файла в единый контекст'''<br>
login \
 
  +
<BR>
-method=userpass \
 
  +
<BR>
username="${NAME_SERVER}-user" \
 
  +
<big><big>'''Важно: Фактические имя пользователя и группа описаны в полях <code>CN</code> (имя пользователя) и <code>O</code> (группа) при авторизации с помощью клиентских сертификатов !!!'''</big></big>
password="${NAME_SERVER}-password"
 
  +
<BR>
  +
<br>Имя в сертификате может не совпадать с полем <code>name</code>, иногда они совпадают для удобства конфигурирования но не более того.
   
  +
===contexts===
  +
Эта секция служит для связывания секций <code>users</code> и <code>clusters</code> и по сути просто сообщает для какого кластера какой пользователь используется.
  +
<br>
  +
Имя контекста <code>name</code> служит для идентификации, так как в одном файле может быть описано множество контекстов (с возможностью переключения между ними)
  +
<BR>
  +
Пример файла следует читать так:<br>
  +
Для контекста с именем <code>default</code> использовать СА и адрес определенные в секции <code>clusters</code> в секции где имя кластера <code>kubernetes-the-hardest-way</code>,<br>
  +
для авторизации использовать данные из секции <code>users</code> где имя <code>name</code> - <code>system:node:worker01.az1.k8s.cluster.home</code>
  +
<br>
  +
При этом слово <code>default</code> в имени контекста не несет какого-то магического смысла - это просто название, на которое можно сослаться, и не более того.
  +
<PRE>
  +
contexts:
  +
- context:
  +
cluster: kubernetes-the-hardest-way
  +
user: system:node:worker01.az1.k8s.cluster.home
  +
name: default
  +
</PRE>
   
  +
===current-contex===
DATE=$(date +%Y%m%dT%H%M)
 
  +
Эта секция определяет какой контекст будет использоваться по-умолчанию
USERNAME="${N}-${AZ}-tls"
 
  +
<br>
  +
В примере ниже используется по умолчанию контекст с именем <code>default</code>, и здесь слово '''default''' не имеет никакого магического значение - это просто имя контекста определенного в секции <code>contexts</code> и не более того
  +
<PRE>
  +
current-context: default
  +
</PRE>
  +
==Общие части для всех kubeconfig==
  +
===clusters===
  +
Так-как это все <code>kubeconfig</code>для одного кластера то у всех их есть общая часть
  +
<PRE>
  +
clusters:
  +
- cluster:
  +
certificate-authority-data: LS0tLS1CRUdJ ... skipped long line ...
  +
server: https://kube-apiserver.k8s.cluster.home:443
  +
name: kubernetes-the-hardest-way
  +
</PRE>
  +
<PRE>
  +
clusters:
  +
- cluster:
  +
certificate-authority: /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem
  +
server: https://kube-apiserver.k8s.cluster.home:443
  +
</PRE>
  +
Отличие тут только в том что для админа данные сертификата включены в файл <code>kubeconfig</code> для того что бы его было проще передавать между пользователями
  +
<br>
  +
Для сервисов же указан путь к СА сертификату <code>kube-apiserver</code>
  +
<br>
  +
Назначения этого сертификата - проверка того что подключение идет к тому кластеру к которому ожидается.
  +
===users===
  +
Секция <code>users</code> тоже имеет похожий вид, но тут для каждого сервиса указан свой пользователь и своя группа внутри сертификата (в поле <code>CN</code> указано имя пользователя, в поле <code>O</code> указана группа)<br>
  +
Так-как все файлы очень похожи далее я буду акцентировать внимание на пользователях и группах
  +
<br>
  +
'''Все клиентские сертификаты подписаны одним и тем же СА - <code>kube_apiserver_client_auth</code>''' и процесс <code>kube-apiserver</code> может проверить каждый из них используя СА указанный в параметре <code>--client-ca-file</code> сертификат.
  +
<PRE>
  +
users:
  +
- name: some-name
  +
user:
  +
client-certificate: some-cert.pem
  +
client-key: some-key.key
  +
</PRE>
   
  +
==Admin==
echo "========"
 
  +
<PRE>
vault \
 
  +
apiVersion: v1
write \
 
  +
clusters:
-format=json \
 
  +
- cluster:
${PKI_NAME}/issue/${NAME_SERVER}-role \
 
  +
certificate-authority-data: LS0tLS1CRUdJ ... skipped long line ...
common_name="${DOMAIN}" \
 
  +
server: https://kube-apiserver.k8s.cluster.home:443
alt_names="${DOMAIN},${BALANCER_DOMAIN}" \
 
  +
name: kubernetes-the-hardest-way
ip_sans="${IP}" \
 
  +
contexts:
ca=false \
 
  +
- context:
ttl="43800h" \
 
  +
cluster: kubernetes-the-hardest-way
> ${CERTS_PATH}/${USERNAME}.crt.json
 
  +
user: admin
  +
name: default
  +
current-context: default
  +
kind: Config
  +
preferences: {}
  +
users:
  +
- name: admin
  +
user:
  +
client-certificate-data: LS0tLS1CRUdJT ... skipped long line ...
  +
client-key-data: LS0tLS1CRUdJTiB ... skipped long line
  +
</PRE>
  +
Просмотр сертификата
  +
<PRE>
  +
openssl x509 -noout -text -in admin.pem | grep "Subject:"
  +
</PRE>
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = system:masters, OU = system, CN = admin
  +
</PRE>
  +
* группа <code> O = system:masters</code>
  +
* Пользователь <code>CN = admin</code>
  +
* Права назначаются СlusterRoleBinding на группу:
  +
<PRE>
  +
kind: Group
  +
name: system:masters
  +
</PRE>
  +
'''Имя ClusterRoleBinding получено методом полного перебора что бы понять в каком из них происходит назначение прав на группу <code>system:masters</code>. Для остальных групп - аналогично, хотя часто имя binding совпадает с названием группы. '''
  +
<BR>
  +
Полный вывод:
  +
<PRE>
  +
kubectl get clusterrolebinding cluster-admin -o yaml
  +
</pre>
  +
<PRE>
  +
apiVersion: rbac.authorization.k8s.io/v1
  +
kind: ClusterRoleBinding
  +
metadata:
  +
annotations:
  +
rbac.authorization.kubernetes.io/autoupdate: "true"
  +
creationTimestamp: "2022-11-08T09:41:39Z"
  +
labels:
  +
kubernetes.io/bootstrapping: rbac-defaults
  +
name: cluster-admin
  +
resourceVersion: "145"
  +
uid: cea153e2-ead5-4fcc-8810-c615d1204fec
  +
roleRef:
  +
apiGroup: rbac.authorization.k8s.io
  +
kind: ClusterRole
  +
name: cluster-admin
  +
subjects:
  +
- apiGroup: rbac.authorization.k8s.io
  +
kind: Group
  +
name: system:masters
  +
</PRE>
   
  +
==<code>kube-controller-manager</code>==
cat \
 
  +
<PRE>
${CERTS_PATH}/${USERNAME}.crt.json \
 
  +
apiVersion: v1
| jq -r '.data.private_key' > ${CERTS_PATH}/${USERNAME}-${DATE}.key
 
  +
clusters:
  +
- cluster:
  +
certificate-authority: /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem
  +
server: https://kube-apiserver.k8s.cluster.home:443
   
  +
name: kubernetes-the-hardest-way
cat \
 
  +
contexts:
${CERTS_PATH}/${USERNAME}.crt.json \
 
  +
- context:
| jq -r '.data.certificate' > ${CERTS_PATH}/${USERNAME}-${DATE}.pem
 
  +
cluster: kubernetes-the-hardest-way
  +
user: system:kube-controller-manager
  +
name: default
  +
current-context: default
  +
kind: Config
  +
preferences: {}
  +
users:
  +
- name: system:kube-controller-manager
  +
user:
  +
client-certificate: /etc/k8s/kube-controller-manager/certs/client_auth/kube-apiserver-client_auth.pem
  +
client-key: /etc/k8s/kube-controller-manager/certs/client_auth/kube-apiserver-client_auth.key
  +
</PRE>
  +
Аналогично админу - можно проверить пользователя, группу и права
  +
<PRE>
  +
openssl x509 -noout -text -in /etc/k8s/kube-controller-manager/certs/client_auth/kube-apiserver-client_auth.pem | grep "Subject:"
  +
</PRE>
  +
<PRE>
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = system:kube-controller-manager, OU = system, CN = system:kube-controller-manager
  +
</PRE>
  +
<PRE>
  +
kubectl get clusterrolebinding system:kube-controller-manager -o yaml
  +
</PRE>
  +
<PRE>
  +
apiVersion: rbac.authorization.k8s.io/v1
  +
kind: ClusterRoleBinding
  +
metadata:
  +
annotations:
  +
rbac.authorization.kubernetes.io/autoupdate: "true"
  +
creationTimestamp: "2022-11-08T09:41:39Z"
  +
labels:
  +
kubernetes.io/bootstrapping: rbac-defaults
  +
name: system:kube-controller-manager
  +
resourceVersion: "151"
  +
uid: 53b7d64d-f3f6-49bc-8954-6c8eea6fb444
  +
roleRef:
  +
apiGroup: rbac.authorization.k8s.io
  +
kind: ClusterRole
  +
name: system:kube-controller-manager
  +
subjects:
  +
- apiGroup: rbac.authorization.k8s.io
  +
kind: User
  +
name: system:kube-controller-manager
  +
</PRE>
   
  +
==<code>kube-proxy</code>==
cat \
 
  +
<PRE>
${CERTS_PATH}/${USERNAME}.crt.json \
 
  +
apiVersion: v1
| jq -r '.data.ca_chain[]' >> ${CERTS_PATH}/${USERNAME}-${DATE}.pem
 
  +
clusters:
  +
- cluster:
  +
certificate-authority: /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem
  +
server: https://kube-apiserver.k8s.cluster.home:443
  +
name: kubernetes-the-hardest-way
   
  +
contexts:
ln -sf ${CERTS_PATH}/${USERNAME}-${DATE}.key ${CERTS_PATH}/${N}-tls.key
 
  +
- context:
ln -sf ${CERTS_PATH}/${USERNAME}-${DATE}.pem ${CERTS_PATH}/${N}-tls.pem
 
  +
cluster: kubernetes-the-hardest-way
  +
user: system:kube-proxy
  +
name: default
  +
current-context: default
  +
  +
kind: Config
  +
preferences: {}
  +
users:
  +
- name: system:kube-proxy
  +
user:
  +
client-certificate: /etc/k8s/kube-proxy/certs/client_auth/kube-apiserver-client_auth.pem
  +
client-key: /etc/k8s/kube-proxy/certs/client_auth/kube-apiserver-client_auth.key
 
</PRE>
 
</PRE>
   
  +
Аналогично админу - можно проверить пользователя, группу и права
=СA для клиентов <code>kube-apiserver</code>=
 
  +
<PRE>
  +
openssl x509 -noout -text -in /etc/k8s/kube-proxy/certs/client_auth/kube-apiserver-client_auth.pem | grep "Subject:"
  +
</PRE>
  +
<PRE>
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = system:node-proxier, OU = system, CN = system:kube-proxy
  +
</PRE>
  +
<PRE>
  +
kubectl get clusterrolebinding system:node-proxier -o yaml
  +
</PRE>
  +
<PRE>
  +
apiVersion: rbac.authorization.k8s.io/v1
  +
kind: ClusterRoleBinding
  +
metadata:
  +
annotations:
  +
rbac.authorization.kubernetes.io/autoupdate: "true"
  +
creationTimestamp: "2022-11-08T09:41:39Z"
  +
labels:
  +
kubernetes.io/bootstrapping: rbac-defaults
  +
name: system:node-proxier
  +
resourceVersion: "150"
  +
uid: 336cfde3-8777-44aa-a70d-e7d1aebd148f
  +
roleRef:
  +
apiGroup: rbac.authorization.k8s.io
  +
kind: ClusterRole
  +
name: system:node-proxier
  +
subjects:
  +
- apiGroup: rbac.authorization.k8s.io
  +
kind: User
  +
name: system:kube-proxy
  +
</PRE>
  +
  +
==<code>kube-scheduler</code>==
  +
<PRE>
  +
apiVersion: v1
  +
clusters:
  +
- cluster:
  +
certificate-authority: /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem
  +
server: https://kube-apiserver.k8s.cluster.home:443
  +
name: kubernetes-the-hardest-way
  +
contexts:
  +
- context:
  +
cluster: kubernetes-the-hardest-way
  +
user: system:kube-scheduler
  +
name: default
  +
current-context: default
  +
kind: Config
  +
preferences: {}
  +
users:
  +
- name: system:kube-scheduler
  +
user:
  +
client-certificate: /etc/k8s/kube-scheduler/certs/client_auth/kube-apiserver-client_auth.pem
  +
client-key: /etc/k8s/kube-scheduler/certs/client_auth/kube-apiserver-client_auth.key
  +
</PRE>
  +
  +
<PRE>
  +
openssl x509 -noout -text -in /etc/k8s/kube-scheduler/certs/client_auth/kube-apiserver-client_auth.pem | grep "Subject:"
  +
</PRE>
  +
<PRE>
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = system:kube-scheduler, OU = system, CN = system:kube-scheduler
  +
</PRE>
  +
  +
<PRE>
  +
kubectl get clusterrolebinding system:kube-scheduler -o yaml
  +
</PRE>
  +
<PRE>
  +
apiVersion: rbac.authorization.k8s.io/v1
  +
kind: ClusterRoleBinding
  +
metadata:
  +
annotations:
  +
rbac.authorization.kubernetes.io/autoupdate: "true"
  +
creationTimestamp: "2022-11-08T09:41:39Z"
  +
labels:
  +
kubernetes.io/bootstrapping: rbac-defaults
  +
name: system:kube-scheduler
  +
resourceVersion: "153"
  +
uid: 4a50831a-e5f8-4a77-8aef-cea46ac24231
  +
roleRef:
  +
apiGroup: rbac.authorization.k8s.io
  +
kind: ClusterRole
  +
name: system:kube-scheduler
  +
subjects:
  +
- apiGroup: rbac.authorization.k8s.io
  +
kind: User
  +
name: system:kube-scheduler
  +
</PRE>
  +
  +
==<code>kubelet</code>==
  +
<PRE>
  +
apiVersion: v1
  +
clusters:
  +
- cluster:
  +
certificate-authority: "/etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem"
  +
server: https://kube-apiserver.k8s.cluster.home:443
  +
name: kubernetes-the-hardest-way
  +
contexts:
  +
- context:
  +
cluster: kubernetes-the-hardest-way
  +
user: system:node:worker01.az1.k8s.cluster.home
  +
name: default
  +
current-context: default
  +
kind: Config
  +
preferences: {}
  +
users:
  +
- name: system:node:worker01.az1.k8s.cluster.home
  +
user:
  +
client-certificate: /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.pem
  +
client-key: /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.key
  +
</PRE>
  +
Аналогично админу - можно проверить пользователя, группу и права
  +
<PRE>
  +
openssl x509 -noout -text -in /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.pem | grep "Subject:"
  +
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = system:nodes, OU = system, CN = system:node:worker01.az1.k8s.cluster.home
  +
</PRE>
  +
Тут есть некоторая тонкость - имя <code>worker01.az1.k8s.cluster.home</code>должно совпадать с хостнеймом или с параметром <code>--hostname-override</code>, и сертификат у <code>kubelet</code>должен позволять использовать это доменное имя (обратить внимание на [[Vault_PKI_Intermediate_CAs_for_ALL_SERVICES_Kubernetes_the_hard_way_v2#kubelet|описание <code>HTTPS/TLS</code> сертификатов <code>kubelet</code>]], описание tlsCertFile, tlsPrivateKeyFile)
  +
<br>
  +
В остальном отличий нет
  +
<PRE>
  +
kubectl get clusterrolebinding system:node -o yaml
  +
</PRE>
  +
<PRE>
  +
apiVersion: rbac.authorization.k8s.io/v1
  +
kind: ClusterRoleBinding
  +
metadata:
  +
annotations:
  +
rbac.authorization.kubernetes.io/autoupdate: "true"
  +
creationTimestamp: "2022-11-08T09:41:39Z"
  +
labels:
  +
kubernetes.io/bootstrapping: rbac-defaults
  +
name: system:node
  +
resourceVersion: "155"
  +
uid: fec38e51-4833-41af-a46e-fb482e5941b4
  +
roleRef:
  +
apiGroup: rbac.authorization.k8s.io
  +
kind: ClusterRole
  +
name: system:node
  +
</PRE>

Текущая версия на 20:05, 20 ноября 2022


Эта страница - часть большой статьи про CA используемые в k8s: Vault_PKI_Kubernetes_the_hard_way_v2


Прежде чем начать читать

Эта часть описывает какие именно сертификаты и СА для чего используются разными сервисами - ее можно прочитать перед тем как настаивать Vault для понимания того что и зачем настраивается или после.
Описание настойки Vault для выпуска сертификатов

Некоторые термины и замечания

  • CA: certificate authority или certification authority ( на русском это звучит как Центр Сертефикации)

В контексте документа может иметь несколько возможных значений - как собственно центр выпуска сертификатов, так и сам корневой (или промежуточный сертификат) этого центра. По сути, сертификат СА, который используется для подписания клиентских и серверных сертификатом не только не является секретным, но наоборот должен быть доступен для доступа так как именно он используется для проверки валидности выпущенных сертификатов

В случае с PKI на основе Vault СA доступны для скачивания без авторизации.



Есть 2 типа сертификатов (конечно их больше но в K8s используется 2 типа). Потому в целом (кроме etcd) есть разделение СА в том числе и по типу выпускаемых сертификатов

  • client_auth - этот суффикс у СА используется в значении "сертификаты используются для авторизации" (другими словами - не используются для организации http)
  • tls - этот суффикс у СА используется в значении "сертификаты используются для организации https/TLS"


  • В целом, если не использовать Vault а использовать другой PKI, будь то на основе OpenSSL или чего-то другого ничего принципиально не меняется, и ничего специфичного для PKI Vault в документе нет
  • В этом разделе нет команд по получению сертификатов или настройке PKI, а только описание параметров сервисов, их назначения и свойства сертификатов которые используются.

В целом для лучшего понимания можно держать в голове такую схему



+-------------+                                     +---------------------------------------------+                                                   +-------------------------------------------------+
| Корневой CA | -------->  им подписан  ------->    |Промежуточный CA для сервиса X и пользования | ------------->     им подписан ---------->        | Конечный сертификат которым пользуется сервис Y |
+-------------+    (процедура подписания          ) +---------------------------------------------+        (процедура подписания скрыта           )   +-------------------------------------------------+
                   (скрыта внутри Vault и         )                                                        (внутри Vault и требует авторизации    )
                   (требует рутовый токен от Vault)                                                        (с логином и паролем, который выдается )
                                                                                                           (тому сервису которому нужен сертификат)

Пример 1

  • Сервису kubelet нужен сертификат для того что бы авторизоваться у kube-apiserver
  • Создается промежуточный CA (внутри Vault) который будет иметь возможность выписывать такие сертификаты, в этом пример это будет СА k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth/
  • Сертификат этого промежуточного СА подписывается (или иногда говорят "заверяется", что в контексте SSL синонимы) Корневым СА (на схеме)
    • k8s_pki_intermediate_ca_for_service_ - префикс общий для всех СA которые используются для K8s (в случае Vault используется например для более чем одного кластера, или еще зачем-то)
    • kube_apiserver - имя сервиса, который будет пользоваться сертификатами, в данном контексте "пользоваться" означает то что kube-apiserverбудет проверять эти сертификаты, а не то что они будут непосредственно указаны в его конфигурационных файлах.
    • client_auth - назначение сертификатов которые будут создаваться с помощью этого CA
    • Создаются правила пользования этим СА - какие пользователи и с какими параметрами могут получать сертификаты для авторизации у kube-apiserver, ограничения касаются CN (подробнее об этом - о настройке PKI для Vault, как например настроено получение сертификатов для Etcd
    • Данные для авторизации выдаются сервису, которому нужен сертификат (в примере - kubelet) который используя API Vault может сам выпустить сертификат (с учетом ограничений CN) и при необходимости перевыпустить его.
    • Автоматизация перевыпуска сертификатов - дело будущей настройки сервисов и будет описана в других разделах



Пример 2

  • Сервису kube-apiserver нужно открыть порт и принимать HTTPS/TLS подключения (авторизация после подключения в этом примере пропущена)
  • Для этого требуется серверный сертификат
  • Для выпуска таких сертификатов создается СА k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/, промежуточный сертификат заверяется корневым
  • отличие - в том что он предназначен для HTTPS/TLS и имеет другой суффикс
  • для сервиса kube-apiserver создается пользователь и пароль в Vault (с ограничениями на CN)
  • имея доступ к API Vault, сервис kube-apiserver может выписать себе сертификат с нужным CN (в пределах ограничений) а так же перевыпустить просроченный сертификат



Отличие между примерами в том, что хотя в обоих случаях СА имеют в имени kube-apiserver

  • k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth
  • k8s_pki_intermediate_ca_for_service_kube_apiserver_tls

В первом пример сертификаты выписанные CA с пометкой client_auth используются для того что бы подключиться к kube-apiserver и не фигурируют в его конфигах Во втором же примере сертификаты выписанные СА с пометкой tls используются самим kube-apiserver

Создание СА для работы кластера K8s

Соглашение о путях к файлам

  • Путь к СА: /etc/k8s/shared/certs/CA
  • Все файлы СА (далее по тексту просто СА) можно загрузить из Vault в любой момент, без авторизации. Эти файлы СА (БЕЗ ключа!) не являются секретными, и могут использоваться только для проверки сертификатов (что бы проверить требуется вся цепочка - Корневой CA -- Промежуточный СА -- Сертификат
  • Скрипт загрузки проходится по списку сервисов и загружает с соответствующих endpoints СA в файлы :
  1. kube_apiserver
  2. kube_controller_manager
  3. kube_scheduler
  4. kubelet

в Vault и загружает промежуточные сертификаты в директорию/etc/k8s/shared/certs/CA


K8s использует СА для выписывания сертификатов 2 типов

  • "Обычные" серверные сертификаты (CN = domain)
  • Сертификаты используемые для авторизации - клиентские (CN=username, O=groupname)


Всего в Vault настроены такие СА:

k8s_pki_intermediate_ca_for_service_etcd/                           pki          pki_13a87e77          PKI Intermediate CA for ETCd service
k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth/     pki          pki_622072da          PKI Intermediate CA for K8S: kube-apiserver CLIENT_AUTH
k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/             pki          pki_d8737474          PKI Intermediate CA for K8S: kube-apiserver TLS
k8s_pki_intermediate_ca_for_service_kube_controller_manager_tls/    pki          pki_34a63553          PKI Intermediate CA for K8S: kube-controller-manager TLS
k8s_pki_intermediate_ca_for_service_kube_scheduler_tls/             pki          pki_5b5f53f5          PKI Intermediate CA for K8S: kube-scheduler TLS
k8s_pki_intermediate_ca_for_service_kubelet_client_auth/            pki          pki_4f1df8fd          PKI Intermediate CA for K8S: kubelet CLIENT_AUTH
k8s_pki_intermediate_ca_for_service_kubelet_tls/                    pki          pki_47e7182a          PKI Intermediate CA for K8S: kubelet TLS
k8s_pki_root_ca/                                                    pki          pki_8b6cae1e          PKI k8s Root CA

Полный список СА (промежуточных СА!)

  • Всего существует 8 СА которые используются в этой инсталляции (один из них - корневой СА).


Если верить документации, то это не предел - каждый файл с CA в настройках сервисов может содержать
более одного сертификата, другими словами 2 процесса kube-apiserver вполне могут использовать разные CA

В частных случаях можно упростить настройку, и вообще использовать 1 СА
Эта инсталляция подразумевает настойку PKI средней сложности.

k8s_pki_intermediate_ca_for_service_etcd/

k8s_pki_intermediate_ca_for_service_etcd/ - используется для клиентских и серверных сертификатов etcd. Строго говоря, не является частью k8s и настраивается отдельно (Настройка PKI для etcd)

  • для шифрования endpoints
  • для авторизации клиентов

k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth/

k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/

  • k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth/ - используется для клиентских сертефикатов kube-apiserver, по которым API проверяет права пользователей.
  • k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/ Используется для обеспечения https при подключении к kube-apiserver. При этом происходит двухсторонняя проверка
    • Все клиенты (как сервисы, часть k8s, например kube-controller-manager, kube-scheduler, kubectl так и для администрирования) должны обладать CA (который как и прочие СА не является секретным), для того что бы иметь возможность проверить кластер, другими словами быть уверенным в том что подключаются туда куда ожидают.

Часть kubeconfig отвечающая за этот сертификат:

clusters:
- cluster:
    certificate-authority: /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem
    server: https://kube-apiserver.k8s.cluster.home:443
    • Со своей стороны сервер проверяет как то что сертефикат клиента подписан правильным СА (k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth/), так и поля CN O в сертификате, которые используются как имя пользователя и группа. Имена групп выбраны не случайно - для них уже есть (или можно создать свои!) ClusterRoleBindings

k8s_pki_intermediate_ca_for_service_kube_controller_manager_tls/

  • k8s_pki_intermediate_ca_for_service_kube_controller_manager_tls/ - используется для обеспечения https, серверные сетефикаты для kube-controller-manager (Серверные сертификаты нужны для API)

k8s_pki_intermediate_ca_for_service_kube_scheduler_tls/

  • k8s_pki_intermediate_ca_for_service_kube_scheduler_tls/ - используется для обеспечения https, серверные сетефикаты для kube-scheduler (Серверные сертификаты нужны для API)

k8s_pki_intermediate_ca_for_service_kubelet_client_auth/

k8s_pki_intermediate_ca_for_service_kubelet_tls/

k8s_pki_intermediate_ca_for_service_kubelet_client_auth/ kubelet в целом устроен аналогично kube-apiserver, и использует 2 СА - один для авторизации клиентов (в случае с kubelet клиентом выступает kube-apiserver), а второй CA используется для обеспечения https

  • У kube-apiserver есть настройка --kubelet-certificate-authority - это файл СА k8s_pki_intermediate_ca_for_service_kubelet_tls/ (другими словами, это тот СА который выписал серверный сертификат для обеспечения HTTPS/TLS API kubelet ( Порт 10250).

Просмотреть содержимое можно например командой

openssl s_client -connect  127.0.0.1:10250

Используя СА k8s_pki_intermediate_ca_for_service_kubelet_tls kube-apiserver может точно знать что он обращается к нужному kubelet, так как его серверный сертефикат подписан этим СА


  • --kubelet-client-certificate--kubelet-client-key содрежат сертификат, выписанный помощью СА k8s_pki_intermediate_ca_for_service_kubelet_client_auth/ и содержат имя пользователя и группу с которыми kube-apiserver авторизуется у kubelet


Например: O = system:masters, OU = system, CN = kube-apiserver-to-kubelet

При этом по-умолчанию соответствующие ClustetRoleBinding отсутствуют, и перед подключением kubelet их требуется создать дополнительно. (эта часть настройки выполняется при конфигурировании kube-apiserver


  • k8s_pki_intermediate_ca_for_service_kubelet_tls/ - используется для обеспечения https, серверные сетефикаты

k8s_pki_root_ca/

  • k8s_pki_root_ca/ - это корневой СА которым подписаны все промежуточные СА, и его сертификат СА обязательно требуется распространить по всем хостам так как он является полностью доверенным (в пределах этой инсталляции, конечно)

Полный список сертификатов с кратким описанием

Это CA (в VAULT, c именами и описаниями) которые используются для выпуска сертификатов для k8s)

k8s_pki_intermediate_ca_for_service_etcd/                           pki          pki_13a87e77          PKI Intermediate CA for ETCd service
k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth/     pki          pki_622072da          PKI Intermediate CA for K8S: kube-apiserver CLIENT_AUTH
k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/             pki          pki_d8737474          PKI Intermediate CA for K8S: kube-apiserver TLS
k8s_pki_intermediate_ca_for_service_kube_controller_manager_tls/    pki          pki_34a63553          PKI Intermediate CA for K8S: kube-controller-manager TLS
k8s_pki_intermediate_ca_for_service_kube_scheduler_tls/             pki          pki_5b5f53f5          PKI Intermediate CA for K8S: kube-scheduler TLS
k8s_pki_intermediate_ca_for_service_kubelet_client_auth/            pki          pki_4f1df8fd          PKI Intermediate CA for K8S: kubelet CLIENT_AUTH
k8s_pki_intermediate_ca_for_service_kubelet_tls/                    pki          pki_47e7182a          PKI Intermediate CA for K8S: kubelet TLS

Note: так как префикс k8s_pki_intermediate_ca_for_service_ в именовании CA общий, то в таблице для удобства форматирования он опущен


kube-apiserver

Сертификаты K8s kube-apiserver
Сервис который использует этот сертификат Параметр сервиса СА выпустивший сертификат Тип сертификата (серверный/клиентский/CA) Назначение Subject и подробности
kube-apiserver --etcd-certfile
--etcd-keyfile
etcd Клиентский
TLS Web Client
Authentication
Авторизация в etcd. В зависимости от настроек содержит имя пользователя
если etcd настроен на такой тип авторизации, используется именно такой способ: (etcd: авторизация с использованием сертификатов)
openssl x509 -noout -text -in /etc/k8s/kube-apiserver/certs/etcd/kube-apiserver.pem
Certificate:
    Data:
        Version: 3 (0x2)
        Serial Number:
            56:ce:57:67:7d:9b:54:76:6d:60:51:4a:0c:09:c7:11:ac:f1:95:3b
        Signature Algorithm: sha256WithRSAEncryption
        Issuer: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, postalCode = 61172, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service ETCd
        Validity
            Not Before: Oct 17 15:23:37 2022 GMT
            Not After : Oct 16 15:24:04 2027 GMT
        Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st 322 app. 311, postalCode = 61172, O = Home Network, OU = IT, CN = kube-apiserver-1
        X509v3 extensions:
            X509v3 Key Usage: critical
                Digital Signature, Key Encipherment
            X509v3 Extended Key Usage:
                TLS Web Client Authentication
            X509v3 Subject Key Identifier:
                F8:E5:28:79:2F:4E:99:EA:BE:43:B7:CA:6C:1B:20:65:E6:0B:B3:72
            X509v3 Authority Key Identifier:
                60:41:31:79:58:90:A9:63:62:C2:26:FD:8F:02:B6:07:1A:1D:5C:50
            Authority Information Access:
                CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_etcd/ca
            X509v3 Subject Alternative Name:
                DNS:kube-apiserver-1
            X509v3 CRL Distribution Points:
                Full Name:
                  URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_etcd/crl

kube-apiserver --tls-cert-file
--tls-private-key-file
kube_apiserver_tls/ Серверный
TLS Web Server
Authentication
HTTPS для API Можно получить
netstat -ntpl | grep kube-api 
tcp        0      0 10.0.12.1:6443          0.0.0.0:*               LISTEN      85224/kube-apiserve

Или взять из параметров kube-apiserver
Обратить внимание - в Alt Names прописан как основной домен (kube-apiserver.az1.k8s.cluster.home), так и домен балансера (kube-apiserver.k8s.cluster.home) а так же адреса по которым может быть доступен сервис. Адрес 10.80.0.1 указывается в настройках kube-apiserver

  • DNS:kube-apiserver.az1.k8s.cluster.home
  • DNS:kube-apiserver.k8s.cluster.home
  • DNS:kubernetes
  • DNS:kubernetes.cluster.home
  • IP Address:10.0.12.1
  • IP Address:10.80.0.1
  • IP Address:127.0.0.1
openssl x509 -noout -text -in /etc/k8s/kube-apiserver/certs/tls/kube-apiserver-tls.pem
Certificate:
    Data:
        Version: 3 (0x2)
        Serial Number:
            71:a8:93:84:83:df:af:ba:78:df:63:3d:fe:4d:7f:f4:22:26:23:24
        Signature Algorithm: sha256WithRSAEncryption
        Issuer: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kube-apiserver TLS
        Validity
            Not Before: Nov 14 08:59:08 2022 GMT
            Not After : Nov 13 08:59:35 2027 GMT
        Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = kube-apiserver.az1.k8s.cluster.home
        Subject Public Key Info:
        X509v3 extensions:
            X509v3 Key Usage: critical
                Digital Signature, Key Encipherment
            X509v3 Extended Key Usage:
                TLS Web Server Authentication
            X509v3 Subject Key Identifier:
                E0:69:16:9A:99:A8:E6:95:AB:2B:2D:BC:58:CF:5C:E0:61:BF:10:51
            X509v3 Authority Key Identifier:
                22:7D:70:47:DB:79:ED:91:79:B3:51:0E:23:5F:32:B9:37:01:8D:C1
            Authority Information Access:
                CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/ca
            X509v3 Subject Alternative Name:
                DNS:kube-apiserver.az1.k8s.cluster.home, DNS:kube-apiserver.k8s.cluster.home, DNS:kubernetes, DNS:kubernetes.cluster.home, IP Address:10.0.12.1, IP Address:10.80.0.1, IP Address:127.0.0.1
            X509v3 CRL Distribution Points:
                Full Name:
                  URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls/crl

kube-apiserver --client-ca-file CA kube_apiserver_client_auth/ Не серверный
Не клиентский
CA
Это СА который используется для проверки сертификатов, с которыми клиенты (другие сервисы или пользователи) подключаются к kube-apiserver.

Важно, что ключ от этого сертификата в настройках kube-apiserver не участвует.
Это означает что kube-apiserver может проверять сертификаты клиентов но не может выписывать новые сертификаты, эта часть - за администратором системы.


Именно с пмощью этого СА проверяются сертификаты как пользователей (если пользователи используют сертификаты) так и сервисов kube-controller-manager, kube-proxy, kube-scheduler, kubelet
В случае PKI на основе Vault CA в любой момент можно скачать.

openssl x509 -noout -text -in /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_client_auth.pem
Certificate:
    Data:
        Version: 3 (0x2)
        Serial Number:
            1a:ba:2f:66:84:5f:65:d4:cf:65:e2:d8:86:6a:a5:22:fd:57:8c:2b
        Signature Algorithm: sha256WithRSAEncryption
        Issuer: C = Ukraine, L = Kharkov, street = app. 131 + street = Lui Pastera St. 322, postalCode = 61172, O = Home Network, OU = IT, CN = Root Certificate Authority for Home Network v2
        Validity
            Not Before: Nov  5 10:21:06 2022 GMT
            Not After : Oct 31 10:21:36 2042 GMT
        Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, CN = Intermediate CA for service kube-apiserver CLIENT_AUTH
        Subject Public Key Info:
        X509v3 extensions:
            X509v3 Key Usage: critical
                Certificate Sign, CRL Sign
            X509v3 Basic Constraints: critical
                CA:TRUE
            X509v3 Subject Key Identifier:
                2F:8E:7A:14:33:0D:E1:66:69:81:85:F5:C5:EC:09:3E:89:E1:B7:DF
            X509v3 Authority Key Identifier:
                02:F8:85:2B:75:F8:E1:1C:69:28:30:32:21:2D:86:71:AF:AB:EC:3C
            Authority Information Access:
                CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_root_ca/ca
            X509v3 CRL Distribution Points:
                Full Name:
                  URI:http://vault.home:8200/v1/k8s_pki_root_ca/crl
kube-apiserver --kubelet-certificate-authority CA
kubelet_tls
Не серверный
Не клиентский
CA
Это CA используется для того, что бы проверить сертификат kubelet, и быть уверенным что подключение к правильному kubelet

Этим же СА подписываются сертификаты kubelet для TLS
(конфигурация kubelet) /etc/k8s/kubelet/kubelet-config.yaml

tlsCertFile: "/etc/k8s/kubelet/certs/tls/kubelet-tls.pem"
tlsPrivateKeyFile: "/etc/k8s/kubelet/certs/tls/kubelet-tls.key"
openssl x509 -noout -text -in /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kubelet_tls.pem
Certificate:
    Data:
        Version: 3 (0x2)
        Serial Number:
            33:04:63:a1:86:f2:80:bd:96:5e:10:46:ae:d5:c8:28:89:d0:74:34
        Signature Algorithm: sha256WithRSAEncryption
        Issuer: C = Ukraine, L = Kharkov, street = app. 131 + street = Lui Pastera St. 322, postalCode = 61172, O = Home Network, OU = IT, CN = Root Certificate Authority for Home Network v2
        Validity
            Not Before: Nov 10 14:11:32 2022 GMT
            Not After : Nov  5 14:12:02 2042 GMT
        Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kubelet TLS
        Subject Public Key Info:
            Public Key Algorithm: rsaEncryption
                Public-Key: (2048 bit)
                Modulus:
                Exponent: 65537 (0x10001)
        X509v3 extensions:
            X509v3 Key Usage: critical
                Certificate Sign, CRL Sign
            X509v3 Basic Constraints: critical
                CA:TRUE
            X509v3 Subject Key Identifier:
                F1:9C:3B:FB:01:4E:9A:3F:F5:E8:28:CE:99:60:9F:E3:5E:51:DA:C8
            X509v3 Authority Key Identifier:
                02:F8:85:2B:75:F8:E1:1C:69:28:30:32:21:2D:86:71:AF:AB:EC:3C
            Authority Information Access:
                CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_root_ca/ca
            X509v3 CRL Distribution Points:
                Full Name:
                  URI:http://vault.home:8200/v1/k8s_pki_root_ca/crl
kube-apiserver --kubelet-client-certificate
--kubelet-client-key
kubelet_client_auth/ Клиентский
TLS Web Clien
Authentication
Это сертификат используется kube-apiserver что бы авторизоваться у kubelet
, это нужно что бы kubelet мог быть уверен что к нему пришел доверенный kube-apiserver

Обратить внимание на CN = kube-apiserver-to-kubelet - для этого пользователя потребуется создать отдельный ClusterRoleBinding, по-умолчанию его нет. Естественно, что для своих ролей имена можно использовать любые, kube-apiserver-to-kubelet это текстовый идентификатор, который можно назначить по своему усмотрению, но, одинаковый как в сертификате так и в ClusterRoleBinding

openssl x509 -noout -text -in /etc/k8s/kube-apiserver/certs/client_auth/kubelet-client_auth.pem
Certificate:
    Data:
        Version: 3 (0x2)
        Serial Number:
            28:07:04:c7:ce:4a:6e:29:fc:f7:c9:60:00:57:2a:9c:16:ca:53:8f
        Signature Algorithm: sha256WithRSAEncryption
        Issuer: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, CN = Intermediate CA for service kubelet CLIENT_AUTH
        Validity
            Not Before: Nov 13 14:43:03 2022 GMT
            Not After : Nov 12 14:43:31 2027 GMT
        Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = system:masters, OU = system, CN = kube-apiserver-to-kubelet
        Subject Public Key Info:
            Public Key Algorithm: rsaEncryption
                Public-Key: (2048 bit)
                Modulus:
                Exponent: 65537 (0x10001)
        X509v3 extensions:
            X509v3 Key Usage: critical
                Digital Signature, Key Encipherment
            X509v3 Extended Key Usage:
                TLS Web Client Authentication
            X509v3 Subject Key Identifier:
                22:7C:92:2B:A3:5F:53:0F:B5:7A:F2:84:FA:55:C9:51:DD:33:78:E8
            X509v3 Authority Key Identifier:
                50:35:A5:C5:B4:C6:FC:65:04:08:76:F7:FB:56:D3:76:6D:96:36:2F
            Authority Information Access:
                CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kubelet_client_auth/ca
            X509v3 Subject Alternative Name:
                DNS:kube-apiserver-to-kubelet
            X509v3 CRL Distribution Points:
                Full Name:
                  URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kubelet_client_auth/crl

kube-controller-manager

Сертификаты K8s kube-controller-manager
Сервис который использует этот сертификат Параметр сервиса СА выпустивший сертификат Тип сертификата (серверный/клиентский/CA) Назначение Subject и подробности
kube-controller-manager

--tls-cert-file
--tls-private-key-file

kube_controller_manager_tls/ Серверный
TLS Web Server
Authentication
kube-controller-manager имеет свой API (по умолчанию - на порту 10257), в котором есть как минимум такие endpoints: /healthz, /readyz, /livez, /metrics.

Этот сертификат служит для организации TLS/HTTPS для этого API

Для разрешения доступа без авторизации служит параметр --authorization-always-allow-paths=/healthz,/readyz,/livez,/metrics, где перечислаются endpoints к которым можно получить доступ.

Получить этот сертификат можно непосредственно подключившись к порту
openssl s_client -connect  kube-controller-manager.az1.k8s.cluster.home:10257
subject=C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = kube-controller-manager.az1.k8s.cluster.home
issuer=C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kube-controller-manager TLS

Или в соответствующем файле (путь - в конфиге сервиса)

openssl x509 -noout -text -in  kube-controller-manager-tls.pem

Certificate:

   Data:
       Version: 3 (0x2)
       Serial Number:
           68:35:c6:9e:d5:7d:c6:c8:ff:64:03:e7:fd:d8:c0:03:ff:ee:ec:50
       Signature Algorithm: sha256WithRSAEncryption
       Issuer: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kube-controller-manager TLS
       Validity
           Not Before: Nov 10 17:18:43 2022 GMT
           Not After : Nov  9 17:19:11 2027 GMT
       Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = kube-controller-manager.az1.k8s.cluster.home
       Subject Public Key Info:
           Public Key Algorithm: rsaEncryption
               Public-Key: (2048 bit)
               Modulus:

...

               Exponent: 65537 (0x10001)
       X509v3 extensions:
           X509v3 Key Usage: critical
               Digital Signature, Key Encipherment
           X509v3 Extended Key Usage:
               TLS Web Server Authentication
           X509v3 Subject Key Identifier:
               7A:16:23:C5:0F:42:C2:D2:F2:FD:4C:2F:98:88:62:4D:C7:C6:E0:2A
           X509v3 Authority Key Identifier:
               3A:B0:CE:B4:3E:05:3F:7C:5F:87:24:BA:89:99:03:C6:9F:4C:2E:B1
           Authority Information Access:
               CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kube_controller_manager_tls/ca
           X509v3 Subject Alternative Name:
               DNS:kube-controller-manager.az1.k8s.cluster.home, DNS:kube-controller-manager.k8s.cluster.home, IP Address:10.0.12.1
           X509v3 CRL Distribution Points:
               Full Name:
                 URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kube_controller_manager_tls/crl
   Signature Algorithm: sha256WithRSAEncryption
   Signature Value:

...

kube-controller-manager --root-ca-file Root СА Не Серверный
Не Клиентский
CA
Этот СА которым подписаны сертификаты для HTTPS/TLS для kube-api-server и он используется для проверки серверных сертификатов. Обладая этим CA можно проверить что подключение происходит к правильному kube-apiserver
openssl x509 -noout -text -in /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem
Certificate:
    Data:
        Version: 3 (0x2)
        Serial Number:
            0c:8b:42:a7:b4:5a:56:0e:b6:72:d0:40:03:70:5c:19:49:03:43:90
        Signature Algorithm: sha256WithRSAEncryption
        Issuer: C = Ukraine, L = Kharkov, street = app. 131 + street = Lui Pastera St. 322, postalCode = 61172, O = Home Network, OU = IT, CN = Root Certificate Authority for Home Network v2
        Validity
            Not Before: Nov 10 14:09:38 2022 GMT
            Not After : Nov  5 14:10:08 2042 GMT
        Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kube-apiserver TLS

kube-proxy

Для kube-proxy за исключением kubeconfig сертификаты не используются

kube-scheduler

Сертификаты K8s kube-scheduler
Сервис который использует этот сертификат Параметр сервиса СА выпустивший сертификат Тип сертификата (серверный/клиентский/CA) Назначение Subject и подробности
kube-scheduler --tls-cert-file
--tls-private-key-file
kube_scheduler_tls Серверный
TLS Web Server
Authentication

kube-scheduler имеет свой API (по умолчанию - на порту 10259), в котором есть как минимум такие endpoints: /healthz, /readyz, /livez, /metrics. Этот сертификат служит для организации TLS/HTTPS для этого API

Для разрешения доступа без авторизации служит параметр --authorization-always-allow-paths=/healthz,/readyz,/livez,/metrics, где перечислаются endpoints к которым можно получить доступ.

Сертификат можно просмотреть:

 openssl s_client -connect  kube-scheduler.az1.k8s.cluster.home:10259
subject=C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = kube-scheduler.az1.k8s.cluster.home
issuer=C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kube-scheduler TLS

Или посмотреть в файле (путь к файлу в параметрах сервиса)

openssl x509 -noout -text -in  kube-scheduler-tls.pem
Certificate:
    Data:
        Version: 3 (0x2)
        Serial Number:
            69:35:40:e1:3d:40:4f:f4:f4:0e:a7:a8:6b:cf:ab:5e:78:fd:76:e4
        Signature Algorithm: sha256WithRSAEncryption
        Issuer: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kube-scheduler TLS
        Validity
            Not Before: Nov 10 17:43:55 2022 GMT
            Not After : Nov  9 17:44:24 2027 GMT
        Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = kube-scheduler.az1.k8s.cluster.home
        Subject Public Key Info:
            Public Key Algorithm: rsaEncryption
                Public-Key: (2048 bit)
                Modulus:
...
                Exponent: 65537 (0x10001)
        X509v3 extensions:
            X509v3 Key Usage: critical
                Digital Signature, Key Encipherment
            X509v3 Extended Key Usage:
                TLS Web Server Authentication
            X509v3 Subject Key Identifier:
                1E:54:7A:95:6C:DF:B4:99:1E:52:AC:33:42:E4:F0:FC:0C:64:55:A0
            X509v3 Authority Key Identifier:
                89:20:99:22:3A:5F:FB:50:26:01:42:BD:36:B6:F6:F3:B7:E4:51:A9
            Authority Information Access:
                CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kube_scheduler_tls/ca
            X509v3 Subject Alternative Name:
                DNS:kube-scheduler.az1.k8s.cluster.home, DNS:kube-scheduler.k8s.cluster.home, IP Address:10.0.12.1
            X509v3 CRL Distribution Points:
                Full Name:
                  URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kube_scheduler_tls/crl
    Signature Algorithm: sha256WithRSAEncryption
    Signature Value:
...

kubelet

Для kubelet сертификаты указываются в файле, определенном в параметре --config=/etc/k8s/kubelet/kubelet-config.yaml

kind: KubeletConfiguration
apiVersion: kubelet.config.k8s.io/v1beta1
authentication:
  anonymous:
    enabled: false
  webhook:
    enabled: true
  x509:
    clientCAFile: "/etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kubelet_client_auth.pem"
authorization:
  mode: Webhook
clusterDomain: "cluster.home"
clusterDNS:
  - "10.80.0.10"
resolvConf: "/run/systemd/resolve/resolv.conf"
runtimeRequestTimeout: "15m"
tlsCertFile: "/etc/k8s/kubelet/certs/tls/kubelet-tls.pem"
tlsPrivateKeyFile: "/etc/k8s/kubelet/certs/tls/kubelet-tls.key"
authorizationMode: Node,RBAC



Сертификаты K8s kubelet
Сервис который использует этот сертификат Параметр сервиса СА выпустивший сертификат Тип сертификата (серверный/клиентский/CA) Назначение Subject и подробности
kubelet clientCAFile Root CA (другими словами этот СА подписан корневым СА, а сам является промежуточным СА) Не серверный
Не клиентский
СА
Предназначен для проверки сертификатов с которыми подключаются клиенты (насколько я знаю это только kube-apiserver, в его параметрах это --kubelet-client-certificate и

--kubelet-client-key.

Сертификат можно просмотреть:

openssl x509 -noout -text -in /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kubelet_client_auth.pem
Certificate:
    Data:
        Version: 3 (0x2)
        Serial Number:
            6e:c2:5c:3f:d0:0d:de:a9:bc:8c:2f:78:39:b9:ce:c6:c4:0f:ce:86
        Signature Algorithm: sha256WithRSAEncryption
        Issuer: C = Ukraine, L = Kharkov, street = app. 131 + street = Lui Pastera St. 322, postalCode = 61172, O = Home Network, OU = IT, CN = Root Certificate Authority for Home Network v2
        Validity
            Not Before: Nov  4 09:26:50 2022 GMT
            Not After : Oct 30 09:27:20 2042 GMT
        Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, CN = Intermediate CA for service kubelet CLIENT_AUTH
        Subject Public Key Info:
            Public Key Algorithm: rsaEncryption
                Public-Key: (2048 bit)
                Modulus:
...
                Exponent: 65537 (0x10001)
        X509v3 extensions:
            X509v3 Key Usage: critical
                Certificate Sign, CRL Sign
            X509v3 Basic Constraints: critical
                CA:TRUE
            X509v3 Subject Key Identifier:
                50:35:A5:C5:B4:C6:FC:65:04:08:76:F7:FB:56:D3:76:6D:96:36:2F
            X509v3 Authority Key Identifier:
                02:F8:85:2B:75:F8:E1:1C:69:28:30:32:21:2D:86:71:AF:AB:EC:3C
            Authority Information Access:
                CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_root_ca/ca
            X509v3 CRL Distribution Points:
                Full Name:
                  URI:http://vault.home:8200/v1/k8s_pki_root_ca/crl
...
kubelet tlsCertFile, tlsPrivateKeyFile kubelet_tls Серверный
TLS Web Server
Authentication
Используется для HTTP/TLS для API kubelet (к которому подключается kube-apiserver, важный параметр - kubeletдолжен регистрироваться в kube-apiserver с одним из имен разрешенных для использования в сертификате.

Обратить внимание что в сертификате прописаны несколько возможных имен

  • DNS:kubelet.az1.k8s.cluster.home
  • DNS:worker01.az1.k8s.cluster.home - используется как основное, и указано в параметрах kubelet: --hostname-override=${KUBELET_HOSTNAME_OVERRIDE} В примере это worker01.az1.k8s.cluster.home
  • IP Address:10.0.12.1

Сертификат можно просмотреть:

openssl x509 -noout -text -in /etc/k8s/kubelet/certs/tls/kubelet-tls.pem
Certificate:
    Data:
        Version: 3 (0x2)
        Serial Number:
            18:6e:c4:32:a9:b7:ba:44:55:0d:52:df:d3:fb:e4:75:f0:29:7b:72
        Signature Algorithm: sha256WithRSAEncryption
        Issuer: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = Intermediate CA for service kubelet TLS
        Validity
            Not Before: Nov 13 16:08:12 2022 GMT
            Not After : Nov 12 16:08:41 2027 GMT
        Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = K8s The Hardest Way Labs, OU = IT, CN = kubelet.az1.k8s.cluster.home
        Subject Public Key Info:
            Public Key Algorithm: rsaEncryption
                Public-Key: (2048 bit)
                Modulus:
...
                Exponent: 65537 (0x10001)
        X509v3 extensions:
            X509v3 Key Usage: critical
                Digital Signature, Key Encipherment
            X509v3 Extended Key Usage:
                TLS Web Server Authentication
            X509v3 Subject Key Identifier:
                42:97:B0:18:FC:0A:03:29:02:92:68:A5:F3:5B:A5:48:23:F1:14:DC
            X509v3 Authority Key Identifier:
                F1:9C:3B:FB:01:4E:9A:3F:F5:E8:28:CE:99:60:9F:E3:5E:51:DA:C8
            Authority Information Access:
                CA Issuers - URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kubelet_tls/ca
            X509v3 Subject Alternative Name:
                DNS:kubelet.az1.k8s.cluster.home, DNS:worker01.az1.k8s.cluster.home, IP Address:10.0.12.1
            X509v3 CRL Distribution Points:
                Full Name:
                  URI:http://vault.home:8200/v1/k8s_pki_intermediate_ca_for_service_kubelet_tls/crl
    Signature Algorithm: sha256WithRSAEncryption
    Signature Value:
...

Файлы kubeconfig

Некоторые сервисы используют kubeconfig для авторизации у kube-apiserver, в том числе плюс-минус такой же конфиг используется для авторизации администратора

Описание формата kubeconfig

Разберем пример файла (для примера взят конфиг от kubelet)

apiVersion: v1
clusters:
- cluster:
    certificate-authority: "/etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem"
    server: https://kube-apiserver.k8s.cluster.home:443
  name: kubernetes-the-hardest-way
contexts:
- context:
    cluster: kubernetes-the-hardest-way
    user: system:node:worker01.az1.k8s.cluster.home
  name: default
current-context: default
kind: Config
preferences: {}
users:
- name: system:node:worker01.az1.k8s.cluster.home
  user:
    client-certificate: /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.pem
    client-key: /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.key

clusters

В этой секции описываются кластера, а именно

  • имя кластера

name: kubernetes-the-hardest-way

  • Адрес по которому доступен kube-apiserver

server: https://kube-apiserver.k8s.cluster.home:443

  • CA файл, с помощью которого можно проверить что подключение происходит к правильному кластеру

certificate-authority: /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem

Имя кластера можно выбрать произвольно, это имя служит только для связывания различных секций файла в единый контекст

users

В этой секции содержится описание пользователя, а именно:

  • Имя пользователя

- name: system:node:worker01.az1.k8s.cluster.home

  • Способ авторизации и параметры авторизации (в этом случае используются клиентские сертификаты
    • client-certificate: /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.pem
    • client-key: /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.key


Имя пользователя в этой секции - просто идентификатор и никак не участвует в процессе авторизации, а служит только для связывания различных секций файла в единый контекст


Важно: Фактические имя пользователя и группа описаны в полях CN (имя пользователя) и O (группа) при авторизации с помощью клиентских сертификатов !!!

Имя в сертификате может не совпадать с полем name, иногда они совпадают для удобства конфигурирования но не более того.

contexts

Эта секция служит для связывания секций users и clusters и по сути просто сообщает для какого кластера какой пользователь используется.
Имя контекста name служит для идентификации, так как в одном файле может быть описано множество контекстов (с возможностью переключения между ними)
Пример файла следует читать так:
Для контекста с именем default использовать СА и адрес определенные в секции clusters в секции где имя кластера kubernetes-the-hardest-way,
для авторизации использовать данные из секции users где имя name - system:node:worker01.az1.k8s.cluster.home
При этом слово default в имени контекста не несет какого-то магического смысла - это просто название, на которое можно сослаться, и не более того.

contexts:
- context:
    cluster: kubernetes-the-hardest-way
    user: system:node:worker01.az1.k8s.cluster.home
  name: default

current-contex

Эта секция определяет какой контекст будет использоваться по-умолчанию
В примере ниже используется по умолчанию контекст с именем default, и здесь слово default не имеет никакого магического значение - это просто имя контекста определенного в секции contexts и не более того

current-context: default

Общие части для всех kubeconfig

clusters

Так-как это все kubeconfigдля одного кластера то у всех их есть общая часть

clusters:
- cluster:
    certificate-authority-data: LS0tLS1CRUdJ ... skipped long line ...
    server: https://kube-apiserver.k8s.cluster.home:443
  name: kubernetes-the-hardest-way
clusters:
- cluster:
    certificate-authority: /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem
    server: https://kube-apiserver.k8s.cluster.home:443

Отличие тут только в том что для админа данные сертификата включены в файл kubeconfig для того что бы его было проще передавать между пользователями
Для сервисов же указан путь к СА сертификату kube-apiserver
Назначения этого сертификата - проверка того что подключение идет к тому кластеру к которому ожидается.

users

Секция users тоже имеет похожий вид, но тут для каждого сервиса указан свой пользователь и своя группа внутри сертификата (в поле CN указано имя пользователя, в поле O указана группа)
Так-как все файлы очень похожи далее я буду акцентировать внимание на пользователях и группах
Все клиентские сертификаты подписаны одним и тем же СА - kube_apiserver_client_auth и процесс kube-apiserver может проверить каждый из них используя СА указанный в параметре --client-ca-file сертификат.

users:
- name: some-name
  user:
    client-certificate: some-cert.pem
    client-key: some-key.key

Admin

apiVersion: v1
clusters:
- cluster:
    certificate-authority-data: LS0tLS1CRUdJ ... skipped long line ...
    server: https://kube-apiserver.k8s.cluster.home:443
  name: kubernetes-the-hardest-way
contexts:
- context:
    cluster: kubernetes-the-hardest-way
    user: admin
  name: default
current-context: default
kind: Config
preferences: {}
users:
- name: admin
  user:
    client-certificate-data: LS0tLS1CRUdJT ... skipped long line ...
    client-key-data: LS0tLS1CRUdJTiB ... skipped long line 

Просмотр сертификата

openssl x509 -noout -text -in admin.pem | grep "Subject:"

Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = system:masters, OU = system, CN = admin

  • группа O = system:masters
  • Пользователь CN = admin
  • Права назначаются СlusterRoleBinding на группу:
  kind: Group
  name: system:masters

Имя ClusterRoleBinding получено методом полного перебора что бы понять в каком из них происходит назначение прав на группу system:masters. Для остальных групп - аналогично, хотя часто имя binding совпадает с названием группы.
Полный вывод:

kubectl get clusterrolebinding cluster-admin -o yaml
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  annotations:
    rbac.authorization.kubernetes.io/autoupdate: "true"
  creationTimestamp: "2022-11-08T09:41:39Z"
  labels:
    kubernetes.io/bootstrapping: rbac-defaults
  name: cluster-admin
  resourceVersion: "145"
  uid: cea153e2-ead5-4fcc-8810-c615d1204fec
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: cluster-admin
subjects:
- apiGroup: rbac.authorization.k8s.io
  kind: Group
  name: system:masters

kube-controller-manager

apiVersion: v1
clusters:
- cluster:
    certificate-authority: /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem
    server: https://kube-apiserver.k8s.cluster.home:443

  name: kubernetes-the-hardest-way
contexts:
- context:
    cluster: kubernetes-the-hardest-way
    user: system:kube-controller-manager
  name: default
current-context: default
kind: Config
preferences: {}
users:
- name: system:kube-controller-manager
  user:
    client-certificate: /etc/k8s/kube-controller-manager/certs/client_auth/kube-apiserver-client_auth.pem
    client-key: /etc/k8s/kube-controller-manager/certs/client_auth/kube-apiserver-client_auth.key

Аналогично админу - можно проверить пользователя, группу и права

openssl x509 -noout -text -in  /etc/k8s/kube-controller-manager/certs/client_auth/kube-apiserver-client_auth.pem  | grep "Subject:"
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = system:kube-controller-manager, OU = system, CN = system:kube-controller-manager
kubectl get clusterrolebinding system:kube-controller-manager -o yaml
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  annotations:
    rbac.authorization.kubernetes.io/autoupdate: "true"
  creationTimestamp: "2022-11-08T09:41:39Z"
  labels:
    kubernetes.io/bootstrapping: rbac-defaults
  name: system:kube-controller-manager
  resourceVersion: "151"
  uid: 53b7d64d-f3f6-49bc-8954-6c8eea6fb444
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: system:kube-controller-manager
subjects:
- apiGroup: rbac.authorization.k8s.io
  kind: User
  name: system:kube-controller-manager

kube-proxy

apiVersion: v1
clusters:
- cluster:
    certificate-authority: /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem
    server: https://kube-apiserver.k8s.cluster.home:443
  name: kubernetes-the-hardest-way

contexts:
- context:
    cluster: kubernetes-the-hardest-way
    user: system:kube-proxy
  name: default
current-context: default

kind: Config
preferences: {}
users:
- name: system:kube-proxy
  user:
    client-certificate: /etc/k8s/kube-proxy/certs/client_auth/kube-apiserver-client_auth.pem
    client-key: /etc/k8s/kube-proxy/certs/client_auth/kube-apiserver-client_auth.key

Аналогично админу - можно проверить пользователя, группу и права

openssl x509 -noout -text -in /etc/k8s/kube-proxy/certs/client_auth/kube-apiserver-client_auth.pem  | grep "Subject:"
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = system:node-proxier, OU = system, CN = system:kube-proxy
kubectl get clusterrolebinding system:node-proxier  -o yaml
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  annotations:
    rbac.authorization.kubernetes.io/autoupdate: "true"
  creationTimestamp: "2022-11-08T09:41:39Z"
  labels:
    kubernetes.io/bootstrapping: rbac-defaults
  name: system:node-proxier
  resourceVersion: "150"
  uid: 336cfde3-8777-44aa-a70d-e7d1aebd148f
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: system:node-proxier
subjects:
- apiGroup: rbac.authorization.k8s.io
  kind: User
  name: system:kube-proxy

kube-scheduler

apiVersion: v1
clusters:
- cluster:
    certificate-authority: /etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem
    server: https://kube-apiserver.k8s.cluster.home:443
  name: kubernetes-the-hardest-way
contexts:
- context:
    cluster: kubernetes-the-hardest-way
    user: system:kube-scheduler
  name: default
current-context: default
kind: Config
preferences: {}
users:
- name: system:kube-scheduler
  user:
    client-certificate: /etc/k8s/kube-scheduler/certs/client_auth/kube-apiserver-client_auth.pem
    client-key: /etc/k8s/kube-scheduler/certs/client_auth/kube-apiserver-client_auth.key
openssl x509 -noout -text -in  /etc/k8s/kube-scheduler/certs/client_auth/kube-apiserver-client_auth.pem  | grep "Subject:"
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = system:kube-scheduler, OU = system, CN = system:kube-scheduler
kubectl get clusterrolebinding system:kube-scheduler -o yaml
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  annotations:
    rbac.authorization.kubernetes.io/autoupdate: "true"
  creationTimestamp: "2022-11-08T09:41:39Z"
  labels:
    kubernetes.io/bootstrapping: rbac-defaults
  name: system:kube-scheduler
  resourceVersion: "153"
  uid: 4a50831a-e5f8-4a77-8aef-cea46ac24231
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: system:kube-scheduler
subjects:
- apiGroup: rbac.authorization.k8s.io
  kind: User
  name: system:kube-scheduler

kubelet

apiVersion: v1
clusters:
- cluster:
    certificate-authority: "/etc/k8s/shared/certs/CA/k8s_pki_intermediate_ca_for_service_kube_apiserver_tls.pem"
    server: https://kube-apiserver.k8s.cluster.home:443
  name: kubernetes-the-hardest-way
contexts:
- context:
    cluster: kubernetes-the-hardest-way
    user: system:node:worker01.az1.k8s.cluster.home
  name: default
current-context: default
kind: Config
preferences: {}
users:
- name: system:node:worker01.az1.k8s.cluster.home
  user:
    client-certificate: /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.pem
    client-key: /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.key

Аналогично админу - можно проверить пользователя, группу и права

openssl x509 -noout -text -in  /etc/k8s/kubelet/certs/client_auth/kube-apiserver-client_auth.pem   | grep "Subject:"
Subject: C = Ukraine, L = Kharkov, street = Lui Pastera st. 322 app. 131, O = system:nodes, OU = system, CN = system:node:worker01.az1.k8s.cluster.home

Тут есть некоторая тонкость - имя worker01.az1.k8s.cluster.homeдолжно совпадать с хостнеймом или с параметром --hostname-override, и сертификат у kubeletдолжен позволять использовать это доменное имя (обратить внимание на описание HTTPS/TLS сертификатов kubelet, описание tlsCertFile, tlsPrivateKeyFile)
В остальном отличий нет

kubectl get clusterrolebinding system:node  -o yaml
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  annotations:
    rbac.authorization.kubernetes.io/autoupdate: "true"
  creationTimestamp: "2022-11-08T09:41:39Z"
  labels:
    kubernetes.io/bootstrapping: rbac-defaults
  name: system:node
  resourceVersion: "155"
  uid: fec38e51-4833-41af-a46e-fb482e5941b4
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: system:node