Отправить большие данные OkHttp3 вне памяти - PullRequest
0 голосов
/ 04 января 2019

Я хочу отправить изображение PDF на сервер в Android.

Для спецификации сервера мне нужно использовать кодировку Base64.

Поэтому я должен преобразовать файл изображения PDF в строку Base64.

Ниже приведен HTTP-запрос POST:

<?xml version="1.0" encoding="UTF-8"?>
<request>
    <auth>
        <!-- auth info -->
    </auth>
    <imagefile>
        <filename>Test Attachment</filename>
        <type>pdf</type>
        <data>"HERE IS BASE64 String"</data>
    </imagefile>
</request>

И я использовал приведенный ниже код, это просто Http-код запроса поста.

fun post(url: String, xml: String) = Observable.defer {
    val request = Request.Builder()
            .url(url)
            .post(RequestBody.create(contentType, xml))
            .build()

    okHttpClient.newCall(request).execute()
}

В случае малогоPDF-файл, все в порядке.(Работает нормально)

Но когда я использовал большой файл PDF (более 20 МБ), возникает нехватка памяти.

Поэтому я попробовал другой способ, подобный приведенному ниже.

fun post(url: String, xmlFile: File) = Observable.defer {
    val request = Request.Builder()
            .url(url)
            .post(RequestBody.create(contentType, xmlFile))
            .build()

    okHttpClient.newCall(request).execute()
}

Разница в том, что я не использую String, а File.

Я создал файл, используя закодированный в Base64 текст с синтаксисом XML.

Но это тоже не удалось.

Как отправить большие данные в Android без OOM?

1 Ответ

0 голосов
/ 05 января 2019

Вам понадобится найти потоковый кодировщик base64 и использовать его для записи RequestBody, который транслируется на сервер.Нет такого кодера, встроенного в OkHttp или Okio, но вы можете использовать тот в самом Android.Используйте перенос для OutputStream, который вы получите в методе writeTo своего пользовательского RequestBody.

https://developer.android.com/reference/java/util/Base64.Encoder

...