- Регистрация
- 23.09.18
- Сообщения
- 12.347
- Реакции
- 176
- Репутация
- 0
Сегодня я подробно разберу настройку аутентификации в Kubernetes с помощью Dex в связке с LDAP, а также покажу, как можно добавлять статических пользователей в Dex.
В статье не буду останавливаться на основных принципах работы Dex, а сразу перейду к установке и настройке LDAP. Познакомиться с принципами работы Dex можно
Что будем делать:
Итак, поехали.
Показывать буду на примере уже
Устанавливаем и настраиваем OpenLDAP-сервер
В качестве LDAP будем использовать OpenLDAP на дистрибутиве ubuntu 18.04.
Имя нашего сервера: openldap.dtln.cloud.
Описываем структуру LDAP-каталога
Подключаем поддержку OpenID Connect
Переходим к настройке кластера Kubernetes.
Домен dex.ash.dtln.cloud используем для обращения Dex к API-серверу, а login.ash.dtln.cloud – для получения доступа к кластеру.
Мы разворачивали кластер без установщиков kubeadm или kops, так что OIDC-конфигурацию можно сразу добавлять в systemd-юнит. В остальных случаях настройку лучше сделать с помощью этих утилит.
Создаем мультидоменный сертификат
Теперь переходим в кластер Kubernetes.
Устанавливаем Dex
Для Dex нам понадобятся ca.crt, ca.key c мастер-сервера. Обычно они лежат в каталоге /etc/kubernetes/pki/
Также нужен сгенерированный нами раннее CA-сертификат с OpenLDAP, расположенный по пути /etc/ssl/certs/cacert.pem
Генерируем kubeconfig
Настраиваем RBAC-авторизацию
На этом настройка Dex в связке с OpenLDAP закончена.
Пара советов напоследок:
В статье не буду останавливаться на основных принципах работы Dex, а сразу перейду к установке и настройке LDAP. Познакомиться с принципами работы Dex можно
You must be registered for see links
.Что будем делать:
-
You must be registered for see links
-
You must be registered for see links.
-
You must be registered for see links.
-
You must be registered for see links.
-
You must be registered for see links.
-
You must be registered for see links.
-
You must be registered for see links.
Итак, поехали.

Показывать буду на примере уже
You must be registered for see links
с Helm версии 3 и Ingress, а также тремя доменными именами.Устанавливаем и настраиваем OpenLDAP-сервер
В качестве LDAP будем использовать OpenLDAP на дистрибутиве ubuntu 18.04.
Имя нашего сервера: openldap.dtln.cloud.
- Подключаемся к серверу и приступаем к установке OpenLDAP. В процессе установки нам предложат установить пароль:
sudo apt update
sudo apt install slapd ldap-utils
- Переконфигурируем OpenLDAP для нашего домена:
sudo dpkg-reconfigure slapd
- Выбираем No:
- Вводим доменное имя:
- Вводим имя организации:
- Повторяем ввод пароля:
- Включаем поддержку STARTTLS. Ставим необходимые пакеты:
sudo apt install gnutls-bin ssl-cert
- Генерируем CA-ключ:
sudo sh -c "certtool --generate-privkey > /etc/ssl/private/cakey.pem"
- Описываем нашу организацию в /etc/ssl/ca.info:
cn = DTLN Company
ca
cert_signing_key
- Генерируем CA-сертификaт и ключ, который в дальнейшем будем использовать:
sudo certtool --generate-self-signed --load-privkey /etc/ssl/private/cakey.pem --template /etc/ssl/ca.info --outfile /etc/ssl/certs/cacert.pem
sudo certtool --generate-privkey --bits 1024 --outfile /etc/ssl/private/openldap_key.pem
- Создаем шаблон для сертификата /etc/ssl/openldap.info:
organization = DTLN Company
cn = openldap.dtln.cloud
tls_www_server
encryption_key
signing_key
expiration_days = 3650
- Генерируем сам сертификат:
sudo certtool --generate-certificate --load-privkey /etc/ssl/private/openldap_key.pem --load-ca-certificate /etc/ssl/certs/cacert.pem --load-ca-privkey /etc/ssl/private/cakey.pem --template /etc/ssl/openldap.info --outfile /etc/ssl/certs/openldap.pem
- Настраиваем OpenLDAP для работы со STARTTLS. Вот что должно быть внутри файла certinfo.dif:
dn: cn=config
add: olcTLSCACertificateFile
olcTLSCACertificateFile: /etc/ssl/certs/cacert.pem
-
add: olcTLSCertificateFile
olcTLSCertificateFile: /etc/ssl/certs/openldap.pem
-
add: olcTLSCertificateKeyFile
olcTLSCertificateKeyFile: /etc/ssl/private/openldap_key.pem
- Применяем созданный нами файл следующей командой:
sudo ldapmodify -Y EXTERNAL -H ldapi:/// -f certinfo.dif
- Назначаем права доступа на сертификат и перезапускаем наш сервис:
sudo chgrp openldap /etc/ssl/private/openldap_key.pem
sudo chmod 0640 /etc/ssl/private/openldap_key.pem
sudo gpasswd -a openldap ssl-cert
sudo systemctl restart slapd.service
- Чтобы проверить работу нашего сервиса с сертификатами, добавляем в /etc/ldap/ldap.conf строчку:
TLS_CACERT /etc/ssl/certs/cacert.pem
- Проверяем работу через STARTTLS:
ldapwhoami -H ldap://openldap.dtln.cloud -x -ZZ
В случае успеха получаем:
В случае проблемы проверяем еще раз пути до сертификатов и выполнение команд:
Описываем структуру LDAP-каталога
- Теперь опишем структуру каталога, создадим группы и двуx пользователей, которые будут ходить в Kubernetes. Создаем файл content.ldif:
dn: ou=People,dc=openldap,dc=dtln,dc=cloud
objectClass: organizationalUnit
ou: People
dn: cn=jane,ou=People,dc=openldap,dc=dtln,dc=cloud
objectClass: person
objectClass: inetOrgPerson
sn: doe
cn: jane
mail: [email protected]
userpassword: foo_password
dn: cn=john,ou=People,dc=openldap,dc=dtln,dc=cloud
objectClass: person
objectClass: inetOrgPerson
sn: doe
cn: john
mail: [email protected]
userpassword: bar_password
# Group definitions.
dn: ou=Groups,dc=openldap,dc=dtln,dc=cloud
objectClass: organizationalUnit
ou: Groups
dn: cn=admins,ou=Groups,dc=openldap,dc=dtln,dc=cloud
objectClass: groupOfNames
cn: admins
member: cn=jane,ou=People,dc=openldap,dc=dtln,dc=cloud
dn: cn=developers,ou=Groups,dc=openldap,dc=dtln,dc=cloud
objectClass: groupOfNames
cn: developers
member: cn=jane,ou=People,dc=openldap,dc=dtln,dc=cloud
member: cn=john,ou=People,dc=openldap,dc=dtln,dc=cloud
- Разворачиваем описанную структуру командой:
ldapadd -x -D cn=admin,dc=openldap,dc=dtln,dc=cloud -W -f content.ldif
- Удостоверимся в наличии наших пользователей в каталоге:
ldapwhoami -vvv -h openldap.dtln.cloud -p 389 -D cn=john,ou=People,dc=openldap,dc=dtln,dc=cloud -x -w bar_password -ZZ
ldapwhoami -vvv -h openldap.dtln.cloud -p 389 -D cn=jane,ou=People,dc=openldap,dc=dtln,dc=cloud -x -w foo_password -ZZ
Подключаем поддержку OpenID Connect
Переходим к настройке кластера Kubernetes.
Домен dex.ash.dtln.cloud используем для обращения Dex к API-серверу, а login.ash.dtln.cloud – для получения доступа к кластеру.
Мы разворачивали кластер без установщиков kubeadm или kops, так что OIDC-конфигурацию можно сразу добавлять в systemd-юнит. В остальных случаях настройку лучше сделать с помощью этих утилит.
- Редактируем юнит /etc/systemd/system/kube-apiserver.service и добавляем параметры запуска в секцию ExecStart:
--oidc-client-id=dex-k8s-authenticator \
--oidc-groups-claim=groups \
--oidc-username-claim=email \
--oidc-issuer-url=You must be registered for see links\ - Рестартуем наши API, проверяем, что они поднялись:
sudo systemctl daemon-reload
sudo systemctl restart kube-apiserver
sudo systemctl status kube-apiserver
Создаем мультидоменный сертификат
Теперь переходим в кластер Kubernetes.
- Ставим cert-manager, используя Helm:
helm repo add jetstackYou must be registered for see links
helm repo update
helm install cert-manager --namespace kube-system jetstack/cert-manager --version v0.13.0
- Описываем запрос на получение SAN-сертификата для наших доменов в cert.yml:
---
apiVersion: cert-manager.io/v1alpha2
kind: ClusterIssuer
metadata:
name: letsencrypt-dex
spec:
acme:
email: [email protected]
server:You must be registered for see links
privateKeySecretRef:
name: letsencrypt-key-dex
solvers:
- http01:
ingress:
class: nginx
---
apiVersion: cert-manager.io/v1alpha2
kind: Certificate
metadata:
name: auth-dex
namespace: kube-system
spec:
secretName: cert-auth-dex
issuerRef:
kind: ClusterIssuer
name: letsencrypt-dex
commonName: dex.ash.dtln.cloud
dnsNames:
- dex.ash.dtln.cloud
- login.ash.dtln.cloud
- Выполняем команду:
kubectl apply -f cert.yaml
- Теперь смотрим состояние нашего запроса на получение сертификата следующими командами:
kubectl get certificates --all-namespaces
kubectl get challenges --all-namespaces
- Ждем подтверждения, процесс может занять некоторое время:
Устанавливаем Dex
Для Dex нам понадобятся ca.crt, ca.key c мастер-сервера. Обычно они лежат в каталоге /etc/kubernetes/pki/
Также нужен сгенерированный нами раннее CA-сертификат с OpenLDAP, расположенный по пути /etc/ssl/certs/cacert.pem
- Скачиваем исходники dex-authenticator и переходим в каталог:
git clone [email protected]:mintel/dex-k8s-authenticator.git
cd dex-k8s-authenticator/
- Готовим конфиг для Dex-auth, вставляем содержимое ранее скопированного ca.crt, важно соблюдать отступы:
---
global:
deployEnv: prod
dexK8sAuthenticator:
clusters:
- name: 'ash.dtln.cloud'
short_description: "k8s cluster"
description: "Kubernetes cluster"
issuer:You must be registered for see links
k8s_master_uri:You must be registered for see links# url or ip
client_id: dex-k8s-authenticator
static_context_name: false
client_secret: acDEgDEcIg7RX0U7A9hlW2pGGraHDuMAZ4qFEKg2fUHHxr8
redirect_uri:You must be registered for see links
k8s_ca_pem: |
-----BEGIN CERTIFICATE-----
# Вставляем содержимое ca.crt
-----END CERTIFICATE-----
ingress:
enabled: true
annotations:
kubernetes.io/ingress.class: nginx
kubernetes.io/tls-acme: "true"
path: /
hosts:
- login.ash.dtln.cloud
tls:
- secretName: cert-auth-dex
hosts:
- login.ash.dtln.cloud
- Переводим содержимое cacert.pem в base64, чтобы добавить его в конфиг:
cacert.pem | base64
- Готовим конфиг для Dex, также важно соблюдать отступы. По желанию добавляем статических пользователей в секцию staticPasswords и генерируем им пароль в формате bcrypt:
---
global:
deployEnv: prod
tls:
certificate: |-
-----BEGIN CERTIFICATE-----
#содержимое ca.crt
-----END CERTIFICATE-----
key: |-
-----BEGIN RSA PRIVATE KEY-----
#содержимое ca.key
-----END RSA PRIVATE KEY-----
ingress:
enabled: true
annotations:
kubernetes.io/ingress.class: nginx
kubernetes.io/tls-acme: "true"
path: /
hosts:
- dex.ash.dtln.cloud
tls:
- secretName: cert-auth-dex
hosts:
- dex.ash.dtln.cloud
serviceAccount:
create: true
name: dex-auth-sa
config:
issuer:You must be registered for see links
storage:
type: kubernetes
config:
inCluster: true
web:
http: 0.0.0.0:5556
frontend:
theme: "coreos"
issuer: "kube-dtln"
issuerUrl: "You must be registered for see links"
expiry:
signingKeys: "6h"
idTokens: "24h"
logger:
level: debug
format: json
oauth2:
responseTypes: ["code", "token", "id_token"]
skipApprovalScreen: true
connectors:
- type: ldap
id: ldap
name: LDAP
config:
insecureNoSSL: false
insecureSkipVerify: false
startTLS: true # Включаем безопасное соединение
rootCAData: |-
#Содержимое cacert.pem в base64
#соблюдаем отступы
host: openldap.dtln.cloud:389
usernamePrompt: Email Address
userSearch:
baseDN: ou=People,dc=openldap,dc=dtln,dc=cloud
filter: "(objectClass=person)"
username: mail
idAttr: DN
emailAttr: mail
nameAttr: cn
groupSearch:
baseDN: ou=Groups,dc=openldap,dc=dtln,dc=cloud
filter: "(objectClass=groupOfNames)"
userMatchers:
- userAttr: DN
groupAttr: member
nameAttr: cn
staticClients:
- id: dex-k8s-authenticator
name: Kubernetes Dev Cluster
secret: 'acDEgDEcIg7RX0U7A9hlW2pGGraHDuMAZ4qFEKg2fUHHxr8'
redirectURIs:
-You must be registered for see links
enablePasswordDB: True
staticPasswords:
# Создаем статического пользователя с паролем в base64
- email: "[email protected]"
# bcrypt hash of the string "password"
hash: "$2a$10$2b2cU8CPhOTaGrs1HRQuAueS7JTT5ZHsHSzYiFPm1leZck7Mc8T4W"
username: "admin"
userID: "08a8684b-db88-4b73-90a9-3cd1661f5466"
- Теперь ставим dex и dex-auth-чарты из текущего каталога с нашими конфигами:
helm install dex --namespace kube-system --values dex.yaml charts/dex
helm install dex-auth --namespace kube-system --values dex-auth.yml charts/dex-k8s-authenticator
Генерируем kubeconfig
- Ждем, когда поднимутся pod’ы. Смотрим их логи и идем по адресу
You must be registered for see links. Логинимся под созданной нами учеткой, для авторизации мы использовали mail-формат логина.
Для static-записи выбираем вход через mail:
- После успешной аутентификации нас перенаправляют на страницу с инструкцией Dex-auth. C ее помощью мы генерируем kubeconfig-файл. В дальнейшем с ним мы будем подключаться к нашему кластеру:
- Теперь попытаемся получить доступ к кластеру и получаем ошибку. Все верно, наш пользователь не имеет прав, так что переходим к настройке RBAC.
Настраиваем RBAC-авторизацию
- Для примера привяжем статического пользователя к системной роли cluster-admin, а пользователей группы developers – к роли view, позволяющей только просматривать ресурсы. Тогда содержимое файла crb.yml должно быть таким:
---
apiVersion: rbac.authorization.k8s.io/v1beta1
kind: ClusterRoleBinding
metadata:
name: dex-admin
namespace: kube-system
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: cluster-admin
subjects:
- kind: User
name: "[email protected]"
---
apiVersion: rbac.authorization.k8s.io/v1beta1
kind: ClusterRoleBinding
metadata:
name: dex-developers
namespace: kube-system
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: view
subjects:
- kind: Group
name: "developers"
- Переключаемся на основной контекст и применяем созданный yaml-файл на кластер:
kubectl config set-context default
kubectl apply -f crb.yml
- Смотрим доступные контексты и переключаемся обратно на нашего пользователя:
kubectl config get-contexts
kubectl config set-context johndoe-ash.dtln.cloud
На этом настройка Dex в связке с OpenLDAP закончена.
Пара советов напоследок:
- Если возникают проблемы, первым делом нужно проверить форматирование yaml-файлов и обратить внимание на отступы.
- Слэши в адресах должны соответствовать примерам.
- Не забудьте посмотреть логи pod’ов Dex, Dex-auth, а также журналы юнитов kube-api на мастерах.