http_network_transaction.h revision c407dc5cd9bdc5668497f21b26b09d988ab439de
1// Copyright (c) 2010 The Chromium Authors. All rights reserved. 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5#ifndef NET_HTTP_HTTP_NETWORK_TRANSACTION_H_ 6#define NET_HTTP_HTTP_NETWORK_TRANSACTION_H_ 7 8#include <string> 9 10#include "base/basictypes.h" 11#include "base/ref_counted.h" 12#include "base/scoped_ptr.h" 13#include "base/time.h" 14#include "net/base/address_list.h" 15#include "net/base/io_buffer.h" 16#include "net/base/load_flags.h" 17#include "net/base/load_states.h" 18#include "net/base/net_log.h" 19#include "net/base/ssl_config_service.h" 20#include "net/http/http_alternate_protocols.h" 21#include "net/http/http_auth.h" 22#include "net/http/http_auth_controller.h" 23#include "net/http/http_auth_handler.h" 24#include "net/http/http_response_info.h" 25#include "net/http/http_transaction.h" 26#include "net/proxy/proxy_service.h" 27#include "net/socket/client_socket_pool.h" 28#include "testing/gtest/include/gtest/gtest_prod.h" 29 30namespace net { 31 32class ClientSocketFactory; 33class ClientSocketHandle; 34class HttpNetworkSession; 35class HttpRequestHeaders; 36class HttpStream; 37class SpdyHttpStream; 38 39class HttpNetworkTransaction : public HttpTransaction { 40 public: 41 explicit HttpNetworkTransaction(HttpNetworkSession* session); 42 43 virtual ~HttpNetworkTransaction(); 44 45 static void SetHostMappingRules(const std::string& rules); 46 47 // Controls whether or not we use the Alternate-Protocol header. 48 static void SetUseAlternateProtocols(bool value); 49 50 // Sets the next protocol negotiation value used during the SSL handshake. 51 static void SetNextProtos(const std::string& next_protos); 52 53 // Sets the HttpNetworkTransaction into a mode where it can ignore 54 // certificate errors. This is for testing. 55 static void IgnoreCertificateErrors(bool enabled); 56 57 // HttpTransaction methods: 58 virtual int Start(const HttpRequestInfo* request_info, 59 CompletionCallback* callback, 60 const BoundNetLog& net_log); 61 virtual int RestartIgnoringLastError(CompletionCallback* callback); 62 virtual int RestartWithCertificate(X509Certificate* client_cert, 63 CompletionCallback* callback); 64 virtual int RestartWithAuth(const std::wstring& username, 65 const std::wstring& password, 66 CompletionCallback* callback); 67 virtual bool IsReadyToRestartForAuth() { 68 return pending_auth_target_ != HttpAuth::AUTH_NONE && 69 HaveAuth(pending_auth_target_); 70 } 71 72 virtual int Read(IOBuffer* buf, int buf_len, CompletionCallback* callback); 73 virtual void StopCaching() {} 74 virtual const HttpResponseInfo* GetResponseInfo() const; 75 virtual LoadState GetLoadState() const; 76 virtual uint64 GetUploadProgress() const; 77 78 private: 79 FRIEND_TEST(HttpNetworkTransactionTest, ResetStateForRestart); 80 81 enum State { 82 STATE_RESOLVE_PROXY, 83 STATE_RESOLVE_PROXY_COMPLETE, 84 STATE_INIT_CONNECTION, 85 STATE_INIT_CONNECTION_COMPLETE, 86 STATE_GENERATE_PROXY_AUTH_TOKEN, 87 STATE_GENERATE_PROXY_AUTH_TOKEN_COMPLETE, 88 STATE_GENERATE_SERVER_AUTH_TOKEN, 89 STATE_GENERATE_SERVER_AUTH_TOKEN_COMPLETE, 90 STATE_SEND_REQUEST, 91 STATE_SEND_REQUEST_COMPLETE, 92 STATE_READ_HEADERS, 93 STATE_READ_HEADERS_COMPLETE, 94 STATE_READ_BODY, 95 STATE_READ_BODY_COMPLETE, 96 STATE_DRAIN_BODY_FOR_AUTH_RESTART, 97 STATE_DRAIN_BODY_FOR_AUTH_RESTART_COMPLETE, 98 STATE_SPDY_GET_STREAM, 99 STATE_SPDY_GET_STREAM_COMPLETE, 100 STATE_SPDY_SEND_REQUEST, 101 STATE_SPDY_SEND_REQUEST_COMPLETE, 102 STATE_SPDY_READ_HEADERS, 103 STATE_SPDY_READ_HEADERS_COMPLETE, 104 STATE_SPDY_READ_BODY, 105 STATE_SPDY_READ_BODY_COMPLETE, 106 STATE_NONE 107 }; 108 109 enum AlternateProtocolMode { 110 kUnspecified, // Unspecified, check HttpAlternateProtocols 111 kUsingAlternateProtocol, // Using an alternate protocol 112 kDoNotUseAlternateProtocol, // Failed to connect once, do not try again. 113 }; 114 115 void DoCallback(int result); 116 void OnIOComplete(int result); 117 118 // Runs the state transition loop. 119 int DoLoop(int result); 120 121 // Each of these methods corresponds to a State value. Those with an input 122 // argument receive the result from the previous state. If a method returns 123 // ERR_IO_PENDING, then the result from OnIOComplete will be passed to the 124 // next state method as the result arg. 125 int DoResolveProxy(); 126 int DoResolveProxyComplete(int result); 127 int DoInitConnection(); 128 int DoInitConnectionComplete(int result); 129 int DoGenerateProxyAuthToken(); 130 int DoGenerateProxyAuthTokenComplete(int result); 131 int DoGenerateServerAuthToken(); 132 int DoGenerateServerAuthTokenComplete(int result); 133 int DoSendRequest(); 134 int DoSendRequestComplete(int result); 135 int DoReadHeaders(); 136 int DoReadHeadersComplete(int result); 137 int DoReadBody(); 138 int DoReadBodyComplete(int result); 139 int DoDrainBodyForAuthRestart(); 140 int DoDrainBodyForAuthRestartComplete(int result); 141 int DoSpdyGetStream(); 142 int DoSpdyGetStreamComplete(int result); 143 int DoSpdySendRequest(); 144 int DoSpdySendRequestComplete(int result); 145 int DoSpdyReadHeaders(); 146 int DoSpdyReadHeadersComplete(int result); 147 int DoSpdyReadBody(); 148 int DoSpdyReadBodyComplete(int result); 149 150 // Record histograms of latency until Connect() completes. 151 static void LogHttpConnectedMetrics(const ClientSocketHandle& handle); 152 153 // Record histogram of time until first byte of header is received. 154 void LogTransactionConnectedMetrics(); 155 156 // Record histogram of latency (durations until last byte received). 157 void LogTransactionMetrics() const; 158 159 // Writes a log message to help debugging in the field when we block a proxy 160 // response to a CONNECT request. 161 void LogBlockedTunnelResponse(int response_code) const; 162 163 static void LogIOErrorMetrics(const ClientSocketHandle& handle); 164 165 // Called to handle a certificate error. Returns OK if the error should be 166 // ignored. Otherwise, stores the certificate in response_.ssl_info and 167 // returns the same error code. 168 int HandleCertificateError(int error); 169 170 // Called to handle a client certificate request. 171 int HandleCertificateRequest(int error); 172 173 // Called to possibly recover from an SSL handshake error. Sets next_state_ 174 // and returns OK if recovering from the error. Otherwise, the same error 175 // code is returned. 176 int HandleSSLHandshakeError(int error); 177 178 // Called to possibly recover from the given error. Sets next_state_ and 179 // returns OK if recovering from the error. Otherwise, the same error code 180 // is returned. 181 int HandleIOError(int error); 182 183 // Gets the response headers from the HttpStream. 184 HttpResponseHeaders* GetResponseHeaders() const; 185 186 // Called when we reached EOF or got an error. Returns true if we should 187 // resend the request. |error| is OK when we reached EOF. 188 bool ShouldResendRequest(int error) const; 189 190 // Resets the connection and the request headers for resend. Called when 191 // ShouldResendRequest() is true. 192 void ResetConnectionAndRequestForResend(); 193 194 // Called when we encounter a network error that could be resolved by trying 195 // a new proxy configuration. If there is another proxy configuration to try 196 // then this method sets next_state_ appropriately and returns either OK or 197 // ERR_IO_PENDING depending on whether or not the new proxy configuration is 198 // available synchronously or asynchronously. Otherwise, the given error 199 // code is simply returned. 200 int ReconsiderProxyAfterError(int error); 201 202 // Decides the policy when the connection is closed before the end of headers 203 // has been read. This only applies to reading responses, and not writing 204 // requests. 205 int HandleConnectionClosedBeforeEndOfHeaders(); 206 207 // Sets up the state machine to restart the transaction with auth. 208 void PrepareForAuthRestart(HttpAuth::Target target); 209 210 // Called when we don't need to drain the response body or have drained it. 211 // Resets |connection_| unless |keep_alive| is true, then calls 212 // ResetStateForRestart. Sets |next_state_| appropriately. 213 void DidDrainBodyForAuthRestart(bool keep_alive); 214 215 // Resets the members of the transaction so it can be restarted. 216 void ResetStateForRestart(); 217 218 // Returns true if we should try to add a Proxy-Authorization header 219 bool ShouldApplyProxyAuth() const; 220 221 // Returns true if we should try to add an Authorization header. 222 bool ShouldApplyServerAuth() const; 223 224 // Handles HTTP status code 401 or 407. 225 // HandleAuthChallenge() returns a network error code, or OK on success. 226 // May update |pending_auth_target_| or |response_.auth_challenge|. 227 int HandleAuthChallenge(); 228 229 bool HaveAuth(HttpAuth::Target target) const { 230 return auth_controllers_[target].get() && 231 auth_controllers_[target]->HaveAuth(); 232 } 233 234 // Get the {scheme, host, path, port} for the authentication target 235 GURL AuthURL(HttpAuth::Target target) const; 236 237 void MarkBrokenAlternateProtocolAndFallback(); 238 239 // Debug helper. 240 static std::string DescribeState(State state); 241 242 static bool g_ignore_certificate_errors; 243 244 scoped_refptr<HttpAuthController> 245 auth_controllers_[HttpAuth::AUTH_NUM_TARGETS]; 246 247 // Whether this transaction is waiting for proxy auth, server auth, or is 248 // not waiting for any auth at all. |pending_auth_target_| is read and 249 // cleared by RestartWithAuth(). 250 HttpAuth::Target pending_auth_target_; 251 252 CompletionCallbackImpl<HttpNetworkTransaction> io_callback_; 253 CompletionCallback* user_callback_; 254 255 scoped_refptr<HttpNetworkSession> session_; 256 257 BoundNetLog net_log_; 258 const HttpRequestInfo* request_; 259 HttpResponseInfo response_; 260 261 ProxyService::PacRequest* pac_request_; 262 ProxyInfo proxy_info_; 263 264 scoped_ptr<ClientSocketHandle> connection_; 265 scoped_ptr<HttpStream> http_stream_; 266 scoped_ptr<SpdyHttpStream> spdy_http_stream_; 267 bool reused_socket_; 268 269 // True if we've validated the headers that the stream parser has returned. 270 bool headers_valid_; 271 272 // True if we've logged the time of the first response byte. Used to 273 // prevent logging across authentication activity where we see multiple 274 // responses. 275 bool logged_response_time_; 276 277 bool using_ssl_; // True if handling a HTTPS request 278 279 // True if this network transaction is using SPDY instead of HTTP. 280 bool using_spdy_; 281 282 // The certificate error while using SPDY over SSL for insecure URLs. 283 int spdy_certificate_error_; 284 285 AlternateProtocolMode alternate_protocol_mode_; 286 287 // Only valid if |alternate_protocol_mode_| == kUsingAlternateProtocol. 288 HttpAlternateProtocols::Protocol alternate_protocol_; 289 290 SSLConfig ssl_config_; 291 292 std::string request_headers_; 293 294 // The size in bytes of the buffer we use to drain the response body that 295 // we want to throw away. The response body is typically a small error 296 // page just a few hundred bytes long. 297 enum { kDrainBodyBufferSize = 1024 }; 298 299 // User buffer and length passed to the Read method. 300 scoped_refptr<IOBuffer> read_buf_; 301 int read_buf_len_; 302 303 // The time the Start method was called. 304 base::Time start_time_; 305 306 // The next state in the state machine. 307 State next_state_; 308 309 // The hostname and port of the endpoint. This is not necessarily the one 310 // specified by the URL, due to Alternate-Protocol or fixed testing ports. 311 HostPortPair endpoint_; 312 313 // True when the tunnel is in the process of being established - we can't 314 // read from the socket until the tunnel is done. 315 bool establishing_tunnel_; 316 317 DISALLOW_COPY_AND_ASSIGN(HttpNetworkTransaction); 318}; 319 320} // namespace net 321 322#endif // NET_HTTP_HTTP_NETWORK_TRANSACTION_H_ 323