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

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

Issue 95133002: Add an extension bubble explaining which extensions are in dev mode. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Sync'ed Created 7 years 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 | Annotate | Revision Log
OLDNEW
(Empty)
1 // Copyright (c) 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.
4
5 #include "chrome/browser/extensions/extension_message_bubble_controller.h"
6
7 #include "base/bind.h"
8 #include "base/metrics/histogram.h"
9 #include "base/strings/utf_string_conversions.h"
10 #include "chrome/browser/extensions/extension_message_bubble.h"
11 #include "chrome/browser/extensions/extension_prefs.h"
12 #include "chrome/browser/extensions/extension_service.h"
13 #include "chrome/browser/ui/browser.h"
14 #include "chrome/browser/ui/browser_finder.h"
15 #include "chrome/common/url_constants.h"
16 #include "content/public/browser/user_metrics.h"
17 #include "grit/chromium_strings.h"
18 #include "grit/generated_resources.h"
19 #include "ui/base/l10n/l10n_util.h"
20
21 namespace {
22
23 // All the different titles we know about.
24 static const int kTitleIds[extensions::NUM_BUBBLE_TYPES] = {
25 IDS_EXTENSIONS_SUSPICIOUS_DISABLED_TITLE,
26 IDS_EXTENSIONS_DISABLE_DEVELOPER_MODE_TITLE,
27 };
28
29 // All the different message bodies we know about. See also kBodyInjectIds.
30 static const int kBodyIds[extensions::NUM_BUBBLE_TYPES] = {
31 IDS_EXTENSIONS_SUSPICIOUS_DISABLED_BODY,
32 IDS_EXTENSIONS_DISABLE_DEVELOPER_MODE_BODY,
33 };
34
35 // Sometimes we substitute a param in one of the kBodyIds, this specifies the
36 // value to use to replace the param. A 0 value means Accept no substitutes!
37 static const int kBodyInjectIds[extensions::NUM_BUBBLE_TYPES] = {
38 IDS_EXTENSION_WEB_STORE_TITLE,
39 0,
40 };
41
42 // All the labels we use for the Accept button. A 0 value means the bubble has
43 // no Accept button.
44 static const int kAcceptIds[extensions::NUM_BUBBLE_TYPES] = {
45 0,
46 IDS_DISABLE,
47 };
48
49 // All the labels we use for the Dismiss button.
50 static const int kDismissIds[extensions::NUM_BUBBLE_TYPES] = {
51 IDS_EXTENSIONS_SUSPICIOUS_DISABLED_BUTTON,
52 IDS_CANCEL,
53 };
54
55 static const char* kLearnMoreLikeIds[extensions::NUM_BUBBLE_TYPES] = {
56 chrome::kRemoveNonCWSExtensionURL,
57 chrome::kChromeUIExtensionsURL,
58 };
59
60 static const bool kShowExtensionList[extensions::NUM_BUBBLE_TYPES] = {
61 true,
62 false,
63 };
64
65 } // namespace
66
67 namespace extensions {
68
69 ////////////////////////////////////////////////////////////////////////////////
70 // ExtensionMessageBubbleController
71
72 ExtensionMessageBubbleController::ExtensionMessageBubbleController(
73 ExtensionListType type, Profile* profile)
74 : service_(extensions::ExtensionSystem::Get(profile)->extension_service()),
75 profile_(profile),
76 user_action_(ACTION_BOUNDARY),
77 type_(type),
78 has_notified_(false),
79 showing_bubble_(false) {
80 }
81
82 ExtensionMessageBubbleController::~ExtensionMessageBubbleController() {
83 }
84
85 bool ExtensionMessageBubbleController::HasExtensionList() {
86 if (has_notified_)
87 return false;
88
89 scoped_ptr<const ExtensionSet> extension_set(
90 service_->GenerateInstalledExtensionsSet());
91 for (ExtensionSet::const_iterator it = extension_set->begin();
92 it != extension_set->end(); ++it) {
93 std::string id = (*it)->id();
94 if (!ShouldIncludeExtension(id))
95 continue;
96 extension_list_.push_back(id);
97 }
98
99 // Log the UMA histogram.
100 switch (type_) {
101 case SUSPICIOUS_EXTENSIONS:
102 UMA_HISTOGRAM_COUNTS_100(
103 "ExtensionWipeoutBubble.ExtensionWipeoutCount",
104 extension_list_.size());
105 break;
106 case DEV_MODE_EXTENSIONS:
107 UMA_HISTOGRAM_COUNTS_100(
108 "DevModeExtensionBubble.ExtensionsInDevModeCount",
109 extension_list_.size());
110 break;
111 case NUM_BUBBLE_TYPES:
112 NOTREACHED();
113 break;
114 }
115
116 has_notified_ = true;
117 return !extension_list_.empty();
118 }
119
120 std::vector<string16>
121 ExtensionMessageBubbleController::GetExtensionList() const {
122 if (extension_list_.empty())
123 return std::vector<string16>();
124
125 std::vector<string16> return_value;
126 for (ExtensionIdList::const_iterator it = extension_list_.begin();
127 it != extension_list_.end(); ++it) {
128 const Extension* extension = service_->GetInstalledExtension(*it);
129 if (extension) {
130 return_value.push_back(UTF8ToUTF16(extension->name()));
131 } else {
132 return_value.push_back(
133 ASCIIToUTF16(std::string("(unknown name) ") + *it));
134 // TODO(finnur): Add this as a string to the grd, for next milestone.
135 }
136 }
137 return return_value;
138 }
139
140 void ExtensionMessageBubbleController::Show(ExtensionMessageBubble* bubble) {
141 // Wire up all the callbacks, to get notified what actions the user took.
142 base::Closure dismiss_button_callback =
143 base::Bind(&ExtensionMessageBubbleController::OnBubbleDismiss,
144 base::Unretained(this));
145 base::Closure action_button_callback =
146 base::Bind(&ExtensionMessageBubbleController::OnBubbleAction,
147 base::Unretained(this));
148 base::Closure link_callback =
149 base::Bind(&ExtensionMessageBubbleController::OnLinkClicked,
150 base::Unretained(this));
151 bubble->OnActionButtonClicked(action_button_callback);
152 bubble->OnDismissButtonClicked(dismiss_button_callback);
153 bubble->OnLinkClicked(link_callback);
154
155 showing_bubble_ = true;
156 bubble->Show();
157 }
158
159 string16 ExtensionMessageBubbleController::GetTitle() const {
160 return l10n_util::GetStringUTF16(kTitleIds[type_]);
161 }
162
163 string16 ExtensionMessageBubbleController::GetMessageBody() const {
164 if (kBodyInjectIds[type_] == 0)
165 return l10n_util::GetStringUTF16(kBodyIds[type_]);
166
167 return l10n_util::GetStringFUTF16(kBodyIds[type_],
168 l10n_util::GetStringUTF16(kBodyInjectIds[type_]));
169 }
170
171 string16 ExtensionMessageBubbleController::GetOverflowText(
172 const string16& overflow_count) const {
173 return l10n_util::GetStringFUTF16(
174 IDS_EXTENSIONS_SUSPICIOUS_DISABLED_AND_N_MORE,
175 overflow_count);
176 }
177
178 string16 ExtensionMessageBubbleController::GetLearnMoreLabel() const {
179 return l10n_util::GetStringUTF16(IDS_LEARN_MORE);
180 }
181
182 string16 ExtensionMessageBubbleController::GetActionButtonLabel() const {
183 if (!kAcceptIds[type_])
184 return string16();
185
186 return l10n_util::GetStringUTF16(kAcceptIds[type_]);
187 }
188
189 string16 ExtensionMessageBubbleController::GetDismissButtonLabel() const {
190 return l10n_util::GetStringUTF16(kDismissIds[type_]);
191 }
192
193 bool ExtensionMessageBubbleController::ShouldShowExtensionList() const {
194 return kShowExtensionList[type_];
195 }
196
197 void ExtensionMessageBubbleController::OnBubbleAction() {
198 DCHECK_EQ(ACTION_BOUNDARY, user_action_);
199 user_action_ = ACTION_EXECUTE;
200
201 RecordAction(ACTION_EXECUTE);
202 PerformAction();
203 AcknowledgeExtensions();
204 }
205
206 void ExtensionMessageBubbleController::OnBubbleDismiss() {
207 DCHECK_EQ(ACTION_BOUNDARY, user_action_);
208 user_action_ = ACTION_DISMISS;
209
210 RecordAction(ACTION_DISMISS);
211 AcknowledgeExtensions();
212 }
213
214 void ExtensionMessageBubbleController::OnLinkClicked() {
215 DCHECK_EQ(ACTION_BOUNDARY, user_action_);
216 user_action_ = ACTION_LEARN_MORE;
217
218 RecordAction(ACTION_LEARN_MORE);
219 Browser* browser =
220 chrome::FindBrowserWithProfile(profile_, chrome::GetActiveDesktop());
221 if (browser) {
222 browser->OpenURL(
223 content::OpenURLParams(GURL(kLearnMoreLikeIds[type_]),
224 content::Referrer(),
225 NEW_FOREGROUND_TAB,
226 content::PAGE_TRANSITION_LINK,
227 false));
228 }
229 AcknowledgeExtensions();
230 }
231
232 void ExtensionMessageBubbleController::AcknowledgeExtensions() {
233 for (ExtensionIdList::const_iterator it = extension_list_.begin();
234 it != extension_list_.end(); ++it)
235 AcknowledgeExtension(*it);
236 showing_bubble_ = false;
237 }
238
239 void ExtensionMessageBubbleController::RecordAction(
240 UmaExtensionListHistogramOptions action) {
241 switch (type_) {
242 case SUSPICIOUS_EXTENSIONS:
243 UMA_HISTOGRAM_ENUMERATION("ExtensionWipeoutBubble.UserSelection",
244 action, ACTION_BOUNDARY);
245 break;
246 case DEV_MODE_EXTENSIONS:
247 UMA_HISTOGRAM_ENUMERATION("DevModeExtensionBubble.UserSelection",
248 action, ACTION_BOUNDARY);
249 break;
250 case NUM_BUBBLE_TYPES:
251 NOTREACHED();
252 break;
253 }
254 }
255
256 } // namespace extensions
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698