Зачем нужен context
Клиент «ФинГура» закрыл вкладку на середине загрузки большого архива, а «Полка» продолжала лить файлы в S3: горели CPU и сеть. Аня на разборе сформулировала правило: отмена — сигнал, на который код отвечает сам.
context — это сигнал отмены и дедлайна, который передаётся сквозь слои программы; отмена кооперативна: каждый слой сам слушает сигнал в своих блокирующих точках.
Сигнал сквозь слои
func handle(ctx context.Context, ch <-chan int) {
for {
select {
case <-ctx.Done():
return // клиент ушёл, дальше работать незачем
case v := <-ch:
process(v) // каждая блокирующая точка слушает отмену
}
}
}
context.Context — интерфейс с методом Done <-chan struct{}. Канал закрывается, когда контекст отменяют — по таймауту, по отмене или по дедлайну. Главная идея: контекст передаётся от верхнего уровня вниз, и каждый слой может слушать один и тот же сигнал. Отмена кооперативна: ctx.Done нужно проверять в select при каждой блокирующей точке. Разовая проверка в начале не работает — если клиент ушёл, пока код «работает», горутина об этом не узнает.
Зачем это нужно
Представь обработчик HTTP-запроса: он зовёт сервис, тот — репозиторий, репозиторий — базу. Если клиент оборвал соединение на полпути, работа всей цепочки стала бессмысленной. Без контекста нижние слои об этом не знают и досчитывают впустую — тратят CPU, держат соединения. С контекстом сигнал «клиент ушёл» доходит до каждого слоя, и все сворачиваются.
Где контекст обязателен
Сетевые и блокирующие операции: запросы к БД, HTTP-вызовы, чтение из каналов. Для них контекст — штатный способ передать сигнал, на который вызов обязан отреагировать сам: драйвер БД и HTTP-клиент слушают ctx и возвращают ошибку при отмене, а голое чтение из канала контекст не прерывает — там нужен select. Вспомни (утечки) и (таймаут и отмена): контекст — штатное лекарство от обеих проблем.
Вы узнаете:
- почему контекст передают первым аргументом
- что даёт
context.Contextкак интерфейс
Проверьте себя
Почему «досчитать впустую» отменённый запрос дорого?
Что даёт context поверх голого done-канала?
Что значит «отмена кооперативна»?
правильных ответов
Context — общий сигнал отмены, передаваемый вниз по слоям; отмена кооперативна, и слушать сигнал нужно в каждой блокирующей точке, а не один раз. Без контекста нижние слои не знают, что их работа больше не нужна.
10 000 ₽ · 60 минут · онлайн