Знакомство с Kubernetes. Часть 3: Поды (Pods)
May 14, 2018 06:17 · 776 words · 4 minute read
В данной статье цикла о знакомстве с оркестратором Kubernetes
детальнее разберемся с подами (Pods
) - наименьшей функциональной единицей для развертывания в объектной модели Kubernetes
.
Pod
(переводится с английского как стручок) состоит обычно из одного или нескольких контейнеров, хранилища (storage), отдельного IP-адреса и опций, которые определяют, как именно контейнер(ы) должны запускаться. Также Pod
представляет собой некий запущенный процесс в кластере Kubernetes
.
Чаще всего в Pod'
ах используются docker-контейнеры (что и не удивительно), но можно использовать и другие контейнеры (например, rkt от CoreOS).
Важно Kubernetes
управляет Pod'
ами, а не контейнерами напрямую.
В кластере Kubernetes
Pod'
ы используются двумя способами:
Pod
из одного контейнера - наиболее распространенный случай использования. В этом вариантеPod
можно представить как обертку вокруг одного контейнера;Pod
из нескольких контейнеров, работающих сообща - контейнеры в данном случае образуют отдельную единицу (сервис) и используют общие ресурсы - например, файлы из одного хранилища (storage). При этом, отдельный контейнерPod'
а может обновлять эти файлы.
Каждый Pod
предназначен для запуска одного экземпляра конкретного приложения. Если есть необходимость горизонтального масштабирования, то можно запустить несколько экземпляров Pod'
а - в терминологии Kubernetes
это называется репликацией. Реплицированные Pod'
ы создаются и управляются как единая группа абстракцией, которая называется контроллер (Controller).
Pod'
ы спроектированы для поддержки множества взаимодействующих процессов (например, контейнеров), которые образуют отдельный сервис (единицу обслуживания). Контейнеры внутри Pod'
а автоматически размещаются и управляются на одной и той же физической (или виртуальной) ноде кластера. Контейнеры в Pod'
е могут совместно использовать ресурсы и зависимости, взаимодействовать друг с другом и определять, когда и как они будут завершаться.
К слову, группировка и запуск нескольких контейнеров в Pod'
е считается “продвинутым” вариантом использования, и применять этот шаблон нужно только при реальной необходимости. Например, у вас может быть контейнер с web-сервером, использующий файлы из общего (относительно Pod'
а) хранилища, и отдельный контейнер, который обновляет эти файлы из удаленного источника.
Pod'
ы предоставляют запущенным внутри контейнерам два типа общих ресурсов: сеть и хранилище.
Сеть
Каждому Pod'
у присваивается уникальный IP-адрес. Внутри Pod'
а каждый контейнер использует общее пространство имен (namespace) сети, включая IP-адрес и сетевые порты. Между собой внутри Pod'
а контейнеры взаимодействуют через localhost. При взаимодействии с объектами, находящимися за пределами Pod'
а, контейнеры “договариваются” между собой и координируют использование общих сетевых ресурсов (таких как порты).
Хранилище
Pod
может определить набор общих томов (volumes) для хранения данных. Контейнеры внутри Pod'
а могут работать с этими томами и, таким образом, обмениваться данными между собой. Благодаря использованию томов, можно сохранить данные, если один из контейнеров Pod'
а (которому нужны эти данные для корректной работы) должен быть перезапущен. Время жизни томов совпадает с временем жизни самого Pod'
а.
Что касается работы в кластере Kubernetes
, то редко когда приходится создавать и запускать отдельные Pod'
ы вручную (варианты запуска при ознакомлении с Kubernetes
мы в расчет не берем). Связано это с тем, что Pod'
ы изначально проектировались как эфемерные объекты, минимальные единицы, “строительные блоки” для сущностей более высокого уровня (например, контроллеров). Когда Pod
создается (не важно, вручную вами или контроллером), он по плану (за это отвечает scheduler) запускается на одной из нод кластера Kubernetes
. На этой ноде Pod
остается до тех пор, пока:
- не завершится процесс внутри
Pod'
а (например, если это одноразовая задача); Pod
не будет удален вручную;Pod
не будет “выселен” с ноды из-за нехватки ресурсов;- нода не выйдет из строя.
Примечание Перезапуск контейнера внутри Pod'
а не следует путать с перезапуском самого Pod'
а.
Сами по себе Pod'
ы не являются “самолечащимися” (self-healing) объектами. Если запуск Pod'
а запланирован на ноде, которая вышла из строя, или сама операция запуска потерпела крах, то Pod
удаляется. Точно также, при нехватке ресурсов на ноде (когда Pod'
ы “выселяются”) или при переводе ноды в режим обслуживания, Pod'
ы не будут запущены на других узлах и удалятся. Для обеспечения запуска на других нодах (и управления Pod'
ами в целом) в Kubernetes
используются абстракции более высокого уровня, называемые контроллерами - в основном именно с ними и приходится иметь дело.
Контроллер может управлять несколькими экземплярами Pod'
ов - в том числе обеспечивать репликацию и самовосстановление в пределах кластера (при выходе из строя ноды, идентичный экземпляр Pod'
а будет запущен на другой ноде). Примером контроллера, который содержит в себе один или несколько экземпляров Pod'
а могут быть:
- Deployment
- StatefulSet
- DaemonSet
Для обеспечения такого функционала контроллеры используют шаблоны Pod'
ов (Pod Templates). Шаблон Pod'
а - спецификация, которая используется контроллерами и другими объектами (например, заданиями - Jobs/CronJob) для запуска настоящего, реального Pod'
а. Ниже приведен пример простой спецификации (ее еще иногда называют манифестом), описывающей контейнер, который напечатает сообщение при запуске и “уснет” на час:
apiVersion: v1
kind: Pod
metadata:
name: myapp-pod
labels:
app: myapp
spec:
containers:
- name: myapp-container
image: busybox
command: ['sh', '-c', 'echo Hello Kubernetes! && sleep 3600']
Предложенный манифест (спецификацию) можно сохранить в файле single-example-pod.yml
и запустить Pod
с помощью утилиты командной строки kubectl
:
kubectl create -f single-example-pod.yml
Больше информации о Pod'
ах можно найти в официальной документации по Kubernetes
, а мы в следующей статье поговорим о репликах.