Как реализовать кэширование данных в оффлайн режиме в iOS
Что проверяют
Понимаете ли вы разницу между «сохранить ответ на диск» и offline-first архитектурой, где приложение работает с локальной базой, а сеть лишь синхронизирует её. Следом почти всегда спрашивают про изменения, сделанные без сети, и конфликты при синхронизации.
Как отвечать
Каркас такой: локальное хранилище это единственный источник правды для UI. Экран читает из базы и подписывается на её изменения, сетевой слой скачивает свежие данные и пишет их в ту же базу. Интерфейс обновляется сам, есть сеть или нет.
- хранилище: Core Data или SwiftData (iOS 17+) для графа объектов, GRDB или SQLite, если нужен контроль над SQL.
UserDefaultsтолько для настроек и флагов, не для данных; - HTTP-кэш:
URLCacheпо умолчанию следует заголовкамCache-Control, а политика.returnCacheDataElseLoadотдаёт из кэша даже просроченный ответ. Базу это не заменяет, кэш могут вытеснить в любой момент; - очередь изменений: действия пользователя без сети пишутся локально и в таблицу исходящих операций. При появлении сети очередь уходит по порядку, у каждой операции есть идентификатор, чтобы повтор не создал дубль на сервере;
- конфликты: заранее выберите правило. Last-write-wins по
updatedAt, версия записи с отказом на сервере или ручное разрешение; - сеть:
NWPathMonitorиз Network framework сообщает о смене пути,waitsForConnectivityуURLSessionConfigurationдожидается соединения, фоновые дозагрузки идут черезBGTaskScheduler.
Упомяните, куда кладутся файлы: Library/Caches система может очистить при нехватке места, а то, что нельзя потерять, живёт в Application Support.
Где спотыкаются
Проверяют «есть ли интернет» перед каждым запросом. Наличие пути не гарантирует доступности сервера, правильнее отправить запрос и обработать ошибку.
Показывают пустой экран до ответа сети, хотя в базе уже лежат вчерашние данные. Сначала покажите кэш с отметкой времени, потом обновите.
Не продумывают повтор неудачной отправки. Без идемпотентного ключа второй запрос после таймаута создаёт на сервере копию заказа или сообщения.