Проучванията за живост в Kubernetes могат да бъдат опасни

Забележка. превод: Водещият инженер от Zalando, Хенинг Джейкъбс, многократно е забелязвал проблеми сред потребителите на Kubernetes при разбирането на целта на сондите за жизненост (и готовност) и правилното им използване. Затова той събра мислите си в тази обемна бележка, която в крайна сметка ще стане част от документацията на K8s.

Проучванията за живост в Kubernetes могат да бъдат опасни

Проверки на здравето, известни в Kubernetes като сонди за жизненост (т.е. буквално "тестове за жизнеспособност" - прибл. превод), може да бъде доста опасно. Препоръчвам да ги избягвате, ако е възможно: единствените изключения са, когато са наистина необходими и сте напълно наясно със спецификата и последствията от тяхното използване. Тази публикация ще говори за проверките на жизненост и готовност и също така ще ви каже в какви случаи Цена и не трябва да ги използвате.

Моят колега Сандор наскоро сподели в Twitter най-честите грешки, които среща, включително тези, свързани с използването на сонди за готовност/жизненост:

Проучванията за живост в Kubernetes могат да бъдат опасни

Неправилно конфигуриран livenessProbe може да влоши ситуациите с високо натоварване (изключване на снежна топка + потенциално дълго време за стартиране на контейнер/приложение) и да доведе до други негативни последици, като спадане на зависимостта (Вижте също скорошната ми статия относно ограничаването на броя заявки в комбинацията K3s+ACME). Още по-лошо е, когато сондата за жизненост се комбинира с проверка на здравето, която е външна база данни: единичен отказ на DB ще рестартира всички ваши контейнери!

Общо съобщение „Не използвайте сонди за жизненост“ в този случай това не помага много, така че нека да разгледаме за какво служат проверките за готовност и жизненост.

Забележка: Повечето от тестовете по-долу първоначално бяха включени във вътрешната документация за разработчици на Zalando.

Проверки за готовност и жизненост

Kubernetes предоставя два важни механизма, наречени сонди за жизненост и сонди за готовност. Те периодично извършват някакво действие - като изпращане на HTTP заявка, отваряне на TCP връзка или изпълнение на команда в контейнера - за да потвърдят, че приложението работи според очакванията.

Kubernetes използва сонди за готовностза да разбере кога контейнерът е готов да приеме трафик. Една капсула се счита за готова за употреба, ако всички нейни контейнери са готови. Една употреба на този механизъм е да се контролира кои подове се използват като бекенд за услугите на Kubernetes (и особено Ingress).

Сонди за живост помогнете на Kubernetes да разбере кога е време да рестартирате контейнера. Например, такава проверка ви позволява да прехванете блокиране, когато дадено приложение заседне на едно място. Рестартирането на контейнера в това състояние помага да стартирате приложението въпреки грешките, но също така може да доведе до каскадни повреди (вижте по-долу).

Ако се опитате да внедрите актуализация на приложение, която не преминава проверките за жизнеспособност/готовност, нейното внедряване ще бъде спряно, докато Kubernetes чака статуса Ready от всички подс.

Пример

Ето пример за сонда за готовност, която проверява път /health чрез HTTP с настройки по подразбиране (интервал: 10 секунди, изчакване: 1 секунда, праг на успех: 1, праг на отказ: 3 XNUMX XNUMX):

# часть общего описания deployment'а/стека
podTemplate:
  spec:
    containers:
    - name: my-container
      # ...
      readinessProbe:
        httpGet:
          path: /health
          port: 8080

препоръки

  1. За микроуслуги с HTTP крайна точка (REST и т.н.) винаги дефинирайте сонда за готовност, който проверява дали приложението (pod) е готово да приема трафик.
  2. Уверете се, че сондата за готовност покрива наличността на действителния порт на уеб сървъра:
    • използване на портове за административни цели, наречени "admin" или "management" (например 9090), за readinessProbe, уверете се, че крайната точка връща OK само ако основният HTTP порт (като 8080) е готов да приеме трафик*;

      *Знам за поне един случай в Zalando, при който това не се е случило, т.е. readinessProbe Проверих порта за управление, но самият сървър не започна да работи поради проблеми със зареждането на кеша.

    • прикачването на сонда за готовност към отделен порт може да доведе до факта, че претоварването на главния порт няма да бъде отразено в проверката на здравето (т.е. пулът от нишки на сървъра е пълен, но проверката на здравето все още показва, че всичко е наред ).
  3. Уверете се, че проверката за готовност позволява инициализация/миграция на база данни;
    • Най-лесният начин да постигнете това е да се свържете с HTTP сървъра само след завършване на инициализацията (например мигриране на база данни от Път за прелитане и така нататък.); т.е. вместо да променяте състоянието на проверката на състоянието, просто не стартирайте уеб сървъра, докато миграцията на базата данни не приключи*.

      * Можете също така да изпълнявате миграции на база данни от init контейнери извън pod. Все още съм фен на самостоятелните приложения, тоест тези, в които контейнерът на приложението знае как да приведе базата данни в желаното състояние без външна координация.

  4. употреба httpGet за проверки на готовност чрез типични крайни точки за проверка на здравето (например, /health).
  5. Разберете параметрите за проверка по подразбиране (interval: 10s, timeout: 1s, successThreshold: 1, failureThreshold: 3):
    • опциите по подразбиране означават, че подът ще стане не е готов след около 30 секунди (3 неуспешни проверки за разумност).
  6. Използвайте отделен порт за „admin“ или „management“, ако технологичният стек (напр. Java/Spring) го позволява, за да отделите управлението на здравето и показателите от обикновения трафик:
    • но не забравяйте за точка 2.
  7. Ако е необходимо, сондата за готовност може да се използва за загряване/зареждане на кеша и връщане на код за състояние 503, докато контейнерът се загрее:

Предупреждения

  1. Не разчитайте на външни зависимости (като хранилища за данни) при провеждане на тестове за готовност/оживеност - това може да доведе до каскадни повреди:
    • Като пример, нека вземем REST услуга с 10 подове в зависимост от една база данни на Postgres: когато проверката зависи от работеща връзка с DB, всичките 10 pods може да се провалят, ако има забавяне от страна на мрежата/DB - обикновено това всичко завършва по-лошо, отколкото би могло;
    • Моля, обърнете внимание, че Spring Data проверява връзката с базата данни по подразбиране*;

      * Това е поведението по подразбиране на Spring Data Redis (поне това беше последният път, когато проверих), което доведе до "катастрофален" провал: когато Redis беше недостъпен за кратко време, всички подове "се сринаха".

    • „външен“ в този смисъл може също да означава други подове от същото приложение, тоест в идеалния случай проверката не трябва да зависи от състоянието на други подове от същия клъстер, за да се предотвратят каскадни сривове:
      • резултатите може да варират за приложения с разпределено състояние (например кеширане в паметта в подове).
  2. Не използвайте сонда за оживление за капсули (изключения са случаите, когато са наистина необходими и сте напълно наясно със спецификата и последствията от използването им):
    • Пробата за оживеност може да помогне за възстановяването на висящи контейнери, но тъй като имате пълен контрол над вашето приложение, неща като висящи процеси и блокировки в идеалния случай не трябва да се случват: най-добрата алтернатива е умишлено да сринете приложението и да го върнете обратно към предишното стабилно състояние;
    • неуспешна сонда за живост ще доведе до рестартиране на контейнера, като по този начин потенциално ще изостри последствията от грешки, свързани със зареждането: рестартирането на контейнера ще доведе до прекъсване (поне за продължителността на стартиране на приложението, да речем 30 секунди), причинявайки нови грешки , увеличаване на натоварването на други контейнери и увеличаване на вероятността от повреда им и др.;
    • проверките на жизненост, комбинирани с външна зависимост, са най-лошата възможна комбинация, заплашваща каскадни повреди: леко забавяне от страна на базата данни ще доведе до рестартиране на всички ваши контейнери!
  3. Параметри за проверка на жизнеспособността и готовността трябва да е различно:
    • можете да използвате сонда за жизненост със същата проверка на здравето, но по-висок праг на отговор (failureThreshold), например, задайте статуса не е готов след 3 опита и смятайте, че сондата за жизненост е неуспешна след 10 опита;
  4. Не използвайте exec проверки, тъй като те са свързани с известни проблеми, които водят до появата на зомби процеси:

Обобщение

  • Използвайте сонди за готовност, за да определите кога под е готов да получи трафик.
  • Използвайте сонди за оживление само когато наистина са необходими.
  • Неправилното използване на сонди за готовност/жизненост може да доведе до намалена наличност и каскадни повреди.

Проучванията за живост в Kubernetes могат да бъдат опасни

Допълнителни материали по темата

Актуализация № 1 от 2019-09-29

Относно init контейнери за миграция на база данни: Добавена е бележка под линия.

EJ ми напомни относно PDB: един от проблемите с проверките за жизненост е липсата на координация между подс. Kubernetes има Бюджети за прекъсване на подовете (PDB) за ограничаване на броя на едновременните повреди, които едно приложение може да изпита, но проверките не вземат предвид PDB. В идеалния случай бихме могли да кажем на K8s „Рестартирайте един под, ако тестът му е неуспешен, но не ги рестартирайте всички, за да избегнете влошаване на нещата“.

Брайън го изрази перфектно: „Използвайте изследване на жизнеността, когато знаете точно какво най-доброто нещо, което можете да направите, е да убиете приложението“ (отново, не се увличайте).

Проучванията за живост в Kubernetes могат да бъдат опасни

Актуализация № 2 от 2019-09-29

По отношение на четенето на документацията преди употреба: създадох съответната заявка (заявка за функция), за да добавите документация относно сонди за жизненост.

PS от преводача

Прочетете също в нашия блог:

Източник: www.habr.com

Добавяне на нов коментар