Как передавать большой отчет на мобильное устройство и уменьшить размер файла
Что проверяют
Видите ли вы задачу целиком: формат отчёта, генерацию на сервере, сеть и поведение клиента. Сжатие здесь только одна деталь, и часто не главная. Следом спрашивают, что делать, если отчёт собирается минуту, а связь на телефоне обрывается.
Как отвечать
Сначала уточните, что за отчёт: данные для экрана приложения или документ для скачивания. От этого зависит решение.
- передавать меньше: мобильному экрану редко нужен весь отчёт. Пагинация по курсору, агрегаты вместо сырых строк, только нужные поля дают больше любого сжатия;
- формат: для данных JSON с HTTP-сжатием или Protobuf, если клиент и сервер ваши. Для документа PDF со сжатыми картинками или XLSX. XLSX внутри уже ZIP-архив, повторный gzip его почти не уменьшает;
- сжатие в Spring Boot:
server.compression.enabled=true, по умолчанию оно выключено и сжимает только типы изmime-typesи ответы большеmin-response-size. Часто сжатие отдают прокси, тогда в приложении его не включают; - генерация без пика памяти: стриминг через
StreamingResponseBody, для ExcelSXSSFWorkbookиз Apache POI, который держит в памяти только окно строк; - долгие отчёты асинхронно: запрос ставит задачу, клиент получает id, по готовности приходит пуш, а файл скачивается из объектного хранилища по временной подписанной ссылке;
- обрыв связи: докачка через
RangeиAccept-Ranges, на Android загрузку ведутWorkManagerилиDownloadManager, а готовый файл кешируется сETag, чтобы не качать неизменившийся отчёт заново.
Где спотыкаются
Называют конкретный процент сжатия как факт. Он зависит от данных: текстовый CSV ужимается в разы, а картинки и XLSX почти никак.
Строят весь отчёт в памяти одним объектом и отдают byte[]. Под нагрузкой несколько таких запросов кладут сервис по памяти.
Предлагают CDN для персонального отчёта. CDN полезен для одинаковых публичных файлов, а личный отчёт кешировать на общих узлах нельзя.