OLD | NEW |
---|---|
(Empty) | |
1 // Copyright 2014 The Chromium Authors. All rights reserved. | |
2 // Use of this source code is governed by a BSD-style license that can be | |
3 // found in the LICENSE file. | |
4 | |
5 #include "extensions/renderer/api_test_base.h" | |
6 | |
7 #include "base/run_loop.h" | |
8 #include "extensions/common/extension_urls.h" | |
9 #include "extensions/renderer/logging_native_handler.h" | |
10 #include "extensions/renderer/send_request_natives.h" | |
11 #include "extensions/renderer/utils_native_handler.h" | |
12 #include "gin/converter.h" | |
13 #include "gin/dictionary.h" | |
14 #include "grit/content_resources.h" | |
15 #include "grit/extensions_renderer_resources.h" | |
16 #include "mojo/bindings/js/core.h" | |
17 #include "mojo/bindings/js/handle.h" | |
18 #include "mojo/bindings/js/support.h" | |
19 #include "mojo/public/cpp/bindings/interface_request.h" | |
20 #include "mojo/public/cpp/system/core.h" | |
21 #include "mojo/public/js/bindings/constants.h" | |
22 | |
23 namespace extensions { | |
24 namespace { | |
25 | |
26 class TestNatives : public gin::Wrappable<TestNatives> { | |
27 public: | |
28 static gin::Handle<TestNatives> Create(v8::Isolate* isolate, | |
29 base::RunLoop* run_loop) { | |
30 return gin::CreateHandle(isolate, new TestNatives(run_loop)); | |
31 } | |
32 | |
33 virtual gin::ObjectTemplateBuilder GetObjectTemplateBuilder( | |
34 v8::Isolate* isolate) OVERRIDE { | |
35 return Wrappable<TestNatives>::GetObjectTemplateBuilder(isolate) | |
36 .SetMethod("Log", &TestNatives::Log) | |
37 .SetMethod("NotifyPass", &TestNatives::NotifyPass) | |
38 .SetMethod("NotifyFail", &TestNatives::NotifyFail); | |
39 } | |
40 | |
41 void Log(const std::string& value) { logs_ += value + "\n"; } | |
42 void NotifyPass() { FinishTesting(); } | |
43 | |
44 void NotifyFail(const std::string& message) { | |
45 FinishTesting(); | |
46 FAIL() << logs_ << message; | |
47 } | |
48 | |
49 void FinishTesting() { | |
50 base::MessageLoop::current()->PostTask(FROM_HERE, run_loop_->QuitClosure()); | |
not at google - send to devlin
2014/07/18 15:09:13
do you mean to also pump the message loop here? ho
Sam McNally
2014/07/21 03:56:27
The test functions and their callbacks run on the
| |
51 } | |
52 | |
53 static gin::WrapperInfo kWrapperInfo; | |
54 | |
55 private: | |
56 explicit TestNatives(base::RunLoop* run_loop) : run_loop_(run_loop) {} | |
57 | |
58 base::RunLoop* run_loop_; | |
59 std::string logs_; | |
60 }; | |
61 | |
62 gin::WrapperInfo TestNatives::kWrapperInfo = {gin::kEmbedderNativeGin}; | |
63 | |
64 } // namespace | |
65 | |
66 gin::WrapperInfo TestServiceProvider::kWrapperInfo = {gin::kEmbedderNativeGin}; | |
67 | |
68 gin::Handle<TestServiceProvider> TestServiceProvider::Create( | |
69 v8::Isolate* isolate) { | |
70 return gin::CreateHandle(isolate, new TestServiceProvider()); | |
71 } | |
72 | |
73 TestServiceProvider::~TestServiceProvider() { | |
74 } | |
75 | |
76 gin::ObjectTemplateBuilder TestServiceProvider::GetObjectTemplateBuilder( | |
77 v8::Isolate* isolate) { | |
78 return Wrappable<TestServiceProvider>::GetObjectTemplateBuilder(isolate) | |
79 .SetMethod("connectToService", &TestServiceProvider::ConnectToService); | |
80 } | |
81 | |
82 mojo::Handle TestServiceProvider::ConnectToService( | |
83 const std::string& service_name) { | |
84 EXPECT_EQ(1u, service_factories_.count(service_name)) | |
85 << "Unregistered service " << service_name << " requested."; | |
86 mojo::MessagePipe pipe; | |
87 std::map<std::string, | |
88 base::Callback<void(mojo::ScopedMessagePipeHandle)> >::iterator it = | |
89 service_factories_.find(service_name); | |
90 if (it != service_factories_.end()) | |
91 it->second.Run(pipe.handle0.Pass()); | |
92 return pipe.handle1.release(); | |
93 } | |
94 | |
95 TestServiceProvider::TestServiceProvider() { | |
96 } | |
97 | |
98 ApiTestBase::ApiTestBase() { | |
99 } | |
100 ApiTestBase::~ApiTestBase() { | |
101 } | |
102 | |
103 void ApiTestBase::SetUp() { | |
104 ModuleSystemTest::SetUp(); | |
105 service_provider_ = TestServiceProvider::Create(env()->isolate()); | |
106 InitializeEnvironment(); | |
107 RegisterModules(); | |
108 } | |
109 | |
110 void ApiTestBase::RegisterModules() { | |
111 v8_schema_registry_.reset(new V8SchemaRegistry); | |
112 env()->RegisterModule("json_schema", IDR_JSON_SCHEMA_JS); | |
not at google - send to devlin
2014/07/18 15:09:13
shame to need to do all of this, since it means th
Sam McNally
2014/07/21 03:56:27
Done.
| |
113 env()->RegisterModule("lastError", IDR_LAST_ERROR_JS); | |
114 env()->RegisterModule(kEventBindings, IDR_EVENT_BINDINGS_JS); | |
115 env()->RegisterModule("schemaUtils", IDR_SCHEMA_UTILS_JS); | |
116 env()->RegisterModule("sendRequest", IDR_SEND_REQUEST_JS); | |
117 env()->RegisterModule("uncaught_exception_handler", | |
118 IDR_UNCAUGHT_EXCEPTION_HANDLER_JS); | |
119 env()->RegisterModule("unload_event", IDR_UNLOAD_EVENT_JS); | |
120 env()->RegisterModule("utils", IDR_UTILS_JS); | |
121 env()->RegisterModule("binding", IDR_BINDING_JS); | |
122 env()->module_system()->RegisterNativeHandler( | |
123 "logging", | |
124 scoped_ptr<NativeHandler>(new LoggingNativeHandler(env()->context()))); | |
125 env()->module_system()->RegisterNativeHandler( | |
126 "schema_registry", v8_schema_registry_->AsNativeHandler()); | |
127 env()->module_system()->RegisterNativeHandler( | |
128 "utils", | |
129 scoped_ptr<NativeHandler>(new UtilsNativeHandler(env()->context()))); | |
130 env()->module_system()->RegisterNativeHandler( | |
131 "sendRequest", | |
132 scoped_ptr<NativeHandler>( | |
133 new SendRequestNatives(NULL, env()->context()))); | |
134 env()->RegisterTestFile("test", "test_unittest_custom_bindings.js"); | |
135 | |
136 env()->OverrideNativeHandler( | |
137 "v8_context", | |
138 "exports.GetAvailability = function() { return {is_available: true}; };"); | |
139 env()->OverrideNativeHandler("activityLogger", | |
140 "exports.LogAPICall = function() {};"); | |
141 env()->OverrideNativeHandler( | |
142 "process", | |
143 "exports.GetContextType = function() { return 'BLESSED_EXTENSION'; };" | |
144 "exports.GetExtensionId = function() { return 'id'; };" | |
145 "exports.GetManifestVersion = function() { return 2 };"); | |
146 env()->OverrideNativeHandler( | |
147 "event_natives", | |
148 "exports.AttachEvent = function() {};" | |
149 "exports.DetachEvent = function() {};" | |
150 "exports.AttachFilteredEvent = function() {};" | |
151 "exports.AttachFilteredEvent = function() {};" | |
152 "exports.MatchAgainstEventFilter = function() { return [] };"); | |
153 | |
154 env()->RegisterModule(mojo::kCodecModuleName, IDR_MOJO_CODEC_JS); | |
155 env()->RegisterModule(mojo::kConnectionModuleName, IDR_MOJO_CONNECTION_JS); | |
156 env()->RegisterModule(mojo::kConnectorModuleName, IDR_MOJO_CONNECTOR_JS); | |
157 env()->RegisterModule(mojo::kRouterModuleName, IDR_MOJO_ROUTER_JS); | |
158 env()->RegisterModule(mojo::kUnicodeModuleName, IDR_MOJO_UNICODE_JS); | |
159 gin::ModuleRegistry::From(env()->context()->v8_context()) | |
160 ->AddBuiltinModule(env()->isolate(), | |
161 mojo::js::Core::kModuleName, | |
162 mojo::js::Core::GetModule(env()->isolate())); | |
163 gin::ModuleRegistry::From(env()->context()->v8_context()) | |
164 ->AddBuiltinModule(env()->isolate(), | |
165 mojo::js::Support::kModuleName, | |
166 mojo::js::Support::GetModule(env()->isolate())); | |
167 gin::ModuleRegistry::From(env()->context()->v8_context()) | |
168 ->AddBuiltinModule(env()->isolate(), | |
169 "content/public/renderer/service_provider", | |
170 service_provider_.ToV8()); | |
171 gin::ModuleRegistry::From(env()->context()->v8_context())->AddBuiltinModule( | |
172 env()->isolate(), | |
173 "testNatives", | |
174 TestNatives::Create(env()->isolate(), &run_loop_).ToV8()); | |
175 } | |
176 | |
177 void ApiTestBase::InitializeEnvironment() { | |
178 gin::Dictionary global(env()->isolate(), | |
179 env()->context()->v8_context()->Global()); | |
180 gin::Dictionary navigator(gin::Dictionary::CreateEmpty(env()->isolate())); | |
181 navigator.Set("appVersion", base::StringPiece("")); | |
182 global.Set("navigator", navigator); | |
183 gin::Dictionary chrome(gin::Dictionary::CreateEmpty(env()->isolate())); | |
184 global.Set("chrome", chrome); | |
185 gin::Dictionary extension(gin::Dictionary::CreateEmpty(env()->isolate())); | |
186 chrome.Set("extension", extension); | |
187 gin::Dictionary runtime(gin::Dictionary::CreateEmpty(env()->isolate())); | |
188 chrome.Set("runtime", runtime); | |
189 } | |
190 | |
191 void ApiTestBase::RunTest(const std::string& file_name, | |
192 const std::string& test_name) { | |
193 env()->RegisterTestFile("testBody", file_name); | |
194 ExpectNoAssertionsMade(); | |
195 base::MessageLoop::current()->PostTask( | |
196 FROM_HERE, | |
197 base::Bind( | |
198 &ApiTestBase::RunTestInner, base::Unretained(this), test_name)); | |
199 base::MessageLoop::current()->PostTask( | |
200 FROM_HERE, | |
201 base::Bind(&ApiTestBase::RunPromisesAgain, base::Unretained(this))); | |
202 run_loop_.Run(); | |
203 } | |
204 | |
205 void ApiTestBase::RunTestInner(const std::string& test_name) { | |
206 v8::HandleScope scope(env()->isolate()); | |
207 ModuleSystem::NativesEnabledScope natives_enabled(env()->module_system()); | |
208 v8::Handle<v8::Value> result = | |
209 env()->module_system()->CallModuleMethod("testBody", test_name); | |
210 if (!result->IsTrue()) { | |
211 run_loop_.Quit(); | |
212 FAIL() << "Failed to run test \"" << test_name << "\""; | |
213 } | |
214 } | |
215 | |
216 void ApiTestBase::RunPromisesAgain() { | |
217 RunResolvedPromises(); | |
218 base::MessageLoop::current()->PostTask( | |
219 FROM_HERE, | |
220 base::Bind(&ApiTestBase::RunPromisesAgain, base::Unretained(this))); | |
221 } | |
222 | |
223 } // namespace extensions | |
OLD | NEW |