Introduce ProfilerMetricsProvider
[chromium-blink-merge.git] / chrome / browser / devtools / devtools_target_impl.cc
blobeb32924dc8ca644b1dbc2741b8ac38f3199efe13
1 // Copyright 2013 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 "chrome/browser/devtools/devtools_target_impl.h"
7 #include "base/strings/stringprintf.h"
8 #include "base/strings/utf_string_conversions.h"
9 #include "chrome/browser/devtools/devtools_window.h"
10 #include "chrome/browser/extensions/extension_service.h"
11 #include "chrome/browser/extensions/extension_tab_util.h"
12 #include "chrome/browser/guest_view/guest_view_base.h"
13 #include "chrome/browser/profiles/profile.h"
14 #include "chrome/browser/ui/tab_contents/tab_contents_iterator.h"
15 #include "chrome/browser/ui/webui/extensions/extension_icon_source.h"
16 #include "chrome/common/extensions/extension_constants.h"
17 #include "content/public/browser/browser_thread.h"
18 #include "content/public/browser/favicon_status.h"
19 #include "content/public/browser/navigation_entry.h"
20 #include "content/public/browser/render_frame_host.h"
21 #include "content/public/browser/render_view_host.h"
22 #include "content/public/browser/web_contents.h"
23 #include "extensions/browser/extension_host.h"
24 #include "extensions/browser/extension_system.h"
25 #include "extensions/common/constants.h"
27 using content::BrowserThread;
28 using content::DevToolsAgentHost;
29 using content::RenderViewHost;
30 using content::WebContents;
31 using content::WorkerService;
33 namespace {
35 const char kTargetTypeApp[] = "app";
36 const char kTargetTypeBackgroundPage[] = "background_page";
37 const char kTargetTypePage[] = "page";
38 const char kTargetTypeWorker[] = "worker";
39 const char kTargetTypeWebView[] = "webview";
40 const char kTargetTypeIFrame[] = "iframe";
41 const char kTargetTypeOther[] = "other";
43 // RenderViewHostTarget --------------------------------------------------------
45 class RenderViewHostTarget : public DevToolsTargetImpl {
46 public:
47 explicit RenderViewHostTarget(RenderViewHost* rvh, bool is_tab);
49 // DevToolsTargetImpl overrides:
50 virtual bool Activate() const OVERRIDE;
51 virtual bool Close() const OVERRIDE;
52 virtual RenderViewHost* GetRenderViewHost() const OVERRIDE;
53 virtual int GetTabId() const OVERRIDE;
54 virtual std::string GetExtensionId() const OVERRIDE;
55 virtual void Inspect(Profile* profile) const OVERRIDE;
57 private:
58 int tab_id_;
59 std::string extension_id_;
62 RenderViewHostTarget::RenderViewHostTarget(RenderViewHost* rvh, bool is_tab)
63 : DevToolsTargetImpl(DevToolsAgentHost::GetOrCreateFor(rvh)),
64 tab_id_(-1) {
65 set_type(kTargetTypeOther);
66 WebContents* web_contents = WebContents::FromRenderViewHost(rvh);
67 if (!web_contents)
68 return; // Orphan RVH will show up with no title/url/icon in clients.
70 content::RenderFrameHost* rfh = rvh->GetMainFrame();
71 if (rfh->IsCrossProcessSubframe()) {
72 set_url(rfh->GetLastCommittedURL());
73 set_type(kTargetTypeIFrame);
74 // TODO(kaznacheev) Try setting the title when the frame navigation
75 // refactoring is done.
76 RenderViewHost* parent_rvh = rfh->GetParent()->GetRenderViewHost();
77 set_parent_id(DevToolsAgentHost::GetOrCreateFor(parent_rvh)->GetId());
78 return;
81 set_title(base::UTF16ToUTF8(web_contents->GetTitle()));
82 set_url(web_contents->GetURL());
83 content::NavigationController& controller = web_contents->GetController();
84 content::NavigationEntry* entry = controller.GetActiveEntry();
85 if (entry != NULL && entry->GetURL().is_valid())
86 set_favicon_url(entry->GetFavicon().url);
87 set_last_activity_time(web_contents->GetLastActiveTime());
89 GuestViewBase* guest = GuestViewBase::FromWebContents(web_contents);
90 if (guest) {
91 set_type(kTargetTypeWebView);
92 RenderViewHost* parent_rvh =
93 guest->embedder_web_contents()->GetRenderViewHost();
94 set_parent_id(DevToolsAgentHost::GetOrCreateFor(parent_rvh)->GetId());
95 return;
98 if (is_tab) {
99 set_type(kTargetTypePage);
100 tab_id_ = extensions::ExtensionTabUtil::GetTabId(web_contents);
101 } else {
102 Profile* profile =
103 Profile::FromBrowserContext(web_contents->GetBrowserContext());
104 if (profile) {
105 ExtensionService* extension_service = profile->GetExtensionService();
106 const extensions::Extension* extension = extension_service->
107 extensions()->GetByID(GetURL().host());
108 if (extension) {
109 set_title(extension->name());
110 extensions::ExtensionHost* extension_host =
111 extensions::ExtensionSystem::Get(profile)->process_manager()->
112 GetBackgroundHostForExtension(extension->id());
113 if (extension_host &&
114 extension_host->host_contents() == web_contents) {
115 set_type(kTargetTypeBackgroundPage);
116 extension_id_ = extension->id();
117 } else if (extension->is_hosted_app()
118 || extension->is_legacy_packaged_app()
119 || extension->is_platform_app()) {
120 set_type(kTargetTypeApp);
122 set_favicon_url(extensions::ExtensionIconSource::GetIconURL(
123 extension, extension_misc::EXTENSION_ICON_SMALLISH,
124 ExtensionIconSet::MATCH_BIGGER, false, NULL));
130 bool RenderViewHostTarget::Activate() const {
131 RenderViewHost* rvh = GetRenderViewHost();
132 if (!rvh)
133 return false;
134 WebContents* web_contents = WebContents::FromRenderViewHost(rvh);
135 if (!web_contents)
136 return false;
137 web_contents->GetDelegate()->ActivateContents(web_contents);
138 return true;
141 bool RenderViewHostTarget::Close() const {
142 RenderViewHost* rvh = GetRenderViewHost();
143 if (!rvh)
144 return false;
145 rvh->ClosePage();
146 return true;
149 RenderViewHost* RenderViewHostTarget::GetRenderViewHost() const {
150 return GetAgentHost()->GetRenderViewHost();
153 int RenderViewHostTarget::GetTabId() const {
154 return tab_id_;
157 std::string RenderViewHostTarget::GetExtensionId() const {
158 return extension_id_;
161 void RenderViewHostTarget::Inspect(Profile* profile) const {
162 RenderViewHost* rvh = GetRenderViewHost();
163 if (!rvh)
164 return;
165 DevToolsWindow::OpenDevToolsWindow(rvh);
168 // WorkerTarget ----------------------------------------------------------------
170 class WorkerTarget : public DevToolsTargetImpl {
171 public:
172 explicit WorkerTarget(const WorkerService::WorkerInfo& worker_info);
174 // content::DevToolsTarget overrides:
175 virtual bool Close() const OVERRIDE;
177 // DevToolsTargetImpl overrides:
178 virtual void Inspect(Profile* profile) const OVERRIDE;
180 private:
181 int process_id_;
182 int route_id_;
185 WorkerTarget::WorkerTarget(const WorkerService::WorkerInfo& worker)
186 : DevToolsTargetImpl(DevToolsAgentHost::GetForWorker(worker.process_id,
187 worker.route_id)) {
188 set_type(kTargetTypeWorker);
189 set_title(base::UTF16ToUTF8(worker.name));
190 set_description(base::StringPrintf("Worker pid:%d",
191 base::GetProcId(worker.handle)));
192 set_url(worker.url);
194 process_id_ = worker.process_id;
195 route_id_ = worker.route_id;
198 static void TerminateWorker(int process_id, int route_id) {
199 WorkerService::GetInstance()->TerminateWorker(process_id, route_id);
202 bool WorkerTarget::Close() const {
203 content::BrowserThread::PostTask(content::BrowserThread::IO, FROM_HERE,
204 base::Bind(&TerminateWorker, process_id_, route_id_));
205 return true;
208 void WorkerTarget::Inspect(Profile* profile) const {
209 DevToolsWindow::OpenDevToolsWindowForWorker(profile, GetAgentHost());
212 } // namespace
214 // DevToolsTargetImpl ----------------------------------------------------------
216 DevToolsTargetImpl::~DevToolsTargetImpl() {
219 DevToolsTargetImpl::DevToolsTargetImpl(
220 scoped_refptr<DevToolsAgentHost> agent_host)
221 : agent_host_(agent_host) {
224 std::string DevToolsTargetImpl::GetParentId() const {
225 return parent_id_;
228 std::string DevToolsTargetImpl::GetId() const {
229 return agent_host_->GetId();
232 std::string DevToolsTargetImpl::GetType() const {
233 return type_;
236 std::string DevToolsTargetImpl::GetTitle() const {
237 return title_;
240 std::string DevToolsTargetImpl::GetDescription() const {
241 return description_;
244 GURL DevToolsTargetImpl::GetURL() const {
245 return url_;
248 GURL DevToolsTargetImpl::GetFaviconURL() const {
249 return favicon_url_;
252 base::TimeTicks DevToolsTargetImpl::GetLastActivityTime() const {
253 return last_activity_time_;
256 scoped_refptr<content::DevToolsAgentHost>
257 DevToolsTargetImpl::GetAgentHost() const {
258 return agent_host_;
261 bool DevToolsTargetImpl::IsAttached() const {
262 return agent_host_->IsAttached();
265 bool DevToolsTargetImpl::Activate() const {
266 return false;
269 bool DevToolsTargetImpl::Close() const {
270 return false;
273 int DevToolsTargetImpl::GetTabId() const {
274 return -1;
277 RenderViewHost* DevToolsTargetImpl::GetRenderViewHost() const {
278 return NULL;
281 std::string DevToolsTargetImpl::GetExtensionId() const {
282 return std::string();
285 void DevToolsTargetImpl::Inspect(Profile*) const {
288 void DevToolsTargetImpl::Reload() const {
291 // static
292 scoped_ptr<DevToolsTargetImpl> DevToolsTargetImpl::CreateForRenderViewHost(
293 content::RenderViewHost* rvh, bool is_tab) {
294 return scoped_ptr<DevToolsTargetImpl>(new RenderViewHostTarget(rvh, is_tab));
297 // static
298 DevToolsTargetImpl::List DevToolsTargetImpl::EnumerateRenderViewHostTargets() {
299 std::set<RenderViewHost*> tab_rvhs;
300 for (TabContentsIterator it; !it.done(); it.Next())
301 tab_rvhs.insert(it->GetRenderViewHost());
303 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
304 DevToolsTargetImpl::List result;
305 std::vector<RenderViewHost*> rvh_list =
306 content::DevToolsAgentHost::GetValidRenderViewHosts();
307 for (std::vector<RenderViewHost*>::iterator it = rvh_list.begin();
308 it != rvh_list.end(); ++it) {
309 bool is_tab = tab_rvhs.find(*it) != tab_rvhs.end();
310 result.push_back(new RenderViewHostTarget(*it, is_tab));
312 return result;
315 static void CreateWorkerTargets(
316 const std::vector<WorkerService::WorkerInfo>& worker_info,
317 DevToolsTargetImpl::Callback callback) {
318 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
319 DevToolsTargetImpl::List result;
320 for (size_t i = 0; i < worker_info.size(); ++i) {
321 result.push_back(new WorkerTarget(worker_info[i]));
323 callback.Run(result);
326 // static
327 void DevToolsTargetImpl::EnumerateWorkerTargets(Callback callback) {
328 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO));
329 content::BrowserThread::PostTask(
330 content::BrowserThread::UI,
331 FROM_HERE,
332 base::Bind(&CreateWorkerTargets,
333 WorkerService::GetInstance()->GetWorkers(),
334 callback));
337 static void CollectAllTargets(
338 DevToolsTargetImpl::Callback callback,
339 const DevToolsTargetImpl::List& worker_targets) {
340 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
341 DevToolsTargetImpl::List result =
342 DevToolsTargetImpl::EnumerateRenderViewHostTargets();
343 result.insert(result.begin(), worker_targets.begin(), worker_targets.end());
344 callback.Run(result);
347 // static
348 void DevToolsTargetImpl::EnumerateAllTargets(Callback callback) {
349 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
350 content::BrowserThread::PostTask(
351 content::BrowserThread::IO,
352 FROM_HERE,
353 base::Bind(&DevToolsTargetImpl::EnumerateWorkerTargets,
354 base::Bind(&CollectAllTargets, callback)));