I have a problem when i activate gzip on WS using retrofit 1.4.1 and okhttp 1.3.0.
RequestInterceptor requestInterceptor = new RequestInterceptor() {
After running into a similar issue (in my case, without adding any Accept-Encoding header, it would occasionally fail to un-gzip the response, leaving also the Content-Encoding: gzip header in it, crashing the JSON parser), and with no clear way around this, I manually enabled gzip for Retrofit by creating the delegated Client implementation below. It works great, except that you probably should not use it for very large (e.g. > 250KB) responses, as they are first copied into a byte array.
public class GzippedClient implements Client {
private Client wrappedClient;
public GzippedClient(Client wrappedClient) {
this.wrappedClient = wrappedClient;
}
@Override
public Response execute(Request request) throws IOException {
Response response = wrappedClient.execute(request);
boolean gzipped = false;
for (Header h : response.getHeaders()) {
if (h.getName() != null && h.getName().toLowerCase().equals("content-encoding") && h.getValue() != null && h.getValue().toLowerCase().equals("gzip")) {
gzipped = true;
break;
}
}
Response r = null;
if (gzipped) {
InputStream is = null;
ByteArrayOutputStream bos = null;
try {
is = new BufferedInputStream(new GZIPInputStream(response.getBody().in()));
bos = new ByteArrayOutputStream();
int b;
while ((b = is.read()) != -1) {
bos.write(b);
}
TypedByteArray body = new TypedByteArray(response.getBody().mimeType(), bos.toByteArray());
r = new Response(response.getUrl(), response.getStatus(), response.getReason(), response.getHeaders(), body);
} finally {
if (is != null) {
is.close();
}
if (bos != null) {
bos.close();
}
}
} else {
r = response;
}
return r;
}
}
You will also have to add an Accept-Encoding header to your requests, e.g. by using a RequestInterceptor
requestFacade.addHeader("Accept-Encoding", "gzip");
Finally, you have to wrap your existing Client into this new GzippedClient, like so:
restBuilder.setClient(new GzippedClient(new OkClient(okHttpClient)));
That's it. Now your data will be gzipped.
EDIT: It seems that in OkHttp version 1.5.1, a bug (https://github.com/square/okhttp/pull/632) seems to have been fixed related to the transparent gzipping which may (or may not) have been the source of my initial issue. If so, the occasional failure to un-gzip may no longer occur, though it happened rarely enough that I cannot confirm this yet. Either way, if you want to rely on your own, rather than the transparent adding/removing of headers and gzipping, then the solution described will work.