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

Side by Side Diff: chrome/browser/extensions/navigation_observer.cc

Issue 2621953003: [Extensions] Remove the prompt to re-enable app when visiting its site (Closed)
Patch Set: . Created 3 years, 11 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
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 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 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 "chrome/browser/extensions/navigation_observer.h" 5 #include "chrome/browser/extensions/navigation_observer.h"
6 6
7 #include "base/memory/ptr_util.h" 7 #include "base/memory/ptr_util.h"
8 #include "chrome/browser/extensions/extension_service.h" 8 #include "chrome/browser/extensions/extension_service.h"
9 #include "chrome/browser/profiles/profile.h" 9 #include "chrome/browser/profiles/profile.h"
10 #include "content/public/browser/navigation_controller.h" 10 #include "content/public/browser/navigation_controller.h"
11 #include "content/public/browser/navigation_entry.h" 11 #include "content/public/browser/navigation_entry.h"
12 #include "content/public/browser/notification_service.h" 12 #include "content/public/browser/notification_service.h"
13 #include "content/public/browser/notification_types.h" 13 #include "content/public/browser/notification_types.h"
14 #include "extensions/browser/extension_prefs.h" 14 #include "extensions/browser/extension_prefs.h"
15 #include "extensions/browser/extension_registry.h" 15 #include "extensions/browser/extension_registry.h"
16 #include "extensions/browser/extension_system.h" 16 #include "extensions/browser/extension_system.h"
17 17
18 using content::NavigationController; 18 using content::NavigationController;
19 using content::NavigationEntry; 19 using content::NavigationEntry;
20 20
21 namespace extensions { 21 namespace extensions {
22 22
23 namespace {
24 // Whether to repeatedly prompt for the same extension id.
25 bool g_repeat_prompting = false;
26 }
27
23 NavigationObserver::NavigationObserver(Profile* profile) 28 NavigationObserver::NavigationObserver(Profile* profile)
24 : profile_(profile), 29 : profile_(profile),
25 extension_registry_observer_(this), 30 extension_registry_observer_(this),
26 weak_factory_(this) { 31 weak_factory_(this) {
27 RegisterForNotifications(); 32 RegisterForNotifications();
28 extension_registry_observer_.Add(ExtensionRegistry::Get(profile)); 33 extension_registry_observer_.Add(ExtensionRegistry::Get(profile));
29 } 34 }
30 35
31 NavigationObserver::~NavigationObserver() {} 36 NavigationObserver::~NavigationObserver() {}
32 37
33 void NavigationObserver::Observe(int type, 38 void NavigationObserver::Observe(int type,
34 const content::NotificationSource& source, 39 const content::NotificationSource& source,
35 const content::NotificationDetails& details) { 40 const content::NotificationDetails& details) {
36 DCHECK_EQ(content::NOTIFICATION_NAV_ENTRY_COMMITTED, type); 41 DCHECK_EQ(content::NOTIFICATION_NAV_ENTRY_COMMITTED, type);
37 42
38 NavigationController* controller = 43 NavigationController* controller =
39 content::Source<NavigationController>(source).ptr(); 44 content::Source<NavigationController>(source).ptr();
40 if (!profile_->IsSameProfile( 45 if (!profile_->IsSameProfile(
41 Profile::FromBrowserContext(controller->GetBrowserContext()))) 46 Profile::FromBrowserContext(controller->GetBrowserContext())))
42 return; 47 return;
43 48
44 PromptToEnableExtensionIfNecessary(controller); 49 PromptToEnableExtensionIfNecessary(controller);
45 } 50 }
46 51
52 // static
53 void NavigationObserver::SetAllowedRepeatedPromptingForTesting(bool allowed) {
54 g_repeat_prompting = allowed;
55 }
56
47 void NavigationObserver::RegisterForNotifications() { 57 void NavigationObserver::RegisterForNotifications() {
48 registrar_.Add(this, content::NOTIFICATION_NAV_ENTRY_COMMITTED, 58 registrar_.Add(this, content::NOTIFICATION_NAV_ENTRY_COMMITTED,
49 content::NotificationService::AllSources()); 59 content::NotificationService::AllSources());
50 } 60 }
51 61
52 void NavigationObserver::PromptToEnableExtensionIfNecessary( 62 void NavigationObserver::PromptToEnableExtensionIfNecessary(
53 NavigationController* nav_controller) { 63 NavigationController* nav_controller) {
54 // Bail out if we're already running a prompt. 64 // Bail out if we're already running a prompt.
55 if (!in_progress_prompt_extension_id_.empty()) 65 if (!in_progress_prompt_extension_id_.empty())
56 return; 66 return;
57 67
58 NavigationEntry* nav_entry = nav_controller->GetVisibleEntry(); 68 NavigationEntry* nav_entry = nav_controller->GetVisibleEntry();
59 if (!nav_entry) 69 if (!nav_entry)
60 return; 70 return;
61 71
62 ExtensionRegistry* registry = extensions::ExtensionRegistry::Get(profile_); 72 const GURL& url = nav_entry->GetURL();
63 const Extension* extension = 73 // NOTE: We only consider chrome-extension:// urls, and deliberately don't
64 registry->disabled_extensions().GetExtensionOrAppByURL( 74 // consider hosted app urls. This is because it's really annoying to visit the
65 nav_entry->GetURL()); 75 // site associated with a hosted app (like calendar.google.com or
76 // drive.google.com) and have it repeatedly prompt you to re-enable an item.
77 // Visiting a chrome-extension:// url is a much stronger signal, and, without
78 // the item enabled, we won't show anything.
79 // TODO(devlin): While true, I still wonder how useful this is. We should get
80 // metrics.
81 if (!url.SchemeIs(kExtensionScheme))
82 return;
83
84 const Extension* extension = ExtensionRegistry::Get(profile_)
85 ->disabled_extensions()
86 .GetExtensionOrAppByURL(url);
66 if (!extension) 87 if (!extension)
67 return; 88 return;
68 89
69 // Try not to repeatedly prompt the user about the same extension. 90 // Try not to repeatedly prompt the user about the same extension.
70 if (prompted_extensions_.find(extension->id()) != prompted_extensions_.end()) 91 if (!prompted_extensions_.insert(extension->id()).second &&
92 !g_repeat_prompting) {
71 return; 93 return;
72 prompted_extensions_.insert(extension->id()); 94 }
73 95
74 ExtensionPrefs* extension_prefs = ExtensionPrefs::Get(profile_); 96 ExtensionPrefs* extension_prefs = ExtensionPrefs::Get(profile_);
97 // TODO(devlin): Why do we only consider extensions that escalate permissions?
98 // Maybe because it's the only one we have a good prompt for?
75 if (extension_prefs->DidExtensionEscalatePermissions(extension->id())) { 99 if (extension_prefs->DidExtensionEscalatePermissions(extension->id())) {
76 // Keep track of the extension id and nav controller we're prompting for. 100 // Keep track of the extension id and nav controller we're prompting for.
77 // These must be reset in OnInstallPromptDone. 101 // These must be reset in OnInstallPromptDone.
78 in_progress_prompt_extension_id_ = extension->id(); 102 in_progress_prompt_extension_id_ = extension->id();
79 in_progress_prompt_navigation_controller_ = nav_controller; 103 in_progress_prompt_navigation_controller_ = nav_controller;
80 104
81 extension_install_prompt_.reset( 105 extension_install_prompt_.reset(
82 new ExtensionInstallPrompt(nav_controller->GetWebContents())); 106 new ExtensionInstallPrompt(nav_controller->GetWebContents()));
83 ExtensionInstallPrompt::PromptType type = 107 ExtensionInstallPrompt::PromptType type =
84 ExtensionInstallPrompt::GetReEnablePromptTypeForExtension(profile_, 108 ExtensionInstallPrompt::GetReEnablePromptTypeForExtension(profile_,
(...skipping 21 matching lines...) Expand all
106 130
107 if (result == ExtensionInstallPrompt::Result::ACCEPTED) { 131 if (result == ExtensionInstallPrompt::Result::ACCEPTED) {
108 NavigationController* nav_controller = 132 NavigationController* nav_controller =
109 in_progress_prompt_navigation_controller_; 133 in_progress_prompt_navigation_controller_;
110 CHECK(nav_controller); 134 CHECK(nav_controller);
111 135
112 // Grant permissions, re-enable the extension, and then reload the tab. 136 // Grant permissions, re-enable the extension, and then reload the tab.
113 extension_service->GrantPermissionsAndEnableExtension(extension); 137 extension_service->GrantPermissionsAndEnableExtension(extension);
114 nav_controller->Reload(content::ReloadType::NORMAL, true); 138 nav_controller->Reload(content::ReloadType::NORMAL, true);
115 } else { 139 } else {
140 // TODO(devlin): These metrics aren't very useful, since they're lumped in
141 // with the same for re-enabling/canceling when the extension first gets
142 // disabled, which is likely significantly more common (though impossible to
143 // tell). We need to separate these.
116 std::string histogram_name = 144 std::string histogram_name =
117 result == ExtensionInstallPrompt::Result::USER_CANCELED 145 result == ExtensionInstallPrompt::Result::USER_CANCELED
118 ? "ReEnableCancel" 146 ? "ReEnableCancel"
119 : "ReEnableAbort"; 147 : "ReEnableAbort";
120 ExtensionService::RecordPermissionMessagesHistogram(extension, 148 ExtensionService::RecordPermissionMessagesHistogram(extension,
121 histogram_name.c_str()); 149 histogram_name.c_str());
122 } 150 }
123 151
124 in_progress_prompt_extension_id_ = std::string(); 152 in_progress_prompt_extension_id_ = std::string();
125 in_progress_prompt_navigation_controller_ = nullptr; 153 in_progress_prompt_navigation_controller_ = nullptr;
126 extension_install_prompt_.reset(); 154 extension_install_prompt_.reset();
127 } 155 }
128 156
129 void NavigationObserver::OnExtensionUninstalled( 157 void NavigationObserver::OnExtensionUninstalled(
130 content::BrowserContext* browser_context, 158 content::BrowserContext* browser_context,
131 const Extension* extension, 159 const Extension* extension,
132 UninstallReason reason) { 160 UninstallReason reason) {
133 if (in_progress_prompt_extension_id_.empty() || 161 if (in_progress_prompt_extension_id_.empty() ||
134 in_progress_prompt_extension_id_ != extension->id()) { 162 in_progress_prompt_extension_id_ != extension->id()) {
135 return; 163 return;
136 } 164 }
137 165
138 in_progress_prompt_extension_id_ = std::string(); 166 in_progress_prompt_extension_id_ = std::string();
139 in_progress_prompt_navigation_controller_ = nullptr; 167 in_progress_prompt_navigation_controller_ = nullptr;
140 extension_install_prompt_.reset(); 168 extension_install_prompt_.reset();
141 } 169 }
142 170
143 } // namespace extensions 171 } // namespace extensions
OLDNEW
« no previous file with comments | « chrome/browser/extensions/navigation_observer.h ('k') | chrome/browser/extensions/navigation_observer_browsertest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698