Chromium Code Reviews| Index: extensions/renderer/event_bindings.cc |
| diff --git a/extensions/renderer/event_bindings.cc b/extensions/renderer/event_bindings.cc |
| index 03635433bed9af6f1ae7e5b0d69a5766d41149f5..da1cba6a4ec535d9fab7e2e3b352eb02d2502bd6 100644 |
| --- a/extensions/renderer/event_bindings.cc |
| +++ b/extensions/renderer/event_bindings.cc |
| @@ -22,11 +22,13 @@ |
| #include "extensions/common/event_filter.h" |
| #include "extensions/common/extension.h" |
| #include "extensions/common/extension_messages.h" |
| +#include "extensions/common/extension_urls.h" |
| #include "extensions/common/value_counter.h" |
| #include "extensions/renderer/extension_frame_helper.h" |
| #include "extensions/renderer/script_context.h" |
| #include "extensions/renderer/service_worker_request_sender.h" |
| #include "extensions/renderer/worker_thread_dispatcher.h" |
| +#include "gin/converter.h" |
| #include "url/gurl.h" |
| namespace extensions { |
| @@ -82,44 +84,6 @@ int DecrementEventListenerCount(ScriptContext* script_context, |
| .Get()[GetKeyForScriptContext(script_context)][event_name]; |
| } |
| -EventFilteringInfo ParseFromObject(v8::Local<v8::Object> object, |
| - v8::Isolate* isolate) { |
| - EventFilteringInfo info; |
| - v8::Local<v8::String> url(v8::String::NewFromUtf8(isolate, "url")); |
| - if (object->Has(url)) { |
| - v8::Local<v8::Value> url_value(object->Get(url)); |
| - info.SetURL(GURL(*v8::String::Utf8Value(url_value))); |
| - } |
| - v8::Local<v8::String> instance_id( |
| - v8::String::NewFromUtf8(isolate, "instanceId")); |
| - if (object->Has(instance_id)) { |
| - v8::Local<v8::Value> instance_id_value(object->Get(instance_id)); |
| - info.SetInstanceID(instance_id_value->IntegerValue()); |
| - } |
| - v8::Local<v8::String> service_type( |
| - v8::String::NewFromUtf8(isolate, "serviceType")); |
| - if (object->Has(service_type)) { |
| - v8::Local<v8::Value> service_type_value(object->Get(service_type)); |
| - info.SetServiceType(*v8::String::Utf8Value(service_type_value)); |
| - } |
| - v8::Local<v8::String> window_types( |
| - v8::String::NewFromUtf8(isolate, "windowType")); |
| - if (object->Has(window_types)) { |
| - v8::Local<v8::Value> window_types_value(object->Get(window_types)); |
| - info.SetWindowType(*v8::String::Utf8Value(window_types_value)); |
| - } |
| - |
| - v8::Local<v8::String> window_exposed( |
| - v8::String::NewFromUtf8(isolate, "windowExposedByDefault")); |
| - if (object->Has(window_exposed)) { |
| - v8::Local<v8::Value> window_exposed_value(object->Get(window_exposed)); |
| - info.SetWindowExposedByDefault( |
| - window_exposed_value.As<v8::Boolean>()->Value()); |
| - } |
| - |
| - return info; |
| -} |
| - |
| // Add a filter to |event_name| in |extension_id|, returning true if it |
| // was the first filter for that event in that extension. |
| bool AddFilter(const std::string& event_name, |
| @@ -157,6 +121,33 @@ bool RemoveFilter(const std::string& event_name, |
| return false; |
| } |
| +// Returns a v8::Array containing the ids of the listeners that match the given |
| +// |event_filter_dict| in the given |script_context|. |
| +v8::Local<v8::Array> GetMatchingListeners( |
| + ScriptContext* script_context, |
| + const std::string& event_name, |
| + const base::DictionaryValue& event_filter_dict) { |
| + EventFilter& event_filter = g_event_filter.Get(); |
|
jbroman
2017/06/12 15:48:51
nit: const&? (use of a singleton across threads li
Devlin
2017/06/12 17:01:54
Done.
|
| + EventFilteringInfo info(event_filter_dict); |
| + v8::Isolate* isolate = script_context->isolate(); |
| + v8::Local<v8::Context> context = script_context->v8_context(); |
| + |
| + // Only match events routed to this context's RenderFrame or ones that don't |
| + // have a routingId in their filter. |
| + std::set<EventFilter::MatcherID> matched_event_filters = |
| + event_filter.MatchEvent(event_name, info, |
| + script_context->GetRenderFrame()->GetRoutingID()); |
| + v8::Local<v8::Array> array( |
| + v8::Array::New(isolate, matched_event_filters.size())); |
| + int i = 0; |
| + for (EventFilter::MatcherID id : matched_event_filters) { |
| + CHECK(array->CreateDataProperty(context, i++, v8::Integer::New(isolate, id)) |
|
lazyboy
2017/06/10 00:22:08
I'll defer to Jeremy for this one.
jbroman
2017/06/12 15:48:51
This looks good to me.
|
| + .ToChecked()); |
| + } |
| + |
| + return array; |
| +} |
| + |
| } // namespace |
| EventBindings::EventBindings(ScriptContext* context) |
| @@ -171,9 +162,6 @@ EventBindings::EventBindings(ScriptContext* context) |
| RouteFunction("DetachFilteredEvent", |
| base::Bind(&EventBindings::DetachFilteredEventHandler, |
| base::Unretained(this))); |
| - RouteFunction("MatchAgainstEventFilter", |
| - base::Bind(&EventBindings::MatchAgainstEventFilter, |
| - base::Unretained(this))); |
| // It's safe to use base::Unretained here because |context| will always |
| // outlive us. |
| @@ -183,6 +171,36 @@ EventBindings::EventBindings(ScriptContext* context) |
| EventBindings::~EventBindings() {} |
| +void EventBindings::DispatchEventInContext( |
| + const std::string& event_name, |
| + const base::ListValue* event_args, |
| + const base::DictionaryValue* filtering_info, |
| + ScriptContext* context) { |
| + v8::HandleScope handle_scope(context->isolate()); |
| + v8::Context::Scope context_scope(context->v8_context()); |
| + |
| + std::vector<v8::Local<v8::Value>> arguments; |
|
jbroman
2017/06/12 15:48:51
super-nit: could at least reserve the buffer here,
Devlin
2017/06/12 17:01:54
sgtm. Little more complicated since we have to pu
|
| + arguments.push_back(gin::StringToSymbol(context->isolate(), event_name)); |
| + |
| + { |
| + std::unique_ptr<content::V8ValueConverter> converter( |
| + content::V8ValueConverter::create()); |
| + arguments.push_back( |
| + converter->ToV8Value(event_args, context->v8_context())); |
| + } |
| + |
| + v8::Local<v8::Array> listener_ids; |
| + if (filtering_info && !filtering_info->empty()) |
| + listener_ids = GetMatchingListeners(context, event_name, *filtering_info); |
| + else |
| + listener_ids = v8::Array::New(context->isolate()); |
| + |
| + arguments.push_back(listener_ids); |
| + |
| + context->module_system()->CallModuleMethodSafe( |
| + kEventBindings, "dispatchEvent", arguments.size(), arguments.data()); |
| +} |
| + |
| void EventBindings::AttachEventHandler( |
| const v8::FunctionCallbackInfo<v8::Value>& args) { |
| CHECK_EQ(1, args.Length()); |
| @@ -262,8 +280,8 @@ void EventBindings::DetachEvent(const std::string& event_name, bool is_manual) { |
| // MatcherID AttachFilteredEvent(string event_name, object filter) |
| // event_name - Name of the event to attach. |
| // filter - Which instances of the named event are we interested in. |
| -// returns the id assigned to the listener, which will be returned from calls |
| -// to MatchAgainstEventFilter where this listener matches. |
| +// returns the id assigned to the listener, which will be provided to calls to |
| +// dispatchEvent(). |
| void EventBindings::AttachFilteredEvent( |
| const v8::FunctionCallbackInfo<v8::Value>& args) { |
| CHECK_EQ(2, args.Length()); |
| @@ -337,29 +355,6 @@ void EventBindings::DetachFilteredEvent(int matcher_id, bool is_manual) { |
| attached_matcher_ids_.erase(matcher_id); |
| } |
| -void EventBindings::MatchAgainstEventFilter( |
| - const v8::FunctionCallbackInfo<v8::Value>& args) { |
| - v8::Isolate* isolate = args.GetIsolate(); |
| - typedef std::set<EventFilter::MatcherID> MatcherIDs; |
| - EventFilter& event_filter = g_event_filter.Get(); |
| - std::string event_name = *v8::String::Utf8Value(args[0]); |
| - EventFilteringInfo info = |
| - ParseFromObject(args[1]->ToObject(isolate), isolate); |
| - // Only match events routed to this context's RenderFrame or ones that don't |
| - // have a routingId in their filter. |
| - MatcherIDs matched_event_filters = event_filter.MatchEvent( |
| - event_name, info, context()->GetRenderFrame()->GetRoutingID()); |
| - v8::Local<v8::Array> array( |
| - v8::Array::New(isolate, matched_event_filters.size())); |
| - int i = 0; |
| - for (MatcherIDs::iterator it = matched_event_filters.begin(); |
| - it != matched_event_filters.end(); |
| - ++it) { |
| - array->Set(v8::Integer::New(isolate, i++), v8::Integer::New(isolate, *it)); |
| - } |
| - args.GetReturnValue().Set(array); |
| -} |
| - |
| std::unique_ptr<EventMatcher> EventBindings::ParseEventMatcher( |
| std::unique_ptr<base::DictionaryValue> filter) { |
| return base::MakeUnique<EventMatcher>( |