blob: d70956414c9881af69407264c75d58b7644d3395 [file] [log] [blame]
[email protected]9e6720a2012-01-24 02:30:561// Copyright (c) 2012 The Chromium Authors. All rights reserved.
[email protected]2c699652010-10-15 18:22:412// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
[email protected]34423532013-11-21 18:13:105#ifndef EXTENSIONS_BROWSER_EVENT_ROUTER_H_
6#define EXTENSIONS_BROWSER_EVENT_ROUTER_H_
[email protected]2c699652010-10-15 18:22:417
[email protected]2c699652010-10-15 18:22:418#include <set>
9#include <string>
thestig7ade5b52017-05-23 23:13:3610#include <unordered_map>
[email protected]2c699652010-10-15 18:22:4111
[email protected]6e850922012-12-05 03:22:4812#include "base/callback.h"
[email protected]17902752011-08-31 22:52:5413#include "base/compiler_specific.h"
avic9cec102015-12-23 00:39:2614#include "base/macros.h"
[email protected]3b63f8f42011-03-28 01:54:1515#include "base/memory/ref_counted.h"
lazyboye464732f2017-06-15 21:17:2716#include "base/memory/weak_ptr.h"
Devlin Croninffbd2fe22018-07-20 17:20:1717#include "base/observer_list.h"
[email protected]4243f9a2014-08-04 18:53:1218#include "base/scoped_observer.h"
[email protected]8a16a032012-06-18 19:37:3119#include "base/values.h"
juncaicf523332015-06-04 00:14:0420#include "components/keyed_service/core/keyed_service.h"
amistry69e9ee422015-05-22 07:40:2521#include "content/public/browser/render_process_host_observer.h"
[email protected]a0e26d42013-11-20 07:04:0422#include "extensions/browser/event_listener_map.h"
Istiaque Ahmeda14ec482018-08-25 01:02:1823#include "extensions/browser/events/event_ack_data.h"
lazyboy75b9def2017-06-06 18:56:5924#include "extensions/browser/events/lazy_event_dispatch_util.h"
kalmanf1b4d782015-06-24 21:14:0525#include "extensions/browser/extension_event_histogram_value.h"
[email protected]4243f9a2014-08-04 18:53:1226#include "extensions/browser/extension_registry_observer.h"
lazyboy63b994a2017-06-30 21:20:2327#include "extensions/browser/lazy_context_task_queue.h"
lazyboye7847242017-06-07 23:29:1828#include "extensions/common/constants.h"
[email protected]4b3e1922013-02-12 04:45:5829#include "extensions/common/event_filtering_info.h"
John Lee6e10a4602019-08-22 21:20:0930#include "extensions/common/features/feature.h"
[email protected]b44f8ad2012-06-15 20:52:5831#include "ipc/ipc_sender.h"
kalmana9f6e672015-08-11 00:22:5032#include "url/gurl.h"
[email protected]2c699652010-10-15 18:22:4133
34class GURL;
Istiaque Ahmed9d1666182017-09-21 23:58:1835struct ServiceWorkerIdentifier;
[email protected]f3b1a082011-11-18 00:34:3036
37namespace content {
[email protected]7061be92013-02-18 15:44:0238class BrowserContext;
[email protected]2c699652010-10-15 18:22:4139class RenderProcessHost;
[email protected]f3b1a082011-11-18 00:34:3040}
[email protected]2c699652010-10-15 18:22:4141
[email protected]1c321ee2012-05-21 03:02:3442namespace extensions {
43class Extension;
[email protected]79cb81bb2012-09-20 02:23:3144class ExtensionPrefs;
[email protected]4243f9a2014-08-04 18:53:1245class ExtensionRegistry;
[email protected]3a1dc572012-07-31 22:25:1346
[email protected]5a38dfd2012-07-23 23:22:1047struct Event;
[email protected]954e13492012-11-15 03:18:2348struct EventListenerInfo;
[email protected]1c321ee2012-05-21 03:02:3449
lazyboye7847242017-06-07 23:29:1850// TODO(lazyboy): Document how extension events work, including how listeners
51// are registered and how listeners are tracked in renderer and browser process.
juncaicf523332015-06-04 00:14:0452class EventRouter : public KeyedService,
[email protected]4243f9a2014-08-04 18:53:1253 public ExtensionRegistryObserver,
amistry69e9ee422015-05-22 07:40:2554 public EventListenerMap::Delegate,
55 public content::RenderProcessHostObserver {
[email protected]2c699652010-10-15 18:22:4156 public:
[email protected]b085856f2012-03-02 04:37:2557 // These constants convey the state of our knowledge of whether we're in
58 // a user-caused gesture as part of DispatchEvent.
59 enum UserGestureState {
60 USER_GESTURE_UNKNOWN = 0,
61 USER_GESTURE_ENABLED = 1,
62 USER_GESTURE_NOT_ENABLED = 2,
63 };
64
[email protected]e74d43c72013-05-17 19:01:4165 // The pref key for the list of event names for which an extension has
66 // registered from its lazy background page.
lazyboye7847242017-06-07 23:29:1867 static const char kRegisteredLazyEvents[];
68 // The pref key for the list of event names for which an extension has
69 // registered from its service worker.
70 static const char kRegisteredServiceWorkerEvents[];
[email protected]e74d43c72013-05-17 19:01:4171
[email protected]c4dc5cc2012-11-09 08:48:3972 // Observers register interest in events with a particular name and are
[email protected]c761a962013-11-20 04:19:4173 // notified when a listener is added or removed. Observers are matched by
74 // the base name of the event (e.g. adding an event listener for event name
75 // "foo.onBar/123" will trigger observers registered for "foo.onBar").
[email protected]c4dc5cc2012-11-09 08:48:3976 class Observer {
77 public:
78 // Called when a listener is added.
[email protected]954e13492012-11-15 03:18:2379 virtual void OnListenerAdded(const EventListenerInfo& details) {}
[email protected]c4dc5cc2012-11-09 08:48:3980 // Called when a listener is removed.
[email protected]954e13492012-11-15 03:18:2381 virtual void OnListenerRemoved(const EventListenerInfo& details) {}
thestig7ade5b52017-05-23 23:13:3682
83 protected:
84 virtual ~Observer() {}
[email protected]c4dc5cc2012-11-09 08:48:3985 };
86
Devlin Croninffbd2fe22018-07-20 17:20:1787 // A test observer to monitor event dispatching.
88 class TestObserver {
89 public:
90 virtual ~TestObserver() = default;
91 virtual void OnWillDispatchEvent(const Event& event) = 0;
Ramin Halavatia4870222018-07-31 05:41:0492 virtual void OnDidDispatchEventToProcess(const Event& event) = 0;
Devlin Croninffbd2fe22018-07-20 17:20:1793 };
94
[email protected]3a368a22014-03-26 19:29:1995 // Gets the EventRouter for |browser_context|.
[email protected]3a368a22014-03-26 19:29:1996 static EventRouter* Get(content::BrowserContext* browser_context);
97
[email protected]c761a962013-11-20 04:19:4198 // Converts event names like "foo.onBar/123" into "foo.onBar". Event names
99 // without a "/" are returned unchanged.
100 static std::string GetBaseEventName(const std::string& full_event_name);
101
[email protected]c9bd90f2012-08-07 23:58:15102 // Sends an event via ipc_sender to the given extension. Can be called on any
103 // thread.
kalmana9f6e672015-08-11 00:22:50104 //
105 // It is very rare to call this function directly. Instead use the instance
106 // methods BroadcastEvent or DispatchEventToExtension.
Istiaque Ahmed68ef38d62019-06-15 00:23:21107 // Note that this method will dispatch the event with
108 // UserGestureState:USER_GESTURE_UNKNOWN.
kalmana9f6e672015-08-11 00:22:50109 static void DispatchEventToSender(IPC::Sender* ipc_sender,
110 void* browser_context_id,
111 const std::string& extension_id,
112 events::HistogramValue histogram_value,
113 const std::string& event_name,
David Bertoni3929f552019-03-28 22:10:36114 int render_process_id,
115 int worker_thread_id,
David Bertonifc97d5ea2019-03-20 04:08:39116 int64_t service_worker_version_id,
dchengf5d241082016-04-21 03:43:11117 std::unique_ptr<base::ListValue> event_args,
kalmana9f6e672015-08-11 00:22:50118 const EventFilteringInfo& info);
[email protected]5a7b5eaf2010-11-02 20:52:19119
lazyboye464732f2017-06-15 21:17:27120 // Returns false when the event is scoped to a context and the listening
121 // extension does not have access to events from that context.
122 static bool CanDispatchEventToBrowserContext(content::BrowserContext* context,
123 const Extension* extension,
124 const Event& event);
125
[email protected]45fd94172013-11-13 03:29:52126 // An EventRouter is shared between |browser_context| and its associated
127 // incognito context. |extension_prefs| may be NULL in tests.
128 EventRouter(content::BrowserContext* browser_context,
129 ExtensionPrefs* extension_prefs);
dcheng9168b2f2014-10-21 12:38:24130 ~EventRouter() override;
[email protected]2c699652010-10-15 18:22:41131
[email protected]c1abb3232014-07-30 18:28:39132 // Add or remove an extension as an event listener for |event_name|.
133 //
[email protected]a7ab1b782010-10-21 23:24:16134 // Note that multiple extensions can share a process due to process
135 // collapsing. Also, a single extension can have 2 processes if it is a split
136 // mode extension.
[email protected]2c699652010-10-15 18:22:41137 void AddEventListener(const std::string& event_name,
[email protected]f3b1a082011-11-18 00:34:30138 content::RenderProcessHost* process,
lazyboye7847242017-06-07 23:29:18139 const ExtensionId& extension_id);
140 void AddServiceWorkerEventListener(const std::string& event_name,
141 content::RenderProcessHost* process,
142 const ExtensionId& extension_id,
lazyboy63b994a2017-06-30 21:20:23143 const GURL& service_worker_scope,
Istiaque Ahmeda14ec482018-08-25 01:02:18144 int64_t service_worker_version_id,
lazyboye7847242017-06-07 23:29:18145 int worker_thread_id);
[email protected]2c699652010-10-15 18:22:41146 void RemoveEventListener(const std::string& event_name,
[email protected]f3b1a082011-11-18 00:34:30147 content::RenderProcessHost* process,
lazyboye7847242017-06-07 23:29:18148 const ExtensionId& extension_id);
149 void RemoveServiceWorkerEventListener(const std::string& event_name,
150 content::RenderProcessHost* process,
151 const ExtensionId& extension_id,
lazyboy63b994a2017-06-30 21:20:23152 const GURL& service_worker_scope,
Istiaque Ahmeda14ec482018-08-25 01:02:18153 int64_t service_worker_version_id,
lazyboye7847242017-06-07 23:29:18154 int worker_thread_id);
[email protected]2c699652010-10-15 18:22:41155
[email protected]c1abb3232014-07-30 18:28:39156 // Add or remove a URL as an event listener for |event_name|.
157 void AddEventListenerForURL(const std::string& event_name,
158 content::RenderProcessHost* process,
159 const GURL& listener_url);
160 void RemoveEventListenerForURL(const std::string& event_name,
161 content::RenderProcessHost* process,
162 const GURL& listener_url);
163
[email protected]f34706b2012-09-04 07:32:09164 EventListenerMap& listeners() { return listeners_; }
165
[email protected]c4dc5cc2012-11-09 08:48:39166 // Registers an observer to be notified when an event listener for
167 // |event_name| is added or removed. There can currently be only one observer
168 // for each distinct |event_name|.
thestig7ade5b52017-05-23 23:13:36169 void RegisterObserver(Observer* observer, const std::string& event_name);
[email protected]c4dc5cc2012-11-09 08:48:39170
171 // Unregisters an observer from all events.
172 void UnregisterObserver(Observer* observer);
173
Devlin Croninffbd2fe22018-07-20 17:20:17174 // Adds/removes test observers.
175 void AddObserverForTesting(TestObserver* observer);
176 void RemoveObserverForTesting(TestObserver* observer);
177
[email protected]36531222012-02-07 19:41:27178 // Add or remove the extension as having a lazy background page that listens
179 // to the event. The difference from the above methods is that these will be
180 // remembered even after the process goes away. We use this list to decide
181 // which extension pages to load when dispatching an event.
182 void AddLazyEventListener(const std::string& event_name,
lazyboye7847242017-06-07 23:29:18183 const ExtensionId& extension_id);
[email protected]36531222012-02-07 19:41:27184 void RemoveLazyEventListener(const std::string& event_name,
lazyboye7847242017-06-07 23:29:18185 const ExtensionId& extension_id);
186 // Similar to Add/RemoveLazyEventListener, but applies to extension service
187 // workers.
188 void AddLazyServiceWorkerEventListener(const std::string& event_name,
189 const ExtensionId& extension_id,
lazyboy63b994a2017-06-30 21:20:23190 const GURL& service_worker_scope);
lazyboye7847242017-06-07 23:29:18191 void RemoveLazyServiceWorkerEventListener(const std::string& event_name,
192 const ExtensionId& extension_id,
lazyboy63b994a2017-06-30 21:20:23193 const GURL& service_worker_scope);
[email protected]36531222012-02-07 19:41:27194
[email protected]d9e559d2012-07-05 01:04:57195 // If |add_lazy_listener| is true also add the lazy version of this listener.
Istiaque Ahmed9d1666182017-09-21 23:58:18196 void AddFilteredEventListener(
197 const std::string& event_name,
198 content::RenderProcessHost* process,
199 const std::string& extension_id,
200 base::Optional<ServiceWorkerIdentifier> sw_identifier,
201 const base::DictionaryValue& filter,
202 bool add_lazy_listener);
[email protected]d9e559d2012-07-05 01:04:57203
204 // If |remove_lazy_listener| is true also remove the lazy version of this
205 // listener.
Istiaque Ahmed9d1666182017-09-21 23:58:18206 void RemoveFilteredEventListener(
207 const std::string& event_name,
208 content::RenderProcessHost* process,
209 const std::string& extension_id,
210 base::Optional<ServiceWorkerIdentifier> sw_identifier,
211 const base::DictionaryValue& filter,
212 bool remove_lazy_listener);
[email protected]d9e559d2012-07-05 01:04:57213
[email protected]2c699652010-10-15 18:22:41214 // Returns true if there is at least one listener for the given event.
thestig7ade5b52017-05-23 23:13:36215 bool HasEventListener(const std::string& event_name) const;
[email protected]2c699652010-10-15 18:22:41216
[email protected]a7ab1b782010-10-21 23:24:16217 // Returns true if the extension is listening to the given event.
thestig7ade5b52017-05-23 23:13:36218 // (virtual for testing only.)
asargentd50b18c2016-04-21 01:17:16219 virtual bool ExtensionHasEventListener(const std::string& extension_id,
thestig7ade5b52017-05-23 23:13:36220 const std::string& event_name) const;
[email protected]a7ab1b782010-10-21 23:24:16221
[email protected]6e850922012-12-05 03:22:48222 // Broadcasts an event to every listener registered for that event.
dchengf5d241082016-04-21 03:43:11223 virtual void BroadcastEvent(std::unique_ptr<Event> event);
[email protected]6e850922012-12-05 03:22:48224
225 // Dispatches an event to the given extension.
226 virtual void DispatchEventToExtension(const std::string& extension_id,
dchengf5d241082016-04-21 03:43:11227 std::unique_ptr<Event> event);
[email protected]6e850922012-12-05 03:22:48228
[email protected]42d24742013-07-23 05:25:55229 // Dispatches |event| to the given extension as if the extension has a lazy
230 // listener for it. NOTE: This should be used rarely, for dispatching events
231 // to extensions that haven't had a chance to add their own listeners yet, eg:
232 // newly installed extensions.
233 void DispatchEventWithLazyListener(const std::string& extension_id,
dchengf5d241082016-04-21 03:43:11234 std::unique_ptr<Event> event);
[email protected]42d24742013-07-23 05:25:55235
[email protected]89102012011-11-01 21:23:56236 // Record the Event Ack from the renderer. (One less event in-flight.)
[email protected]45fd94172013-11-13 03:29:52237 void OnEventAck(content::BrowserContext* context,
David Bertoni3e1e9fa2018-08-29 20:39:30238 const std::string& extension_id,
239 const std::string& event_name);
[email protected]89102012011-11-01 21:23:56240
lazyboyac968912017-05-16 17:50:09241 // Returns whether or not the given extension has any registered events.
Istiaque Ahmed805f6a83b2017-10-05 01:23:26242 bool HasRegisteredEvents(const ExtensionId& extension_id) const;
lazyboyac968912017-05-16 17:50:09243
244 // Clears registered events for testing purposes.
lazyboye7847242017-06-07 23:29:18245 void ClearRegisteredEventsForTest(const ExtensionId& extension_id);
lazyboyac968912017-05-16 17:50:09246
kalmana9f6e672015-08-11 00:22:50247 // Reports UMA for an event dispatched to |extension| with histogram value
248 // |histogram_value|. Must be called on the UI thread.
249 //
250 // |did_enqueue| should be true if the event was queued waiting for a process
251 // to start, like an event page.
252 void ReportEvent(events::HistogramValue histogram_value,
253 const Extension* extension,
254 bool did_enqueue);
255
lazyboy75b9def2017-06-06 18:56:59256 LazyEventDispatchUtil* lazy_event_dispatch_util() {
257 return &lazy_event_dispatch_util_;
258 }
259
Istiaque Ahmeda14ec482018-08-25 01:02:18260 EventAckData* event_ack_data() { return &event_ack_data_; }
261
Devlin Cronin6e1ee262017-10-05 01:38:34262 // Returns true if there is a registered lazy/non-lazy listener for the given
rdevlin.cronin91f0c8a32017-07-19 21:26:33263 // |event_name|.
264 bool HasLazyEventListenerForTesting(const std::string& event_name);
Devlin Cronin6e1ee262017-10-05 01:38:34265 bool HasNonLazyEventListenerForTesting(const std::string& event_name);
rdevlin.cronin91f0c8a32017-07-19 21:26:33266
[email protected]fb6ff23b2012-03-13 23:13:42267 private:
lazyboy348e5ca2016-12-05 21:43:29268 friend class EventRouterFilterTest;
[email protected]c1abb3232014-07-30 18:28:39269 friend class EventRouterTest;
[email protected]c761a962013-11-20 04:19:41270
lazyboye7847242017-06-07 23:29:18271 enum class RegisteredEventType {
272 kLazy,
273 kServiceWorker,
274 };
275
[email protected]c9bd90f2012-08-07 23:58:15276 // TODO(gdk): Document this.
277 static void DispatchExtensionMessage(
278 IPC::Sender* ipc_sender,
lazyboye7847242017-06-07 23:29:18279 int worker_thread_id,
[email protected]513b8032013-11-18 07:47:49280 void* browser_context_id,
[email protected]c9bd90f2012-08-07 23:58:15281 const std::string& extension_id,
chirantan669993c2015-03-05 23:38:33282 int event_id,
[email protected]c9bd90f2012-08-07 23:58:15283 const std::string& event_name,
284 base::ListValue* event_args,
[email protected]c9bd90f2012-08-07 23:58:15285 UserGestureState user_gesture,
286 const extensions::EventFilteringInfo& info);
287
lazyboyac968912017-05-16 17:50:09288 // Returns or sets the list of events for which the given extension has
289 // registered.
lazyboye7847242017-06-07 23:29:18290 std::set<std::string> GetRegisteredEvents(const std::string& extension_id,
291 RegisteredEventType type) const;
lazyboyac968912017-05-16 17:50:09292 void SetRegisteredEvents(const std::string& extension_id,
lazyboye7847242017-06-07 23:29:18293 const std::set<std::string>& events,
294 RegisteredEventType type);
lazyboyac968912017-05-16 17:50:09295
[email protected]4243f9a2014-08-04 18:53:12296 // ExtensionRegistryObserver implementation.
dcheng9168b2f2014-10-21 12:38:24297 void OnExtensionLoaded(content::BrowserContext* browser_context,
298 const Extension* extension) override;
299 void OnExtensionUnloaded(content::BrowserContext* browser_context,
300 const Extension* extension,
limasdf0deef2042017-05-03 19:17:17301 UnloadedExtensionReason reason) override;
[email protected]2c699652010-10-15 18:22:41302
lazyboy63b994a2017-06-30 21:20:23303 void AddLazyEventListenerImpl(std::unique_ptr<EventListener> listener,
304 RegisteredEventType type);
305 void RemoveLazyEventListenerImpl(std::unique_ptr<EventListener> listener,
306 RegisteredEventType type);
lazyboye7847242017-06-07 23:29:18307
kalmana9f6e672015-08-11 00:22:50308 // Shared by all event dispatch methods. If |restrict_to_extension_id| is
309 // empty, the event is broadcast. An event that just came off the pending
310 // list may not be delayed again.
[email protected]d9e559d2012-07-05 01:04:57311 void DispatchEventImpl(const std::string& restrict_to_extension_id,
Devlin Cronin6db70572018-12-21 23:23:24312 std::unique_ptr<Event> event);
[email protected]fb6ff23b2012-03-13 23:13:42313
[email protected]c1abb3232014-07-30 18:28:39314 // Dispatches the event to the specified extension or URL running in
315 // |process|.
[email protected]d9e559d2012-07-05 01:04:57316 void DispatchEventToProcess(const std::string& extension_id,
[email protected]c1abb3232014-07-30 18:28:39317 const GURL& listener_url,
[email protected]d9e559d2012-07-05 01:04:57318 content::RenderProcessHost* process,
Istiaque Ahmeda14ec482018-08-25 01:02:18319 int64_t service_worker_version_id,
lazyboye7847242017-06-07 23:29:18320 int worker_thread_id,
Devlin Cronin6db70572018-12-21 23:23:24321 Event* event,
kalmana9f6e672015-08-11 00:22:50322 const base::DictionaryValue* listener_filter,
323 bool did_enqueue);
[email protected]fb6ff23b2012-03-13 23:13:42324
[email protected]e74d43c72013-05-17 19:01:41325 // Adds a filter to an event.
326 void AddFilterToEvent(const std::string& event_name,
327 const std::string& extension_id,
Istiaque Ahmed9ce21b32017-10-10 20:43:18328 bool is_for_service_worker,
[email protected]e74d43c72013-05-17 19:01:41329 const base::DictionaryValue* filter);
330
331 // Removes a filter from an event.
332 void RemoveFilterFromEvent(const std::string& event_name,
333 const std::string& extension_id,
Istiaque Ahmed9ce21b32017-10-10 20:43:18334 bool is_for_service_worker,
[email protected]e74d43c72013-05-17 19:01:41335 const base::DictionaryValue* filter);
336
337 // Returns the dictionary of event filters that the given extension has
338 // registered.
339 const base::DictionaryValue* GetFilteredEvents(
Istiaque Ahmed9ce21b32017-10-10 20:43:18340 const std::string& extension_id,
341 RegisteredEventType type);
[email protected]e74d43c72013-05-17 19:01:41342
chirantan669993c2015-03-05 23:38:33343 // Track the dispatched events that have not yet sent an ACK from the
344 // renderer.
[email protected]45fd94172013-11-13 03:29:52345 void IncrementInFlightEvents(content::BrowserContext* context,
David Bertonifc97d5ea2019-03-20 04:08:39346 content::RenderProcessHost* process,
chirantan669993c2015-03-05 23:38:33347 const Extension* extension,
348 int event_id,
David Bertonifc97d5ea2019-03-20 04:08:39349 const std::string& event_name,
350 int64_t service_worker_version_id);
[email protected]fb6ff23b2012-03-13 23:13:42351
[email protected]db9f2142013-05-27 22:56:16352 // static
kalmana9f6e672015-08-11 00:22:50353 static void DoDispatchEventToSenderBookkeepingOnUI(
354 void* browser_context_id,
355 const std::string& extension_id,
356 int event_id,
David Bertoni3929f552019-03-28 22:10:36357 int render_process_id,
David Bertonifc97d5ea2019-03-20 04:08:39358 int64_t service_worker_version_id,
kalmana9f6e672015-08-11 00:22:50359 events::HistogramValue histogram_value,
360 const std::string& event_name);
[email protected]db9f2142013-05-27 22:56:16361
lazyboy63b994a2017-06-30 21:20:23362 void DispatchPendingEvent(
Devlin Cronin6db70572018-12-21 23:23:24363 std::unique_ptr<Event> event,
lazyboy63b994a2017-06-30 21:20:23364 std::unique_ptr<LazyContextTaskQueue::ContextInfo> params);
[email protected]fb6ff23b2012-03-13 23:13:42365
[email protected]5a38dfd2012-07-23 23:22:10366 // Implementation of EventListenerMap::Delegate.
dcheng9168b2f2014-10-21 12:38:24367 void OnListenerAdded(const EventListener* listener) override;
368 void OnListenerRemoved(const EventListener* listener) override;
[email protected]d9e559d2012-07-05 01:04:57369
amistry69e9ee422015-05-22 07:40:25370 // RenderProcessHostObserver implementation.
Bo Liu2a489402018-04-24 23:41:27371 void RenderProcessExited(
372 content::RenderProcessHost* host,
373 const content::ChildProcessTerminationInfo& info) override;
amistry69e9ee422015-05-22 07:40:25374 void RenderProcessHostDestroyed(content::RenderProcessHost* host) override;
375
thestig7ade5b52017-05-23 23:13:36376 content::BrowserContext* const browser_context_;
[email protected]45fd94172013-11-13 03:29:52377
[email protected]513b8032013-11-18 07:47:49378 // The ExtensionPrefs associated with |browser_context_|. May be NULL in
379 // tests.
thestig7ade5b52017-05-23 23:13:36380 ExtensionPrefs* const extension_prefs_;
[email protected]2c699652010-10-15 18:22:41381
[email protected]4243f9a2014-08-04 18:53:12382 ScopedObserver<ExtensionRegistry, ExtensionRegistryObserver>
383 extension_registry_observer_;
384
[email protected]d81d3a192012-11-09 00:32:50385 EventListenerMap listeners_;
[email protected]58c90952012-11-09 00:03:30386
[email protected]c761a962013-11-20 04:19:41387 // Map from base event name to observer.
thestig7ade5b52017-05-23 23:13:36388 using ObserverMap = std::unordered_map<std::string, Observer*>;
[email protected]c4dc5cc2012-11-09 08:48:39389 ObserverMap observers_;
390
Trent Apteda250ec3ab2018-08-19 08:52:19391 base::ObserverList<TestObserver>::Unchecked test_observers_;
Devlin Croninffbd2fe22018-07-20 17:20:17392
amistry69e9ee422015-05-22 07:40:25393 std::set<content::RenderProcessHost*> observed_process_set_;
394
lazyboy75b9def2017-06-06 18:56:59395 LazyEventDispatchUtil lazy_event_dispatch_util_;
396
Istiaque Ahmeda14ec482018-08-25 01:02:18397 EventAckData event_ack_data_;
398
Jeremy Roman9fc2de62019-07-12 14:15:03399 base::WeakPtrFactory<EventRouter> weak_factory_{this};
lazyboye464732f2017-06-15 21:17:27400
[email protected]5a38dfd2012-07-23 23:22:10401 DISALLOW_COPY_AND_ASSIGN(EventRouter);
[email protected]2c699652010-10-15 18:22:41402};
403
[email protected]5a38dfd2012-07-23 23:22:10404struct Event {
reillyg5464e7e2014-12-11 00:35:08405 // This callback should return true if the event should be dispatched to the
406 // given context and extension, and false otherwise.
thestig7ade5b52017-05-23 23:13:36407 using WillDispatchCallback =
Devlin Cronin66bfdb82018-12-27 23:54:42408 base::RepeatingCallback<bool(content::BrowserContext*,
John Lee6e10a4602019-08-22 21:20:09409 Feature::Context,
Devlin Cronin66bfdb82018-12-27 23:54:42410 const Extension*,
411 Event*,
412 const base::DictionaryValue*)>;
[email protected]6e850922012-12-05 03:22:48413
kalmanf1b4d782015-06-24 21:14:05414 // The identifier for the event, for histograms. In most cases this
415 // correlates 1:1 with |event_name|, in some cases events will generate
416 // their own names, but they cannot generate their own identifier.
thestig7ade5b52017-05-23 23:13:36417 const events::HistogramValue histogram_value;
kalmanf1b4d782015-06-24 21:14:05418
[email protected]6e850922012-12-05 03:22:48419 // The event to dispatch.
thestig7ade5b52017-05-23 23:13:36420 const std::string event_name;
[email protected]6e850922012-12-05 03:22:48421
422 // Arguments to send to the event listener.
dchengf5d241082016-04-21 03:43:11423 std::unique_ptr<base::ListValue> event_args;
[email protected]6e850922012-12-05 03:22:48424
lazyboy59155a42017-05-24 22:23:35425 // If non-null, then the event will not be sent to other BrowserContexts
[email protected]45fd94172013-11-13 03:29:52426 // unless the extension has permission (e.g. incognito tab update -> normal
427 // tab only works if extension is allowed incognito access).
lazyboy59155a42017-05-24 22:23:35428 content::BrowserContext* const restrict_to_browser_context;
[email protected]6e850922012-12-05 03:22:48429
430 // If not empty, the event is only sent to extensions with host permissions
431 // for this url.
432 GURL event_url;
433
434 // Whether a user gesture triggered the event.
[email protected]5a38dfd2012-07-23 23:22:10435 EventRouter::UserGestureState user_gesture;
[email protected]6e850922012-12-05 03:22:48436
437 // Extra information used to filter which events are sent to the listener.
438 EventFilteringInfo filter_info;
439
440 // If specified, this is called before dispatching an event to each
441 // extension. The third argument is a mutable reference to event_args,
442 // allowing the caller to provide different arguments depending on the
443 // extension and profile. This is guaranteed to be called synchronously with
444 // DispatchEvent, so callers don't need to worry about lifetime.
[email protected]2c6e3b04c2014-07-24 12:48:09445 //
446 // NOTE: the Extension argument to this may be NULL because it's possible for
447 // this event to be dispatched to non-extension processes, like WebUI.
[email protected]6e850922012-12-05 03:22:48448 WillDispatchCallback will_dispatch_callback;
449
lazyboy59155a42017-05-24 22:23:35450 // TODO(lazyboy): This sets |restrict_to_browser_context| to nullptr, this
451 // will dispatch the event to unrelated profiles, not just incognito. Audit
452 // and limit usages of this constructor and introduce "include incognito"
453 // option to a constructor version for clients that need to disptach events to
454 // related browser_contexts. See https://crbug.com/726022.
kalmanf1b4d782015-06-24 21:14:05455 Event(events::HistogramValue histogram_value,
456 const std::string& event_name,
dchengf5d241082016-04-21 03:43:11457 std::unique_ptr<base::ListValue> event_args);
[email protected]d9e559d2012-07-05 01:04:57458
kalmanf1b4d782015-06-24 21:14:05459 Event(events::HistogramValue histogram_value,
460 const std::string& event_name,
dchengf5d241082016-04-21 03:43:11461 std::unique_ptr<base::ListValue> event_args,
[email protected]45fd94172013-11-13 03:29:52462 content::BrowserContext* restrict_to_browser_context);
[email protected]f0eb58a2012-12-17 22:10:49463
kalmanf1b4d782015-06-24 21:14:05464 Event(events::HistogramValue histogram_value,
465 const std::string& event_name,
dchengf5d241082016-04-21 03:43:11466 std::unique_ptr<base::ListValue> event_args,
[email protected]45fd94172013-11-13 03:29:52467 content::BrowserContext* restrict_to_browser_context,
[email protected]6e850922012-12-05 03:22:48468 const GURL& event_url,
[email protected]5a38dfd2012-07-23 23:22:10469 EventRouter::UserGestureState user_gesture,
470 const EventFilteringInfo& info);
[email protected]d9e559d2012-07-05 01:04:57471
[email protected]5a38dfd2012-07-23 23:22:10472 ~Event();
[email protected]6e850922012-12-05 03:22:48473
Devlin Cronin614b0142018-12-10 22:08:53474 // Makes a deep copy of this instance.
475 std::unique_ptr<Event> DeepCopy() const;
[email protected]d9e559d2012-07-05 01:04:57476};
477
[email protected]954e13492012-11-15 03:18:23478struct EventListenerInfo {
David Bertoni3929f552019-03-28 22:10:36479 // Constructor for a listener from a non-ServiceWorker context (background
480 // page, popup, tab, etc)
[email protected]954e13492012-11-15 03:18:23481 EventListenerInfo(const std::string& event_name,
[email protected]c761a962013-11-20 04:19:41482 const std::string& extension_id,
[email protected]c1abb3232014-07-30 18:28:39483 const GURL& listener_url,
[email protected]c761a962013-11-20 04:19:41484 content::BrowserContext* browser_context);
David Bertoni3929f552019-03-28 22:10:36485
486 // Constructor for a listener from a ServiceWorker context.
487 EventListenerInfo(const std::string& event_name,
488 const std::string& extension_id,
489 const GURL& listener_url,
490 content::BrowserContext* browser_context,
491 int worker_thread_id,
492 int64_t service_worker_version_id);
493
[email protected]c761a962013-11-20 04:19:41494 // The event name including any sub-event, e.g. "runtime.onStartup" or
495 // "webRequest.onCompleted/123".
[email protected]954e13492012-11-15 03:18:23496 const std::string event_name;
[email protected]954e13492012-11-15 03:18:23497 const std::string extension_id;
[email protected]c1abb3232014-07-30 18:28:39498 const GURL listener_url;
thestig7ade5b52017-05-23 23:13:36499 content::BrowserContext* const browser_context;
David Bertoni3929f552019-03-28 22:10:36500 const int worker_thread_id;
501 const int64_t service_worker_version_id;
[email protected]954e13492012-11-15 03:18:23502};
503
[email protected]5a38dfd2012-07-23 23:22:10504} // namespace extensions
[email protected]d9e559d2012-07-05 01:04:57505
[email protected]34423532013-11-21 18:13:10506#endif // EXTENSIONS_BROWSER_EVENT_ROUTER_H_