Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(420)

Side by Side Diff: extensions/renderer/api_bindings_system_unittest.cc

Issue 2763493003: [Extensions Bindings] Make APIBindingsSystemTest reusable (Closed)
Patch Set: . Created 3 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « extensions/renderer/api_bindings_system_unittest.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 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 #include "extensions/renderer/api_bindings_system.h" 5 #include "extensions/renderer/api_bindings_system.h"
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "base/macros.h" 8 #include "base/macros.h"
9 #include "base/memory/ptr_util.h" 9 #include "base/memory/ptr_util.h"
10 #include "base/stl_util.h" 10 #include "base/stl_util.h"
11 #include "base/strings/stringprintf.h" 11 #include "base/strings/stringprintf.h"
12 #include "base/values.h" 12 #include "base/values.h"
13 #include "extensions/common/extension_api.h" 13 #include "extensions/common/extension_api.h"
14 #include "extensions/renderer/api_binding.h" 14 #include "extensions/renderer/api_binding.h"
15 #include "extensions/renderer/api_binding_hooks.h" 15 #include "extensions/renderer/api_binding_hooks.h"
16 #include "extensions/renderer/api_binding_test.h"
17 #include "extensions/renderer/api_binding_test_util.h" 16 #include "extensions/renderer/api_binding_test_util.h"
18 #include "extensions/renderer/api_binding_types.h" 17 #include "extensions/renderer/api_binding_types.h"
18 #include "extensions/renderer/api_bindings_system_unittest.h"
19 #include "gin/arguments.h" 19 #include "gin/arguments.h"
20 #include "gin/converter.h" 20 #include "gin/converter.h"
21 #include "gin/try_catch.h" 21 #include "gin/try_catch.h"
22 22
23 namespace extensions { 23 namespace extensions {
24 24
25 namespace { 25 namespace {
26 26
27 // Fake API for testing. 27 // Fake API for testing.
28 const char kAlphaAPIName[] = "alpha"; 28 const char kAlphaAPIName[] = "alpha";
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after
85 " 'parameters': [{ 'name': 'someRef', '$ref': 'alpha.objRef' }]" 85 " 'parameters': [{ 'name': 'someRef', '$ref': 'alpha.objRef' }]"
86 " }]" 86 " }]"
87 "}"; 87 "}";
88 88
89 bool AllowAllAPIs(const std::string& name) { 89 bool AllowAllAPIs(const std::string& name) {
90 return true; 90 return true;
91 } 91 }
92 92
93 } // namespace 93 } // namespace
94 94
95 // The base class to test the APIBindingsSystem. This allows subclasses to 95 APIBindingsSystemTest::APIBindingsSystemTest() {}
96 // retrieve API schemas differently. 96 APIBindingsSystemTest::~APIBindingsSystemTest() = default;
97 class APIBindingsSystemTest : public APIBindingTest { 97
98 public: 98 void APIBindingsSystemTest::SetUp() {
99 // Returns the DictionaryValue representing the schema with the given API 99 APIBindingTest::SetUp();
100 // name. 100
101 const base::DictionaryValue& GetAPISchema(const std::string& api_name) { 101 // Create the fake API schemas.
102 EXPECT_TRUE(base::ContainsKey(api_schemas_, api_name)); 102 for (const auto& api : GetAPIs()) {
103 return *api_schemas_[api_name]; 103 std::unique_ptr<base::DictionaryValue> api_schema =
104 DictionaryValueFromString(api.spec);
105 ASSERT_TRUE(api_schema);
106 api_schemas_[api.name] = std::move(api_schema);
104 } 107 }
105 108
106 // Stores the request in |last_request_|. 109 bindings_system_ = base::MakeUnique<APIBindingsSystem>(
107 void OnAPIRequest(std::unique_ptr<APIRequestHandler::Request> request, 110 base::Bind(&RunFunctionOnGlobalAndIgnoreResult),
108 v8::Local<v8::Context> context) { 111 base::Bind(&RunFunctionOnGlobalAndReturnHandle),
109 ASSERT_FALSE(last_request_); 112 base::Bind(&APIBindingsSystemTest::GetAPISchema, base::Unretained(this)),
110 last_request_ = std::move(request); 113 base::Bind(&APIBindingsSystemTest::OnAPIRequest, base::Unretained(this)),
111 } 114 base::Bind(&APIBindingsSystemTest::OnEventListenersChanged,
115 base::Unretained(this)),
116 APILastError(base::Bind(&APIBindingsSystemTest::GetLastErrorParent,
117 base::Unretained(this))));
118 }
112 119
113 void OnEventListenersChanged(const std::string& event_name, 120 void APIBindingsSystemTest::TearDown() {
114 binding::EventListenersChanged changed, 121 // Dispose all contexts now so that we call WillReleaseContext().
115 v8::Local<v8::Context> context) {} 122 DisposeAllContexts();
123 bindings_system_.reset();
124 APIBindingTest::TearDown();
125 }
116 126
117 protected: 127 void APIBindingsSystemTest::OnWillDisposeContext(
118 APIBindingsSystemTest() {} 128 v8::Local<v8::Context> context) {
119 void SetUp() override { 129 bindings_system_->WillReleaseContext(context);
120 APIBindingTest::SetUp(); 130 }
121 131
122 // Create the fake API schemas. 132 std::vector<APIBindingsSystemTest::FakeSpec> APIBindingsSystemTest::GetAPIs() {
123 { 133 return {
124 struct APIData { 134 {kAlphaAPIName, kAlphaAPISpec},
125 const char* name; 135 {kBetaAPIName, kBetaAPISpec},
126 const char* spec; 136 {kGammaAPIName, kGammaAPISpec},
127 } api_data[] = { 137 };
128 {kAlphaAPIName, kAlphaAPISpec}, 138 }
129 {kBetaAPIName, kBetaAPISpec},
130 {kGammaAPIName, kGammaAPISpec},
131 };
132 for (const auto& api : api_data) {
133 std::unique_ptr<base::DictionaryValue> api_schema =
134 DictionaryValueFromString(api.spec);
135 ASSERT_TRUE(api_schema);
136 api_schemas_[api.name] = std::move(api_schema);
137 }
138 }
139 139
140 bindings_system_ = base::MakeUnique<APIBindingsSystem>( 140 v8::Local<v8::Object> APIBindingsSystemTest::GetLastErrorParent(
141 base::Bind(&RunFunctionOnGlobalAndIgnoreResult), 141 v8::Local<v8::Context> context) {
142 base::Bind(&RunFunctionOnGlobalAndReturnHandle), 142 return v8::Local<v8::Object>();
143 base::Bind(&APIBindingsSystemTest::GetAPISchema, 143 }
144 base::Unretained(this)),
145 base::Bind(&APIBindingsSystemTest::OnAPIRequest,
146 base::Unretained(this)),
147 base::Bind(&APIBindingsSystemTest::OnEventListenersChanged,
148 base::Unretained(this)),
149 APILastError(APILastError::GetParent()));
150 }
151 144
152 void TearDown() override { 145 const base::DictionaryValue& APIBindingsSystemTest::GetAPISchema(
153 // Dispose all contexts now so that we call WillReleaseContext(). 146 const std::string& api_name) {
154 DisposeAllContexts(); 147 EXPECT_TRUE(base::ContainsKey(api_schemas_, api_name));
155 bindings_system_.reset(); 148 return *api_schemas_[api_name];
156 APIBindingTest::TearDown(); 149 }
157 }
158 150
159 void OnWillDisposeContext(v8::Local<v8::Context> context) override { 151 void APIBindingsSystemTest::OnAPIRequest(
160 bindings_system_->WillReleaseContext(context); 152 std::unique_ptr<APIRequestHandler::Request> request,
161 } 153 v8::Local<v8::Context> context) {
154 ASSERT_FALSE(last_request_);
155 last_request_ = std::move(request);
156 }
162 157
163 // Checks that |last_request_| exists and was provided with the 158 void APIBindingsSystemTest::OnEventListenersChanged(
164 // |expected_name| and |expected_arguments|. 159 const std::string& event_name,
165 void ValidateLastRequest(const std::string& expected_name, 160 binding::EventListenersChanged changed,
166 const std::string& expected_arguments) { 161 v8::Local<v8::Context> context) {}
167 ASSERT_TRUE(last_request());
168 // Note that even if no arguments are provided by the API call, we should
169 // have an empty list.
170 ASSERT_TRUE(last_request()->arguments);
171 EXPECT_EQ(expected_name, last_request()->method_name);
172 EXPECT_EQ(ReplaceSingleQuotes(expected_arguments),
173 ValueToString(*last_request()->arguments));
174 }
175 162
176 void CallFunctionOnObject(v8::Local<v8::Context> context, 163 void APIBindingsSystemTest::ValidateLastRequest(
177 v8::Local<v8::Object> object, 164 const std::string& expected_name,
178 const std::string& script_source) { 165 const std::string& expected_arguments) {
179 std::string wrapped_script_source = 166 ASSERT_TRUE(last_request());
180 base::StringPrintf("(function(obj) { %s })", script_source.c_str()); 167 // Note that even if no arguments are provided by the API call, we should
168 // have an empty list.
169 ASSERT_TRUE(last_request()->arguments);
170 EXPECT_EQ(expected_name, last_request()->method_name);
171 EXPECT_EQ(ReplaceSingleQuotes(expected_arguments),
172 ValueToString(*last_request()->arguments));
173 }
181 174
182 v8::Local<v8::Function> func = 175 void APIBindingsSystemTest::CallFunctionOnObject(
183 FunctionFromString(context, wrapped_script_source); 176 v8::Local<v8::Context> context,
184 ASSERT_FALSE(func.IsEmpty()); 177 v8::Local<v8::Object> object,
178 const std::string& script_source) {
179 std::string wrapped_script_source =
180 base::StringPrintf("(function(obj) { %s })", script_source.c_str());
185 181
186 v8::Local<v8::Value> argv[] = {object}; 182 v8::Local<v8::Function> func =
187 RunFunction(func, context, 1, argv); 183 FunctionFromString(context, wrapped_script_source);
188 } 184 ASSERT_FALSE(func.IsEmpty());
189 185
190 const APIRequestHandler::Request* last_request() const { 186 v8::Local<v8::Value> argv[] = {object};
191 return last_request_.get(); 187 RunFunction(func, context, 1, argv);
192 } 188 }
193 void reset_last_request() { last_request_.reset(); }
194 APIBindingsSystem* bindings_system() { return bindings_system_.get(); }
195
196 private:
197 // The API schemas for the fake APIs.
198 std::map<std::string, std::unique_ptr<base::DictionaryValue>> api_schemas_;
199
200 // The APIBindingsSystem associated with the test. Safe to use across multiple
201 // contexts.
202 std::unique_ptr<APIBindingsSystem> bindings_system_;
203
204 // The last request to be received from the APIBindingsSystem, or null if
205 // there is none.
206 std::unique_ptr<APIRequestHandler::Request> last_request_;
207
208 DISALLOW_COPY_AND_ASSIGN(APIBindingsSystemTest);
209 };
210 189
211 // Tests API object initialization, calling a method on the supplied APIs, and 190 // Tests API object initialization, calling a method on the supplied APIs, and
212 // triggering the callback for the request. 191 // triggering the callback for the request.
213 TEST_F(APIBindingsSystemTest, TestInitializationAndCallbacks) { 192 TEST_F(APIBindingsSystemTest, TestInitializationAndCallbacks) {
214 v8::HandleScope handle_scope(isolate()); 193 v8::HandleScope handle_scope(isolate());
215 v8::Local<v8::Context> context = MainContext(); 194 v8::Local<v8::Context> context = MainContext();
216 195
217 v8::Local<v8::Object> alpha_api = bindings_system()->CreateAPIInstance( 196 v8::Local<v8::Object> alpha_api = bindings_system()->CreateAPIInstance(
218 kAlphaAPIName, context, isolate(), base::Bind(&AllowAllAPIs), nullptr); 197 kAlphaAPIName, context, isolate(), base::Bind(&AllowAllAPIs), nullptr);
219 ASSERT_FALSE(alpha_api.IsEmpty()); 198 ASSERT_FALSE(alpha_api.IsEmpty());
(...skipping 211 matching lines...) Expand 10 before | Expand all | Expand 10 after
431 { 410 {
432 // Test a simple call -> response. 411 // Test a simple call -> response.
433 const char kTestCall[] = "obj.functionWithExternalRef({prop1: 'foo'});"; 412 const char kTestCall[] = "obj.functionWithExternalRef({prop1: 'foo'});";
434 CallFunctionOnObject(context, gamma_api, kTestCall); 413 CallFunctionOnObject(context, gamma_api, kTestCall);
435 ValidateLastRequest("gamma.functionWithExternalRef", "[{'prop1':'foo'}]"); 414 ValidateLastRequest("gamma.functionWithExternalRef", "[{'prop1':'foo'}]");
436 reset_last_request(); 415 reset_last_request();
437 } 416 }
438 } 417 }
439 418
440 } // namespace extensions 419 } // namespace extensions
OLDNEW
« no previous file with comments | « extensions/renderer/api_bindings_system_unittest.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698