com.google.api.client.http.HttpResponse Maven / Gradle / Ivy
Show all versions of google-api-client Show documentation
/*
* Copyright (c) 2010 Google Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except
* in compliance with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software distributed under the License
* is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
* or implied. See the License for the specific language governing permissions and limitations under
* the License.
*/
package com.google.api.client.http;
import com.google.api.client.util.ClassInfo;
import com.google.api.client.util.FieldInfo;
import com.google.api.client.util.Strings;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.logging.Level;
import java.util.logging.Logger;
import java.util.zip.GZIPInputStream;
/**
* HTTP response.
*
* @since 1.0
* @author Yaniv Inbar
*/
public final class HttpResponse {
/** HTTP response content or {@code null} before {@link #getContent()}. */
private InputStream content;
/** Content encoding or {@code null}. */
public final String contentEncoding;
/**
* Content length or less than zero if not known. May be reset by {@link #getContent()} if
* response had GZip compression.
*/
private long contentLength;
/** Content type or {@code null} for none. */
public final String contentType;
/**
* HTTP headers.
*
* If a header name is used for multiple headers, only the last one is retained.
*
* This field's value is instantiated using the same class as that of the
* {@link HttpTransport#defaultHeaders}.
*/
public final HttpHeaders headers;
/** Whether received a successful status code {@code >= 200 && < 300}. */
public final boolean isSuccessStatusCode;
/** Low-level HTTP response. */
private LowLevelHttpResponse response;
/** Status code. */
public final int statusCode;
/** Status message or {@code null}. */
public final String statusMessage;
/** HTTP transport. */
public final HttpTransport transport;
/**
* Whether to disable response content logging during {@link #getContent()} (unless
* {@link Level#ALL} is loggable which forces all logging).
*
* Useful for example if content has sensitive data such as an authentication token. Defaults to
* {@code false}.
*/
public boolean disableContentLogging;
@SuppressWarnings("unchecked")
HttpResponse(HttpTransport transport, LowLevelHttpResponse response) {
this.transport = transport;
this.response = response;
contentLength = response.getContentLength();
contentType = response.getContentType();
contentEncoding = response.getContentEncoding();
int code = response.getStatusCode();
statusCode = code;
isSuccessStatusCode = isSuccessStatusCode(code);
String message = response.getReasonPhrase();
statusMessage = message;
Logger logger = HttpTransport.LOGGER;
boolean loggable = logger.isLoggable(Level.CONFIG);
StringBuilder logbuf = null;
if (loggable) {
logbuf = new StringBuilder();
logbuf.append("-------------- RESPONSE --------------").append(Strings.LINE_SEPARATOR);
String statusLine = response.getStatusLine();
if (statusLine != null) {
logbuf.append(statusLine);
} else {
logbuf.append(code);
if (message != null) {
logbuf.append(' ').append(message);
}
}
logbuf.append(Strings.LINE_SEPARATOR);
}
// headers
int size = response.getHeaderCount();
Class extends HttpHeaders> headersClass = transport.defaultHeaders.getClass();
ClassInfo classInfo = ClassInfo.of(headersClass);
HttpHeaders headers = this.headers = ClassInfo.newInstance(headersClass);
HashMap fieldNameMap = HttpHeaders.getFieldNameMap(headersClass);
for (int i = 0; i < size; i++) {
String headerName = response.getHeaderName(i);
String headerValue = response.getHeaderValue(i);
if (loggable) {
logbuf.append(headerName + ": " + headerValue).append(Strings.LINE_SEPARATOR);
}
String fieldName = fieldNameMap.get(headerName);
if (fieldName == null) {
fieldName = headerName;
}
// use field information if available
FieldInfo fieldInfo = classInfo.getFieldInfo(fieldName);
if (fieldInfo != null) {
Class> type = fieldInfo.type;
// collection is used for repeating headers of the same name
if (Collection.class.isAssignableFrom(type)) {
Collection