Вопрос или проблема
Я управляю развертыванием Elasticsearch в Kubernetes. Я вижу, что дисковое пространство близко к полному, поэтому хотел бы увеличить размер постоянных томов.
Я хочу изменить это значение в Stateful Set:
spec.volumeClaimTemplates[0].spec.resources.requests.storage : "10Gi"
Но когда я делаю это через Kubernetes-dashboard, я получаю следующее сообщение:
Ошибка внутреннего сервера
StatefulSet.apps “es-cluster” недействителен: spec: Запрещено: обновления statefulset > spec для полей, кроме ‘replicas’, ‘template’ и ‘updateStrategy’, запрещены.
Это заставляет меня думать, что мне придется удалить существующий Stateful Set и развернуть новый.
Возможно ли увеличить дисковое пространство на под без прерывания сервиса или потери данных?
Дополнительные детали
У меня несколько подов данных Elasticsearch и я использую количество реплик = 1, так что если я смогу их отключить и обновить дисковое пространство по одному поду за раз, это не должно вызвать проблем. Я просто не вижу, как это сделать с учетом указанных выше ограничений.
Собрал эту процедуру на основе других комментариев на https://github.com/kubernetes/kubernetes/issues/68737. Я протестировал это на kubernetes 1.14:
kubectl edit pvc <имя>
для каждого PVC в StatefulSet, чтобы увеличить его емкость.kubectl delete sts --cascade=orphan <имя>
для удаления StatefulSet и сохранения его подов.kubectl apply -f <имя>
для воссоздания StatefulSet.kubectl rollout restart sts <имя>
для перезапуска подов, по одному за раз. Во время перезапуска PVC пода будет изменен в размере.
Если вы хотите следить за происходящим, запустите еще два терминала с этими командами перед любыми из команд выше:
kubectl get pod -w
kubectl get pvc -w
Чтобы применить этот принцип к helm chart, я смог сделать следующее, основываясь на приведенной выше информации, а также на некоторых рекомендациях в этой теме: https://github.com/kubernetes/kubernetes/issues/68737#issuecomment-469647348
Пример ниже использует следующие значения:
- Имя StorageClass: standard
- Имя StatefulSet: rabbitmq-server
- Имя PersistentVolumeClaim (PVC): data-rabbitmq-server-0
- Имя релиза helm: rabbitmq-server
- ИмяChart helm: stable/rabbitmq
Эти значения можно найти в вашей среде, используя следующие команды:
- Имя PVC и имя StorageClass:
kubectl get pvc
- Имя StatefulSet:
kubectl get sts
- Имя релиза helm:
helm list
- Имя helm chart: Вы должны знать, какой helm chart вы пытаетесь обновить 😀
И вот шаги для обновления размера PV в StatefulSet helm chart:
kubectl edit storageClass standard
и установить/убедиться, что allowVolumeExpansion: true (в моем случае оно уже было)kubectl delete sts --cascade=orphan rabbitmq-server
kubectl edit pvc data-rabbitmq-server-0
и изменить spec size на 50Gi- Изменить размер в моем helm chart (rabbitmq-values.yaml) на 50Gi
helm upgrade --recreate-pods --reuse-values -f rabbit-values.yaml rabbitmq-server stable/rabbitmq
ЗАМЕТКА: На последнем шаге используется флаг --recreate-pods
, чтобы force перезапуск подов, что запускает фактическое изменение файловой системы. Это также вызывает простой для этих подов. Если вы хотите попробовать сделать это без простоя, вы можете попробовать убрать этот флаг и вручную завершать/перезапускать один под за раз или что-то в этом роде.
Вот полный скрипт для изменения размера томов STS на основе других ответов. Мне не пришлось использовать --cascade=false
при удалении STS, потому что он уже был уменьшен до 0 перед этим шагом.
- Убедитесь, что StorageClass поддерживает увеличение объема, если необходимо, отредактируйте его:
kubectl get -o jsonpath="{.allowVolumeExpansion}" sc <SC-NAME>
# должно вернуть true, в противном случае, патчите его:
kubectl patch -p '{"allowVolumeExpansion": true}' sc <SC-NAME>
# затем снова выполните первую команду
- Уменьшите количество реплик StatefulSet до 0 для возможности изменения объема.
# нам нужно сохранить оригинальное количество реплик, поэтому давайте сохраним его перед уменьшением
REPLICAS=`kubectl get -o jsonpath="{.spec.replicas}" sts/<STS-NAME>`
kubectl scale sts/<STS-NAME> --replicas 0
- Исправьте PersistentVolumeClaim с новым размером, это немедленно изменит размер PersistentVolume и его диска. Вы можете проверить, описывая PV и проверяя портал облачного провайдера для диска.
Тем не менее, описание PVC не будет отражать новый размер, пока под не будет запущен, после чего он автоматически изменит размер файловой системы:
NEW_SIZE=128Gi
for i in `seq 0 $[REPLICAS-1]`; do
PVC=<PVC-NAME-PREFIX>-$i
echo "Обновление PVC $PVC"
# Печатаем текущий размер:
kubectl get -o jsonpath="{.spec.resources.requests.storage} " pvc/$PVC
# Устанавливаем новый размер:
kubectl patch -p '{"spec": {"resources": {"requests": {"storage": "'$NEW_SIZE'"}}}}' pvc/$PVC
# Проверяем PV:
echo "Ожидание 10 секунд, чтобы PV зафиксировало изменение..."
echo "Если вы все еще видите такой же размер, не беспокойтесь, чтобы увидеть новый размер, просто запустите этот скрипт снова"
sleep 10
PV=`kubectl get -o jsonpath="{.spec.volumeName}" pvc/$PVC`
kubectl get -o jsonpath="{.spec.capacity.storage} " pv/$PV
echo "Готово"
done
- Удалите STS для обновления с новым размером.
kubectl delete sts <STS-NAME>
- Воссоздайте STS (helm upgrade или kubectl apply) после редактирования запрашиваемого размера, который должен соответствовать новому размеру, примененному к PVC. После запуска каждый под в
репликах запустит изменение размера файловой системы, и это немедленно отразится на его PVC
for i in `seq 0 $[REPLICAS-1]`; do
PVC=<PVC-NAME-PREFIX>-$i
echo "Проверка размера PVC $PVC"
# Проверяем текущий размер:
kubectl get -o jsonpath="{.status.capacity.storage} " pvc/$PVC
done
Несмотря на то что Изменение размера постоянных томов с использованием Kubernetes с Kubernetes 1.11, похоже, что с этим есть некоторые проблемы.
Как обсуждалось в GitHub: StatefulSet: поддержка изменения размера PVC хранилища в K8s v1.11 #68737
Из-за этого ограничения многие операторы баз данных для Kubernetes не поддерживают изменение размера PVC.
Это критическая проблема, потому что когда ваша база данных становится больше, чем вы ожидали – у вас нет выбора, и необходимо создать резервную копию БД и воссоздать новую БД из резервной копии.
Вам следует изменить его, удалив Statefulset, что приведет к удалению всех подов и вызовет простой.
Решение было опубликовано DaveWHarvey
Я обошел это ограничение на elasticsearch из-за работы, которую мне пришлось провести, чтобы избежать невозможности назначить EBS тома, потому что они находятся в неправильной зоне доступности, т.е. я создал statefulset для каждой AZ. Если я хочу изменить некоторые характеристики хранения, я создаю новую “AZ”, используя тот же класс хранения, а затем мигрирую все данные на поды в эту новую AZ, после чего уничтожаю старую AZ.
Надеюсь, это немного поможет вам.
Вот шаги, которые сработали для меня:
- Убедитесь, что расширение объема включено в классе хранения, используемом в PVC.
- Используйте kubectl для редактирования PVC, который вы хотите обновить. (Скажем, обновите объем до 50 ГБ)
- Убедитесь, что kubectl удаляет stateful set с каскадированием=false
- Отредактируйте Statefulset в файле манифеста.
- Вернитесь к версии/релизу, который развернут в кластере.
- Снова выполните kubectl/Helm upgrade стека, чтобы снова создать Statefulset.
- Теперь у вас должен быть обновленный Statefulset и PVC. (Обновление объема на 50 ГБ)
- Перезапустите Statefulset с помощью kubectl rollout.
Можно расширить PVC statefulset в AKS, следуя этим четырем шагам: https://stackoverflow.com/a/71175193/4083568
Без удаления sts и поддержания работы вашего сервиса в процессе:
- отредактируйте все спецификации pvc с новым размером (возможно, также отредактируйте crd, контролирующий размер pvc)
- для каждого po:
- закройте все no
- удалите po
- подождите, пока pv не станет нового размера
- разомкните один no
- подождите, пока sts не станет “здоровым”, в зависимости от вашего сервиса
- проверьте, что pvc имеет новый размер
- перейдите к следующему po
Ответ или решение
Для увеличения размера диска в StatefulSet (например, для развертывания Elasticsearch в Kubernetes) необходимо следовать определенной процедуре, так как прямое изменение spec.volumeClaimTemplates
в StatefulSet приведет к ошибке из-за ограничений Kubernetes. Следующие шаги помогут вам увеличить размер диска без остановки сервиса и потери данных:
Шаги по изменению размера диска в StatefulSet
-
Проверьте поддержку увеличения размера в StorageClass:
Убедитесь, что вашStorageClass
позволяет изменения. Выполните следующую команду:kubectl get storageclass <SC-NAME> -o jsonpath="{.allowVolumeExpansion}"
Если ответ не ‘true’, выполните команду:
kubectl patch storageclass <SC-NAME> -p '{"allowVolumeExpansion": true}'
-
Измените PVC для всех подов:
Используйте командуkubectl edit pvc <PVC-NAME>
для изменения размера PVC для каждого пода в StatefulSet. Замените значениеspec.resources.requests.storage
на новый размер (например,50Gi
). -
Удалите StatefulSet без каскадного удаления:
Удалите StatefulSet с помощью следующей команды, чтобы сохранить поды и PVC:kubectl delete sts <STS-NAME> --cascade=orphan
-
Пересоздайте StatefulSet:
Обновите манифест StatefulSet с установленным новым размером хранения и примените его командой:kubectl apply -f <statefulset-definition.yaml>
-
Перезапустите поды для применения изменения размера:
Запустите команду следующего вида, чтобы перезапустить поды:kubectl rollout restart sts <STS-NAME>
Это приведет к тому, что каждый под начнет использовать обновленный размер PVC и выполнит автоматическое изменение размера файловой системы.
-
Мониторинг процесса:
Вы можете использовать команды в нескольких терминалах для мониторинга процесса:kubectl get pod -w kubectl get pvc -w
Важно:
- Избегайте удаления Pod’ов вручную: Вместо удаления вам следует просто перезапустить StatefulSet, чтобы минимизировать даунтайм и обеспечить целостность данных.
- Тестирование: Рекомендуется протестировать этот процесс в тестовой среде перед применением в продакшене, чтобы убедиться, что у вас есть резервные копии данных и что все работает должным образом.
Дополнительная информация:
Дополнительно вы можете рассмотреть применение Helm для управления вашими развертываниями, если вы используете его. В этом случае изменение значений в values.yaml
, как было описано в комментариях, также может упростить обновление ваших StatefulSet’ов и PVC.
Следуя данным шагам, вы сможете увеличить размер диска в StatefulSet без потери данных и с минимальными перерывами в обслуживании вашей службы.