blob: e71c3f93baa92d1911606adddd276711306b4070 [file] [log] [blame]
asanka5ffd5d72016-03-23 16:20:491// Copyright (c) 2012 The Chromium Authors. All rights reserved.
[email protected]228404f2010-06-24 04:31:412// 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_AUTH_CONTROLLER_H_
6#define NET_HTTP_HTTP_AUTH_CONTROLLER_H_
7
danakj1fd259a02016-04-16 03:17:098#include <memory>
[email protected]cee63122010-07-20 04:43:319#include <set>
[email protected]228404f2010-06-24 04:31:4110#include <string>
11
[email protected]3b63f8f42011-03-28 01:54:1512#include "base/memory/ref_counted.h"
gab47aa7da2017-06-02 16:09:4313#include "base/threading/thread_checker.h"
Bence Béky7236fb72018-08-01 14:35:0914#include "net/base/completion_once_callback.h"
[email protected]172da1b2011-08-12 15:52:2615#include "net/base/net_export.h"
[email protected]228404f2010-06-24 04:31:4116#include "net/http/http_auth.h"
[email protected]f89276a72013-07-12 06:41:5417#include "url/gurl.h"
[email protected]228404f2010-06-24 04:31:4118
19namespace net {
20
21class AuthChallengeInfo;
[email protected]f3cf9802011-10-28 18:44:5822class AuthCredentials;
[email protected]560c0432010-07-13 20:45:3123class HttpAuthHandler;
[email protected]3598c6022010-09-17 23:13:0924class HttpAuthHandlerFactory;
25class HttpAuthCache;
[email protected]228404f2010-06-24 04:31:4126class HttpRequestHeaders;
Eric Orthbe2efac2019-03-06 01:11:1127class HostResolver;
mikecironef22f9812016-10-04 03:40:1928class NetLogWithSource;
[email protected]228404f2010-06-24 04:31:4129struct HttpRequestInfo;
asanka5ffd5d72016-03-23 16:20:4930class SSLInfo;
[email protected]228404f2010-06-24 04:31:4131
Matt Menke84586d82017-09-28 19:39:2832// HttpAuthController is interface between other classes and HttpAuthHandlers.
33// It handles all challenges when attempting to make a single request to a
34// server, both in the case of trying multiple sets of credentials (Possibly on
35// different sockets), and when going through multiple rounds of auth with
36// connection-based auth, creating new HttpAuthHandlers as necessary.
37//
38// It is unaware of when a round of auth uses a new socket, which can lead to
39// problems for connection-based auth.
[email protected]172da1b2011-08-12 15:52:2640class NET_EXPORT_PRIVATE HttpAuthController
gab47aa7da2017-06-02 16:09:4341 : public base::RefCounted<HttpAuthController> {
[email protected]228404f2010-06-24 04:31:4142 public:
43 // The arguments are self explanatory except possibly for |auth_url|, which
44 // should be both the auth target and auth path in a single url argument.
Matt Menke84586d82017-09-28 19:39:2845 // |target| indicates whether this is for authenticating with a proxy or
46 // destination server.
[email protected]3598c6022010-09-17 23:13:0947 HttpAuthController(HttpAuth::Target target,
48 const GURL& auth_url,
49 HttpAuthCache* http_auth_cache,
Eric Orthbe2efac2019-03-06 01:11:1150 HttpAuthHandlerFactory* http_auth_handler_factory,
51 HostResolver* host_resolver);
[email protected]228404f2010-06-24 04:31:4152
53 // Generate an authentication token for |target| if necessary. The return
54 // value is a net error code. |OK| will be returned both in the case that
55 // a token is correctly generated synchronously, as well as when no tokens
56 // were necessary.
asanka5e8286c32017-02-23 16:13:4257 int MaybeGenerateAuthToken(const HttpRequestInfo* request,
Bence Béky7236fb72018-08-01 14:35:0958 CompletionOnceCallback callback,
asanka5e8286c32017-02-23 16:13:4259 const NetLogWithSource& net_log);
[email protected]228404f2010-06-24 04:31:4160
61 // Adds either the proxy auth header, or the origin server auth header,
62 // as specified by |target_|.
asanka5e8286c32017-02-23 16:13:4263 void AddAuthorizationHeader(HttpRequestHeaders* authorization_headers);
[email protected]228404f2010-06-24 04:31:4164
65 // Checks for and handles HTTP status code 401 or 407.
[email protected]65d34382010-07-01 18:12:2666 // |HandleAuthChallenge()| returns OK on success, or a network error code
67 // otherwise. It may also populate |auth_info_|.
asanka5e8286c32017-02-23 16:13:4268 int HandleAuthChallenge(scoped_refptr<HttpResponseHeaders> headers,
69 const SSLInfo& ssl_info,
70 bool do_not_send_server_auth,
71 bool establishing_tunnel,
72 const NetLogWithSource& net_log);
[email protected]228404f2010-06-24 04:31:4173
[email protected]228404f2010-06-24 04:31:4174 // Store the supplied credentials and prepare to restart the auth.
asanka5e8286c32017-02-23 16:13:4275 void ResetAuth(const AuthCredentials& credentials);
[email protected]228404f2010-06-24 04:31:4176
asanka5e8286c32017-02-23 16:13:4277 bool HaveAuthHandler() const;
[email protected]228404f2010-06-24 04:31:4178
asanka5e8286c32017-02-23 16:13:4279 bool HaveAuth() const;
[email protected]228404f2010-06-24 04:31:4180
Bence Béky3238f2e12017-09-22 22:44:4981 // Return whether the authentication scheme is incompatible with HTTP/2
82 // and thus the server would presumably reject a request on HTTP/2 anyway.
83 bool NeedsHTTP11() const;
84
asanka5e8286c32017-02-23 16:13:4285 scoped_refptr<AuthChallengeInfo> auth_info();
[email protected]228404f2010-06-24 04:31:4186
asanka5e8286c32017-02-23 16:13:4287 bool IsAuthSchemeDisabled(HttpAuth::Scheme scheme) const;
88 void DisableAuthScheme(HttpAuth::Scheme scheme);
89 void DisableEmbeddedIdentity();
[email protected]cee63122010-07-20 04:43:3190
davidben8c7089a2017-04-17 20:38:2291 // Called when the connection has been closed, so the current handler (which
92 // contains state bound to the connection) should be dropped. If retrying on a
93 // new connection, the next call to MaybeGenerateAuthToken will retry the
94 // current auth scheme.
95 void OnConnectionClosed();
96
[email protected]3598c6022010-09-17 23:13:0997 private:
[email protected]463f8352011-02-18 14:26:5598 // Actions for InvalidateCurrentHandler()
99 enum InvalidateHandlerAction {
100 INVALIDATE_HANDLER_AND_CACHED_CREDENTIALS,
[email protected]26d84b02011-08-31 14:07:08101 INVALIDATE_HANDLER_AND_DISABLE_SCHEME,
[email protected]463f8352011-02-18 14:26:55102 INVALIDATE_HANDLER
103 };
104
[email protected]3598c6022010-09-17 23:13:09105 // So that we can mock this object.
[email protected]e772db3f2010-07-12 18:11:13106 friend class base::RefCounted<HttpAuthController>;
[email protected]3598c6022010-09-17 23:13:09107
David Benjamin5af27d42018-08-24 17:07:36108 ~HttpAuthController();
[email protected]e772db3f2010-07-12 18:11:13109
[email protected]228404f2010-06-24 04:31:41110 // Searches the auth cache for an entry that encompasses the request's path.
111 // If such an entry is found, updates |identity_| and |handler_| with the
112 // cache entry's data and returns true.
tfarina42834112016-09-22 13:38:20113 bool SelectPreemptiveAuth(const NetLogWithSource& net_log);
[email protected]228404f2010-06-24 04:31:41114
[email protected]cd0efd22011-02-24 15:25:55115 // Invalidates the current handler. If |action| is
116 // INVALIDATE_HANDLER_AND_CACHED_CREDENTIALS, then also invalidate
117 // the cached credentials used by the handler.
[email protected]463f8352011-02-18 14:26:55118 void InvalidateCurrentHandler(InvalidateHandlerAction action);
[email protected]eca50e122010-09-11 14:03:30119
[email protected]228404f2010-06-24 04:31:41120 // Invalidates any auth cache entries after authentication has failed.
121 // The identity that was rejected is |identity_|.
122 void InvalidateRejectedAuthFromCache();
123
Asanka Herathbc3f8f62018-11-16 23:08:30124 // Allows reusing last used identity source. If the authentication handshake
125 // breaks down halfway, then the controller needs to restart it from the
126 // beginning and resue the same identity.
127 void PrepareIdentityForReuse();
128
[email protected]228404f2010-06-24 04:31:41129 // Sets |identity_| to the next identity that the transaction should try. It
130 // chooses candidates by searching the auth cache and the URL for a
131 // username:password. Returns true if an identity was found.
132 bool SelectNextAuthIdentityToTry();
133
134 // Populates auth_info_ with the challenge information, so that
[email protected]f3cf9802011-10-28 18:44:58135 // URLRequestHttpJob can prompt for credentials.
[email protected]228404f2010-06-24 04:31:41136 void PopulateAuthChallenge();
137
asankae2257db2016-10-11 22:03:16138 // Handle the result of calling GenerateAuthToken on an HttpAuthHandler. The
139 // return value of this function should be used as the return value of the
140 // GenerateAuthToken operation.
141 int HandleGenerateTokenResult(int result);
[email protected]76b0f682011-03-30 16:54:54142
asanka463ca4262016-11-16 02:34:31143 void OnGenerateAuthTokenDone(int result);
[email protected]cee63122010-07-20 04:43:31144
[email protected]228404f2010-06-24 04:31:41145 // Indicates if this handler is for Proxy auth or Server auth.
146 HttpAuth::Target target_;
147
148 // Holds the {scheme, host, path, port} for the authentication target.
149 const GURL auth_url_;
150
151 // Holds the {scheme, host, port} for the authentication target.
152 const GURL auth_origin_;
153
154 // The absolute path of the resource needing authentication.
155 // For proxy authentication the path is empty.
156 const std::string auth_path_;
157
158 // |handler_| encapsulates the logic for the particular auth-scheme.
159 // This includes the challenge's parameters. If NULL, then there is no
160 // associated auth handler.
danakj1fd259a02016-04-16 03:17:09161 std::unique_ptr<HttpAuthHandler> handler_;
[email protected]228404f2010-06-24 04:31:41162
[email protected]f3cf9802011-10-28 18:44:58163 // |identity_| holds the credentials that should be used by
164 // the handler_ to generate challenge responses. This identity can come from
[email protected]228404f2010-06-24 04:31:41165 // a number of places (url, cache, prompt).
166 HttpAuth::Identity identity_;
167
168 // |auth_token_| contains the opaque string to pass to the proxy or
169 // server to authenticate the client.
170 std::string auth_token_;
171
172 // Contains information about the auth challenge.
173 scoped_refptr<AuthChallengeInfo> auth_info_;
174
[email protected]f3cf9802011-10-28 18:44:58175 // True if we've used the username:password embedded in the URL. This
[email protected]228404f2010-06-24 04:31:41176 // makes sure we use the embedded identity only once for the transaction,
177 // preventing an infinite auth restart loop.
178 bool embedded_identity_used_;
179
180 // True if default credentials have already been tried for this transaction
181 // in response to an HTTP authentication challenge.
182 bool default_credentials_used_;
183
[email protected]3598c6022010-09-17 23:13:09184 // These two are owned by the HttpNetworkSession/IOThread, which own the
185 // objects which reference |this|. Therefore, these raw pointers are valid
186 // for the lifetime of this object.
187 HttpAuthCache* const http_auth_cache_;
188 HttpAuthHandlerFactory* const http_auth_handler_factory_;
Eric Orthbe2efac2019-03-06 01:11:11189 HostResolver* const host_resolver_;
[email protected]cee63122010-07-20 04:43:31190
[email protected]547fc792011-01-13 13:31:17191 std::set<HttpAuth::Scheme> disabled_schemes_;
[email protected]cee63122010-07-20 04:43:31192
Bence Béky7236fb72018-08-01 14:35:09193 CompletionOnceCallback callback_;
gab47aa7da2017-06-02 16:09:43194
195 THREAD_CHECKER(thread_checker_);
[email protected]228404f2010-06-24 04:31:41196};
197
198} // namespace net
199
200#endif // NET_HTTP_HTTP_AUTH_CONTROLLER_H_