Этой ночью вышла новая версия Kubernetes — 1.27. Среди главных изменений — переход на собственный полноценный реестр registry.k8s.io, обновление запросов и лимитов пода «на месте» — т.е. без необходимости перезапускать под или его контейнеры — и ряд усовершенствований в области безопасности (stable-статус фичи seccomp by default, in-process-валидация запросов к API-серверу и др.). Для подготовки статьи использовалась информация из таблицы Kubernetes enhancements tracking, CHANGELOG-1.27, обзора Sysdig, а также конкретные Issues, Pull Requests и Kubernetes Enhancement Proposals (KEPs). Всего в новом релизе 60 изменений. Из них: 18 новых функций (alpha);  29 продолжают улучшаться (beta); 13 признаны стабильными (stable). Примечание Мы сознательно не переводим названия фич на русский. Они в основном состоят из специальной терминологии, с которой инженеры чаще встречаются в оригинальной формулировке. #3325 KEP от «Фланта» перешел в beta-стадию. Он добавляет в группу authentication.k8s.io новый эндпоинт API — SelfSubjectReview. С помощью команды kubectl auth whoami можно обратиться к этому эндпоинту и посмотреть атрибуты текущего пользователя после завершения процесса аутентификации. Подробнее о KEP’е — в обзоре нововведений Kubernetes 1.26. #3673; KEP KEP добавляет в kubelet ограничение на число параллельно скачиваемых образов на уровне узла. Извлечение образов в Kubernetes ограничивается параметрами QPS и burst. Их недостаток в том, что лимитируется только число запросов, отправляемых в среду исполнения, при этом число загрузок «в процессе» не учитывается. Другими словами, даже при минимальном значении QPS параллельно может скачиваться множество образов, если процесс загрузки по тем или иным причинам занимает продолжительное время (см., например, Issue #112044). В результате число параллельно запрашиваемых образов оказывается ничем не ограничено. KEP добавляет параметр maxParallelImagePulling в конфигурацию kubelet’а. Он ограничивает максимальное количество параллельно запрашиваемых образов. Любой запрос, превышающий заданный лимит, будет блокироваться до тех пор, пока не завершится скачивание одного из образов «в процессе». Подробнее о логике работы механизма можно узнать из предложения по улучшению. #1287; KEP KEP позволяет обновлять запросы и лимиты пода «на месте» — т.е. без необходимости перезапускать под или его контейнеры. Идея состоит в том, чтобы сделать PodSpec изменяемой (mutable) в отношении определенных ресурсов. PodStatus также будет доработан — он сможет предоставлять информацию о ресурсах, выделенных для пода, а также фактических ресурсах, потребляемых подом и его контейнерами. KEP базируется на предложении по вертикальному масштабированию в реальном времени и «на месте» и концепции вертикального масштабирования ресурсов в Kubernetes. Также планируется дополнить API Container Runtime Interface функциями, необходимыми для управления конфигурацией ресурсов CPU и памяти контейнера в среде исполнения. В настоящее время изменения, связанные с ресурсами пода, требуют пересоздания последнего из-за неизменяемости (immutable) PodSpec. В то время как перезапуски подов обычно не страшны, в ряде случаев (например, если число подов невелико или рабочие нагрузки являются stateful) перезапуск нежелателен и приводит к снижению доступности. Решить эту проблему позволяет прямое изменение ресурсной конфигурации пода без необходимости пересоздавать под или контейнеры в нем. Кроме того, вертикальное масштабирование пода «на месте» полагается на Container Runtime Interface при обновлении запросов/лимитов на CPU и память для контейнера(-ов) пода. В нынешнем виде API CRI имеет ряд недостатков, которые необходимо устранить: UpdateContainerResources принимает параметр, описывающий ресурсы контейнера, предназначенные для обновления, для Linux-контейнеров. Это грозит проблемами для Windows-контейнеров и контейнеров, требующих сред исполнения, не базирующихся на Linux. Не существует механизма CRI, позволяющего kubelet’у из среды исполнения контейнера запрашивать и обнаруживать лимиты CPU и памяти, заданные для контейнера. Ожидаемое поведение среды исполнения, которая обрабатывает API CRI UpdateContainerResources, слабо определено и плохо документировано. В рамках KEP’а спецификацию PodSpec предлагается сделать изменяемой в части ресурсов контейнеров. Первоначально правки в спецификацию будут вноситься путем ее обновления; в бета-версии для этих целей планируется создать новый подресурс /resize. В дальнейшем его можно будет применять к другим ресурсам, работающим с шаблонами подов, таким как Deployment’ы, ReplicaSet’ы, Job’ы и StatefulSet’ы. Это позволит открывать контроллерам вроде VPA частичный RBAC-доступ, не давая полного доступа на запись к спецификациям подов. Кроме того, в разделе PodSpec.Containers появится ResizePolicy со следующими значениями: RestartNotRequired — значение по умолчанию; K8s попытается изменить размер контейнера без его перезапуска, если это возможно. Restart — для применения новых значений ресурсов требуется перезапуск. Примечание: RestartNotRequired не гарантирует, что контейнер не будет перезапущен. Среда исполнения может остановить контейнер для обновления спецификации ресурсов, если это потребуется. Подробности реализации доступны в разделе Proposal KEP’а. #2570; KEP cgroups v1 в Kubernetes поддерживает только ограничение ресурсов CPU с помощью cpu_shares / cpu_set / cpu_quota / cpu_period. Управление ресурсами памяти не поддерживается. Авторы KEP’а предлагают воспользоваться возможностями контроллера памяти в cgroups v2 для обеспечения QoS и гарантирования запросов/лимитов памяти подов/контейнеров. #3063; KEP Kubernetes все чаще используется в качестве решения для управления новыми рабочими нагрузками (пакетная обработка) и в новых средах (граничные вычисления). Таким рабочим нагрузкам нужны не только оперативная память и процессор, но и доступ к специализированному оборудованию. Усовершенствование инфраструктуры  центров обработки данных позволяет устанавливать ускорители вне конкретных узлов и подключаться к ним динамически по мере необходимости. KEP реализует API, позволяющий описывать новые типы ресурсов, необходимые поду. Поддерживаются: Ресурсы, подключаемые по сети. Существующий API плагинов устройств ограничен аппаратным обеспечением на узле. Совместное использование ресурсов несколькими контейнерами или подами. Существующий API диспетчера устройств вообще не поддерживает совместное использование. Его можно дополнить, после чего станет возможен обмен ресурсами между контейнерами в одном поде, но для обмена ресурсами между подами потребуется совершенно новый API, подобный тому, который представлен в данном KEP’е. Ресурсы, инициализация которых в разных подах обходится слишком дорого (на данный момент оптимизировать этот процесс невозможно). Кастомные параметры, описывающие требования к ресурсам и их инициализацию. Параметры не всегда бывают линейными и счетными. В текущей реализации API пода для работы с такими параметрами используются аннотации, а для доступа к ним из драйвера CSI или плагина устройства приходится выдумывать различные «костыли». Новое оборудование будет поддерживаться дополнениями от его производителей. Больше не нужно будет вносить правки в сам Kubernetes. KEP не заменяет другие способы запроса традиционных ресурсов (память/CPU, тома, расширенные ресурсы). Планировщик будет координировать работу дополнений, «владеющих»  ресурсами (драйвер CSI, драйвер ресурсов), и ресурсами, которыми «владеет» и  выделяет планировщик (память/CPU, расширенные ресурсы). Идея в том, чтобы отдать все операции, специфичные для ресурса, на откуп драйверу, управляющему этим ресурсом. Сюда входят операции на уровне управляющего слоя (отслеживание того, где в кластере доступны ресурсы, помощь в принятии решений о планировании подов, выделение ресурсов по запросу), а также на уровне узла (подготовка запуска контейнеров). Такой драйвер может быть реализован на произвольном языке программирования — главное, чтобы он поддерживал протокол распределения ресурсов и интерфейсы gRPC, определенные в данном KEP’е. Его развертывание не будет зависеть от изменения конфигурации базовых компонентов Kubernetes, таких как планировщик. Новые объекты API будут определять параметры запроса на ресурс (ResourceClaim в API) и отслеживать его состояние. Спецификация пода будет соответствующим образом дополнена. под будет назначаться только на тот узел, на котором есть нужные ресурсы и они зарезервированы для его запросов. Это предотвратит ситуацию, когда под планируется на узел и «застревает» на нем в ожидании доступных ресурсов. #127; KEP KEP добавляет поддержку пользовательских пространств имен в stateless-подах.  Из документации к user_namespaces(7): «Пользовательские пространства имен изолируют связанные с безопасностью идентификаторы и атрибуты, в частности, идентификаторы пользователей и групп, корневую директорию, ключи и возможности. Идентификаторы пользователя и группы процесса могут быть разными внутри и вне пространства имен пользователя. Процесс может иметь обычный непривилегированный ID пользователя вне пользовательского пространства имен и в то же время ID = 0 внутри пространства имен; другими словами, у процесса будут полные привилегии внутри пользовательского пространства имен и ограниченные — вне его». Идея в том, чтобы запускать процессы в подах с другими ID пользователя и группы, нежели на хосте. В этом случае привилегированный процесс в поде будет непривилегированным на хосте. В случае, если такой процесс «вырвется» за пределы контейнера, потенциальный вред будет минимизирован, поскольку на хосте его привилегии будут ограничены. KEP полностью или частично устраняет ряд CVE (их список — в разделе Motivation). В спецификации пода появляется параметр pod.spec.hostUsers: *bool. Если он не определен или true, используется пространство имен хоста (текущее поведение). Если false, для пода создается новое пользовательское пространство имен. По умолчанию параметр не задан. #3695; KEP Предлагается дополнить API PodResources и включить в него ресурсы, распределяемые механизмом динамического распределения ресурсов (DRA). Кроме того, предлагается расширить API, чтобы сделать его более дружественным для использования мета-плагинами CNI. Этот KEP развивает идеи в 2043-pod-resource-concrete-assignments и 2403-pod-resources-allocatable-resources. Новый API PodResources позволит агентам мониторинга узлов собирать информацию о ресурсах, выделяемых DRA. Мета-плагины CNI, такие как multus и DANM, полагаются на API PodResources при добавления ресурсов, выделяемых плагинами устройств, в качестве аргументов CNI. Данный KEP позволит этим CNI-плагинам ссылаться на ресурсы, выделяемые DRA. Дальнейшее расширение API облегчит мета-плагинам CNI доступ к ресурсам, выделенным конкретному поду — им не придется фильтровать ресурсы для всех подов на узле. Авторы предлагают дополнить существующий сервис gRPC PodResources kubelet’а, включив повторяющееся поле DynamicResource в сообщение ContainerResources. Новое поле будет содержать информацию о классе DRA-ресурса, его ресурсных claim’ах и списке устройств CDI, распределенных драйвером DRA. Кроме того, к существующему сервису gRPC добавится метод Get(), с помощью которого можно будет опрашивать конкретные поды на предмет выделенных им ресурсов. #3386 Улучшение модернизирует подход, предложенный в KEP’е Kubelet: Pod Lifecycle Event Generator (PLEG) и меняет механизм работы CRI. Теперь kubelet получает актуальные данные о состоянии пода по модели List/Watch. В частности, прослушивает потоковые события сервера gRPC из CRI, которые необходимы для генерации событий жизненного цикла пода — то есть не опрашивает среду исполнения. В результате снижается необязательное использование ресурсов CPU kubelet’ом и нагрузка на CRI. Подробнее — в обзоре новинок Kubernetes 1.26. #2053 Нисходящий (downward) API позволяет контейнерам получать информацию о себе или кластере без использования клиента Kubernetes или сервера API. Данный KEP открывает контейнерам доступ к информации о hugepages. В спецификацию API добавляются параметры requests.hugepages-<pagesize> и limits.hugepages-<pagesize>, с которыми можно работать так же, как с аналогичными параметрами для CPU, памяти и эфемерного хранилища. #2413 Seccomp by default: эта важная и долгожданная фича наконец переходит в статус stable. Она повышает безопасность «ванильного» Kubernetes, автоматически включая фильтрацию системных вызовов при запуске любых контейнеров (в предыдущих версиях K8s это нужно делать вручную).  Seccomp — режим, при котором все неразрешенные системные вызовы блокируются. Это помогает избегать атак на узел или целый кластер через контейнер, а также повышает устойчивость K8s к zero day-уязвимостям. Подробнее об алгоритме работы новой фичи мы писали в этой новости. #693 Менеджер топологии узла (Node Topology Manager) унифицирует подход к тонкой настройке распределения аппаратных ресурсов для различных компонентов в Kubernetes. Впервые он был представлен в далекой v1.16, и вот, наконец, переходит в стабильный статус. Подробнее о нем можно почитать в нашем обзоре нововведений Kubernetes 1.16. #2727 Liveness, Readiness и Startup probes — три разных типа проверки состояния пода. Сейчас они работают по протоколам HTTP(S) и TCP. Новая фича добавляет поддержку gRPC — открытого фреймворка для удаленного вызова процедур, который часто используется в микросервисной архитектуре.  Возможность использовать встроенный gRPC среди прочего избавляет от необходимости использовать сторонние инструменты для проверки состояния контейнеров вроде grpc_health_probe(1). Подробнее — в обзоре Kubernetes 1.23. #2238 Liveness-проверки используют параметр terminationGracePeriodSeconds как при обычном прекращении работы, так и при сбоях. Если значение параметра велико и проверка неудачна, kubelet будет ждать указанное (длительное) время, прежде чем перезапустить рабочую нагрузку. Авторы KEP’а предлагают добавить в API новое поле, probe.terminationGracePeriodSeconds. Оно будет определять период ожидания для liveness- и startup-проверок, переопределяя terminationGracePeriodSeconds, но игнорироваться для readiness-проверок. #3017 KEP добавляет поле podHealthyPolicy. С его помощью можно указать, что поды «здоровы» и, следовательно, подпадают под ограничения Pod Disruption Budget, либо их следует рассматривать как уже отключенные, и поэтому они могут быть проигнорированы PDB. Новые статусы для подов: status.currentHealthy, status.desiredHealthy и spec.unhealthyPodEvictionPolicy. #3715 Индексированные Job’ы появились в Kubernetes 1.21, чтобы облегчить планирование высокопараллелизуемых заданий. Однако после создания изменить количество (spec.completions) или допустимое число параллельных Job’ов (spec.parallelism) невозможно. Это довольно проблематично для некоторых рабочих нагрузок, например, связанных с глубоким обучением. Данный KEP делает эти поля (spec.completions и spec.parallelism) изменяемыми (mutable), но с некоторыми ограничениями (они должны быть равны). #3335 Цель KEP’а — разрешить миграцию StatefulSet’а между пространствами имен, между кластерами, а также разбивать его на сегменты без простоев в работе приложения. В манифест StatefulSet’а добавляется новое поле spec.ordinals.start, в котором указывается стартовый номер для реплик, контролируемых StatefulSet’ом. Подробнее — в нашем обзоре нововведений Kubernetes 1.26. #3329 Чтобы ограничить время выполнения Job’а, используются два параметра:  activeDeadlineSeconds — максимальное время выполнения Job’а; backoffLimit — количество попыток запуска Job’а за отведенное (в предыдущем параметре) время. Если Job не запускается, и политика перезапуска установлена в OnFailure, Kubernetes попытается запустить его заново — столько раз, сколько указано в backoffLimit. KEP помогает учитывать некоторые причины незапуска Job’а и, при необходимости, завершать его досрочно, игнорируя backoffLimit. Для этого в Job API добавлено новое поле podFailurePolicy. Дополнительная информация и пример конфигурации с использованием podFailurePolicy — в обзоре новинок K8s 1.25. #1847 KEP вводит необязательное поле .spec.persistentVolumeClaimRetentionPolicy для контроля за тем, когда и как PVC удаляются во время жизненного цикла StatefulSet’а. #3140 CronJob создает Job’ы в соответствии с графиком, который определен пользователем. Однако часовой пояс, используемый в процессе создания Job’а, соответствует часовому поясу kube-controller-manager’а. Если пользователь забыл это учесть, Job может быть выполнен не по плану. KEP добавляет в CronJob API новое поле .spec.timeZone, в котором можно заранее установить часовой пояс для запуска Job’а. #3476; KEP KEP реализует API Kubernetes, позволяющий снимать согласованные snapshot’ы сразу с нескольких томов. Для группировки PVC используются селекторы меток. В рамках KEP 3476 добавляется поддержка snapshot’ов групп томов для драйверов томов CSI. Существующий API VolumeSnapshot позволяет делать snapshot’ы томов для защиты от потери или повреждения данных. Однако часть потребностей им не покрывается. Некоторые системы хранения поддерживают согласованный snapshot, т.е. снимок с нескольких томов в один и тот же момент времени для соблюдения согласованности порядка записи. Такая функция может пригодиться для приложений, работающих сразу с несколькими томами. Например, данные такого приложения могут храниться на одном томе, логи — на другом. Если snapshot’ы с этих томов снимать в разное время, информация на них окажется рассогласована. Соответственно, приложение не сможет нормально функционировать, если эти snapshot’ы использовать для восстановления после сбоя. Да, можно предварительно «заморозить» (quiesce) приложение, однако это требует дополнительного времени и не всегда возможно. Кроме того, последовательное снятие snapshot’ов также может занять больше времени, нежели согласованное групповое. KEP вводит новые CRD VolumeGroupSnapshot, VolumeGroupSnapshotContent и VolumeGroupSnapshotClass.  Для объединения нескольких PVC в VolumeGroupSnapshot на них навешивается соответствующая метка, которая затем указывается в селекторе labelSelector в VolumeGroupSnapshot, если драйвер CSI поддерживает возможность CREATE_DELETE_GET_VOLUME_GROUP_SNAPSHOT. Подробнее о логике работы можно почитать в разделе Proposal KEP’а.  #2485 В Kubernetes нет режима доступа для PersistentVolumes, который позволяет ограничить доступ так, чтобы на одном узле мог работать только один такой под. Это чревато проблемами для некоторых рабочих нагрузок. Пример: некая рабочая нагрузка выполняет обновление устройства хранения (с помощью ReadWriteOnce) и масштабируется на несколько подов. В этом случае второй под может оказаться на том же узле и начать работать с устройством хранения параллельно с первым. В случае критичных рабочих нагрузок отсутствие режима, который позволяет ограничить доступ так, чтобы на одном узле мог работать только один под, приходится обходить другими способами (например, планируя лишь один под на узел и используя ReadWriteOnce), что может приводить к неэффективному использованию ресурсов в кластере. KEP вводит новых режим доступа ReadWriteOncePod, который позволяет ограничить доступ к PersistentVolumes одиночным подом на одиночном узле. Для сравнения, существующий режим ReadWriteOnce (RWO) ограничивает доступ к одиночному узлу, но разрешает одновременный доступ к этому узлу из нескольких подов. #3107 Для передачи секретов в RPC-запросах к CSI-драйверам при расширении емкости томов на узле с помощью операции nodeExpandVolume. В запрос nodeExpandVolume, который kubelet отправляет CSI-драйверу, добавлено новое поле secretRef. Кроме того, в объект CSIPersistentVolumeSource добавлен параметр NodeExpandSecretRef для передачи секретов в PVC-запросах на расширение тома. Подробнее — в обзоре нововведений Kubernetes 1.25. #3141 С помощью API-ресурса VolumeSnapshot можно создавать PVC (PersistentVolumeClaim) из снапшота. Это делается через установку в PVC параметра Spec.dataSource, который указывает на существующий ​​VolumeSnapshot. При этом нет никакого механизма проверки, соответствует ли режим доступа у вновь созданного PVC режиму доступа, заданному для исходного PVC. Чтобы улучшить контроль за режимом доступа к тому, авторы KEP’а предлагают следующие изменения: добавить новое поле SourceVolumeModeв спецификации API VolumeSnapshotContent; в нем устанавливается режим доступа к тому, с которого сделан снапшот; добавить аннотацию со ссылкой на ресурс, который может использовать доверенный пользователь для VolumeSnapshot; усовершенствовать методы контроля за snapshot-controller и external-provisioner. #1710 На хостах с SELinux в принудительном режиме (enforcing mode) пользователи одного контейнера не могут получить доступ к другому контейнеру или к хосту. Это обеспечивается за счет контекста, который уникален для каждого контейнера, и лейблов, которые назначаются каждому файлу в каждом томе. Злоумышленник, которому удалось выбраться из контейнера, не сможет получить доступ к данным в других контейнерах, потому что у каждого контейнера свои тома со своими лейблами. Однако такая защита может усложнять жизнь пользователям, которые разворачивают кластеры на базе SELinux: при запуске нового контейнера запускается рекурсивное переназначение лейблов для всех файлов в томе, привязанном к поду. Если том большой, процесс переназначения может затянуться. Новая функция позволяет пропустить этап переназначения лейблов и тем самым ускорить монтирование тома. Подробности см. в обзоре Kubernetes 1.25. #3756 Этот KEP является частью предыдущего, #1710, поэтому сразу позиционируется как бета. Его цель — уменьшить время, необходимое kubelet’у для восстановления информации о примонтированных томах после перезапуска. Такая информация теряется после перезапуска kubelet’а, и для ее восстановления ему приходится сопоставлять данные сервера API и ОС хоста. Kubelet проверяет, какие поды должны быть запущены и какие тома примонтированы на самом деле. Однако этот процесс несовершенен и лишен некоторой ключевой информации, например, о том, какие опции для монтирования томов использовал прежний kubelet. KEP #3756 является своего рода работой над ошибками и предусматривает значительный рефакторинг кода. Именно поэтому он выделен из «родительского» KEP’а и снабжен отдельным переключателем функциональности (feature flag) NewVolumeManagerReconstruction.  #3521 Поды считаются готовыми к планированию сразу после того, как созданы. Планировщик Kubernetes ищет узлы для размещения всех ожидающих подов. Однако в реальности некоторые поды могут долго оставаться в состоянии miss-essential-resources («отсутствие необходимых ресурсов»). Эти поды «сбивают с толку» планировщик и компоненты типа Cluster Autoscaler. В улучшении дорабатывается API и механика — так, чтобы пользователи или оркестраторы понимали, когда под полностью готов для планирования. В Pod API добавляется поле .spec.schedulingGates со значением по умолчанию nil. Поды, у которых значение этого поля не равно nil, будут «припаркованы» во внутреннем пуле unschedulablePods планировщика. Он обработает их, когда поле изменится на nil. #3838 KEP #3521 Pod scheduling readiness позволяет помечать поды как готовые к планированию. Данный KEP развивает эту идею, делая переключатели планирования (scheduling gates) изменяемыми, чтобы другие компоненты, например, кастомные контроллеры планирования, могли использовать их для расширения возможностей kube-scheduler’а. См. KEP #3521 выше. #3243 KEP решает проблему с несбалансированным распределением подов при плавающих обновлениях Deployment’а. В TopologySpreadConstraint вводится новое поле MatchLabelKeys в качестве дополнения к существующему labelSelector. В новом поле передается набор ключей для лейблов подов — их планировщик учитывает при распределении. Фича позволяет применять ограничения PodTopologySpread только в границах новой ревизии Depolyment’а, а не во всех ревизиях. #2926 Начиная с Kubernetes 1.23, появилась возможность обновлять поля node affinity, node selector, tolerations, labels и annotations в шаблоне пода Job’а перед его запуском. Это позволяет контролировать, где будут запущены поды, например, в одной зоне или на узлах с одинаковой моделью GPU. #3705; KEP kubelet поддерживает dual-stack-значения --node-ip для необлачных кластеров (например, bare-metal-кластеров), но не для их облачных аналогов. Данный KEP исправляет это. В настоящее время при передаче параметра --cloud-provider в kubelet последний ожидает, что --node-ip не будет задан или будет представлять собой один IP-адрес. Если сразу указаны и --cloud-provider, и --node-ip (при этом --node-ip отличен от 0.0.0.0 или ::), kubelet добавит к узлу аннотацию alpha.kubernetes.io/provided-node-ip. Облачные провайдеры ожидают, что эта аннотация будет соответствовать установленному синтаксису --node-ip (т.е. значение будет единственным); в ином случае они выдадут ошибку и не уберут с узла taint node.cloudprovider.kubernetes.io/uninitialized, в результате чего тот окажется непригодным для использования до перезапуска kubelet’а с действительным (или пустым) --node-ip. KEP позволит администраторам кластеров, в которых используются внешние облачные ресурсы, гибко менять IP-адреса узлов, назначаемые облаком. Администраторы смогут: переопределять IP-адрес узла в dual-stack-кластере, и это не будет приводить к тому, что узел станет single-stack; переопределять оба IP-адреса узла в dual-stack-кластере; изменять порядок IP-адресов узлов в dual-stack-кластере (т.е. задавать первичность IPv6 или IPv4); переключать узлы в single-stack-режим, когда поставщик облачных услуг предлагает dual-stack-режим, без необходимости указывать конкретный IP-адрес узла в формате IPv4 или IPv6. #3668; KEP Этот KEP развивает идею KEP 3070 (см. обзор нововведений Kubernetes 1.24), помогая избежать конфликтов при резервировании портов для сервисов типа NodePort. Сервис Kubernetes — это абстрактный способ открыть для внешнего трафика приложение, работающее на некотором наборе подов. У сервиса есть виртуальный ClusterIP, который позволяет балансировать трафик между подами. ClusterIP может назначаться: динамически: кластер выбирает один адрес из указанного диапазона сервисных IP-адресов. статически: пользователь задает один адрес в пределах указанного диапазона сервисных IP-адресов. В настоящее время, создавая сервис со статическим ClusterIP, невозможно узнать, не выбрал ли этот адрес какой-либо другой сервис динамически. Диапазон IP-адресов сервисов можно логически разделить, избежав тем самым риска конфликтов между сервисами, использующими статическое и динамическое распределение IP-адресов. При создании сервиса типа NodePort kube-proxy выделяет порт в диапазоне 30000-32767 и открывает этот порт на интерфейсе eth0 каждого узла. Подключения к этому порту затем перенаправляются на IP-адрес сервиса в кластере. KEP 3668 позволяет зарезервировать диапазон портов за определенным сервисом.  #1880; KEP Позволяет динамически увеличивать количество IP-адресов, доступных для сервисов. Некоторые типы сервисов — ClusterIP, NodePort и LoadBalancer — используют виртуальный IP-адрес ClusterIP, который должен быть уникальным в пределах кластера. Попытка создать сервис с адресом ClusterIP, который уже занят, приведет к ошибке. Текущая реализация логики распределения IP-адресов для сервисов имеет несколько ограничений: Нельзя менять размер или увеличивать диапазоны IP, выделяемых сервисам; это приводит к проблемам, когда сети перекрываются или в кластере заканчиваются доступные IP. Диапазон IP-адресов сервисов не разглашается (not exposed), поэтому другие компоненты в кластере не могут его использовать. Конфигурация привязана к конкретному серверу API; консенсус отсутствует; в результате разные серверы API могут конкурировать между собой, удаляя IP-адреса, закрепленные друг за другом. Для IPv4 размер префикса для сервиса ограничен /12, однако для IPv6 он составляет /112 или меньше. Это вызывает проблемы у пользователей IPv6, поскольку /64 является стандартной и минимально рекомендуемой длиной префикса. Feature gate 3070 позволяет использовать только зарезервированный диапазон IP-адресов сервиса. Данный KEP ставит своей целью реализацию новой логики механизма распределения. Предлагается создать два объекта API — ServiceCIDR и IPAddress — и позволить пользователям динамически увеличивать количество доступных для сервисов IP-адресов, задавая новые диапазоны ServiceCIDR. #3178 KEP оптимизирует работу с цепочками iptables, создаваемыми kubelet’ом. Опция IPTablesOwnershipCleanup запрещает kubelet’у создавать цепочки KUBE-MARK-DROP, KUBE-MARK-MASQ, KUBE-POSTROUTING и KUBE-KUBELET-CANARY (остается лишь KUBE-FIREWALL для обработки марсианских пакетов). Кроме того, она предупреждает, что аргументы kubelet’а --iptables-masquerade-bit и --iptables-drop-bit устарели и больше не работают. #3453 KEP повышает производительность работы kube-proxy в режиме iptables, убирая из вызовов к iptables-restore правила, которые не изменились (подробнее — в обзоре нововведений Kubernetes 1.26). #3458 Контроллер сервисов в Kubernetes cloud controller manager (KCCM) добавляет/удаляет узлы из набора узлов балансировщиков нагрузки в следующих случаях: Когда на узел навешивается/с узла удаляется taint ToBeDeletedByClusterAutoscaler;  Когда узел переходит в состояние Ready/NotReady. Однако второй случай относится только к сервисам с externalTrafficPolicy: Cluster. При этом в обоих случаях удаление узла из набора узлов балансировщиков нагрузки приведет к тому, что все соединения на этом узле будут мгновенно прерваны. Подобное поведение представляется неоптимальным для узлов в переходном состоянии готовности или завершающих свою работу и выглядит как ошибка, поскольку в таких случаях соединениям не разрешается разрываться, даже если балансировщик нагрузки поддерживает это.  Данный KEP предусматривает прекращение синхронизации набора узлов балансировщиков нагрузки в таких случаях. Для удобства в систему будет интегрирован feature gate StableLoadBalancerNodeSet. #3716; KEP KEP добавляет так называемые «условия соответствия» (match conditions) к admission-вебхукам как расширение существующих правил для определения области применения вебхука. matchCondition представляет собой CEL-выражение. Если оно истинно, admission-запрос будет отправлен на вебхук. Если оно ложно, вебхук запрос пропустит (неявно разрешено). Авторы KEP’а считают, что предложенный механизм позволит оптимизировать работу с вебхуками в следующих областях: Надежность. Для многих пользователей Kubernetes admission-вебхуки остаются больным местом. Выход вебхука из строя может оказать значительное влияние на доступность кластера. Данное предложение смягчает (но не устраняет) эти проблемы, делая вебхуки более узконаправленными и целевыми. Производительность. Admission-вебхуки критически важны для write-запросов. Проверочные (validating) вебхуки могут выполняться параллельно, но мутирующие (mutating) веб хуки должны выполняться последовательно (до 2 раз!). Это делает их чрезвычайно чувствительными к задержкам, и даже те вебхуки, которые не выполняет никакой работы, все равно несут процесс из-за  круговых задержек (RTT). Поддерживаемость. В случае hosted- или managed-дистрибутивов Kubernetes вебхуки могут мешать запросам managed-компонентов. Существующие критерии для фильтрации запросов для многих случаев недостаточны, и их нелегко дополнить правилами провайдера. KEP добавляет поле MatchConditions в объекты ValidatingWebhook и MutatingWebhook (в admissionregistration.k8s.io). Оценка условия  MatchCondition выполняется теми же библиотеками, которые используются для CEL ValidatingAdmissionPolicy. Единственное различие в выражениях заключается в наличии переменной params. Выражения, требующие доступа к дополнительной информации вне AdmissionRequest, должны выполняться в вебхуке и выходят за рамки данного предложения. #3488; KEP KEP реализует настраиваемую in-process-валидацию запросов к API-серверу Kubernetes как альтернативу для проверочных (validating) admission-вебхуков. Предложение базируется на возможностях CRD Validation Rules (в beta, начиная с v1.25), но с акцентом на возможности применения политик при валидации контроля допуска. KEP снижает инфраструктурный барьер для внедрения кастомизируемых политик и реализует примитивы, способствующие применению лучших практик при работе как с K8s, так и его расширениями. В настоящее время кастомные политики реализуются с помощью admission-вебхуков. Эти хуки отличаются высокой гибкостью, но имеют ряд недостатков по сравнению с применением политик «в процессе»: Требуют создания инфраструктуры для размещения admission-вебхуков. Увеличивают задержку. Из-за дополнительных инфраструктурных зависимостей вебхуки менее надежны, чем их in-process-аналоги.  Управление вебхуками обременительно для администраторов кластера. Приходится заботиться о наблюдаемости и безопасности, а также формировать план выпуска/развертывания/отката вебхуков. KEP вводит новый kind ValidatingAdmissionPolicy в группу admissionregistration.k8s.io. На высоком уровне API будет поддерживать: Сопоставление запросов (по типу правил сопоставления для admission-вебхуков, с учетом RBAC, priority & fairness и аудита). Оценку правил CEL (аналогично правилам проверки CRD, но с доступом к данным в AdmissionRequest). Преобразование версий (аналогично MatchPolicy admission-вебхуков). Доступ к старому объекту (аналогично правилам перехода и oldObject в AdmissionRequest) Конфигурируемость. Ряд других возможностей. KEP разделен на два этапа, каждый из которых должен быть завершен до того, как фича перейдет в beta-версию. Сделано это для того, чтобы работу над каждым из этапов можно было завершить в течение одного релиз-цикла Kubernetes. #3157; KEP В некоторых случаях API-сервер Kubernetes страдает от взрывного роста потребления памяти. Эта проблема особенно очевидна в больших кластерах, где всего несколько LIST-запросов могут привести к серьезным сбоям. Неконтролируемое и неограниченное потребление памяти серверами влияет не только на кластеры, работающие в режиме HA, но и на другие программы на узле. KEP реализует запросы WATCH в качестве альтернативы запросам LIST. Чтобы снизить потребление памяти при получении списка данных и сделать его более предсказуемым, авторы предлагают использовать потоковую передачу из watch-cache вместо подкачки из etcd. В первую очередь изменения затронут информеры, поскольку они обычно являются наиболее активными пользователями LIST-запросов. Основная идея в том, чтобы использовать стандартную механику WATCH-запросов для получения потока отдельных объектов, но применять ее для LIST'ов. Подробнее — в описании KEP’а. #3352 Об операциях, которые поддерживает сервер API Kubernetes, сообщается через набор небольших документов, разделенных по группам в соответствии с номером версии. Клиенты API Kubernetes (например, kubectl) вынуждены отправлять запросы в каждую группу в «поисках» доступных API. Результат: множество запросов к кластерам, задержки и троттлинг. Когда в API добавляются новые типы, их нужно извлекать заново, что приводит к дополнительному потоку запросов.  KEP предлагает централизовать механизм «обнаружения» в двух агрегированных документах, чтобы клиентам не нужно было отправлять множество запросов API-серверу для извлечения всех доступных операций. #2876 KEP предлагает упрощенный вариант проверки пользовательских ресурсов (custom resources), которые добавляются в CRD (Custom Resource Definition). Ранее для этого использовались только validation-вебхуки, в которых прописывались правила проверки. Такой механизм усложнял разработку и мог влиять на работоспособность CRD. Теперь правила можно писать на скриптовом языке Common Expression Language (CEL) прямо в схемах ​​CustomResourceDefinition с помощью x-kubernetes-validations extension (подробности и пример правил — в обзоре Kubernetes 1.23). #2885 KEP перекладывает функцию проверки неизвестных и дублирующих полей в запросах к API-серверу с клиентской части (пользователя) на серверную. Мотив: проверку на стороне клиента организовать значительно сложнее, чем на стороне сервера. #2896 KEP добавляет kube-apiserver’у возможность обслуживать ресурсы и типы Kubernetes как объекты OpenAPI v3. Ранее конвертация определений OpenAPI v3 проводилась через CRD; делалось это не вполне корректно. #3638; KEP KEP позволяет использовать внешние плагины в качестве подкоманд встроенных команд, если подкоманда не существует. Многие пользователи Kubernetes желали бы дополнить некоторые встроенные команды kubectl новыми подкомандами. К примеру, create (по состоянию на v1.25) поддерживает создание 18 ресурсов в рамках простой команды (например, kubectl create job), при этом периодически возникают запросы на включение новых ресурсов. Это ожидаемо, учитывая популярность CustomResourceDefinitions, но нецелесообразно с точки зрения усилий, которые затрачиваются на поддержание всей этой функциональности. KEP предлагает плагины как альтернативу для подкоманд, встраиваемых в kubectl. В этом случае при попытке выполнить неизвестную подкоманду kubectl будет искать ее во внешних плагинах со структурой имени, аналогичной текущему механизму поиска плагинов (например, kubectl-create-foo). Пример: $ kubectl create foo (выполняется плагин kubectl-create-foo) Активировать функциональность, предлагаемую KEP’ом, можно с помощью переменной окружения: $ export KUBECTL_ENABLE_CMD_SHADOW=true #3659; KEP Команда kubectl apply позволяет создавать или обновлять объекты из YAML-файла. C помощью флага --prune можно удалить объекты, которых больше нет в файле. Однако этот процесс несовершенен и может приводить к непредсказуемому поведению. Этот KEP пытается заменить флаг --prune на новый, более перспективный и надежный подход. Пользователи смогу объединяться объекты в группы ApplySet, помогая kubectl понять, какие именно объекты подлежат удалению. Для этого на объекты будут навешиваться лейблы с префиксом applyset.k8s.io. Например, лейбл applyset.k8s.io/part-of будет указывать, частью какого ApplySet’а является объект. С подробностями можно ознакомиться в KEP’е. #2590 Процесс извлечения подресурсов API-объектов status и scale через kubectl не очень удобен: приходится пользоваться kubectl --raw. А обновлять эти подресурсы можно только при помощи запросов к API через curl (или другой клиент). Это усложняет их тестирование и отладку. KEP добавляет новый флаг --subresource=[subresource-name] к командам kubectl get и kubectl patch. Это позволит запрашивать и обновлять подресурсы status, scale и др., оперируя командами kubectl. Дополнительная информация доступна в обзоре нововведений Kubernetes 1.24. #3515 Open API v3 расширяет возможности API Kubernetes: пользователи могут получить доступ к таким атрибутам как nullable, default, полям валидации oneOf, anyOf и так далее. Поддержка Open API v3 в Kubernetes достигла бета-версии в 1.24. Сейчас CRD определяют свои схемы в формате OpenAPI v3. Для обслуживания документа /openapi/v2, который использует kubectl, приходится преобразовывать формат v3 в v2. Это приводит к ошибкам, например, при попытке использовать kubectl explain c полями типа nullable. KEP вносит следующие усовершенствования в kubectl explain: источник данных меняется с OpenAPI v2 на Open API v3; поддерживаются разные форматы вывода, в том числе простой текст и markdown.  #2227 В поды была добавлена аннотация kubectl.kubernetes.io/default-container для определения контейнера по умолчанию. Это упрощает использование таких инструментов, как kubectl logs или kubectl exec на подах с sidecar-контейнерами. #2258; KEP Чтобы посмотреть логи сервисов на узле, например, containerd, kubelet’а и т.п., администратор кластера Kubernetes должен подключиться к узлу по SSH и смотреть файлы логов напрямую. Более простым и элегантным способом было бы задействовать CLI kubectl для просмотра логов на узле по аналогии с тем, как это делается при других взаимодействиях с кластером. KEP предлагает команду kubectl node-logs для работы с объектами узлов, а также клиент для работы с просмотрщиком эндпоинта /var/log/ kubelet’а. Дополнительную информацию о специфике реализации для разных ОС можно узнать из раздела Proposal KEP’а.  #2699; KEP KEP подробно описывает усовершенствование структуры CCM с целью обеспечить поддержку вебхуков, специфичных для облачных провайдеров. Цель состоит в том, чтобы упростить генерацию исполняемого кода или усовершенствовать CCM, чтобы тот поддерживал такие кастомные вебхуки. Cloud Controller Manager (CCM) — сервис, который содержит специфические для облака контроллеры, необходимые для  правильной работы кластера Kubernetes. В некоторых случаях желательно, чтобы все эти кастомные ресурсы применялись синхронно, во время обработки запросов API-сервера, а не асинхронно после того, как изменения уже были применены. #1731; KEP В KEP’е подробно описаны усилия и текущие изменения, внесенные в релизный процесс и инфраструктуру сборки пакетов. Конечная цель — перейти от принадлежащего Google репозитория пакетов к управляемому сообществом репозиторию Open Build Service (OBS). #3299 KEP направлен на улучшение сервиса Key Management Service (KMS), который используется для шифрования данных etcd по схеме envelope encryption. Глобальная цель фичи — упростить работу с KMS. Дополнительная информация — в обзоре Kubernetes 1.25. #2799 KEP избавляет от необходимости использовать токен из секрета с учетными данными для доступа к API. Данные передаются напрямую из TokenRequest API и монтируются в под с помощью защищенного тома. #647 KEP расширят возможности трассировки API-сервера с помощью стандарта распределенного трейсинга и мониторинга OpenTelemetry. Коллектор OpenTelemetry умеет собирать метрики и трейсы из множества источников и транслировать их в нужный пользователю формат: Prometheus, Jaeger, VictoriaMetrics и т. Д. #3466 KEP позволяет отправлять данные SLI в структурированном виде и последовательно — так, чтобы агенты мониторинга могли их использовать с более высокими интервалами очистки и создавать SLO и алерты на основе этих SLI. В компоненты Kubernetes добавляется новый endpoint /metrics/sli, который возвращает данные SLI в формате Prometheus. Kubernetes получает стандартный формат для запроса данных о состоянии его компонентов (бинарников и т. п.). Вместе с этим отпадает необходимость в Prometheus exporter’е. Подробнее — в обзоре Kubernetes 1.26. #3498 Порядок стабилизации метрик первоначально был введен для защиты значимых метрик от проблем при использовании в downstream’е. Метрики могут быть alpha или stable. Гарантировано стабильны только stable-метрики. KEP вводит дополнительные классы стабильности — в первую очередь, чтобы синхронизировать этапы стабилизации метрик с этапами стабилизации релизов Kubernetes. К полям метрик добавляются статусы Internal (метрики для внутреннего использования) и Beta (более зрелая стадия метрики с бóльшими гарантиями стабильности, нежели alpha или internal, но менее стабильная, чем stable). #3203 Авторы KEP’а предлагают создать автоматически обновляемый список Kubernetes CVEs и разместить его по адресу https://kubernetes.io/docs/reference/issues-security/official-cve-feed со ссылкой на странице Kubernetes Security and Disclosure Information. Список будет пополняться issues, которым присвоен лейбл official-cve-feed. #1610 В настоящее время Horizontal Pod Autoscaler (HPA) может масштабировать рабочие нагрузки на основе ресурсов, используемых их подами, т.е. учитывается совокупное использование ресурсов всеми контейнерами пода. Данный KEP позволяет HPA масштабировать рабочие нагрузки на основе использования ресурсов отдельными контейнерами. #1748 KEP создает «из коробки» достаточное количество метрик, необходимых для планирования ресурсов кластера и простого представления модели ресурсов Kubernetes. Для её реализации в kube-scheduler появились новые метрики по запрашиваемым ресурсам (kube_pod_resource_requests) и желаемым лимитам (kube_pod_resource_limits) для всех запущенных подов. #3720 В прошлом году с выходом версии Kubernetes 1.25 проект перешел на свой полноценный реестр registry.k8s.io, однако значительная часть трафика по-прежнему была направлена на предыдущий эндпоинт k8s.gcr.io. Переход данного KEP’а на stable-стадию знаменует окончание затянувшегося переезда на новый реестр. #3744 Kubernetes написан на Go. В рамках минорных версий его разработчики стараются не менять версию Go, чтобы избежать дестабилизирующих изменений. Это означает, что к концу жизненного цикла конкретный релиз может сильно отстать от исправлений безопасности, реализованных в Go. KEP описывает процесс обновления поддерживаемых ветвей Kubernetes минорных версий release-1.x для сборки и выпуска с новыми минорными версиями Go, с упором на сохранение нормальной работоспособности и совместимости патч-релизов Kubernetes. Ниже приведен список переключателей функциональности, флагов и т.п., которые признаны устаревшими в Kubernetes 1.27: Kubeadm v1beta2; миграцию на v1beta3 можно провести с помощью kubeadm config migrate. resource.k8s.io/v1alpha1.PodScheduling: переход на resource.k8s.io/v1alpha2.PodSchedulingContext. DynamicResourceManagement v1alpha1: переход на v1alpha2. CSIStorageCapacity: Storage.k8s.io/v1beta1: переход на v1. Аннотации seccomp.security.alpha.kubernetes.io/pod и container.seccomp.security.alpha.kubernetes.io: вместо них используйте поле securityContext.seccompProfile. Плагин допуска SecurityContextDeny. Аннотация service.kubernetes.io/topology-aware-hints: переход на service.kubernetes.io/topology-mode. Вместо k8s.gcr.io используйте registry.k8s.io. Переключатели функциональности: IPv6DualStack ExpandCSIVolumes ExpandInUsePersistentVolumes ExpandPersistentVolumes ControllerManagerLeaderMigration Миграция CSI CSIInlineVolume EphemeralContainers LocalStorageCapacityIsolation NetworkPolicyEndPort StatefulSetMinReadySeconds IdentifyPodOS DaemonSetUpdateSurge appProtocol: kubernetes.io/grpc. Флаг kube-apiserver’а: --master-service-namespace. Флаги CLI: --enable-taint-manager и --pod-eviction-timeout. Флаги kubelet’а: --container-runtime, --master-service-namespace. In-tree-плагин дискового хранилища Azure. Поставщик учетных данных kubelet’а AWS: используйте ecr-credential-provider. Метрики: node_collector_evictions_number заменена на node_collector_evictions_total scheduler_e2e_scheduling_duration_seconds заменена на scheduler_scheduling_attempt_duration_seconds Список изменений, под которые необходимо адаптировать конфигурации: kubelet: --container-runtime-endpoint и --image-service-endpoint перенесены в kubelet config. Имена StatefulSet’ов должны быть DNS метками, а не поддоменами. Поле resourceClaims было изменено с set на map. Плагин NodeAffinity Filter: фильтр не запускается, если PreFilter возвращает Skip. Планировщик: больше не выполняет определенные методы, когда они не нужны: Фильтр NodeAffinity; Фильтр InterPodAffinity. Score resource.k8s.io/v1alpha1/ResourceClaim теперь отклоняет повторно используемые UID. kubelet: больше не создает некоторые legacy-правила iptables по умолчанию. kubelet: значение по умолчанию для MemoryThrottlingFactor теперь равно 0.9. API пода: поле .spec.schedulingGates[].name требует квалифицированных имен. Правила проверки для него теперь такие же, как для .spec.readinessGates[].name. PodSpec: отклоняет недопустимые имена ResourceClaim и ResourceClaimTemplate. API resource.k8s.io: несовместимое изменение в структуре AllocationResult. Перед обновлением рекомендуем ознакомиться с CHANGELOG’ом. Читайте также в нашем блоге: «Kubernetes 1.26: обзор нововведений, включая первый KEP „Фланта“»; «Kubernetes 1.25: обзор нововведений»; «Kubernetes 1.24: обзор нововведений».