[Перевод] Миграция с Docker на containerd в среде Kubernetes

ez9pwvnwp4gixqa2menttnf6n9e.jpeg

Kubernetes отказывается от Docker для выполнения контейнеров после версии 1.20. (Прим. переводчика: в декабре мы уже писали о том, как это изменение повлияет на задачи разработчиков и инженеров эксплуатации: «Docker is deprecated — и как теперь быть?»)

Без паники. Контейнеры Docker все еще поддерживаются, но без dockershim/Docker — слоя между Kubernetes и containerd, который будет удален, начиная с версии 1.22+.

Если вы используете Docker, нужно перейти на поддерживаемый интерфейс container runtime interface (CRI). Хорошим вариантом будет containerd — он уже есть у вас на ноде Kubernetes, если вы работаете с Docker.

Дополнительное преимущество — меньше издержек благодаря отсутствию dockershim и уровней преобразования Docker, как видно на иллюстрации.

lzmugyjmxidhhy00cqr7qgxg8qu.png
Переход с dockershim на containerd CRI


Как мигрировать?

Сначала проверяем, какая среда запуска контейнеров (container runtime) у нас используется. Это можно сделать командой kubectl get nodes -o wide

Как видите, здесь у нас Docker.

NAME       STATUS   ROLES                  AGE     VERSION   INTERNAL-IP    EXTERNAL-IP   OS-IMAGE             KERNEL-VERSION                             CONTAINER-RUNTIME
k8s-cn01   Ready    control-plane,master   78m     v1.20.4   10.65.79.164           Ubuntu 20.04.2 LTS   5.4.0-67-generic                           docker://20.10.5
k8s-wn01   Ready                     64m     v1.20.4   10.65.79.131           Ubuntu 20.04.2 LTS   5.4.0-67-generic                           docker://20.10.5
k8s-wn02   Ready                     4m16s   v1.20.4   10.65.79.244           CentOS Linux 8       4.18.0-240.15.1.el8_3.centos.plus.x86_64   docker://20.10.5

kubectl get nodes -o wide

Проверим, есть ли у нас containerd CLI /usr/bin/ctr и неймспейс moby из Docker.

NAME LABELS
moby

просмотр неймспейсов

Можно посмотреть запущенные контейнеры в этом неймспейсе.

CONTAINER                                                           IMAGE    RUNTIME
04f9500885c473c9cb2b4f8d09dc4feea5c24838519b9a01251011830bab16a2    -        io.containerd.runc.v2
57d4c75ab9947829228a087b857b203c48a9d1c83de0a1b49af3624fb08c9d33    -        io.containerd.runc.v2
934c007a259018a5cbda56dd8e066a66f2c9cfcb8003e7f8d25833fe462582fd    -        io.containerd.runc.v2
94315822d8f8a05e1be5adb7e5c18add33cbf2604057100c87572b5fc55169cd    -        io.containerd.runc.v2
dfa01906e845239c74a0b35d457e845382468dd9ad6e99dd0c16be30f8a23a2d    -        io.containerd.runc.v2

Просмотр списка контейнеров в неймспейсе moby

Если все выглядит нормально, можно изменить CRI. Меняем по одной ноде за раз, начиная с рабочих и заканчивая мастером. Если мастер только один, вы временно потеряете доступ к кластеру, но он восстановится сам.


Cordon и drain

Выполняем cordon и drain для нод, чтобы перенести поды на другие ноды.

root@k8s-cn01:~# kubectl cordon k8s-wn01
node/k8s-wn01 cordoned

root@k8s-cn01:~# kubectl drain k8s-wn01 --ignore-daemonsets
node/k8s-wn01 already cordoned
WARNING: ignoring DaemonSet-managed Pods: kube-system/kube-proxy-9wnh4, kube-system/weave-net-pgptm
evicting pod default/nginx-6799fc88d8-r44x9
pod/nginx-6799fc88d8-r44x9 evicted
node/k8s-wn01 evicted

root@k8s-cn01:~# kubectl get nodes
NAME       STATUS                     ROLES                  AGE    VERSION
k8s-cn01   Ready                      control-plane,master   138m   v1.20.4
k8s-wn01   Ready,SchedulingDisabled                    124m   v1.20.4
k8s-wn02   Ready                                       64m    v1.20.4

Останавливаем сервисы

 systemctl stop kubelet
  systemctl stop docker

остановка kubelet и docker


Удаляем Docker (по желанию)

Удалять Docker не обязательно, но так все будет понятнее, на диске освободится немного места, а риска ошибок будет меньше.

apt purge docker-ce docker-ce-cli
OR
yum remove docker-ce docker-ce-cli

удаление docker


Конфигурация containerd

Отключим строку disabled_plugins в /etc/containerd/config.toml, чтобы CRI загрузился.

#disabled_plugins = ["cri"]

/etc/containerd/config.tom

Если для cotainerd нет файла конфигурации, создайте новый дефолтный файл.

containerd config default > /etc/containerd/config.toml

создание файла конфигурации

Перезапустим containerd.

systemctl restart containerd

Меняем среду запуска

Правим файл /var/lib/kubelet/kubeadm-flags.env и добавляем среду containerd во флаги — --container-runtimeremote и --container-runtimeendpoint=unix:///run/containerd/containerd.sock"

Файл kubeadm-flags будет выглядеть как-то так:

KUBELET_KUBEADM_ARGS="--cgroup-driver=systemd --network-plugin=cni --pod-infra-container-image=k8s.gcr.io/pause:3.2
--resolv-conf=/run/systemd/resolve/resolv.conf --container-runtime=remote --container-runtime-endpoint=unix:///run/containerd/containerd.sock"

/var/lib/kubelet/kubeadm-flags.env


Запускаем kubelet

Изменив среду запуска, запускаем сервис kubelet.

systemctl start kubelet

запуск kubelet


Проверяем

Запускаем kubectl get nodes -o wide и видим, что у измененной ноды новая среда запуска.

NAME       STATUS                   ROLES                  AGE    VERSION   INTERNAL-IP    EXTERNAL-IP   OS-IMAGE             KERNEL-VERSION                             CONTAINER-RUNTIME
k8s-cn01   Ready                    control-plane,master   131m   v1.20.4   10.65.79.164           Ubuntu 20.04.2 LTS   5.4.0-67-generic                           docker://20.10.5
k8s-wn01   Ready,,SchedulingDisabled                         117m   v1.20.4   10.65.79.131                 Ubuntu 20.04.2 LTS   5.4.0-67-generic                           containerd://1.4.4
k8s-wn02   Ready                              57m    v1.20.4   10.65.79.244           CentOS Linux 8       4.18.0-240.15.1.el8_3.centos.plus.x86_64   docker://20.10.5

Измененная нода все еще имеет статус cordoned. Отменим его.

root@k8s-cn01:~# kubectl uncordon k8s-wn01
node/k8s-wn01 uncordoned

root@k8s-cn01:~# kubectl get nodes
NAME       STATUS   ROLES                  AGE    VERSION
k8s-cn01   Ready    control-plane,master   143m   v1.20.4
k8s-wn01   Ready                     129m   v1.20.4
k8s-wn02   Ready                     69m    v1.20.4

Если проверить неймспейсы на ноде сейчас, увидим k8s.io. Неймспейс moby теперь пуст, никакие контейнеры в нем не выполняются — все мигрировало в k8s.io.

root@k8s-wn01:~# ctr namespaces list
NAME   LABELS
k8s.io
moby

root@k8s-wn01:~# ctr --namespace moby container list
CONTAINER    IMAGE    RUNTIME

root@k8s-wn01:~# ctr --namespace k8s.io container list
CONTAINER                                                           IMAGE                                    RUNTIME
08d4b5ca1f0ddd08fff7f64ea4eb12be66b8ec860d119565e553c84d16942d26    docker.io/weaveworks/weave-kube:2.8.1    io.containerd.runc.v2
1c9e3f61f542b12abb4b849075b084fb7fe3f69b89ce668d73022c2cd647bcd1    k8s.gcr.io/pause:3.2                     io.containerd.runc.v2
1f8e0c5a6f8219de1c8f25bbb28d5d5c71b74e9ccfb9620007701847d29f23a2    k8s.gcr.io/kube-proxy:v1.20.4            io.containerd.runc.v2
39296ebd6017a7c83cd58004c94708c927f10a996a4e6ba0bbf003c6713fe713    docker.io/weaveworks/weave-kube:2.8.1    io.containerd.runc.v2
67f812954f46fa5c1f6ab39e681e2481f868309f28bd1b8ba44cce53f5c0071c    docker.io/weaveworks/weave-npc:2.8.1     io.containerd.runc.v2
9caed1d57d40cedef736e45adf550eda6a0befd32712e5b6af5d711681ba71f0    k8s.gcr.io/pause:3.2                     io.containerd.runc.v2

просмотр нового неймспейса k8s.io

Мы успешно изменили CRI, теперь можно повторить все то же самое для следующей ноды.

© Habrahabr.ru