Короткий ответ
Нужно переходить на graceful cutover: сначала направлять на новое окружение только новые соединения, давая старым WebSocket-сессиям на «синем» окружении доработать и закрыться естественным образом (drain) в течение ограниченного окна, а клиентскую часть снабдить логикой автоматического переподключения с backoff, чтобы кратковременный разрыв не ощущался пользователем как сбой.
Как это работает подробнее
обычное мгновенное переключение балансировщика хорошо работает для коротких stateless HTTP-запросов, но долгоживущие соединения (WebSocket, gRPC streaming, SSE) обрываются принудительно, если старое окружение сразу выводится из ротации. Паттерн connection draining — балансировщик перестаёт направлять новые соединения на старое окружение, но позволяет уже установленным соединениям доработать до естественного завершения или истечения тайм-аута, прежде чем окружение останавливается.
Пример кода
# Пример настройки drain для существующих соединений перед остановкой upstream
# (конкретный механизм зависит от балансировщика/ingress-контроллера)
upstream blue_backend {
server blue-1:8080 max_fails=0;
}
# При cutover: новые соединения — на green,
# blue помечается как "draining" на 60 секунд, затем останавливаетсяЧто использовать на практике
- На практике. для WebSocket-приложений стоит явно проектировать клиентскую логику переподключения (reconnect with exponential backoff и восстановление состояния подписки), чтобы кратковременный разрыв воспринимался как штатная реконнект-пауза, а не как сбой. Также полезно ограничить максимальное окно drain (например, 60 секунд), после которого оставшиеся соединения принудительно закрываются, чтобы не блокировать полное освобождение старого окружения бесконечно.
- Пример. Ожидаемое поведение: в течение 60-секундного окна drain количество активных WebSocket-соединений к blue-окружению постепенно снижается до нуля по мере их естественного закрытия или истечения тайм-аута, при этом метрика `websocket_reconnects_total` показывает управляемый, а не массовый единовременный всплеск переподключений.
Подводные камни
- Частые ошибки. выключают старое окружение сразу после переключения листенера, не дав установленным соединениям время на graceful close, что гарантированно обрывает все активные сессии одновременно; не реализуют автоматический реконнект на клиенте, из-за чего пользователю приходится вручную обновлять страницу.