add: k3s (подключение внешнего

узла, part-1)
This commit is contained in:
Sergei Erjemin 2025-03-02 20:00:06 +03:00
parent ea88f3065a
commit a86d2d5ed7

View File

@ -461,3 +461,167 @@ kube-dns 10.42.1.8:53,10.42.2.6:53,10.42.1.8:53 + 3 more... 5d23h
### Разные архитектуры на узлах кластера (гетерогенность)
Когда мы подключили узлы (мастеры и воркеры) к кластеру, мы использовали одинаковые Orange Pi 5 Plus. Но, в реальности,
кластеры Kubernetes часто состоят из узлов с разными архитектурами и характеристиками. Например, если подключить к
к кластеру Raspberry Pi 3B увидим примерно такую картину:
```text
NAME STATUS ROLES AGE VERSION
opi5plus-1 Ready control-plane,etcd,master 3d3h v1.31.5+k3s1
opi5plus-2 Ready control-plane,etcd,master 6d3h v1.31.5+k3s1
opi5plus-3 Ready control-plane,etcd,master 5d1h v1.31.5+k3s1
rpi3b Ready <none> 27s v1.31.6+k3s1
```
Но надо помнить, что разные архитектуры могут быть оказаться несовместимы с некоторыми приложениями и образами.
Например, Raspberry Pi 3B — это 32-битный ARMv7 (armv7l), а Orange Pi 5 Plus — 64-битный ARMv8 (aarch64). Если в
подах используются бинарные файлы, скомпилированные под определённую архитектуру, то они могут не работать на узлах
с другой архитектурой. Также, некоторые образы Docker могут быть доступны только для определённых архитектур.
В ограниченном объеме можно подключать узлы на других платформах. Например, Windows, может иметь только воркер-узлы на k8s
(начиная с версии 1.14), а в k3s экспериментальная поддержка Windows-воркеров (начиная с с версии 1.24). На macOS нет
официальной поддержки Kubernetes/k3s для узлов на macOS (можно использовать обходные пути с использованием виртуальныех
машин).
### Добавление узлов во "внешнем" интернете
В моем проекте (специализированном поисковике) будет нужно парсить и интернет сайты, включая заблокированные сайты.
К сожалению современный интернет имеет взаимные региональные блокировки и просто использовать VPN интернет-соединения
не сработает. Выходом может стать использование воркер-узлов во внешнем интернете. Идея в том, что если какой-нибудь
URL не получится обработать на поде одного узла, то можно попробовать обработать его на другом узле, в другой локации.
Так как узлы k3s взаимодействуют через API на 6443-порте, то для доступа к кластеру из внешнего интернета нужно будет
обеспечить проброс трафика через роутер сети на один из мастер-узлов. НО у нас три мастер-узла, а значит если упадет
узел на который происходит проброс, то удаленный воркер-узел "отвелится" и потеряет доступ к кластеру. Объединить
IP всеx мастер-узлов в один можно с помощью балансировщика нагрузки **Keepalived**. Он создает виртуальный IP-адрес
(VIP), c которого перенапрвляет трафик на один из мастер-узлов, и если этот узел упадет, то трафик перенаправится
на другой и так далее.
Установи `Keepalived` на все мастер-ноды:
```bash
sudo apt update
sudo apt install keepalived
```
Настроим `Keepalived` последовательно на каждом мастере. Для этого отредактируем (создадим) файл конфигурации
`/etc/keepalived/keepalived.conf`:
```bash
sudo nano /etc/keepalived/keepalived.conf
```
На первом мастер-узле (хост -- `opi5plus-1`, IP -- `192.168.1.26`):
```text
vrrp_instance VI_1 {
state MASTER # ЭТО ГЛАВНЫЙ ХОСТ. ПО УМОЛЧАНИЮ ТРАФИК С VIP БУДЕТ ПЕРЕНАПРАВЛЯТЬСЯ НА ЭТОТ ХОСТ
interface enP4p65s0 # У Orange Pi 5 plus два интерфейса, и хост подключен по интерфейсу enP4p65s0
virtual_router_id 51
priority 100 # Самый высокий приоритет
advert_int 1
unicast_src_ip 192.168.1.26 # IP текущего хоста (opi5plus-1)
unicast_peer {
192.168.1.27 # IP второго хоста (opi5plus-2)
192.168.1.28 # IP третьего хоста (opi5plus-3)
}
virtual_ipaddress {
192.168.1.200 # Виртуальный IP (VIP), он должен быть исключен из диапазона DHCP
}
}
```
На втором мастер-узле (хост -- `opi5plus-2`, IP -- `192.168.1.27`):
```text
vrrp_instance VI_1 {
state BACKUP # ЭТО ВТОРОЙ ХОСТ. ОН БУДЕТ ПОЛУЧАТЬ ТРАФИК С VIP, ЕСЛИ ГЛАВНЫЙ ХОСТ УПАДЕТ
interface enP4p65s0 # У Orange Pi 5 plus два интерфейса, и хост подключен по интерфейсу enP4p65s0
virtual_router_id 51
priority 90 # Меньший приоритет
advert_int 1
unicast_src_ip 192.168.1.27 # IP текущего хоста (opi5plus-2)
unicast_peer {
192.168.1.26 # IP первого хоста (opi5plus-1)
192.168.1.28 # IP третьего хоста (opi5plus-3)
}
virtual_ipaddress {
192.168.1.200 # Виртуальный IP
}
}
```
И, наконец, на третьем мастер-узле (хост -- `opi5plus-3`, IP -- `192.168.1.28`):
```text
vrrp_instance VI_1 {
state BACKUP # ЭТО ТРЕТИЙ ХОСТ. ОН БУДЕТ ПОЛУЧАТЬ ТРАФИК С VIP, ЕСЛИ ГЛАВНЫЙ- И БЭКАП-ХОСТ УПАДЕТ
interface enP4p65s0 # У Orange Pi 5 plus два интерфейса, и этот узел подключен по enP4p65s0
virtual_router_id 51
priority 80 # Еще меньший приоритет
advert_int 1
unicast_src_ip 192.168.1.28 # IP текущего хоста (opi5plus-3)
unicast_peer {
192.168.1.27 # IP первого хоста (opi5plus-1)
192.168.1.28 # IP второго хоста (opi5plus-2)
}
virtual_ipaddress {
192.168.1.200 # Виртуальный IP
}
}
```
Добавим `Keepalived` в автозагрузку на всех мастер-узлах и запустим его:
```bash
sudo systemctl enable keepalived
sudo systemctl start keepalived
```
Теперь, если вы на первом мастер-узле (opi5plus-1) проверить доступные IP-адреса:
```bash
ip addr show
```
то увидим:
```text
...
...
2: enP4p65s0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc fq_codel state UP group default qlen 1000
link/ether c0:74:2b:fd:42:3c brd ff:ff:ff:ff:ff:ff
inet 192.168.1.26/24 brd 192.168.1.255 scope global dynamic noprefixroute enP4p65s0
valid_lft 68779sec preferred_lft 68779sec
inet 192.168.1.200/32 scope global enP4p65s0
valid_lft forever preferred_lft forever
...
```
Обратите внимание на виртуальный IP-адрес `192.168.1.200` находится в другой подсети (CIDR) и имеет маску `/32` (то
есть с маской подсети `255.255.255.255`). Это "точечная" подсеть, содержащая только один адрес, не привязан к основной
подсети интерфейса (/24) и это позволяет VIP "плавать" между узлами, не вызывая конфликтов с основными IP-адресами
и не требуя изменения подсети на каждом узле. VIP рассматривается как уникальный адрес, не требующий маршрутизации,
он просто "привязан" к интерфейсу.
Теперь панель `Traefik` доступна по VIP-адресу `http://192.168.1.200:9000/dashboard/#`, т.к. трафик с этого адреса
будет перенаправлен на один из мастер-узлов.
API Kubernetes тоже теперь доступен по VIP-адресу. Все воркер-узлы, подключенные к кластеру, лучше подключать к
кластеру через VIP-адрес. Сами мастер узлы знают свои IP и взаимодействую через `etcd`, но воркеры подключаясь
через VIP будут более устойчивы к сбоям мастер-узлов. Подсоединить удаленный воркер-узел к кластеру лучше через VIP.
Для этого нужно на роутере сети настроить проброс порта `6443` с внешнего IP роутера, на виртуальный IP-адрес внутри
сети (тоже на `6443` порт). После проверить, что с внешнего хоста API Kubernetes доступно:
```bash
curl -k https://<PUBLIC_IP_ROUTER>:6443
```
Если отклик есть (например, `Unauthorized`), то можно подключить удаленый воркер-узел к кластеру:
```bash
curl -sfL https://get.k3s.io | sh -s - agent --server https://<PUBLIC_IP_ROUTER>:6443 --token <TOKEN>
```
Когда процесс завершится, на любом мастер-узле можно проверить, что воркер-узел подключился:
```bash
sudo k3s kubectl get nodes
```
Получим, например:
```text
NAME STATUS ROLES AGE VERSION
opi5plus-1 Ready control-plane,etcd,master 5d4h v1.31.5+k3s1
opi5plus-2 Ready control-plane,etcd,master 8d v1.31.5+k3s1
opi5plus-3 Ready control-plane,etcd,master 7d2h v1.31.5+k3s1
rpi3b Ready <none> 25h v1.31.6+k3s1
vps-sw-eye Ready <none> 7h35m v1.31.6+k3s1
```