====== Доступ к приложениям в Bare-Metal Kubernetes ====== ===== Реклама ===== * Если Вы придерживаетесь рекомендации "не разворачивайте Kubernetes сами, а воспользуетесь managed service" то эту задачу за Вас решит провайдер, но, если Ваш путь - Kubernetes The Hard Way - Bare Metal, добро пожаловать поскольку эта тема меньше других освещена в документации * На нашем вебинаре мы на практических примерах разберем использование вариантов доступа к приложениям в Kubernetes через port-forward, proxy и ingress, узнаем, как лучше развернуть Ingress Controller и выясним, чем отличаются балансировщики нагрузки Nginx, HAProxy и Keepalived ===== Техническое задание ===== * Развернуть несколько web приложений, в том числе, Keycloak, в корпоративном On-Premises Kubernetes * Предоставить к ним безопасный, отказоустойчивой https доступ ===== Запись вебинара ===== * https://youtu.be/oIczkkD-hOU * Тэги: Kubernetes, LoadBalancer, ClusterIP, MetalLB, Nginx, Keepalived, Ingress-Nginx, Helm, HAProxy, ArgoCD, Dashboard ===== Методическая подготовка ===== * В процессе прохождения курса [[DevOps2. Использование Kubernetes]] в конце лабораторной работы 5.3 обнаружено, что кластер kubernetes, развернутый kubespray не поддерживает insecure-registry * Вместо решения, описанного в последнем фрагменте видео выбираем альтернативный вариант ===== Шаг 1. Исходные данные ===== * kubernetes развернут через kubespray "по дефолту" (уже сделано, что бы не ждать 40 минут) ~/kubespray# time ansible-playbook -i inventory/mycluster/hosts.yaml reset.yml ~/kubespray# git checkout origin/release-2.22 ~/kubespray# time pip3 install -r requirements.txt ~/kubespray# cp -rvfpT inventory/sample inventory/mycluster ~/kubespray# time ansible-playbook -i inventory/mycluster/hosts.yaml cluster.yml kube1:~# kubectl get nodes kube1:~# kubectl get ns * GitLab и его registry c http доступом и проектом с образом gowebd ===== Шаг 2. Переводим GitLab и его registry на https ===== * [[Пакет OpenSSL#Создание самоподписанного сертификата]] wildcard * [[Инструмент GitLab#Включение TLS]] * [[Инструмент GitLab#Установка через docker-compose]] ===== Шаг 3. Добавляем корпоративный сертификат в кластер kubernetes и рабочие станции ===== server# mkdir -p /var/www/html/ cp wild.crt /var/www/html/ca.crt bash -c ' scp /var/www/html/ca.crt kube1:/usr/local/share/ca-certificates/ ssh kube1 update-ca-certificates ssh kube1 systemctl restart containerd scp /var/www/html/ca.crt kube2:/usr/local/share/ca-certificates/ ssh kube2 update-ca-certificates ssh kube2 systemctl restart containerd scp /var/www/html/ca.crt kube3:/usr/local/share/ca-certificates/ ssh kube3 update-ca-certificates ssh kube3 systemctl restart containerd ' kubeN# crictl pull server.corp13.un:5000/student/gowebd crictl images crictl rmi server.corp13.un:5000/student/gowebd * Разворачиваем win client2 (ip/m: 172.16.1.100+X/24, dns: 192.168.X.10) * В паузах: * Знакомимся * Схема стенда (новые названия сетей LAN - KUBENET, INTERNET - CORPNET) * [[Преимущества обучения в specialist.ru]] * Добавляем в client2 ca.crt server# ss -lnp | grep ':80' server# apt install apache2 server# rm /var/www/html/index.html * Проверяем https доступ в gitlab с client2 и загрузку образа в k8s ===== Шаг 4. Доступ к приложению в Kubernetes через LoadBalancer ===== * Разворачиваем gowebd в [[Система Kubernetes#namespace для своего приложения]] с kube1 * Добавляем LoadBalancer [[Система Kubernetes#MetalLB]] * Добавляем [[Система Kubernetes#Service]] типа LoadBalancer ===== Шаг 5. Использование Nginx для HTTPS доступа к приложению ===== server# scp wild.crt gate:gowebd.crt; scp wild.key gate:gowebd.key * Устанавливаем на gate [[Сервис HTTP#NGINX]] * Настраиваем [[Сервис HTTP#HTTPS Прокси (пример 4)]] server# cat /etc/bind/corpX.un ... gowebd A 172.16.1.13 * Тестируем с client2 C:\Users\student>nslookup gowebd.corp13.un MSIE: https://gowebd.corp13.un * Тестируем отказоустойчивость, отключая узлы kubeN ===== Шаг 6. Делаем отказоустойчивым gate ===== * Импортируем gate2 server# cat /etc/bind/corp13.un ... gate1 A 192.168.13.21 gate2 A 192.168.13.22 * Превращаем gate в gate1 gate# hostnamectl set-hostname gate1.corp13.un gate# cat /etc/network/interfaces auto lo iface lo inet loopback auto eth0 iface eth0 inet static address 192.168.13.2N netmask 255.255.255.0 gateway 192.168.13.1 auto eth1 iface eth1 inet manual up ip link set eth1 up * Устанавливаем [[Сервис Keepalived]] gateN# cat /etc/keepalived/keepalived.conf vrrp_instance KUBE_GATE { state MASTER # state BACKUP interface eth0 virtual_router_id 1 virtual_ipaddress { 172.16.1.13/24 dev eth1 192.168.13.1/24 dev eth0 } virtual_routes { 0.0.0.0/0 via 172.16.1.254 dev eth1 } } gate# init 6 gate2# ifconfig eth0 inet 192.168.13.22 server# ssh-copy-id gate1 ssh-copy-id gate2 server# scp -3 gate1:/etc/network/interfaces gate2:/etc/network/ scp -3 gate1:/etc/resolv.conf gate2:/etc/ scp -3 gate1:/etc/sysctl.conf gate2:/etc/ gate2# hostnamectl set-hostname gate2.corp13.un gate2# cat /etc/network/interfaces gate2# init 6 gate2# apt update && apt install keepalived nginx -y server# scp -3 gate1:/etc/keepalived/keepalived.conf gate2:/etc/keepalived/ scp -3 gate1:/etc/nginx/sites-available/gowebd gate2:/etc/nginx/sites-available/gowebd scp -3 gate1:/etc/nginx/sites-enabled/gowebd gate2:/etc/nginx/sites-enabled/gowebd scp -3 gate1:gowebd.* gate2: gate2# cat /etc/keepalived/keepalived.conf * Сервис Keepalived [[Сервис Keepalived#Запуск и мониторинг]] * Сервис Nginx [[Сервис HTTP#Подключение, тестирование, применение и мониторинг конфигурации]] server# ssh gate1 tail -f /var/log/nginx/access.log server# ssh gate2 tail -f /var/log/messages * Обсуждаем достоинства (все работает) и недостатки (учет IP адресов в ПО версии 0.14.3 :) * Если есть время и желание выполняем [[#Шаг 6.2. Закрываем доступ в сеть кластера]] ===== Шаг 7. Заменяем nginx на ingress-nginx ===== * Меняем [[Система Kubernetes#Service]] на ClusterIP * Удаляем [[Система Kubernetes#MetalLB]] gateN# systemctl disable nginx --now * Установка [[Система Kubernetes#Helm]] на kube1 * Развертываем через [[Система Kubernetes#Работа с готовыми Charts]] [[Система Kubernetes#ingress-nginx]] ===== Шаг 8. Использование ingress для http/https доступа к приложению ===== server:~# scp wild.key kube1:gowebd.key; scp wild.crt kube1:gowebd.crt * Создаем [[Система Kubernetes#secrets tls]] для приложения gowebd * Развертываем [[Система Kubernetes#ingress example]] для приложения gowebd $ curl --connect-to "":"":kubeN:443 https://gowebd.corpX.un #-vk * Обсуждаем, почему не стоит прописать в DNS адреса узлов k8s для приложения gowebd? ===== Шаг 9. Отказоустойчивой доступ к приложению с использованием Keepalived ===== gateN# cat /etc/keepalived/keepalived.conf ... virtual_server 172.16.1.13 443 { protocol TCP lb_algo wlc lb_kind NAT real_server 192.168.13.221 443 {TCP_CHECK {}} real_server 192.168.13.222 443 {TCP_CHECK {}} real_server 192.168.13.223 443 {TCP_CHECK {}} } * Сервис Keepalived [[Сервис Keepalived#Запуск и мониторинг]] * Обсуждаем достоинства (все работает) и недостатки (сертификаты внутри кластера, кластер только один) ===== Шаг 10. Использование Helm репозитория для развертывания http приложения ===== kube1# kubectl delete ns my-ns * Продолжаем с момента, на котором остановились в курсе - [[Система Kubernetes#Работа со своим репозиторием]] Helm для переноса приложения с node на kube кластер $ curl http://kubeN/ -H "Host: gowebd.corp13.un" ===== Шаг 11. Использование HAProxy для https доступа к приложению ===== * Комментируем virtual_server в keepalived на gateN server# scp wild.* gate1: * [[Решение HAProxy]] server# ssh gate2 apt install haproxy server# scp -3 gate1:/etc/ssl/private/* gate2:/etc/ssl/private/ scp -3 gate1:/etc/haproxy/haproxy.cfg gate2:/etc/haproxy/haproxy.cfg ssh gate2 service haproxy restart server# ssh gateN tail -f /var/log/haproxy.log ===== Шаг 12. Использование ArgoCD для развертывания http приложения ===== * Удаляем приложение, можно просто namespace kube1# kubectl delete ns my-ns * Разворачиваем [[Контроллер ArgoCD]] * Устанавливаем [[Система Kubernetes#Инструмент командной строки kubectl]] и настраиваем [[Система Kubernetes#Подключение к кластеру]] на рабочей станции администратора * Используя port-forward подключаем рабочую станцию администратора к ArgoCD * Используя [[Контроллер ArgoCD#Управление приложениями через kubectl]] разворачиваем приложение * Подключаемся через [[Система Kubernetes#port-forward]] к нашему приложению cmder> kubectl port-forward -n my-ns services/my-webd-webd-chart 1234:80 * http://localhost:1234/ * Меняем в файле проекта gowebd-k8s/webd-chart/Chart.yaml версию образа и ждем обновление через argocd ===== Шаг 13. Использование Dashboard для работы с кластером ===== * Разворачиваем [[Система Kubernetes#Kubernetes Dashboard]] * Используя [[Система Kubernetes#kubectl proxy]] подключаем рабочую станцию администратора к Dashboard * Подключаемся через [[Система Kubernetes#kubectl proxy]] к нашему приложению * http://localhost:8001/api/v1/namespaces/my-ns/services/my-webd-webd-chart:80/proxy/ ===== Шаг 14. Готовимся к развертыванию Кeycloak ===== * Настраиваем HAProxy на работу с несколькими кластерами gate1# cp /etc/ssl/private/wild.crtkey /etc/ssl/private/gowebd.crtkey cp /etc/ssl/private/wild.crtkey /etc/ssl/private/keycloak.crtkey gate1# cat /etc/haproxy/haproxy.cfg ... gate1# service haproxy restart server# scp -3 gate1:/etc/haproxy/haproxy.cfg gate2:/etc/haproxy/haproxy.cfg scp -3 gate1:/etc/ssl/private/* gate2:/etc/ssl/private/ ssh gate2 service haproxy restart ===== Вопросы ===== * Сколько вариантов доступа к приложению в k8s Вы насчитали? :) ===== Дополнительные материалы ===== ===== Шаг 6.2. Закрываем доступ в сеть кластера ===== * Добавляем [[Сервис NAT]] gateN# apt install iptables conntrack iptables-persistent gateN# iptables -t nat --flush iptables -t nat -A POSTROUTING -o eth1 -j SNAT --to-source 172.16.1.13 iptables -t nat -A PREROUTING -i eth1 --destination 172.16.1.13 -p udp --dport 53 -j DNAT --to-destination 192.168.13.10:53 iptables --flush iptables -A FORWARD -i eth0 -j ACCEPT iptables -A FORWARD -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT iptables -A FORWARD -i eth1 -p udp -d 192.168.13.10 --dport 53 -j ACCEPT iptables -A FORWARD -j DROP conntrack -F netfilter-persistent save * Настраиваем win client2 dns: 172.16.1.13 ===== Как все вернуть обратно ===== * 1. Удалить gowebd с kube kube1:~# kubectl delete -f application.yaml kube1:~# kubectl delete ns my-ns kube1:~# rm application.yaml kube1:~# crictl rmi server.corp13.un:5000/student/gowebd:ver1.1 kube1:~# crictl rmi server.corp13.un:5000/student/gowebd:ver1.2 * 2. Удалить [[Система Kubernetes#Kubernetes Dashboard]] и Argo CD kube1:~# kubectl delete -n argocd -f https://raw.githubusercontent.com/argoproj/argo-cd/stable/manifests/install.yaml kube1:~# kubectl delete ns argocd cmder> rm -rf ~/.kube/ cmder> rm /usr/bin/kubectl.exe * 3. Удалить ingress-nginx и Helm с kube1 kube1:~# helm delete ingress-nginx --namespace ingress-nginx kube1:~# kubectl delete ns ingress-nginx kube1:~# rm -r helm* linux-amd64/ /usr/local/bin/helm kube1:~# rm -r gowebd/ ingress-nginx/ * 4. Удалить корневые сертификаты с kubeN kubeN# rm /usr/local/share/ca-certificates/ca.crt /etc/ssl/certs/ca.pem update-ca-certificates systemctl restart containerd * 5. Удалить манифесты и сертификаты проекта gowebd с kube1 kube1:~# rm gowebd.crt gowebd.key my-ingress.yaml my-webd-service.yaml my-webd-deployment.yaml * 6. Удалить VM client2 и gate2 * 7. Перезагрузить gate.isp.un * 8. Восстановить из снапшотов gate и server * 9. Удалить, чего не было в курсе server# rm -rf /var/www/ server# rm server.key