I am downloading a file using an OkHttp GET request:
import com.squareup.okhttp.OkHttpClient;
import com.squareup.okhttp.Request;
import com.squareup.okhttp.Response;
...
OkHttpClient okClient = new OkHttpClient();
Request request = Request.Builder().url(url).get();
Response response = okClient.newCall(request).execute();
I read from the response body and decorating it with a BufferedInputStream
, with a buffer size of 4096:
BufferedInputStream in = new BufferedInputStream(response.body().byteStream(), 4096);
However, when I try to read from the buffer, the first read returns 1179 bytes. After that, I am only able to read 2048 bytes at a time:
byte[] buffer = new byte[4096];
while (true) {
int bytesRead = in.read(buffer); //bytesRead is always 2048, except the first read
if (bytesRead == -1) break;
}
Several related questions:
InputStream
being paged to a size of 2048 bytes, instead of the value specified by the BufferedInputStream
wrapper?OkHttpClient
to read more than 2048 bytes from the buffer?What could be causing the first read to return 1179 bytes? Some sort of file header?
The HTTP header is 869 bytes for the response you are reading.
Why are reads from the InputStream being paged to a size of 2048 bytes, instead of the value specified by the BufferedInputStream wrapper?
You'd have to go digging in BufferedInputStream
to find out why it's not joining two pages together.
The InputStream
from OkHttp is handing 2048 chunks because it uses a pool of them to save allocations.
Is there a way to configure the OkHttpClient to read more than 2048 bytes from the buffer?
No.
Depending on what you are doing, you'll generally have a much better time using the BufferedSource
from response.body().source()
rather than using BufferedInputStream
. You can learn more about them on the Okio repo.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With