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 "base/memory/ref_counted.h"
6 #include "chrome/browser/extensions/extension_error_controller.h"
7 #include "chrome/browser/extensions/extension_error_ui.h"
8 #include "chrome/browser/extensions/extension_service.h"
9 #include "chrome/browser/extensions/extension_service_test_base.h"
10 #include "chrome/browser/profiles/profile.h"
11 #include "chrome/test/base/testing_profile.h"
12 #include "extensions/browser/extension_prefs.h"
13 #include "extensions/browser/extension_registry.h"
14 #include "extensions/common/extension.h"
15 #include "extensions/common/extension_builder.h"
16 #include "extensions/common/value_builder.h"
18 namespace extensions
{
22 // Create a mock for the UI component of the error alert that is shown for
23 // blacklisted extensions. This allows us to test which extensions the alert
24 // is showing, and also eliminates the UI component (since this is a unit
26 class MockExtensionErrorUI
: public ExtensionErrorUI
{
28 explicit MockExtensionErrorUI(ExtensionErrorUI::Delegate
* delegate
);
29 ~MockExtensionErrorUI() override
;
31 // Wrappers around the similar methods in ExtensionErrorUI.
36 ExtensionErrorUI::Delegate
* delegate() { return delegate_
; }
39 // ExtensionErrorUI implementation.
40 bool ShowErrorInBubbleView() override
;
41 void ShowExtensions() override
;
42 void Close() override
;
44 // Keep a copy of the delegate around for ourselves.
45 ExtensionErrorUI::Delegate
* delegate_
;
48 // We use this as a slight hack to get the created Error UI, if any. We should
49 // only ever have one (since this is a single-profile test), and this avoids
50 // the need for any kind of accessor to the ErrorController from
52 MockExtensionErrorUI
* g_error_ui
= NULL
;
54 MockExtensionErrorUI::MockExtensionErrorUI(
55 ExtensionErrorUI::Delegate
* delegate
)
56 : ExtensionErrorUI(delegate
),
58 // We should never make more than one of these in a test.
63 MockExtensionErrorUI::~MockExtensionErrorUI() {
67 void MockExtensionErrorUI::CloseUI() {
71 void MockExtensionErrorUI::Accept() {
72 BubbleViewAcceptButtonPressed();
75 void MockExtensionErrorUI::Details() {
76 BubbleViewCancelButtonPressed();
79 bool MockExtensionErrorUI::ShowErrorInBubbleView() {
83 void MockExtensionErrorUI::ShowExtensions() {}
85 void MockExtensionErrorUI::Close() {
89 ExtensionErrorUI
* CreateMockUI(ExtensionErrorUI::Delegate
* delegate
) {
90 return new MockExtensionErrorUI(delegate
);
93 // Builds and returns a simple extension.
94 scoped_refptr
<const Extension
> BuildExtension() {
95 return ExtensionBuilder()
96 .SetManifest(DictionaryBuilder().Set("name", "My Wonderful Extension")
97 .Set("version", "0.1.1.0")
98 .Set("manifest_version", 2)
105 class ExtensionErrorControllerUnitTest
: public ExtensionServiceTestBase
{
107 void SetUp() override
;
109 // Add an extension to chrome, and mark it as blacklisted in the prefs.
110 testing::AssertionResult
AddBlacklistedExtension(const Extension
* extension
);
112 // Return the ExtensionPrefs associated with the test.
113 ExtensionPrefs
* GetPrefs();
115 Profile
* profile() { return profile_
.get(); }
118 void ExtensionErrorControllerUnitTest::SetUp() {
119 ExtensionServiceTestBase::SetUp();
120 // Make sure we use the mock UI instead of the real UI.
121 ExtensionErrorController::SetUICreateMethodForTesting(CreateMockUI
);
123 // We don't want a first-run ExtensionService, since we ignore warnings
125 ExtensionServiceInitParams params
= CreateDefaultInitParams();
126 params
.is_first_run
= false;
127 InitializeExtensionService(params
);
130 testing::AssertionResult
131 ExtensionErrorControllerUnitTest::AddBlacklistedExtension(
132 const Extension
* extension
) {
133 GetPrefs()->SetExtensionBlacklisted(extension
->id(), true);
134 service_
->AddExtension(extension
);
136 // Make sure the extension is added to the blacklisted set.
137 if (!ExtensionRegistry::Get(profile())->blacklisted_extensions()
138 .Contains(extension
->id())) {
139 return testing::AssertionFailure()
140 << "Failed to add blacklisted extension.";
143 return testing::AssertionSuccess();
146 ExtensionPrefs
* ExtensionErrorControllerUnitTest::GetPrefs() {
147 return ExtensionPrefs::Get(profile());
150 // Test that closing the extension alert for blacklisted extensions counts
151 // as acknowledging them in the prefs.
152 TEST_F(ExtensionErrorControllerUnitTest
, ClosingAcknowledgesBlacklisted
) {
153 // Add a blacklisted extension.
154 scoped_refptr
<const Extension
> extension
= BuildExtension();
155 ASSERT_TRUE(AddBlacklistedExtension(extension
.get()));
159 // Make sure that we created an error "ui" to warn about the blacklisted
161 ASSERT_TRUE(g_error_ui
);
162 ExtensionErrorUI::Delegate
* delegate
= g_error_ui
->delegate();
163 ASSERT_TRUE(delegate
);
165 // Make sure that the blacklisted extension is reported (and that no other
167 const ExtensionSet
& delegate_blacklisted_extensions
=
168 delegate
->GetBlacklistedExtensions();
169 EXPECT_EQ(1u, delegate_blacklisted_extensions
.size());
170 EXPECT_TRUE(delegate_blacklisted_extensions
.Contains(extension
->id()));
172 // Close, and verify that the extension ids now acknowledged.
173 g_error_ui
->CloseUI();
174 EXPECT_TRUE(GetPrefs()->IsBlacklistedExtensionAcknowledged(extension
->id()));
175 // Verify we cleaned up after ourselves.
176 EXPECT_FALSE(g_error_ui
);
179 // Test that clicking "accept" on the extension alert counts as acknowledging
180 // blacklisted extensions.
181 TEST_F(ExtensionErrorControllerUnitTest
, AcceptingAcknowledgesBlacklisted
) {
182 // Add a blacklisted extension.
183 scoped_refptr
<const Extension
> extension
= BuildExtension();
184 ASSERT_TRUE(AddBlacklistedExtension(extension
.get()));
188 // Make sure that we created an error "ui" to warn about the blacklisted
190 ASSERT_TRUE(g_error_ui
);
192 // Accept, and verify that the extension ids now acknowledged.
193 g_error_ui
->Accept();
194 EXPECT_TRUE(GetPrefs()->IsBlacklistedExtensionAcknowledged(extension
->id()));
195 // Verify we cleaned up after ourselves.
196 EXPECT_FALSE(g_error_ui
);
199 // Test that we don't warn for extensions which are blacklisted, but have
200 // already been acknowledged.
201 TEST_F(ExtensionErrorControllerUnitTest
, DontWarnForAcknowledgedBlacklisted
) {
202 scoped_refptr
<const Extension
> extension
= BuildExtension();
203 ASSERT_TRUE(AddBlacklistedExtension(extension
.get()));
205 GetPrefs()->AcknowledgeBlacklistedExtension(extension
->id());
209 // We should never have made an alert, because the extension should already
211 ASSERT_FALSE(g_error_ui
);
214 } // namespace extensions