DownloadManager загружает файлы более 2,1 ГБ

Я работаю над приложением, и одна из функций, над которыми я работаю, - это загрузка некоторых двоичных файлов. Некоторые из них действительно большие (более нескольких мегабайт). Загрузки заканчиваются нормально, пока размер файла меньше 2 ГБ.

Я застрял в файле размером 3,2 ГБ, чтобы получить обновления для процесса обновления (я собираю DownloadManager для обновлений прогресса), но когда загрузка завершена, файл отсутствует в пути к целевому файлу. Опросив DownloadManager для этого идентификатора загрузки, я получаю STATUS_FAILED и причину ERROR_UNKNOWN - список любимых ошибок, которые вы когда-либо пожелаете!

Что странно, так это то, что это появляется на большинстве устройств, но для некоторых (например, Samsung SG 4 Active OS 4.2.2 и LG Nexus 5 OS 4.4.2) оно не появляется.

Проведя дополнительное исследование, я узнал, что это выглядит как ошибка в реализации Android DownloadManager. Кажется, реализация Android хранит счетчик скачиваний как int, но когда этот счет идет выше Integer.MAX_VALUE, загрузка заканчивается как неудачная.

Я собираюсь заменить использование DownloadManager на службу переднего плана, но я бы не сдался...

Вы, ребята, смотрели на это, и если да, то как вы это исправили? Есть ли необходимость использовать DownloadManager в пред-4.2.2, чтобы я мог загрузить более 2,1 ГБ на файл?

Ответы

Ответ 1

Чтобы загрузить такие большие файлы, вам нужно загрузить их в куски. Либо вы можете использовать любую библиотеку, которая поддерживает параметры диапазона HTTP, позволяющие вытаскивать один файл в нескольких частях, поддерживая возобновление и т.д.

Или вы можете разделить свой большой файл на своем сервере, а затем иметь текстовый файл с хешем MD5 каждого файла, когда вы сначала начнете загружаться, затем получите файл MD5 после завершения, затем проверьте, что хеши соответствуют загруженным фрагментам. Если они этого не сделают, удалите эту часть и добавьте ее в очередь загружаемых элементов.

Как только все куски загружены и MD5, вы можете поместить части обратно вместе как один файл.

Если вы хотите загрузить файл на SD-карту, тогда FAT32 является файловой системой по умолчанию. В этой файловой системе есть ограничение по 4 ГБ на файл.

Ответ 2

От взгляда на исходный код Android, похоже, эта проблема была решена в JB-MR2.

Кажется, что единственный способ обойти это на более старых версиях платформы - это изменить сервер таким образом, чтобы для этих больших ресурсов использовалась кодированная передача кодирования [1]. В этом случае Менеджер загрузки игнорирует и не пытается проанализировать заголовок Content-Length.

[1] http://en.wikipedia.org/wiki/Chunked_transfer_encoding

Ответ 3

Есть один явный результат:

Вы не можете исправить DownloadManager. Если это ошибка в нем, это будет так. Поэтому, короче говоря, No, вы не можете обойти эту проблему, используя DownloadManager. Однако вы могли бы обойти это, используя подход на стороне сервера, который был добавлен в слова в других ответах.

Итак, я думаю, что вашим самым простым решением было бы заставить минимальный уровень sdk для JB-MR2, потому что @ksasq упомянул, что эта проблема решена.

Если это не правдоподобно и в вашем случае возможно, вы можете найти лучшую библиотеку загрузки файлов и создать интерфейс, аналогичный DownloadManager для этой библиотеки. Конечно, этот интерфейс должен быть реализован для использования стандартного DownloadManager для версий, которые не имеют этой ошибки, и используют специальную библиотеку для тех, у кого была эта ошибка (и для файлов, которые могут вызвать проблему, если это возможно).

К сожалению, поиск в google показал yingyixu android-download-manager, последний раз обновленный в 2012 году.

Еще одна неудачная заметка об этой теме от CommonsWare просто проверяет, нет ли DownloadManager в библиотеках поддержки google. Хуже всего то, что парень отказался от идеи реализовать свой собственный порт, потому что это было слишком сложно. Вы можете только надеяться, что библиотека yingyixu или какая-то другая библиотека, которую вы, надеюсь, найдете, достаточно хороша.

Ответ 4

Вы можете передать эту проблему, разделив файл на более мелкие zip файлы. Следующий шаг - объединить их в цель, я нашел - > this < -, который может вам помочь. Если вы не будете сжимать файл (только для разделения), у вас должна быть хорошая производительность. Другая проблема заключается в том, что вам потребуется вдвое больше места для хранения. Вы можете загружать файлы меньшего размера, около 100 МБ, записывать их в объединенный буфер и удалять файловую систему формы, что позволит сэкономить пространство.

Ответ 5

Вы также можете взять фиксированную версию DownloadManager, изменить пакет на свою структуру пакета и использовать эту версию вместо версии системы, В конце концов вам нужно импортировать некоторые классы из исходного пакета android.app. Затем зарегистрируйте свою реализацию как службу.