Combine
Combine — реактивный фреймворк Apple для работы с асинхронными значениями, которые приходят во времени: нажатия, ответы сети, изменения свойств. Вместо колбэков и делегатов вы описываете поток значений и подписываетесь на него. Ключевая идея — разделение ролей: одна сторона значения выдаёт, другая запрашивает, а связь между ними управляет спросом и жизненным циклом.
Главные ловушки новичка спрятаны именно в этих ролях. Publisher не «толкает» значения сам по себе — он ждёт спроса от подписчика. Подписчик — это не то же самое, что subscription, которая связывает пару и живёт, только пока вы держите AnyCancellable. А CurrentValueSubject и @Published добавляют поверх потока хранимое состояние, которое чаще всего и связывают с UI во MVVM. Полная карта — в слоях ниже.
Карта темы
- Publisher — источник потока значений и события завершения либо ошибки, ленивый до появления спроса.
- Подписчик — сторона, запрашивающая и получающая значения;
sinkиassignкак готовые подписчики. - AnyCancellable — токен подписки, удержание которого держит её живой, а освобождение — отменяет.
- CurrentValueSubject — publisher, который ещё и хранит текущее значение и переотдаёт его новым подписчикам.
- Свойство @Published — property wrapper, превращающий обычное свойство в publisher, доступный через префикс
$.
Частые ошибки и ловушки
| Ошибка | Последствие |
|---|---|
| Считать, что publisher выдаёт значения сразу, не считаясь со спросом | Неверная модель — без подписчика и спроса поток не течёт |
| Путать подписчика с объектом subscription | Непонимание, что именно управляет спросом и жизненным циклом |
Не удерживать AnyCancellable | Подписка отменяется сразу, экран перестаёт обновляться |
Путать CurrentValueSubject с PassthroughSubject | Ждут переотдачи текущего значения там, где его нет |
Забыть префикс $ у @Published-свойства | Обращение к значению вместо его publisher, подписка не создаётся |
| Считать любой publisher одноразовым колбэком | Теряют, что это поток из многих значений плюс завершение |
Значение для собеседований
Combine спрашивают, чтобы проверить, различаете ли вы источник, приёмник и связь между ними, а не только умеете написать .sink. Кандидат, который объясняет поток как «publisher выдаёт значения по спросу подписчика, а subscription этим спросом управляет и живёт, пока держится cancellable», сразу опережает того, кто зовёт всё это «подписками».
Что обычно проверяют:
- Разницу между publisher, подписчиком и subscription и кто из них чем управляет.
- Почему
AnyCancellableнужно хранить и где именно во view model. - Отличие
CurrentValueSubjectотPassthroughSubjectи от@Published. - Как связать состояние view model с контроллером или SwiftUI-представлением.
Типичный неверный ответ: «publisher — это переменная, которая хранит значение, а подписчик читает его синхронно». На самом деле publisher — это поток во времени, значения текут только по спросу подписчика, а без удержанного cancellable подписка немедленно отменяется.