Русский
Русский
English
Статистика
Реклама

Cri-o

CRI-O как замена Docker в качестве исполняемой среды для Kubernetes настройка на CentOS 8

20.08.2020 12:11:50 | Автор: admin
Привет! Меня зовут Сергей, я DevOps в Surf. DevOps-отдел в Surf ставит своей задачей не только налаживание взаимодействия между специалистами и интеграцию рабочих процессов, но и активные исследования и внедрение актуальных технологий как в собственную инфраструктуру, так и в инфраструктуру заказчика.

Ниже я немного расскажу об изменениях в технологическом стеке для контейнеров, с которыми мы встретились при изучении дистрибутива CentOS 8 и о том, что такое CRI-O и как быстро настроить с его помощью исполняемую среду для Kubernetes.



Почему Docker отсутствует в стандартной поставке CentOS 8


После установки последних крупных релизов RHEL 8 или CentOS 8 нельзя не заметить: в этих дистрибутивах и официальных репозиториях отсутствует приложение Docker, которое идеологически и функционально заменяют собой пакеты Podman, Buildah (присутствуют в дистрибутиве по умолчанию) и CRI-O. Это связано с практической реализацией стандартов, разрабатываемых, в том числе, и компанией Red Hat в рамках проекта Open Container Initiative (OCI).

Цель OCI, являющейся частью The Linux Foundation, создание открытых индустриальных стандартов для форматов и исполняемой среды контейнеров, которые бы решали сразу несколько задач. Во-первых, не противоречили как философии Linux (например, в той её части, что каждая программа должна выполнять какое-то одно действие, а Docker представляет собой этакий комбайн всё-в-одном). Во-вторых, могли бы устранить все имеющиеся недостатки в программном обеспечении Docker. В-третьих, были бы полностью совместимыми с бизнес-требованиями, выдвигаемыми ведущими коммерческими платформами для развёртывания, управления и обслуживания контейнеризованных приложений (например, Red Hat OpenShift).

Недостатки Docker и достоинства нового ПО уже были довольно подробно описаны в этой статье, а с подробным описанием как всего предлагаемого в рамках проекта OCI стека ПО и его архитектурными особенностями можно ознакомиться в официальной документации и статьях как от самой Red Hat (неплохая статья в Red Hat blog), так и в сторонних обзорах.

Важно отметить, какую функциональность имеют компоненты предлагаемого стека:

  • Podman непосредственное взаимодействие с контейнерами и хранилищем образов через процесс runC;
  • Buildah сборка и загрузка в реестр образов;
  • CRI-O исполняемая среда для систем оркестрации контейнеров (например, Kubernetes).

Думаю, что для понимания общей схемы взаимодействия между компонентами стека целесообразно привести здесь схему связей Kubernetes c runC и низкоуровневыми библиотеками с использованием CRI-O:



CRI-O и Kubernetes придерживаются одного и того же цикла выпуска и поддержки (матрица совместимости очень проста: мажорные версии Kubernetes и CRI-O совпадают), а это, с учётом ориентира на полное и всестороннее тестирование работы данного стека разработчиками, даёт нам право ожидать максимально достижимой стабильности в работе при любых сценариях использования (здесь на пользу идет и относительная легковесность CRI-O по сравнению с Docker в силу целенаправленного ограничения функциональности).

При установке Kubernetes right way способом (по мнению OCI, конечно) с использованием CRI-O на CentOS 8 мы столкнулись с небольшими затруднениями, которые, однако, успешно преодолели. Буду рад поделиться с вами инструкцией по установке и настройке, которые в совокупности займут от силы 10 минут.

Как развернуть Kubernetes на CentOS 8 с использованием среды CRI-O


Предварительные условия: наличие как минимум одного хоста (2 cores, 4 GB RAM, накопитель не менее 15 GB) с установленной CentOS 8 (рекомендуется профиль установки Server), а также записи для него в локальном DNS (в крайнем случае можно обойтись записью в /etc/hosts). И не забудьте отключить swap.

Все операции на хосте производим от имени пользователя root, будьте внимательны.

  1. На первом шаге настроим ОС, установим и настроим предварительные зависимости для CRI-O.
    • Обновим ОС:

      dnf -y update
      

    • Далее требуется настроить файрволл и SELinux. Здесь у нас всё зависит от окружения, в котором будут работать наш хост или хосты. Вы можете либо настроить файрволл по рекомендациям из документации, либо, если находитесь в доверенной сети или применяете сторонний файрволл, изменить зону по умолчанию на доверенную или выключить файрволл:

      firewall-cmd --set-default-zone trustedfirewall-cmd --reload
      

      Чтобы выключить файрволл можно использовать следующую команду:

      systemctl disable --now firewalld
      

      SELinux требуется выключить либо перевести в режим permissive:

      setenforce 0sed -i 's/^SELINUX=enforcing$/SELINUX=permissive/' /etc/selinux/config
      

    • загрузим необходимые модули ядра и пакеты, настроим автоматическую загрузку модуля br_netfilter при старте системы:

      modprobe overlaymodprobe br_netfilterecho "br_netfilter" >> /etc/modules-load.d/br_netfilter.confdnf -y install iproute-tc
      

    • для активации форвардинга пакетов и корректной обработки трафика сделаем соответствующие настройки:

      cat > /etc/sysctl.d/99-kubernetes-cri.conf <<EOFnet.bridge.bridge-nf-call-iptables = 1net.ipv4.ip_forward = 1net.bridge.bridge-nf-call-ip6tables = 1EOF
      

      применим сделанные настройки:

      sysctl --system
      

    • зададим необходимую версию CRI-O (мажорная версия CRI-O, как уже упоминалось, совпадают с требуемой версией Kubernetes), так как последняя стабильная версия Kubernetes на данный момент 1.18:

      export REQUIRED_VERSION=1.18
      

      добавим необходимые репозитории:

      dnf -y install 'dnf-command(copr)'dnf -y copr enable rhcontainerbot/container-selinuxcurl -L -o /etc/yum.repos.d/devel:kubic:libcontainers:stable.repo https://download.opensuse.org/repositories/devel:kubic:libcontainers:stable/CentOS_8/devel:kubic:libcontainers:stable.repocurl -L -o /etc/yum.repos.d/devel:kubic:libcontainers:stable:cri-o:$REQUIRED_VERSION.repo https://download.opensuse.org/repositories/devel:kubic:libcontainers:stable:cri-o:$REQUIRED_VERSION/CentOS_8/devel:kubic:libcontainers:stable:cri-o:$REQUIRED_VERSION.repo
      

    • теперь мы можем установить CRI-O:

      dnf -y install cri-o
      

      Обратите внимание на первый нюанс, который мы встречаем в процессе инсталляции: необходимо отредактировать конфигурацию CRI-O перед запуском сервиса, так как требуемый компонент conmon имеет отличное от указанного место размещения:

      sed -i 's/\/usr\/libexec\/crio\/conmon/\/usr\/bin\/conmon/' /etc/crio/crio.conf
      


      Теперь можно активировать и запустить демон CRI-O:

      systemctl enable --now crio
      


      Можно проверить статус демона:

      systemctl status crio
      

  2. Установка и активация Kubernetes.
    • Добавим требуемый репозиторий:

      cat <<EOF > /etc/yum.repos.d/kubernetes.repo[kubernetes]name=Kubernetesbaseurl=https://packages.cloud.google.com/yum/repos/kubernetes-el7-\$basearchenabled=1gpgcheck=1repo_gpgcheck=1gpgkey=https://packages.cloud.google.com/yum/doc/yum-key.gpg https://packages.cloud.google.com/yum/doc/rpm-package-key.gpgexclude=kubelet kubeadm kubectlEOF
      

      Теперь мы можем установить Kubernetes (версии 1.18, как уже указывалось выше):

      dnf install -y kubelet-1.18* kubeadm-1.18* kubectl-1.18* --disableexcludes=kubernetes
      

    • Второй важный нюанс: так как мы не используем демон Docker, а используем демон CRI-O, до запуска и инициализации Kubernetes требуется внести соответствующие настройки в конфигурационный файл /var/lib/kubelet/config.yaml, предварительно создав нужный каталог:

      mkdir /var/lib/kubeletcat <<EOF > /var/lib/kubelet/config.yamlapiVersion: kubelet.config.k8s.io/v1beta1kind: KubeletConfigurationcgroupDriver: systemdEOF
      

    • Третий важный момент, с которым мы сталкиваемся при установке: несмотря на то, что мы указали используемый драйвер cgroup, и его настройка через аргументы передаваемые kubelet устарела (на что прямо указано в документации), нам необходимо добавить в файл аргументы, иначе наш кластер не инициализируется:

      cat /dev/null > /etc/sysconfig/kubeletcat <<EOF > /etc/sysconfig/kubeletKUBELET_EXTRA_ARGS=--container-runtime=remote --cgroup-driver=systemd --container-runtime-endpoint='unix:///var/run/crio/crio.sock'EOF
      

    • Теперь мы можем активировать демон kubelet:

      sudo systemctl enable --now kubelet
      

      Чтобы настроить control-plane или worker ноды за считанные минуты, вы можете воспользоваться этим скриптом.

  3. Пора инициализировать наш кластер.
    • Для инициализации кластера выполните команду:

      kubeadm init --pod-network-cidr=10.244.0.0/16
      

      Обязательно запишите команду присоединения к кластеру kubeadm join ..., которой предлагается воспользоваться в конце вывода, либо, как минимум, указанные токены.

    • Установим плагин (CNI) для работы Pod network. Я рекомендую использовать Calico. Возможно, более популярный Flannel имеет проблемы с совместимостью с nftables, да и Calico единственная реализация CNI, рекомендуемая и полностью протестированная проектом Kubernetes:

      kubectl --kubeconfig /etc/kubernetes/admin.conf apply -f https://docs.projectcalico.org/v3.15/manifests/calico.yaml 
      

    • Для подключения worker ноды к нашему кластеру её требуется настроить по пунктам инструкции 1 и 2, либо воспользоваться скриптом, затем выполнить команду из вывода kubeadm init ..., которую мы записали на предыдущем этапе:

      kubeadm join $CONTROL_PLANE_ADDRESS:6443 --token $TOKEN \    --discovery-token-ca-cert-hash $TOKEN_HASH
      

    • Проверим, что наш кластер инициализирован и начал работу:

      kubectl --kubeconfig=/etc/kubernetes/admin.conf get pods -A
      

    Готово! Вы уже можете размещать на вашем K8s кластере полезную нагрузку.

Что нас ждёт впереди


Надеюсь, что инструкция выше помогла сэкономить вам немного времени и нервов.
Исход процессов, происходящих в индустрии, зачастую зависит от того, как их принимает основная масса конечных пользователей и разработчиков другого ПО в соответствующей нише. Пока не совсем ясно, к какому итогу через несколько лет приведут инициативы OCI, но мы будем с удовольствием за этим следить. Своим мнением вы можете поделиться прямо сейчас в комментариях.
Stay tuned!

Данная статья появилась благодаря следующим источникам:

Подробнее..

Перевод Как заменить container runtime в Kubernetes

14.03.2021 18:20:23 | Автор: admin

Братцы! Скорее всего вы уже знаете, что Kubernetes отказался от поддержки Docker в качестве среды выполнения контейнеров (container runtime) в будующих версиях. В релизе 1.20, вышедшем в конце 2020 года Dockershim помечен как не рекомендованный (depricated). В релизе 1.22, выход которого запланирован на конец 2021 года, от его поддержки планируют полностью отказаться.

Если вы используете управляемые кластеры Kubernetes (такие как GKE, EKS, AKS) это не станет для вас серьезной проблемой и скорее всего переключение будет простым. Но если вы управляете кластером самостоятельно (например с помощью kubeadm) и используете Docker в container runtime, рано или поздно, вам придется заменить ее, чтобы иметь возможность обновлениять Kubernetes до последних версий.

Задача этой статьи не дать исчерпывающую информацию о причинах такого решения со стороны разработчиков Kubernetes или подробно изучить поведения конкретных container runtime в кластере Kubernetes. Вместо этого мы шаг за шагом разберемся как переключить Docker container runtime на другое решение, поддерживающее стандарт Container Runtime Interface(CRI). Если вас интересуют причины из-за которых Docker больше не рекомендован к использованию, ознакомьтесь со статьей из официального блога Kubernetes Don't Panic: Kubernetes and Docker.

Чтобы не пропустить новые статьи подписывайтесь на телеграм-канал Mops DevOps

Что проверять в первую очередь

Влияние на рабочие нагрузки, выполняемые в вашем кластере, должно быть минимальным. Единственное, о чем вам нужно позаботиться, - это используете ли вы Docker-in-Docker в любой из ваших контейнерных рабочих нагрузок, смонтировав сокет Docker /var/run/docker.sock. В этом случае вам нужно будет найти альтернативу (например, Kaniko), прежде чем переключаться с Docker на новую container runtime.

Также настоятельно рекомендуется сделать резервную копию ваших данных, прежде чем переходить к переключению среды выполнения контейнера!

Приступим к работе!

Отлично, теперь, когда вы готовы к переключению container runtime, можно начинать. В этой статье бедем использовать containerd в качестве container runtime, но приведенные ниже шаги можно адаптировать к другой среде выполнения контейнера, например, CRI-O.

Мы начнем с рабочих узлов (worker nodes) и только потом выполним аналогичные действия на мастерах (control plane).

Worker nodes

Указанные ниже шаги нужно выполнить на всех рабочих узлах кластера.

1) Вначале выполним drain и cordon узла кластера, чтобы эвакуировать нагрузки с него и предотвратить планирование новых нагрузок во время выполнения последующих операций:

kubectl cordon <node_name>kubectl drain <node_name>

Замечание: если на узлах кластера запущены DaemonSets, необходимо использовать флаг --ignore-daemonsets, чтобы продолжить эвакуацию остальных pods. Не волнуйтесь kubelet эти pods автоматически пересоздаст с помощью новой container runtime, когда процедура переключения будет завершена. Если у вас есть критические сервисы, запущенные в DaemonSet, и вы не хотите, чтобы они работали во время процесса переключения, вы можете либо указать nodeSelector в своем DaemonSet, либо полностью удалить и переустановить их в конце процесса.

2) Останавливаем сервис kubelet:

sudo systemctl stop kubeletsudo systemctl status kubelet

3) Удаляем Docker

Я не буду подробно описывать команды, поскольку это зависит от вашего дистрибутива Linux и способа установки Docker. Просто будьте осторожны, если вы хотите полностью очистить артефакты Docker, возможно, вам придется вручную удалить некоторые файлы (например, /var/ lib/docker).

Подробную инструкцию вы найдете в документации Docker.

4) Устанавливаем countainerd используя официальному руководству для вашей версии операционной системы.

5) Выполняем Enableи Startсервиса containerd:

sudo systemctl enable containerdsudo systemctl start containerdsudo systemctl status containerd

6) Kubernetes взаимодействует с container runtime через плагин CRI . Убедитесь, что этот плагин не был отключен при установке containerd.

Проверим файл конфигурации:

vim /etc/containerd/config.toml проверяем параметрdisabled_plugins = [""]

Если на предыдущем шаге внесены изменения в конфигурационный файл, необходимо перезагрузить сервис containerd:

sudo systemctl restart containerd

7) Отредактируем конфигурационный файл kubelet:

vim /var/lib/kubelet/kubeadm-flags.envДобавим в конфигурационный файл флаги для переменной KUBELET_KUBEADM_ARGS(при необходимости измените путь к container runtime)--container-runtime=remote --container-runtime-endpoint=/run/containerd/containerd.sock

8) Запускаем сервис kubelet:

sudo systemctl start kubelet

9) Проверяем, что на узле запущена требуемая версия container runtime:

kubectl describe node <node_name>
System Info:  Machine ID:                 21a5dd31f86c4  System UUID:                4227EF55-BA3BCCB57BCE  Boot ID:                    77229747-9ea581ec6773  Kernel Version:             3.10.0-1127.10.1.el7.x86_64  OS Image:                   Red Hat Enterprise Linux Server 7.8 (Maipo)  Operating System:           linux  Architecture:               amd64>>Container Runtime Version:  containerd://1.4.3  Kubelet Version:            v1.20.2  Kube-Proxy Version:         v1.20.2

10) Выполняем Uncordon на узле, чтобы разрешить планировать на него нагрузки, и проверим статус работы pods:

kubectl uncordon <node_name>

Вот и все, как только все ваши поды будут перезапущены, вы можете перейти к настройке следующего узла кластера!

Control Plane

Процедура обновление container runtime на мастерах полностью повторяет установку на рабочих узлах кластера. Однако будьте осторожны, если ваш кластер запущен с единственным мастером.

Пока новая container runtime будет загружать образы kube-apiserver, etcd и coredns и создавать соответствующие pods, кластер будет недоступен. У вас также не должна быть возможности запускать команду kubectl.

Вот несколько советов, которые помогут вам следить за запуском container runtime и устранять потенциальные проблемы:

1) Используем journalctl, чтобы отслеживать изменения в журналах kubelet:

journalctl -u kubelet

2) Проверяем журналы containerd:

journalctl -u containerd

3) Используем утилиту crictl, чтобы убедится, что контейнеры запущены:

crictl --runtime-endpoint /run/containerd/containerd.sock ps

4) После замены container runtime убедимся, что используем требуемую версию, выполнив команду на всех узлах кластера:

kubectl describe node <master_node_name>также можем выполнить команду, она выведет информацию сразу по всем узлам кластераkubectl get node -o wide

Поздравляю! Кластер Kubernetes настроен без Docker, теперь проблем с обновлением на новые версии возникнуть не должно.


Телеграм-канал Mops DevOps - анонсы вебинаров и конференций, полезные статьи и видео, а так же регулярные скидки на обучение!

Подробнее..

Категории

Последние комментарии

  • Имя: Макс
    24.08.2022 | 11:28
    Я разраб в IT компании, работаю на арбитражную команду. Мы работаем с приламы и сайтами, при работе замечаются постоянные баны и лаги. Пацаны посоветовали сервис по анализу исходного кода,https://app Подробнее..
  • Имя: 9055410337
    20.08.2022 | 17:41
    поможем пишите в телеграм Подробнее..
  • Имя: sabbat
    17.08.2022 | 20:42
    Охренеть.. это просто шикарная статья, феноменально круто. Большое спасибо за разбор! Надеюсь как-нибудь с тобой связаться для обсуждений чего-либо) Подробнее..
  • Имя: Мария
    09.08.2022 | 14:44
    Добрый день. Если обладаете такой информацией, то подскажите, пожалуйста, где можно найти много-много материала по Yggdrasil и его уязвимостях для написания диплома? Благодарю. Подробнее..
© 2006-2024, personeltest.ru