Kubernetes the hard way kube apiserver
Kube-apiserver
Соглашение о расположении файлов
- bin -
/usr/local/bin/
- конфиги, в том числе сертификаты -
/etc/k8s/<имя сервиса>
например/etc/k8s/kube-apiserver/
- конфиги, в том числе сертификаты общие для нескольких сервисов -
/etc/k8s/shared/
Загрузка
Общий для всех базовых компонентов скрипт
#!/bin/bash VERSION="1.25.1" ARCH="arm64" mkdir -p k8s_${VERSION} cd k8s_${VERSION} wget -q --show-progress --https-only --timestamping \ "https://storage.googleapis.com/kubernetes-release/release/v${VERSION}/bin/linux/${ARCH}/kube-apiserver" \ "https://storage.googleapis.com/kubernetes-release/release/v${VERSION}/bin/linux/${ARCH}/kube-controller-manager" \ "https://storage.googleapis.com/kubernetes-release/release/v${VERSION}/bin/linux/${ARCH}/kube-scheduler" \ "https://storage.googleapis.com/kubernetes-release/release/v${VERSION}/bin/linux/${ARCH}/kubectl"
Шифрование и encryption-provider-config
encryption-config.yaml
https://kubernetes.io/docs/tasks/administer-cluster/encrypt-data/
encryption-provider-config - конфигурация шифрования в etcd
Файл encryption-config.yaml
должен быть одинаковый у всех участников кластера, для того что бы они могли расшифровать данные друг друга
В целом судя по документации может быть более сложная конфигурация чем "один ключ для всего", но особого смысла в этом я не вижу
head -c 32 /dev/urandom | base64 <PRE> <PRE> cat configs/encryption-config.yaml kind: EncryptionConfig apiVersion: v1 resources: - resources: - secrets providers: - aescbc: keys: - name: key1 secret: sCfG58h5SdUxSFephLyE6M6ppxYfnVFUi+GB2b5+kd4= - identity: {}
Сертификаты которые использует kube-apiserver
--etcd-certfile
, --etcd-keyfile
Самая простая часть - это сертификат и ключ с помощью которых можно авторизоваться у etcd сервера и писать/читать данные.
Этот вопрос уже обсуждался при настройке etcd
TODO: вставить ссылку!!!
Для каждого kube-apiserver можно получить от CA настроенного для etcd
отдельный сертификат и ключ, с отдельным пользователем и ролью:
(имя пользователя и пароль для VAULT были созданы при работе с etcd CA (TODO: ССЫЛКА!)
- PKI - тот же что использовался для ETCD
- Для каждого AZ свой пользователь
Получение сертификатов
#!/bin/bash PKI_NAME="k8s_pki_intermediate_ca_for_service_etcd" CERTS_PATH="/etc/k8s/kube-apiserver/certs/etcd" mkdir -p ${CERTS_PATH} AZ=1 DOMAIN="etcd.master.az${AZ}.k8s.cluster.home" NAME="${DOMAIN}-client" vault \ login \ -method=userpass \ username="${NAME}-user" \ password="${NAME}-password" USERNAME_PREFIX="kube-apiserver" DATE=$(date +%Y%m%dT%H%M) USERNAME="${USERNAME_PREFIX}-${AZ}" echo "========" vault \ write \ -format=json \ ${PKI_NAME}/issue/${NAME}-role \ common_name="${USERNAME}" \ ca=false \ ttl="43800h" \ > ${CERTS_PATH}/${USERNAME}.crt.json cat \ ${CERTS_PATH}/${USERNAME}.crt.json \ | jq -r '.data.private_key' > ${CERTS_PATH}/${USERNAME}-${DATE}.key cat \ ${CERTS_PATH}/${USERNAME}.crt.json \ | jq -r '.data.certificate' > ${CERTS_PATH}/${USERNAME}-${DATE}.pem cat \ ${CERTS_PATH}/${USERNAME}.crt.json \ | jq -r '.data.ca_chain[]' >> ${CERTS_PATH}/${USERNAME}-${DATE}.pem ln -sf ${CERTS_PATH}/${USERNAME}-${DATE}.key ${CERTS_PATH}/${USERNAME_PREFIX}.key ln -sf ${CERTS_PATH}/${USERNAME}-${DATE}.pem ${CERTS_PATH}/${USERNAME_PREFIX}.pem
Проверить что пользователь верный: kube-apiserver-1
openssl x509 -noout -text -in 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
Назначение прав в кластере etcd
--tls-cert-file
--tls-private-key-file
--tls-cert-file string File containing the default x509 Certificate for HTTPS. (CA cert, if any, concatenated after server cert). If HTTPS serving is enabled, and --tls-cert-file and --tls-private-key-file are not provided, a self-signed certificate and key are generated for the public address and saved to /var/run/kubernetes. --tls-private-key-file string File containing the default x509 private key matching --tls-cert-file. You’re probably using TLS to connect to your Kubernetes API server. These two options (to the API server) let you pick what certificate the API server should use. Once you set a TLS cert, you’ll need to set up a kubeconfig file for the components (like the kubelet and kubectl) that want to talk to the API server. The kubeconfig file will look something like this: current-context: my-context apiVersion: v1 clusters: - cluster: certificate-authority: /path/to/my/ca.crt # CERTIFICATE AUTHORITY THAT ISSUED YOUR TLS CERT server: https://horse.org:4443 # this name needs to be on the certificate in --tls-cert-file name: my-cluster kind: Config users: - name: green-user user: client-certificate: path/to/my/client/cert # we'll get to this later client-key: path/to/my/client/key # we'll get to this later One thing I found surprising about this is – almost everything else in the universe that uses TLS will look in /etc/ssl to find a list of certificate authorities the computer trusts by default. But Kubernetes doesn’t do that, instead it mandates “no, you have to say exactly which CA issued the API server’s TLS cert”. You can pass this kubeconfig file into any kubernetes component with --kubeconfig /path/to/kubeconfig.yaml So! We’ve met our first certificate authority: the CA that issues the API server’s TLS cert. This CA doesn’t need to be the same as any of the other certificate authorities we’re going to discuss.