1// Copyright (c) 2012 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 "chrome/browser/ui/uma_browsing_activity_observer.h" 6 7#include "base/metrics/histogram.h" 8#include "chrome/browser/chrome_notification_types.h" 9#include "chrome/browser/search_engines/template_url_service.h" 10#include "chrome/browser/search_engines/template_url_service_factory.h" 11#include "chrome/browser/ui/browser.h" 12#include "chrome/browser/ui/browser_finder.h" 13#include "chrome/browser/ui/browser_iterator.h" 14#include "chrome/browser/ui/browser_window.h" 15#include "chrome/browser/ui/tabs/tab_strip_model.h" 16#include "content/public/browser/navigation_controller.h" 17#include "content/public/browser/navigation_details.h" 18#include "content/public/browser/navigation_entry.h" 19#include "content/public/browser/notification_service.h" 20#include "content/public/browser/render_process_host.h" 21#include "content/public/browser/user_metrics.h" 22 23namespace chrome { 24namespace { 25 26UMABrowsingActivityObserver* g_instance = NULL; 27 28} // namespace 29 30// static 31void UMABrowsingActivityObserver::Init() { 32 DCHECK(!g_instance); 33 // Must be created before any Browsers are. 34 DCHECK_EQ(0U, chrome::GetTotalBrowserCount()); 35 g_instance = new UMABrowsingActivityObserver; 36} 37 38UMABrowsingActivityObserver::UMABrowsingActivityObserver() { 39 registrar_.Add(this, content::NOTIFICATION_NAV_ENTRY_COMMITTED, 40 content::NotificationService::AllSources()); 41 registrar_.Add(this, chrome::NOTIFICATION_APP_TERMINATING, 42 content::NotificationService::AllSources()); 43} 44 45UMABrowsingActivityObserver::~UMABrowsingActivityObserver() { 46} 47 48void UMABrowsingActivityObserver::Observe( 49 int type, 50 const content::NotificationSource& source, 51 const content::NotificationDetails& details) { 52 if (type == content::NOTIFICATION_NAV_ENTRY_COMMITTED) { 53 const content::LoadCommittedDetails load = 54 *content::Details<content::LoadCommittedDetails>(details).ptr(); 55 56 content::NavigationController* controller = 57 content::Source<content::NavigationController>(source).ptr(); 58 // Track whether the page loaded is a search results page (SRP). Track 59 // the non-SRP navigations as well so there is a control. 60 content::RecordAction(content::UserMetricsAction("NavEntryCommitted")); 61 // Attempting to determine the cause of a crash originating from 62 // IsSearchResultsPageFromDefaultSearchProvider but manifesting in 63 // TemplateURLRef::ExtractSearchTermsFromURL(...). 64 // See http://crbug.com/291348. 65 CHECK(load.entry); 66 if (TemplateURLServiceFactory::GetForProfile( 67 Profile::FromBrowserContext(controller->GetBrowserContext()))-> 68 IsSearchResultsPageFromDefaultSearchProvider( 69 load.entry->GetURL())) { 70 content::RecordAction( 71 content::UserMetricsAction("NavEntryCommitted.SRP")); 72 } 73 74 if (!load.is_navigation_to_different_page()) 75 return; // Don't log for subframes or other trivial types. 76 77 LogRenderProcessHostCount(); 78 LogBrowserTabCount(); 79 } else if (type == chrome::NOTIFICATION_APP_TERMINATING) { 80 delete g_instance; 81 g_instance = NULL; 82 } 83} 84 85void UMABrowsingActivityObserver::LogRenderProcessHostCount() const { 86 int hosts_count = 0; 87 for (content::RenderProcessHost::iterator i( 88 content::RenderProcessHost::AllHostsIterator()); 89 !i.IsAtEnd(); i.Advance()) 90 ++hosts_count; 91 UMA_HISTOGRAM_CUSTOM_COUNTS("MPArch.RPHCountPerLoad", hosts_count, 92 1, 50, 50); 93} 94 95void UMABrowsingActivityObserver::LogBrowserTabCount() const { 96 int tab_count = 0; 97 int app_window_count = 0; 98 int popup_window_count = 0; 99 int tabbed_window_count = 0; 100 for (chrome::BrowserIterator it; !it.done(); it.Next()) { 101 // Record how many tabs each window has open. 102 Browser* browser = *it; 103 UMA_HISTOGRAM_CUSTOM_COUNTS("Tabs.TabCountPerWindow", 104 browser->tab_strip_model()->count(), 105 1, 200, 50); 106 tab_count += browser->tab_strip_model()->count(); 107 108 if (browser->window()->IsActive()) { 109 // Record how many tabs the active window has open. 110 UMA_HISTOGRAM_CUSTOM_COUNTS("Tabs.TabCountActiveWindow", 111 browser->tab_strip_model()->count(), 112 1, 200, 50); 113 } 114 115 if (browser->is_app()) 116 app_window_count++; 117 else if (browser->is_type_popup()) 118 popup_window_count++; 119 else if (browser->is_type_tabbed()) 120 tabbed_window_count++; 121 } 122 // Record how many tabs total are open (across all windows). 123 UMA_HISTOGRAM_CUSTOM_COUNTS("Tabs.TabCountPerLoad", tab_count, 1, 200, 50); 124 125 // Record how many windows are open, by type. 126 UMA_HISTOGRAM_COUNTS_100("WindowManager.AppWindowCountPerLoad", 127 app_window_count); 128 UMA_HISTOGRAM_COUNTS_100("WindowManager.PopUpWindowCountPerLoad", 129 popup_window_count); 130 UMA_HISTOGRAM_COUNTS_100("WindowManager.TabbedWindowCountPerLoad", 131 tabbed_window_count); 132} 133 134} // namespace chrome 135