Привет! Я Саша Хренников, руководитель DevOps-юнита в KTS.
Новогоднее испытание для DevOps-инженеров подошло к концу, и сегодня я пошагово разберу решение задачи. Но сначала я сделаю два объявления.
Во-первых, с этого дня мы открываем доступ ко всем архивным челленджам. Если вы не успели поучаствовать, но хотите проверить свои силы и подготовиться к будущим испытаниям, вы можете перейти в нашего бота, и он расскажет, что делать. Главное — попробуйте разобраться самостоятельно, не спойлерите себе решение.
Почитать описания архивных челленджей можно здесь:
-
Назад в прошлое: запускаем k8s v.0.1 из 2014 и анонсируем челлендж
-
DevOps Challenge: восстановите работу MySQL и выиграйте крутой мерч
Во-вторых, я с радостью поздравляю победителей текущего испытания — тринадцать участников, которые быстрее всех справились с заданием и уже освобождают место в шкафу для нашего мерча. Итак, поздравляем с победой:
-
Konstantin aka @526***: 5 мин 42 сек
-
Chatbot aka @mr_hightlook: 5 мин 51 сек
-
ne0ba aka @ne0ba: 5 мин 53 сек
-
Alexey AnyOps aka @mozgoo: 9 мин 1 сек
-
ssch aka @ssch1337: 10 мин 22 сек
-
Dmitry Tigrov aka @dmitrytiger: 15 мин 26 сек
-
Alexandr Boltris aka @AlexandrBoltris: 17 мин 41 сек
-
Alexander Evsikov aka @Evsikov: 18 мин 33 сек
-
Igor Dronov aka @Benosa19: 19 мин 33 сек
-
Кирилл aka @kirill_serguta: 20 мин 26 сек
-
Azat aka @nevmetovazat: 22 мин 26 сек
-
Sergei D aka @sergei0d: 26 мин 0 сек
-
Vladimir Fedorov aka @FdrvVldmr: 26 мин 0 сек
Именно им, а не своим оленям, Деду Морозу стоило поручать развертывание приложения. А пока Дедушка развозит подарки, я предлагаю разобраться с тем, что натворили наши парнокопытные.
Оглавление
Диагностика
Сперва посмотрим, что запущено в кластере и какие ошибки мы видим при запуске.
#kubectl get po NAME READY STATUS RESTARTS AGE newyear-76ccb4dffd-kxtc5 0/1 CrashLoopBackOff 4 (49s ago) 2m32s #kubectl logs newyear-76ccb4dffd-kxtc5 2024/12/31 23:59:59 err
Похоже, что для отладки придется погружаться в под. Для этого отредактируем deployment, предварительно сохранив его.
#kubectl get deploy NAME READY UP-TO-DATE AVAILABLE AGE newyear 0/1 1 0 4m27s #kubectl get deploy newyear -o yaml > ./deploy.yaml #kubectl edit deploy newyear
Во время редактирования стоит удалить livenessProbe и заменить параметр command на что-то, что не будет падать при запуске. Например, так:
-
Исходный вариант:
spec: containers: - command: - /build/newyaer image: cr.yandex/crpeghj733dngql9boeu/challenges-new-year-disk:0.0.1 imagePullPolicy: IfNotPresent livenessProbe: failureThreshold: 3 httpGet: path: /status port: 8080 scheme: HTTP periodSeconds: 10 successThreshold: 1 timeoutSeconds: 1
-
Результат:
spec: containers: - command: - tail - -f - /etc/hosts image: cr.yandex/crpeghj733dngql9boeu/challenges-new-year-disk:0.0.1 imagePullPolicy: IfNotPresent
Теперь можно попасть в запущенный под через exec
и сразу воспроизвести проблему.
#kubectl get po NAME READY STATUS RESTARTS AGE newyear-559dd4766f-dcbtz 1/1 Running 0 26s #kubectl exec -it newyear-559dd4766f-dcbtz -- /bin/bash root@newyear-559dd4766f-dcbtz:/build# /build/newyaer 2024/12/31 23:59:59 err
Далее есть два способа разобраться, что же не так с приложением.
-
Первый — для староверов и любителей низкоуровневой отладки:
root@newyear-559dd4766f-dcbtz:/build# strace /build/newyaer openat(AT_FDCWD, "/opt/storage/2024HNY.txt", O_WRONLY|O_CREAT|O_TRUNC|O_CLOEXEC, 0644) = -1 ENOSPC (No space left on device)
-
Второй для тех, кто верит, что даже олени способны на разумные действия:
root@newyear-559dd4766f-dcbtz:/build# /build/newyaer -h You can add -v 2024/12/31 23:59:59 err root@newyear-559dd4766f-dcbtz:/build# /build/newyaer -v 2024/12/31 23:59:59 open /opt/storage/2024HNY.txt: no space left on device
В обоих случаях мы узнаем, что приложение не может создать файл /opt/storage/2024HNY.txt из-за нехватки места на диске. Видимо, стоит посмотреть, что происходит со свободным местом.
root@newyear-559dd4766f-dcbtz:/build# df -h Filesystem Size Used Avail Use% Mounted on … /dev/vdb 488M 129M 349M 28% /opt/storage …
Странная ситуация. Непохоже, что места недостаточно. Но и в этом случае стоит проверить еще один вариант — индексные дескрипторы, они же inode.
root@newyear-559dd4766f-dcbtz:/build# df -i Filesystem Inodes IUsed IFree IUse% Mounted on … /dev/vdb 32768 32768 0 100% /opt/storage …
Вот и наша проблема. Все дескрипторы загружены, и приложение не может запуститься.
Фикс
Сначала нужно посмотреть, чем же заняты все дескрипторы.
ls -lah /opt/storage/ | head -n 10 total 129M drwxr-xr-x 3 root root 928K Dec 16 20:56 . drwxr-xr-x 1 root root 4.0K Dec 16 21:05 .. -rw-r--r-- 1 root root 2 Dec 16 20:56 0.txt -rw-r--r-- 1 root root 2 Dec 16 20:56 1.txt -rw-r--r-- 1 root root 3 Dec 16 20:56 10.txt -rw-r--r-- 1 root root 4 Dec 16 20:56 100.txt -rw-r--r-- 1 root root 5 Dec 16 20:56 1000.txt -rw-r--r-- 1 root root 6 Dec 16 20:56 10000.txt -rw-r--r-- 1 root root 6 Dec 16 20:56 10001.txt
Большое количество мусорных файлов. Скорее всего, чистить все и сразу не стоит. В качестве эксперимента попробуем удалить один и запустить приложение:
root@newyear-559dd4766f-dcbtz:/build# cd /opt/storage/ root@newyear-559dd4766f-dcbtz:/opt/storage# rm ./1.txt root@newyear-559dd4766f-dcbtz:/opt/storage# /build/newyaer -v 2024/12/31 23:59:59 open /opt/storage/2025HNY.txt: no space left on device
Любопытно, ошибка сохраняется, но имя файла поменялось. Похоже, что приложение хочет создать больше одного файла. Что ж, давайте попробуем удалить весь мусор.
root@newyear-559dd4766f-dcbtz:/opt/storage# rm ./*.txt root@newyear-559dd4766f-dcbtz:/opt/storage# ls -lah total 952K drwxr-xr-x 3 root root 928K Dec 16 21:12 . drwxr-xr-x 1 root root 4.0K Dec 16 21:05 .. -rw-r--r-- 1 root root 69 Dec 16 20:56 2025conf.yaml
Увлекательно. Оказывается, у приложения был еще и конфиг. Кстати, если его удалить, то с ключом -v
вы получите подсказки по его восстановлению.
root@newyear-559dd4766f-dcbtz:/opt/storage# rm ./2025conf.yaml root@newyear-559dd4766f-dcbtz:/opt/storage# /build/newyaer -v 2024/12/31 23:59:59 open /opt/storage/2025conf.yaml: no such file or directory root@newyear-559dd4766f-dcbtz:/opt/storage# > ./2025conf.yaml root@newyear-559dd4766f-dcbtz:/opt/storage# /build/newyaer 2024/12/31 23:59:59 config error /build/newyaer -v 2024/12/31 23:59:59 Please fill out the configuration in the following format: config: timeout: 5 year: 2025 greeting: "Happy New Year"
Наконец, когда проблема с файлами решена, мы можем проверить, что приложение перестало падать. Для этого запустим и прервем оригинальный бинарник /build/newyear.
И теперь, когда мы убедились, что приложение не падает, можно вернуть исходную конфигурацию deployment и проверить его работоспособность.
#kubectl edit deploy newyear #kubectl get po NAME READY STATUS RESTARTS AGE newyear-559dd4766f-dcbtz 1/1 Terminating 0 12m newyear-76ccb4dffd-zgg28 1/1 Running 0 3s #kubectl exec -it newyear-76ccb4dffd-zgg28 -- /bin/bash root@newyear-76ccb4dffd-zgg28:/build# curl 127.0.0.1:8080/status Happy New Year
Заключение
Вот, собственно, и все решение. На этот раз мы постарались не перегибать со сложностью, но все же оставить простор для гипотез и рассуждений. Будем благодарны, если вы поделитесь впечатлениями в комментариях и расскажете, что стоит улучшить к следующему разу.
Если же вам не хватает задач, вы уже прорешали все архивные челленджи и хотите окончательно преисполниться в своем познании перед новогодними праздниками, рекомендую почитать наши статьи для DevOps-инженеров. Там мы с коллегами делимся опытом и описываем технологии, которыми сами пользуемся в работе:
-
JupyterHub на стероидах: реализация KubeFlow фич без масштабных интеграций
-
Поднимаем динамические окружения для stateless- и stateful-сервисов
И желаем вам удачи с любыми испытаниями в наступающем году!
ссылка на оригинал статьи https://habr.com/ru/articles/867882/
Добавить комментарий