mobile/android/thirdparty/ch/boye/httpclientandroidlib/impl/conn/DefaultClientConnection.java

Wed, 31 Dec 2014 06:09:35 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Wed, 31 Dec 2014 06:09:35 +0100
changeset 0
6474c204b198
permissions
-rw-r--r--

Cloned upstream origin tor-browser at tor-browser-31.3.0esr-4.5-1-build1
revision ID fc1c9ff7c1b2defdbc039f12214767608f46423f for hacking purpose.

michael@0 1 /*
michael@0 2 * ====================================================================
michael@0 3 * Licensed to the Apache Software Foundation (ASF) under one
michael@0 4 * or more contributor license agreements. See the NOTICE file
michael@0 5 * distributed with this work for additional information
michael@0 6 * regarding copyright ownership. The ASF licenses this file
michael@0 7 * to you under the Apache License, Version 2.0 (the
michael@0 8 * "License"); you may not use this file except in compliance
michael@0 9 * with the License. You may obtain a copy of the License at
michael@0 10 *
michael@0 11 * http://www.apache.org/licenses/LICENSE-2.0
michael@0 12 *
michael@0 13 * Unless required by applicable law or agreed to in writing,
michael@0 14 * software distributed under the License is distributed on an
michael@0 15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
michael@0 16 * KIND, either express or implied. See the License for the
michael@0 17 * specific language governing permissions and limitations
michael@0 18 * under the License.
michael@0 19 * ====================================================================
michael@0 20 *
michael@0 21 * This software consists of voluntary contributions made by many
michael@0 22 * individuals on behalf of the Apache Software Foundation. For more
michael@0 23 * information on the Apache Software Foundation, please see
michael@0 24 * <http://www.apache.org/>.
michael@0 25 *
michael@0 26 */
michael@0 27
michael@0 28 package ch.boye.httpclientandroidlib.impl.conn;
michael@0 29
michael@0 30 import java.io.IOException;
michael@0 31 import java.net.Socket;
michael@0 32 import java.util.HashMap;
michael@0 33 import java.util.Map;
michael@0 34
michael@0 35 import ch.boye.httpclientandroidlib.annotation.NotThreadSafe;
michael@0 36
michael@0 37 import ch.boye.httpclientandroidlib.androidextra.HttpClientAndroidLog;
michael@0 38 /* LogFactory removed by HttpClient for Android script. */
michael@0 39 import ch.boye.httpclientandroidlib.Header;
michael@0 40 import ch.boye.httpclientandroidlib.HttpException;
michael@0 41 import ch.boye.httpclientandroidlib.HttpHost;
michael@0 42 import ch.boye.httpclientandroidlib.HttpRequest;
michael@0 43 import ch.boye.httpclientandroidlib.HttpResponse;
michael@0 44 import ch.boye.httpclientandroidlib.HttpResponseFactory;
michael@0 45 import ch.boye.httpclientandroidlib.params.HttpParams;
michael@0 46 import ch.boye.httpclientandroidlib.params.HttpProtocolParams;
michael@0 47 import ch.boye.httpclientandroidlib.protocol.HttpContext;
michael@0 48 import ch.boye.httpclientandroidlib.impl.SocketHttpClientConnection;
michael@0 49 import ch.boye.httpclientandroidlib.io.HttpMessageParser;
michael@0 50 import ch.boye.httpclientandroidlib.io.SessionInputBuffer;
michael@0 51 import ch.boye.httpclientandroidlib.io.SessionOutputBuffer;
michael@0 52
michael@0 53 import ch.boye.httpclientandroidlib.conn.OperatedClientConnection;
michael@0 54
michael@0 55 /**
michael@0 56 * Default implementation of an operated client connection.
michael@0 57 * <p>
michael@0 58 * The following parameters can be used to customize the behavior of this
michael@0 59 * class:
michael@0 60 * <ul>
michael@0 61 * <li>{@link ch.boye.httpclientandroidlib.params.CoreProtocolPNames#STRICT_TRANSFER_ENCODING}</li>
michael@0 62 * <li>{@link ch.boye.httpclientandroidlib.params.CoreProtocolPNames#HTTP_ELEMENT_CHARSET}</li>
michael@0 63 * <li>{@link ch.boye.httpclientandroidlib.params.CoreConnectionPNames#SOCKET_BUFFER_SIZE}</li>
michael@0 64 * <li>{@link ch.boye.httpclientandroidlib.params.CoreConnectionPNames#MAX_LINE_LENGTH}</li>
michael@0 65 * <li>{@link ch.boye.httpclientandroidlib.params.CoreConnectionPNames#MAX_HEADER_COUNT}</li>
michael@0 66 * </ul>
michael@0 67 *
michael@0 68 * @since 4.0
michael@0 69 */
michael@0 70 @NotThreadSafe // connSecure, targetHost
michael@0 71 public class DefaultClientConnection extends SocketHttpClientConnection
michael@0 72 implements OperatedClientConnection, HttpContext {
michael@0 73
michael@0 74 public HttpClientAndroidLog log = new HttpClientAndroidLog(getClass());
michael@0 75 public HttpClientAndroidLog headerLog = new HttpClientAndroidLog("ch.boye.httpclientandroidlib.headers");
michael@0 76 public HttpClientAndroidLog wireLog = new HttpClientAndroidLog("ch.boye.httpclientandroidlib.wire");
michael@0 77
michael@0 78 /** The unconnected socket */
michael@0 79 private volatile Socket socket;
michael@0 80
michael@0 81 /** The target host of this connection. */
michael@0 82 private HttpHost targetHost;
michael@0 83
michael@0 84 /** Whether this connection is secure. */
michael@0 85 private boolean connSecure;
michael@0 86
michael@0 87 /** True if this connection was shutdown. */
michael@0 88 private volatile boolean shutdown;
michael@0 89
michael@0 90 /** connection specific attributes */
michael@0 91 private final Map<String, Object> attributes;
michael@0 92
michael@0 93 public DefaultClientConnection() {
michael@0 94 super();
michael@0 95 this.attributes = new HashMap<String, Object>();
michael@0 96 }
michael@0 97
michael@0 98 public final HttpHost getTargetHost() {
michael@0 99 return this.targetHost;
michael@0 100 }
michael@0 101
michael@0 102 public final boolean isSecure() {
michael@0 103 return this.connSecure;
michael@0 104 }
michael@0 105
michael@0 106 @Override
michael@0 107 public final Socket getSocket() {
michael@0 108 return this.socket;
michael@0 109 }
michael@0 110
michael@0 111 public void opening(Socket sock, HttpHost target) throws IOException {
michael@0 112 assertNotOpen();
michael@0 113 this.socket = sock;
michael@0 114 this.targetHost = target;
michael@0 115
michael@0 116 // Check for shutdown after assigning socket, so that
michael@0 117 if (this.shutdown) {
michael@0 118 sock.close(); // allow this to throw...
michael@0 119 // ...but if it doesn't, explicitly throw one ourselves.
michael@0 120 throw new IOException("Connection already shutdown");
michael@0 121 }
michael@0 122 }
michael@0 123
michael@0 124 public void openCompleted(boolean secure, HttpParams params) throws IOException {
michael@0 125 assertNotOpen();
michael@0 126 if (params == null) {
michael@0 127 throw new IllegalArgumentException
michael@0 128 ("Parameters must not be null.");
michael@0 129 }
michael@0 130 this.connSecure = secure;
michael@0 131 bind(this.socket, params);
michael@0 132 }
michael@0 133
michael@0 134 /**
michael@0 135 * Force-closes this connection.
michael@0 136 * If the connection is still in the process of being open (the method
michael@0 137 * {@link #opening opening} was already called but
michael@0 138 * {@link #openCompleted openCompleted} was not), the associated
michael@0 139 * socket that is being connected to a remote address will be closed.
michael@0 140 * That will interrupt a thread that is blocked on connecting
michael@0 141 * the socket.
michael@0 142 * If the connection is not yet open, this will prevent the connection
michael@0 143 * from being opened.
michael@0 144 *
michael@0 145 * @throws IOException in case of a problem
michael@0 146 */
michael@0 147 @Override
michael@0 148 public void shutdown() throws IOException {
michael@0 149 shutdown = true;
michael@0 150 try {
michael@0 151 super.shutdown();
michael@0 152 log.debug("Connection shut down");
michael@0 153 Socket sock = this.socket; // copy volatile attribute
michael@0 154 if (sock != null)
michael@0 155 sock.close();
michael@0 156 } catch (IOException ex) {
michael@0 157 log.debug("I/O error shutting down connection", ex);
michael@0 158 }
michael@0 159 }
michael@0 160
michael@0 161 @Override
michael@0 162 public void close() throws IOException {
michael@0 163 try {
michael@0 164 super.close();
michael@0 165 log.debug("Connection closed");
michael@0 166 } catch (IOException ex) {
michael@0 167 log.debug("I/O error closing connection", ex);
michael@0 168 }
michael@0 169 }
michael@0 170
michael@0 171 @Override
michael@0 172 protected SessionInputBuffer createSessionInputBuffer(
michael@0 173 final Socket socket,
michael@0 174 int buffersize,
michael@0 175 final HttpParams params) throws IOException {
michael@0 176 if (buffersize == -1) {
michael@0 177 buffersize = 8192;
michael@0 178 }
michael@0 179 SessionInputBuffer inbuffer = super.createSessionInputBuffer(
michael@0 180 socket,
michael@0 181 buffersize,
michael@0 182 params);
michael@0 183 if (wireLog.isDebugEnabled()) {
michael@0 184 inbuffer = new LoggingSessionInputBuffer(
michael@0 185 inbuffer,
michael@0 186 new Wire(wireLog),
michael@0 187 HttpProtocolParams.getHttpElementCharset(params));
michael@0 188 }
michael@0 189 return inbuffer;
michael@0 190 }
michael@0 191
michael@0 192 @Override
michael@0 193 protected SessionOutputBuffer createSessionOutputBuffer(
michael@0 194 final Socket socket,
michael@0 195 int buffersize,
michael@0 196 final HttpParams params) throws IOException {
michael@0 197 if (buffersize == -1) {
michael@0 198 buffersize = 8192;
michael@0 199 }
michael@0 200 SessionOutputBuffer outbuffer = super.createSessionOutputBuffer(
michael@0 201 socket,
michael@0 202 buffersize,
michael@0 203 params);
michael@0 204 if (wireLog.isDebugEnabled()) {
michael@0 205 outbuffer = new LoggingSessionOutputBuffer(
michael@0 206 outbuffer,
michael@0 207 new Wire(wireLog),
michael@0 208 HttpProtocolParams.getHttpElementCharset(params));
michael@0 209 }
michael@0 210 return outbuffer;
michael@0 211 }
michael@0 212
michael@0 213 @Override
michael@0 214 protected HttpMessageParser createResponseParser(
michael@0 215 final SessionInputBuffer buffer,
michael@0 216 final HttpResponseFactory responseFactory,
michael@0 217 final HttpParams params) {
michael@0 218 // override in derived class to specify a line parser
michael@0 219 return new DefaultResponseParser
michael@0 220 (buffer, null, responseFactory, params);
michael@0 221 }
michael@0 222
michael@0 223 public void update(Socket sock, HttpHost target,
michael@0 224 boolean secure, HttpParams params)
michael@0 225 throws IOException {
michael@0 226
michael@0 227 assertOpen();
michael@0 228 if (target == null) {
michael@0 229 throw new IllegalArgumentException
michael@0 230 ("Target host must not be null.");
michael@0 231 }
michael@0 232 if (params == null) {
michael@0 233 throw new IllegalArgumentException
michael@0 234 ("Parameters must not be null.");
michael@0 235 }
michael@0 236
michael@0 237 if (sock != null) {
michael@0 238 this.socket = sock;
michael@0 239 bind(sock, params);
michael@0 240 }
michael@0 241 targetHost = target;
michael@0 242 connSecure = secure;
michael@0 243 }
michael@0 244
michael@0 245 @Override
michael@0 246 public HttpResponse receiveResponseHeader() throws HttpException, IOException {
michael@0 247 HttpResponse response = super.receiveResponseHeader();
michael@0 248 if (log.isDebugEnabled()) {
michael@0 249 log.debug("Receiving response: " + response.getStatusLine());
michael@0 250 }
michael@0 251 if (headerLog.isDebugEnabled()) {
michael@0 252 headerLog.debug("<< " + response.getStatusLine().toString());
michael@0 253 Header[] headers = response.getAllHeaders();
michael@0 254 for (Header header : headers) {
michael@0 255 headerLog.debug("<< " + header.toString());
michael@0 256 }
michael@0 257 }
michael@0 258 return response;
michael@0 259 }
michael@0 260
michael@0 261 @Override
michael@0 262 public void sendRequestHeader(HttpRequest request) throws HttpException, IOException {
michael@0 263 if (log.isDebugEnabled()) {
michael@0 264 log.debug("Sending request: " + request.getRequestLine());
michael@0 265 }
michael@0 266 super.sendRequestHeader(request);
michael@0 267 if (headerLog.isDebugEnabled()) {
michael@0 268 headerLog.debug(">> " + request.getRequestLine().toString());
michael@0 269 Header[] headers = request.getAllHeaders();
michael@0 270 for (Header header : headers) {
michael@0 271 headerLog.debug(">> " + header.toString());
michael@0 272 }
michael@0 273 }
michael@0 274 }
michael@0 275
michael@0 276 public Object getAttribute(final String id) {
michael@0 277 return this.attributes.get(id);
michael@0 278 }
michael@0 279
michael@0 280 public Object removeAttribute(final String id) {
michael@0 281 return this.attributes.remove(id);
michael@0 282 }
michael@0 283
michael@0 284 public void setAttribute(final String id, final Object obj) {
michael@0 285 this.attributes.put(id, obj);
michael@0 286 }
michael@0 287
michael@0 288 }

mercurial