| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #ifndef CHROME_BROWSER_CUSTOM_HANDLERS_PROTOCOL_HANDLER_REGISTRY_H_ | 5 #ifndef CHROME_BROWSER_CUSTOM_HANDLERS_PROTOCOL_HANDLER_REGISTRY_H_ |
| 6 #define CHROME_BROWSER_CUSTOM_HANDLERS_PROTOCOL_HANDLER_REGISTRY_H_ | 6 #define CHROME_BROWSER_CUSTOM_HANDLERS_PROTOCOL_HANDLER_REGISTRY_H_ |
| 7 | 7 |
| 8 #include <map> | 8 #include <map> |
| 9 #include <string> | 9 #include <string> |
| 10 #include <vector> | 10 #include <vector> |
| 11 | 11 |
| 12 #include "base/basictypes.h" | 12 #include "base/basictypes.h" |
| 13 #include "base/memory/ref_counted.h" | 13 #include "base/memory/ref_counted.h" |
| 14 #include "base/sequenced_task_runner_helpers.h" | 14 #include "base/sequenced_task_runner_helpers.h" |
| 15 #include "base/values.h" | 15 #include "base/values.h" |
| 16 #include "chrome/browser/profiles/profile.h" | 16 #include "chrome/browser/profiles/profile.h" |
| 17 #include "chrome/browser/shell_integration.h" | 17 #include "chrome/browser/shell_integration.h" |
| 18 #include "chrome/common/custom_handlers/protocol_handler.h" | 18 #include "chrome/common/custom_handlers/protocol_handler.h" |
| 19 #include "content/public/browser/browser_thread.h" | 19 #include "content/public/browser/browser_thread.h" |
| 20 #include "content/public/browser/notification_service.h" | 20 #include "content/public/browser/notification_service.h" |
| 21 #include "net/url_request/url_request.h" | 21 #include "net/url_request/url_request.h" |
| 22 #include "net/url_request/url_request_job.h" | 22 #include "net/url_request/url_request_job.h" |
| 23 #include "net/url_request/url_request_job_factory.h" |
| 23 | 24 |
| 24 // This is where handlers for protocols registered with | 25 // This is where handlers for protocols registered with |
| 25 // navigator.registerProtocolHandler() are registered. Each Profile owns an | 26 // navigator.registerProtocolHandler() are registered. Each Profile owns an |
| 26 // instance of this class, which is initialized on browser start through | 27 // instance of this class, which is initialized on browser start through |
| 27 // Profile::InitRegisteredProtocolHandlers(), and they should be the only | 28 // Profile::InitRegisteredProtocolHandlers(), and they should be the only |
| 28 // instances of this class. | 29 // instances of this class. |
| 30 class ProtocolHandlerRegistry : public ProfileKeyedService { |
| 29 | 31 |
| 30 class ProtocolHandlerRegistry | |
| 31 : public base::RefCountedThreadSafe< | |
| 32 ProtocolHandlerRegistry, content::BrowserThread::DeleteOnIOThread> { | |
| 33 public: | 32 public: |
| 33 // Provides notification of when the OS level user agent settings |
| 34 // are changed. |
| 34 class DefaultClientObserver | 35 class DefaultClientObserver |
| 35 : public ShellIntegration::DefaultWebClientObserver { | 36 : public ShellIntegration::DefaultWebClientObserver { |
| 36 public: | 37 public: |
| 37 explicit DefaultClientObserver(ProtocolHandlerRegistry* registry); | 38 explicit DefaultClientObserver(ProtocolHandlerRegistry* registry); |
| 38 virtual ~DefaultClientObserver(); | 39 virtual ~DefaultClientObserver(); |
| 39 | 40 |
| 40 // Get response from the worker regarding whether Chrome is the default | 41 // Get response from the worker regarding whether Chrome is the default |
| 41 // handler for the protocol. | 42 // handler for the protocol. |
| 42 virtual void SetDefaultWebClientUIState( | 43 virtual void SetDefaultWebClientUIState( |
| 43 ShellIntegration::DefaultWebClientUIState state) OVERRIDE; | 44 ShellIntegration::DefaultWebClientUIState state) OVERRIDE; |
| 44 | 45 |
| 45 // Give the observer a handle to the worker, so we can find out the protocol | 46 // Give the observer a handle to the worker, so we can find out the protocol |
| 46 // when we're called and also tell the worker if we get deleted. | 47 // when we're called and also tell the worker if we get deleted. |
| 47 void SetWorker(ShellIntegration::DefaultProtocolClientWorker* worker); | 48 void SetWorker(ShellIntegration::DefaultProtocolClientWorker* worker); |
| 48 | 49 |
| 49 protected: | 50 protected: |
| 50 ShellIntegration::DefaultProtocolClientWorker* worker_; | 51 ShellIntegration::DefaultProtocolClientWorker* worker_; |
| 51 | 52 |
| 52 private: | 53 private: |
| 53 virtual bool IsOwnedByWorker() OVERRIDE { return true; } | 54 virtual bool IsOwnedByWorker() OVERRIDE { return true; } |
| 54 // This is a raw pointer, not reference counted, intentionally. In general | 55 // This is a raw pointer, not reference counted, intentionally. In general |
| 55 // subclasses of DefaultWebClientObserver are not able to be refcounted | 56 // subclasses of DefaultWebClientObserver are not able to be refcounted |
| 56 // e.g. the browser options page | 57 // e.g. the browser options page |
| 57 ProtocolHandlerRegistry* registry_; | 58 ProtocolHandlerRegistry* registry_; |
| 58 | 59 |
| 59 DISALLOW_COPY_AND_ASSIGN(DefaultClientObserver); | 60 DISALLOW_COPY_AND_ASSIGN(DefaultClientObserver); |
| 60 }; | 61 }; |
| 61 | 62 |
| 62 // TODO(koz): Refactor this to eliminate the unnecessary virtuals. All that | 63 // |Delegate| provides an interface for interacting asynchronously |
| 63 // should be needed is a way to ensure that the list of websafe protocols is | 64 // with the underlying OS for the purposes of registering Chrome |
| 64 // updated. | 65 // as the default handler for specific protocols. |
| 65 class Delegate { | 66 class Delegate { |
| 66 public: | 67 public: |
| 67 virtual ~Delegate(); | 68 virtual ~Delegate(); |
| 68 virtual void RegisterExternalHandler(const std::string& protocol); | 69 virtual void RegisterExternalHandler(const std::string& protocol); |
| 69 virtual void DeregisterExternalHandler(const std::string& protocol); | 70 virtual void DeregisterExternalHandler(const std::string& protocol); |
| 70 virtual bool IsExternalHandlerRegistered(const std::string& protocol); | 71 virtual bool IsExternalHandlerRegistered(const std::string& protocol); |
| 71 virtual ShellIntegration::DefaultProtocolClientWorker* CreateShellWorker( | 72 virtual ShellIntegration::DefaultProtocolClientWorker* CreateShellWorker( |
| 72 ShellIntegration::DefaultWebClientObserver* observer, | 73 ShellIntegration::DefaultWebClientObserver* observer, |
| 73 const std::string& protocol); | 74 const std::string& protocol); |
| 74 virtual DefaultClientObserver* CreateShellObserver( | 75 virtual DefaultClientObserver* CreateShellObserver( |
| 75 ProtocolHandlerRegistry* registry); | 76 ProtocolHandlerRegistry* registry); |
| 76 virtual void RegisterWithOSAsDefaultClient( | 77 virtual void RegisterWithOSAsDefaultClient( |
| 77 const std::string& protocol, | 78 const std::string& protocol, |
| 78 ProtocolHandlerRegistry* registry); | 79 ProtocolHandlerRegistry* registry); |
| 79 }; | 80 }; |
| 80 | 81 |
| 81 typedef std::map<std::string, ProtocolHandler> ProtocolHandlerMap; | 82 typedef std::map<std::string, ProtocolHandler> ProtocolHandlerMap; |
| 82 typedef std::vector<ProtocolHandler> ProtocolHandlerList; | 83 typedef std::vector<ProtocolHandler> ProtocolHandlerList; |
| 83 typedef std::map<std::string, ProtocolHandlerList> ProtocolHandlerMultiMap; | 84 typedef std::map<std::string, ProtocolHandlerList> ProtocolHandlerMultiMap; |
| 84 typedef std::vector<DefaultClientObserver*> DefaultClientObserverList; | 85 typedef std::vector<DefaultClientObserver*> DefaultClientObserverList; |
| 85 | 86 |
| 87 // Creates a new instance. Assumes ownership of |delegate|. |
| 86 ProtocolHandlerRegistry(Profile* profile, Delegate* delegate); | 88 ProtocolHandlerRegistry(Profile* profile, Delegate* delegate); |
| 89 virtual ~ProtocolHandlerRegistry(); |
| 90 |
| 91 // Returns a net::URLRequestJobFactory::Interceptor suitable |
| 92 // for use on the IO thread, but is initialized on the UI thread. |
| 93 // Callers assume responsibility for deleting this object. |
| 94 net::URLRequestJobFactory::Interceptor* CreateURLInterceptor(); |
| 87 | 95 |
| 88 // Called when a site tries to register as a protocol handler. If the request | 96 // Called when a site tries to register as a protocol handler. If the request |
| 89 // can be handled silently by the registry - either to ignore the request | 97 // can be handled silently by the registry - either to ignore the request |
| 90 // or to update an existing handler - the request will succeed. If this | 98 // or to update an existing handler - the request will succeed. If this |
| 91 // function returns false the user needs to be prompted for confirmation. | 99 // function returns false the user needs to be prompted for confirmation. |
| 92 bool SilentlyHandleRegisterHandlerRequest(const ProtocolHandler& handler); | 100 bool SilentlyHandleRegisterHandlerRequest(const ProtocolHandler& handler); |
| 93 | 101 |
| 94 // Called when the user accepts the registration of a given protocol handler. | 102 // Called when the user accepts the registration of a given protocol handler. |
| 95 void OnAcceptRegisterProtocolHandler(const ProtocolHandler& handler); | 103 void OnAcceptRegisterProtocolHandler(const ProtocolHandler& handler); |
| 96 | 104 |
| (...skipping 12 matching lines...) Expand all Loading... |
| 109 // Returns a list of protocol handlers that can be replaced by the given | 117 // Returns a list of protocol handlers that can be replaced by the given |
| 110 // handler. | 118 // handler. |
| 111 ProtocolHandlerList GetReplacedHandlers(const ProtocolHandler& handler) const; | 119 ProtocolHandlerList GetReplacedHandlers(const ProtocolHandler& handler) const; |
| 112 | 120 |
| 113 // Clears the default for the provided protocol. | 121 // Clears the default for the provided protocol. |
| 114 void ClearDefault(const std::string& scheme); | 122 void ClearDefault(const std::string& scheme); |
| 115 | 123 |
| 116 // Returns true if this handler is the default handler for its protocol. | 124 // Returns true if this handler is the default handler for its protocol. |
| 117 bool IsDefault(const ProtocolHandler& handler) const; | 125 bool IsDefault(const ProtocolHandler& handler) const; |
| 118 | 126 |
| 119 // Loads a user's registered protocol handlers. | 127 // Initializes default protocol settings and loads them from prefs. |
| 120 void Load(); | 128 // This method must be called to complete initialization of the |
| 129 // registry after creation, and prior to use. |
| 130 void InitProtocolSettings(); |
| 121 | 131 |
| 122 // Returns the offset in the list of handlers for a protocol of the default | 132 // Returns the offset in the list of handlers for a protocol of the default |
| 123 // handler for that protocol. | 133 // handler for that protocol. |
| 124 int GetHandlerIndex(const std::string& scheme) const; | 134 int GetHandlerIndex(const std::string& scheme) const; |
| 125 | 135 |
| 126 // Get the list of protocol handlers for the given scheme. | 136 // Get the list of protocol handlers for the given scheme. |
| 127 ProtocolHandlerList GetHandlersFor(const std::string& scheme) const; | 137 ProtocolHandlerList GetHandlersFor(const std::string& scheme) const; |
| 128 | 138 |
| 129 // Get the list of ignored protocol handlers. | 139 // Get the list of ignored protocol handlers. |
| 130 ProtocolHandlerList GetIgnoredHandlers(); | 140 ProtocolHandlerList GetIgnoredHandlers(); |
| (...skipping 17 matching lines...) Expand all Loading... |
| 148 | 158 |
| 149 // Returns true if an equivalent protocol handler is being ignored. | 159 // Returns true if an equivalent protocol handler is being ignored. |
| 150 bool HasIgnoredEquivalent(const ProtocolHandler& handler) const; | 160 bool HasIgnoredEquivalent(const ProtocolHandler& handler) const; |
| 151 | 161 |
| 152 // Causes the given protocol handler to not be ignored anymore. | 162 // Causes the given protocol handler to not be ignored anymore. |
| 153 void RemoveIgnoredHandler(const ProtocolHandler& handler); | 163 void RemoveIgnoredHandler(const ProtocolHandler& handler); |
| 154 | 164 |
| 155 // Returns true if the protocol has a default protocol handler. | 165 // Returns true if the protocol has a default protocol handler. |
| 156 bool IsHandledProtocol(const std::string& scheme) const; | 166 bool IsHandledProtocol(const std::string& scheme) const; |
| 157 | 167 |
| 158 // Returns true if the protocol has a default protocol handler. | |
| 159 // Should be called only from the IO thread. | |
| 160 bool IsHandledProtocolIO(const std::string& scheme) const; | |
| 161 | |
| 162 // Removes the given protocol handler from the registry. | 168 // Removes the given protocol handler from the registry. |
| 163 void RemoveHandler(const ProtocolHandler& handler); | 169 void RemoveHandler(const ProtocolHandler& handler); |
| 164 | 170 |
| 165 // Remove the default handler for the given protocol. | 171 // Remove the default handler for the given protocol. |
| 166 void RemoveDefaultHandler(const std::string& scheme); | 172 void RemoveDefaultHandler(const std::string& scheme); |
| 167 | 173 |
| 168 // Returns the default handler for this protocol, or an empty handler if none | 174 // Returns the default handler for this protocol, or an empty handler if none |
| 169 // exists. | 175 // exists. |
| 170 const ProtocolHandler& GetHandlerFor(const std::string& scheme) const; | 176 const ProtocolHandler& GetHandlerFor(const std::string& scheme) const; |
| 171 | 177 |
| 172 // Creates a URL request job for the given request if there is a matching | |
| 173 // protocol handler, returns NULL otherwise. | |
| 174 net::URLRequestJob* MaybeCreateJob(net::URLRequest* request) const; | |
| 175 | |
| 176 // Puts this registry in the enabled state - registered protocol handlers | 178 // Puts this registry in the enabled state - registered protocol handlers |
| 177 // will handle requests. | 179 // will handle requests. |
| 178 void Enable(); | 180 void Enable(); |
| 179 | 181 |
| 180 // Puts this registry in the disabled state - registered protocol handlers | 182 // Puts this registry in the disabled state - registered protocol handlers |
| 181 // will not handle requests. | 183 // will not handle requests. |
| 182 void Disable(); | 184 void Disable(); |
| 183 | 185 |
| 184 // This is called by the UI thread when the system is shutting down. This | 186 // This is called by the UI thread when the system is shutting down. This |
| 185 // does finalization which must be done on the UI thread. | 187 // does finalization which must be done on the UI thread. |
| 186 void Finalize(); | 188 virtual void Shutdown() OVERRIDE; |
| 187 | 189 |
| 188 // Registers the preferences that we store registered protocol handlers in. | 190 // Registers the preferences that we store registered protocol handlers in. |
| 189 static void RegisterPrefs(PrefService* prefService); | 191 static void RegisterPrefs(PrefService* prefService); |
| 190 | 192 |
| 191 bool enabled() const { return enabled_; } | 193 bool enabled() const { return enabled_; } |
| 192 | 194 |
| 193 // Add a predefined protocol handler. This has to be called before the first | 195 // Add a predefined protocol handler. This has to be called before the first |
| 194 // load command was issued, otherwise the command will be ignored. | 196 // load command was issued, otherwise the command will be ignored. |
| 195 void AddPredefinedHandler(const ProtocolHandler& handler); | 197 void AddPredefinedHandler(const ProtocolHandler& handler); |
| 196 | 198 |
| 197 private: | 199 private: |
| 198 friend class base::DeleteHelper<ProtocolHandlerRegistry>; | 200 friend class base::DeleteHelper<ProtocolHandlerRegistry>; |
| 199 friend struct content::BrowserThread::DeleteOnThread< | 201 friend struct content::BrowserThread::DeleteOnThread< |
| 200 content::BrowserThread::IO>; | 202 content::BrowserThread::IO>; |
| 201 friend class ProtocolHandlerRegistryTest; | 203 friend class ProtocolHandlerRegistryTest; |
| 202 friend class RegisterProtocolHandlerBrowserTest; | 204 friend class RegisterProtocolHandlerBrowserTest; |
| 203 | 205 |
| 204 ~ProtocolHandlerRegistry(); | 206 // Forward declaration of the internal implementation classes. |
| 207 class Core; |
| 208 class URLInterceptor; |
| 205 | 209 |
| 206 // Puts the given handler at the top of the list of handlers for its | 210 // Puts the given handler at the top of the list of handlers for its |
| 207 // protocol. | 211 // protocol. |
| 208 void PromoteHandler(const ProtocolHandler& handler); | 212 void PromoteHandler(const ProtocolHandler& handler); |
| 209 | 213 |
| 210 // Clears the default for the provided protocol. | |
| 211 // Should be called only from the IO thread. | |
| 212 void ClearDefaultIO(const std::string& scheme); | |
| 213 | |
| 214 // Makes this ProtocolHandler the default handler for its protocol. | |
| 215 // Should be called only from the IO thread. | |
| 216 void SetDefaultIO(const ProtocolHandler& handler); | |
| 217 | |
| 218 // Indicate that the registry has been enabled in the IO thread's copy of the | |
| 219 // data. | |
| 220 void EnableIO() { enabled_io_ = true; } | |
| 221 | |
| 222 // Indicate that the registry has been disabled in the IO thread's copy of | |
| 223 // the data. | |
| 224 void DisableIO() { enabled_io_ = false; } | |
| 225 | |
| 226 // Saves a user's registered protocol handlers. | 214 // Saves a user's registered protocol handlers. |
| 227 void Save(); | 215 void Save(); |
| 228 | 216 |
| 229 // Returns a pointer to the list of handlers registered for the given scheme, | 217 // Returns a pointer to the list of handlers registered for the given scheme, |
| 230 // or NULL if there are none. | 218 // or NULL if there are none. |
| 231 const ProtocolHandlerList* GetHandlerList(const std::string& scheme) const; | 219 const ProtocolHandlerList* GetHandlerList(const std::string& scheme) const; |
| 232 | 220 |
| 233 // Makes this ProtocolHandler the default handler for its protocol. | 221 // Makes this ProtocolHandler the default handler for its protocol. |
| 234 void SetDefault(const ProtocolHandler& handler); | 222 void SetDefault(const ProtocolHandler& handler); |
| 235 | 223 |
| (...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 270 // The Profile that owns this ProtocolHandlerRegistry. | 258 // The Profile that owns this ProtocolHandlerRegistry. |
| 271 Profile* profile_; | 259 Profile* profile_; |
| 272 | 260 |
| 273 // The Delegate that registers / deregisters external handlers on our behalf. | 261 // The Delegate that registers / deregisters external handlers on our behalf. |
| 274 scoped_ptr<Delegate> delegate_; | 262 scoped_ptr<Delegate> delegate_; |
| 275 | 263 |
| 276 // If false then registered protocol handlers will not be used to handle | 264 // If false then registered protocol handlers will not be used to handle |
| 277 // requests. | 265 // requests. |
| 278 bool enabled_; | 266 bool enabled_; |
| 279 | 267 |
| 280 // Copy of enabled_ that is only accessed on the IO thread. | |
| 281 bool enabled_io_; | |
| 282 | |
| 283 // Whether or not we are loading. | 268 // Whether or not we are loading. |
| 284 bool is_loading_; | 269 bool is_loading_; |
| 285 | 270 |
| 286 // When the table gets loaded this flag will be set and any further calls to | 271 // When the table gets loaded this flag will be set and any further calls to |
| 287 // AddPredefinedHandler will be rejected. | 272 // AddPredefinedHandler will be rejected. |
| 288 bool is_loaded_; | 273 bool is_loaded_; |
| 289 | 274 |
| 275 // Copy of registry data for use on the IO thread. Changes to the registry |
| 276 // are posted to the IO thread where updates are applied to this object. |
| 277 scoped_refptr<Core> core_; |
| 278 |
| 290 DefaultClientObserverList default_client_observers_; | 279 DefaultClientObserverList default_client_observers_; |
| 291 | 280 |
| 292 // Copy of default_handlers_ that is only accessed on the IO thread. | |
| 293 ProtocolHandlerMap default_handlers_io_; | |
| 294 | |
| 295 DISALLOW_COPY_AND_ASSIGN(ProtocolHandlerRegistry); | 281 DISALLOW_COPY_AND_ASSIGN(ProtocolHandlerRegistry); |
| 296 }; | 282 }; |
| 297 #endif // CHROME_BROWSER_CUSTOM_HANDLERS_PROTOCOL_HANDLER_REGISTRY_H_ | 283 #endif // CHROME_BROWSER_CUSTOM_HANDLERS_PROTOCOL_HANDLER_REGISTRY_H_ |
| OLD | NEW |