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.
5 #include "content/browser/devtools/embedded_worker_devtools_manager.h"
7 #include "base/memory/scoped_ptr.h"
8 #include "base/message_loop/message_loop.h"
9 #include "base/run_loop.h"
10 #include "content/browser/browser_thread_impl.h"
11 #include "content/browser/devtools/devtools_agent_host_impl.h"
12 #include "content/browser/devtools/embedded_worker_devtools_agent_host.h"
13 #include "content/browser/shared_worker/shared_worker_instance.h"
14 #include "content/browser/shared_worker/worker_storage_partition.h"
15 #include "content/public/test/test_browser_context.h"
16 #include "testing/gtest/include/gtest/gtest.h"
21 class TestDevToolsClientHost : public DevToolsAgentHostClient {
23 TestDevToolsClientHost() {}
24 virtual ~TestDevToolsClientHost() {}
25 virtual void DispatchProtocolMessage(
26 DevToolsAgentHost* agent_host, const std::string& message) OVERRIDE {}
27 virtual void AgentHostClosed(
28 DevToolsAgentHost* agent_host, bool replaced) OVERRIDE {}
30 void InspectAgentHost(DevToolsAgentHost* agent_host) {
31 if (agent_host_.get())
32 agent_host_->DetachClient();
33 agent_host_ = agent_host;
34 if (agent_host_.get())
35 agent_host_->AttachClient(this);
38 scoped_refptr<DevToolsAgentHost> agent_host_;
39 DISALLOW_COPY_AND_ASSIGN(TestDevToolsClientHost);
43 class EmbeddedWorkerDevToolsManagerTest : public testing::Test {
45 typedef EmbeddedWorkerDevToolsAgentHost::WorkerState WorkerState;
47 EmbeddedWorkerDevToolsManagerTest()
48 : ui_thread_(BrowserThread::UI, &message_loop_),
49 browser_context_(new TestBrowserContext()),
51 new WorkerStoragePartition(browser_context_->GetRequestContext(),
59 partition_id_(*partition_.get()) {}
62 virtual void SetUp() OVERRIDE {
63 manager_ = EmbeddedWorkerDevToolsManager::GetInstance();
65 virtual void TearDown() OVERRIDE {
66 EmbeddedWorkerDevToolsManager::GetInstance()->ResetForTesting();
69 void CheckWorkerState(int worker_process_id,
72 const EmbeddedWorkerDevToolsManager::WorkerId id(worker_process_id,
74 EmbeddedWorkerDevToolsManager::AgentHostMap::iterator it =
75 manager_->workers_.find(id);
76 EXPECT_TRUE(manager_->workers_.end() != it);
77 EXPECT_EQ(state, it->second->state_);
80 void CheckWorkerNotExist(int worker_process_id, int worker_route_id) {
81 const EmbeddedWorkerDevToolsManager::WorkerId id(worker_process_id,
83 EXPECT_TRUE(manager_->workers_.end() == manager_->workers_.find(id));
86 void CheckWorkerCount(size_t size) {
87 EXPECT_EQ(size, manager_->workers_.size());
90 base::MessageLoopForIO message_loop_;
91 BrowserThreadImpl ui_thread_;
92 scoped_ptr<TestBrowserContext> browser_context_;
93 scoped_ptr<WorkerStoragePartition> partition_;
94 const WorkerStoragePartitionId partition_id_;
95 EmbeddedWorkerDevToolsManager* manager_;
98 TEST_F(EmbeddedWorkerDevToolsManagerTest, BasicTest) {
99 scoped_refptr<DevToolsAgentHostImpl> agent_host;
101 SharedWorkerInstance instance1(GURL("http://example.com/w.js"),
104 blink::WebContentSecurityPolicyTypeReport,
105 browser_context_->GetResourceContext(),
108 agent_host = manager_->GetDevToolsAgentHostForWorker(1, 1);
109 EXPECT_FALSE(agent_host.get());
111 // Created -> Started -> Destroyed
112 CheckWorkerNotExist(1, 1);
113 manager_->SharedWorkerCreated(1, 1, instance1);
114 CheckWorkerState(1, 1, WorkerState::WORKER_UNINSPECTED);
115 manager_->WorkerReadyForInspection(1, 1);
116 CheckWorkerState(1, 1, WorkerState::WORKER_UNINSPECTED);
117 manager_->WorkerContextStarted(1, 1);
118 CheckWorkerState(1, 1, WorkerState::WORKER_UNINSPECTED);
119 manager_->WorkerDestroyed(1, 1);
120 CheckWorkerNotExist(1, 1);
122 // Created -> GetDevToolsAgentHost -> Started -> Destroyed
123 CheckWorkerNotExist(1, 2);
124 manager_->SharedWorkerCreated(1, 2, instance1);
125 CheckWorkerState(1, 2, WorkerState::WORKER_UNINSPECTED);
126 agent_host = manager_->GetDevToolsAgentHostForWorker(1, 2);
127 EXPECT_TRUE(agent_host.get());
128 CheckWorkerState(1, 2, WorkerState::WORKER_UNINSPECTED);
129 EXPECT_EQ(agent_host.get(), manager_->GetDevToolsAgentHostForWorker(1, 2));
130 manager_->WorkerReadyForInspection(1, 2);
131 CheckWorkerState(1, 2, WorkerState::WORKER_UNINSPECTED);
132 manager_->WorkerContextStarted(1, 2);
133 CheckWorkerState(1, 2, WorkerState::WORKER_UNINSPECTED);
134 manager_->WorkerDestroyed(1, 2);
135 CheckWorkerState(1, 2, WorkerState::WORKER_TERMINATED);
137 CheckWorkerNotExist(1, 2);
139 // Created -> Started -> GetDevToolsAgentHost -> Destroyed
140 CheckWorkerNotExist(1, 3);
141 manager_->SharedWorkerCreated(1, 3, instance1);
142 CheckWorkerState(1, 3, WorkerState::WORKER_UNINSPECTED);
143 manager_->WorkerReadyForInspection(1, 3);
144 CheckWorkerState(1, 3, WorkerState::WORKER_UNINSPECTED);
145 manager_->WorkerContextStarted(1, 3);
146 CheckWorkerState(1, 3, WorkerState::WORKER_UNINSPECTED);
147 agent_host = manager_->GetDevToolsAgentHostForWorker(1, 3);
148 EXPECT_TRUE(agent_host.get());
149 CheckWorkerState(1, 3, WorkerState::WORKER_UNINSPECTED);
150 manager_->WorkerDestroyed(1, 3);
151 CheckWorkerState(1, 3, WorkerState::WORKER_TERMINATED);
153 CheckWorkerNotExist(1, 3);
155 // Created -> Destroyed
156 CheckWorkerNotExist(1, 4);
157 manager_->SharedWorkerCreated(1, 4, instance1);
158 CheckWorkerState(1, 4, WorkerState::WORKER_UNINSPECTED);
159 manager_->WorkerDestroyed(1, 4);
160 CheckWorkerNotExist(1, 4);
162 // Created -> GetDevToolsAgentHost -> Destroyed
163 CheckWorkerNotExist(1, 5);
164 manager_->SharedWorkerCreated(1, 5, instance1);
165 CheckWorkerState(1, 5, WorkerState::WORKER_UNINSPECTED);
166 agent_host = manager_->GetDevToolsAgentHostForWorker(1, 5);
167 EXPECT_TRUE(agent_host.get());
168 CheckWorkerState(1, 5, WorkerState::WORKER_UNINSPECTED);
169 manager_->WorkerDestroyed(1, 5);
170 CheckWorkerState(1, 5, WorkerState::WORKER_TERMINATED);
172 CheckWorkerNotExist(1, 5);
174 // Created -> GetDevToolsAgentHost -> Free agent_host -> Destroyed
175 CheckWorkerNotExist(1, 6);
176 manager_->SharedWorkerCreated(1, 6, instance1);
177 CheckWorkerState(1, 6, WorkerState::WORKER_UNINSPECTED);
178 agent_host = manager_->GetDevToolsAgentHostForWorker(1, 6);
179 EXPECT_TRUE(agent_host.get());
180 CheckWorkerState(1, 6, WorkerState::WORKER_UNINSPECTED);
182 manager_->WorkerDestroyed(1, 6);
183 CheckWorkerNotExist(1, 6);
186 TEST_F(EmbeddedWorkerDevToolsManagerTest, AttachTest) {
187 scoped_refptr<DevToolsAgentHostImpl> agent_host1;
188 scoped_refptr<DevToolsAgentHostImpl> agent_host2;
190 SharedWorkerInstance instance1(GURL("http://example.com/w1.js"),
193 blink::WebContentSecurityPolicyTypeReport,
194 browser_context_->GetResourceContext(),
196 SharedWorkerInstance instance2(GURL("http://example.com/w2.js"),
199 blink::WebContentSecurityPolicyTypeReport,
200 browser_context_->GetResourceContext(),
203 // Created -> GetDevToolsAgentHost -> Register -> Started -> Destroyed
204 scoped_ptr<TestDevToolsClientHost> client_host1(new TestDevToolsClientHost());
205 CheckWorkerNotExist(2, 1);
206 manager_->SharedWorkerCreated(2, 1, instance1);
207 CheckWorkerState(2, 1, WorkerState::WORKER_UNINSPECTED);
208 agent_host1 = manager_->GetDevToolsAgentHostForWorker(2, 1);
209 EXPECT_TRUE(agent_host1.get());
210 CheckWorkerState(2, 1, WorkerState::WORKER_UNINSPECTED);
211 EXPECT_EQ(agent_host1.get(), manager_->GetDevToolsAgentHostForWorker(2, 1));
212 client_host1->InspectAgentHost(agent_host1.get());
213 CheckWorkerState(2, 1, WorkerState::WORKER_INSPECTED);
214 manager_->WorkerReadyForInspection(2, 1);
215 CheckWorkerState(2, 1, WorkerState::WORKER_INSPECTED);
216 manager_->WorkerContextStarted(2, 1);
217 CheckWorkerState(2, 1, WorkerState::WORKER_INSPECTED);
218 manager_->WorkerDestroyed(2, 1);
219 CheckWorkerState(2, 1, WorkerState::WORKER_TERMINATED);
220 EXPECT_EQ(agent_host1.get(), manager_->GetDevToolsAgentHostForWorker(2, 1));
222 // Created -> Started -> GetDevToolsAgentHost -> Register -> Destroyed
223 scoped_ptr<TestDevToolsClientHost> client_host2(new TestDevToolsClientHost());
224 manager_->SharedWorkerCreated(2, 2, instance2);
225 CheckWorkerState(2, 2, WorkerState::WORKER_UNINSPECTED);
226 manager_->WorkerReadyForInspection(2, 2);
227 CheckWorkerState(2, 2, WorkerState::WORKER_UNINSPECTED);
228 manager_->WorkerContextStarted(2, 2);
229 CheckWorkerState(2, 2, WorkerState::WORKER_UNINSPECTED);
230 agent_host2 = manager_->GetDevToolsAgentHostForWorker(2, 2);
231 EXPECT_TRUE(agent_host2.get());
232 EXPECT_NE(agent_host1.get(), agent_host2.get());
233 EXPECT_EQ(agent_host2.get(), manager_->GetDevToolsAgentHostForWorker(2, 2));
234 CheckWorkerState(2, 2, WorkerState::WORKER_UNINSPECTED);
235 client_host2->InspectAgentHost(agent_host2.get());
236 CheckWorkerState(2, 2, WorkerState::WORKER_INSPECTED);
237 manager_->WorkerDestroyed(2, 2);
238 CheckWorkerState(2, 2, WorkerState::WORKER_TERMINATED);
239 EXPECT_EQ(agent_host2.get(), manager_->GetDevToolsAgentHostForWorker(2, 2));
241 // Re-created -> Started -> ClientHostClosing -> Destroyed
242 CheckWorkerState(2, 1, WorkerState::WORKER_TERMINATED);
243 manager_->SharedWorkerCreated(2, 3, instance1);
244 CheckWorkerNotExist(2, 1);
245 CheckWorkerState(2, 3, WorkerState::WORKER_PAUSED_FOR_REATTACH);
246 EXPECT_EQ(agent_host1.get(), manager_->GetDevToolsAgentHostForWorker(2, 3));
247 manager_->WorkerReadyForInspection(2, 3);
248 CheckWorkerState(2, 3, WorkerState::WORKER_INSPECTED);
249 manager_->WorkerContextStarted(2, 3);
250 CheckWorkerState(2, 3, WorkerState::WORKER_INSPECTED);
251 client_host1->InspectAgentHost(NULL);
252 manager_->WorkerDestroyed(2, 3);
253 CheckWorkerState(2, 3, WorkerState::WORKER_TERMINATED);
255 CheckWorkerNotExist(2, 3);
257 // Re-created -> Destroyed
258 CheckWorkerState(2, 2, WorkerState::WORKER_TERMINATED);
259 manager_->SharedWorkerCreated(2, 4, instance2);
260 CheckWorkerNotExist(2, 2);
261 CheckWorkerState(2, 4, WorkerState::WORKER_PAUSED_FOR_REATTACH);
262 EXPECT_EQ(agent_host2.get(), manager_->GetDevToolsAgentHostForWorker(2, 4));
263 manager_->WorkerDestroyed(2, 4);
264 CheckWorkerNotExist(2, 2);
265 CheckWorkerState(2, 4, WorkerState::WORKER_TERMINATED);
267 // Re-created -> ClientHostClosing -> Destroyed
268 manager_->SharedWorkerCreated(2, 5, instance2);
269 CheckWorkerNotExist(2, 2);
270 CheckWorkerState(2, 5, WorkerState::WORKER_PAUSED_FOR_REATTACH);
271 EXPECT_EQ(agent_host2.get(), manager_->GetDevToolsAgentHostForWorker(2, 5));
272 client_host2->InspectAgentHost(NULL);
276 manager_->WorkerDestroyed(2, 5);
280 TEST_F(EmbeddedWorkerDevToolsManagerTest, ReattachTest) {
281 SharedWorkerInstance instance(GURL("http://example.com/w3.js"),
284 blink::WebContentSecurityPolicyTypeReport,
285 browser_context_->GetResourceContext(),
287 scoped_ptr<TestDevToolsClientHost> client_host(new TestDevToolsClientHost());
288 // Created -> GetDevToolsAgentHost -> Register -> Destroyed
289 manager_->SharedWorkerCreated(3, 1, instance);
290 CheckWorkerState(3, 1, WorkerState::WORKER_UNINSPECTED);
291 scoped_refptr<DevToolsAgentHost> agent_host(
292 manager_->GetDevToolsAgentHostForWorker(3, 1));
293 EXPECT_TRUE(agent_host.get());
294 CheckWorkerState(3, 1, WorkerState::WORKER_UNINSPECTED);
295 client_host->InspectAgentHost(agent_host.get());
296 CheckWorkerState(3, 1, WorkerState::WORKER_INSPECTED);
297 manager_->WorkerDestroyed(3, 1);
298 CheckWorkerState(3, 1, WorkerState::WORKER_TERMINATED);
299 // ClientHostClosing -> Re-created -> release agent_host -> Destroyed
300 client_host->InspectAgentHost(NULL);
301 CheckWorkerState(3, 1, WorkerState::WORKER_TERMINATED);
302 manager_->SharedWorkerCreated(3, 2, instance);
303 CheckWorkerState(3, 2, WorkerState::WORKER_UNINSPECTED);
305 CheckWorkerState(3, 2, WorkerState::WORKER_UNINSPECTED);
306 manager_->WorkerDestroyed(3, 2);
307 CheckWorkerNotExist(3, 2);
311 } // namespace content