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/basictypes.h"
6 #include "base/memory/ref_counted.h"
7 #include "base/memory/scoped_ptr.h"
8 #include "base/prefs/pref_store_observer_mock.h"
9 #include "base/values.h"
10 #include "extensions/browser/extension_pref_value_map.h"
11 #include "testing/gmock/include/gmock/gmock.h"
12 #include "testing/gtest/include/gtest/gtest.h"
15 const char kExt1
[] = "ext1";
16 const char kExt2
[] = "ext2";
17 const char kExt3
[] = "ext3";
19 const char kPref1
[] = "path1.subpath";
20 const char kPref2
[] = "path2";
21 const char kPref3
[] = "path3";
22 const char kPref4
[] = "path4";
25 static base::Value
* CreateVal(const char* str
) {
26 return new base::StringValue(str
);
29 static base::Time
CreateTime(int64 t
) {
30 return base::Time::FromInternalValue(t
);
33 template <typename BASECLASS
>
34 class ExtensionPrefValueMapTestBase
: public BASECLASS
{
36 static const extensions::ExtensionPrefsScope kRegular
=
37 extensions::kExtensionPrefsScopeRegular
;
38 static const extensions::ExtensionPrefsScope kRegularOnly
=
39 extensions::kExtensionPrefsScopeRegularOnly
;
40 static const extensions::ExtensionPrefsScope kIncognitoPersistent
=
41 extensions::kExtensionPrefsScopeIncognitoPersistent
;
42 static const extensions::ExtensionPrefsScope kIncognitoSessionOnly
=
43 extensions::kExtensionPrefsScopeIncognitoSessionOnly
;
45 // Returns an empty string if the key is not set.
46 std::string
GetValue(const char * key
, bool incognito
) const {
47 const base::Value
*value
=
48 epvm_
.GetEffectivePrefValue(key
, incognito
, NULL
);
49 std::string string_value
;
51 value
->GetAsString(&string_value
);
55 // Registers the extension as enabled but without incognito permission.
56 void RegisterExtension(const std::string
& ext_id
,
57 const base::Time
& install_time
) {
58 epvm_
.RegisterExtension(
59 ext_id
, install_time
, true /*enabled*/, false /*incognito*/);
63 ExtensionPrefValueMap epvm_
;
66 class ExtensionPrefValueMapTest
67 : public ExtensionPrefValueMapTestBase
<testing::Test
> {
70 // A gmock-ified implementation of PrefStore::Observer.
71 class ExtensionPrefValueMapObserverMock
72 : public ExtensionPrefValueMap::Observer
{
74 ExtensionPrefValueMapObserverMock() {}
75 virtual ~ExtensionPrefValueMapObserverMock() {}
77 MOCK_METHOD1(OnPrefValueChanged
, void(const std::string
&));
78 MOCK_METHOD0(OnInitializationCompleted
, void());
79 MOCK_METHOD0(OnExtensionPrefValueMapDestruction
, void());
82 DISALLOW_COPY_AND_ASSIGN(ExtensionPrefValueMapObserverMock
);
85 TEST_F(ExtensionPrefValueMapTest
, SetAndGetPrefValue
) {
86 RegisterExtension(kExt1
, CreateTime(10));
87 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val1"));
88 EXPECT_EQ("val1", GetValue(kPref1
, false));
91 TEST_F(ExtensionPrefValueMapTest
, GetNotSetPrefValue
) {
92 RegisterExtension(kExt1
, CreateTime(10));
93 EXPECT_EQ(std::string(), GetValue(kPref1
, false));
96 // Make sure the last-installed extension wins for each preference.
97 TEST_F(ExtensionPrefValueMapTest
, Override
) {
98 RegisterExtension(kExt1
, CreateTime(10));
99 RegisterExtension(kExt2
, CreateTime(20));
100 RegisterExtension(kExt3
, CreateTime(30));
102 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val1"));
103 epvm_
.SetExtensionPref(kExt2
, kPref1
, kRegular
, CreateVal("val2"));
104 epvm_
.SetExtensionPref(kExt3
, kPref1
, kRegular
, CreateVal("val3"));
106 epvm_
.SetExtensionPref(kExt1
, kPref2
, kRegular
, CreateVal("val4"));
107 epvm_
.SetExtensionPref(kExt2
, kPref2
, kRegular
, CreateVal("val5"));
109 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val6"));
110 epvm_
.SetExtensionPref(kExt1
, kPref2
, kRegular
, CreateVal("val7"));
111 epvm_
.SetExtensionPref(kExt1
, kPref3
, kRegular
, CreateVal("val8"));
113 EXPECT_EQ("val3", GetValue(kPref1
, false));
114 EXPECT_EQ("val5", GetValue(kPref2
, false));
115 EXPECT_EQ("val8", GetValue(kPref3
, false));
118 TEST_F(ExtensionPrefValueMapTest
, OverrideChecks
) {
119 RegisterExtension(kExt1
, CreateTime(10));
120 RegisterExtension(kExt2
, CreateTime(20));
121 RegisterExtension(kExt3
, CreateTime(30));
123 EXPECT_FALSE(epvm_
.DoesExtensionControlPref(kExt1
, kPref1
, NULL
));
124 EXPECT_FALSE(epvm_
.DoesExtensionControlPref(kExt2
, kPref1
, NULL
));
125 EXPECT_FALSE(epvm_
.DoesExtensionControlPref(kExt3
, kPref1
, NULL
));
126 EXPECT_TRUE(epvm_
.CanExtensionControlPref(kExt1
, kPref1
, false));
127 EXPECT_TRUE(epvm_
.CanExtensionControlPref(kExt2
, kPref1
, false));
128 EXPECT_TRUE(epvm_
.CanExtensionControlPref(kExt3
, kPref1
, false));
130 epvm_
.SetExtensionPref(kExt2
, kPref1
, kRegular
, CreateVal("val1"));
132 EXPECT_FALSE(epvm_
.DoesExtensionControlPref(kExt1
, kPref1
, NULL
));
133 EXPECT_TRUE(epvm_
.DoesExtensionControlPref(kExt2
, kPref1
, NULL
));
134 EXPECT_FALSE(epvm_
.DoesExtensionControlPref(kExt3
, kPref1
, NULL
));
135 EXPECT_FALSE(epvm_
.CanExtensionControlPref(kExt1
, kPref1
, false));
136 EXPECT_TRUE(epvm_
.CanExtensionControlPref(kExt2
, kPref1
, false));
137 EXPECT_TRUE(epvm_
.CanExtensionControlPref(kExt3
, kPref1
, false));
140 TEST_F(ExtensionPrefValueMapTest
, SetAndGetPrefValueIncognito
) {
141 RegisterExtension(kExt1
, CreateTime(10));
142 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val1"));
143 // Check that the value is not propagated until the extension gets incognito
145 EXPECT_EQ(std::string(), GetValue(kPref1
, true));
146 epvm_
.SetExtensionIncognitoState(kExt1
, true);
147 EXPECT_EQ("val1", GetValue(kPref1
, true));
148 epvm_
.SetExtensionIncognitoState(kExt1
, false);
149 EXPECT_EQ(std::string(), GetValue(kPref1
, true));
152 TEST_F(ExtensionPrefValueMapTest
, UninstallOnlyExtension
) {
153 RegisterExtension(kExt1
, CreateTime(10));
154 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val1"));
155 epvm_
.UnregisterExtension(kExt1
);
157 EXPECT_EQ(std::string(), GetValue(kPref1
, false));
160 // Tests uninstalling an extension that wasn't winning for any preferences.
161 TEST_F(ExtensionPrefValueMapTest
, UninstallIrrelevantExtension
) {
162 RegisterExtension(kExt1
, CreateTime(10));
163 RegisterExtension(kExt2
, CreateTime(10));
165 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val1"));
166 epvm_
.SetExtensionPref(kExt2
, kPref1
, kRegular
, CreateVal("val2"));
168 epvm_
.SetExtensionPref(kExt1
, kPref2
, kRegular
, CreateVal("val3"));
169 epvm_
.SetExtensionPref(kExt2
, kPref2
, kRegular
, CreateVal("val4"));
171 epvm_
.UnregisterExtension(kExt1
);
173 EXPECT_EQ("val2", GetValue(kPref1
, false));
174 EXPECT_EQ("val4", GetValue(kPref2
, false));
177 // Tests uninstalling an extension that was winning for all preferences.
178 TEST_F(ExtensionPrefValueMapTest
, UninstallExtensionFromTop
) {
179 RegisterExtension(kExt1
, CreateTime(10));
180 RegisterExtension(kExt2
, CreateTime(20));
181 RegisterExtension(kExt3
, CreateTime(30));
183 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val1"));
184 epvm_
.SetExtensionPref(kExt2
, kPref1
, kRegular
, CreateVal("val2"));
185 epvm_
.SetExtensionPref(kExt3
, kPref1
, kRegular
, CreateVal("val3"));
187 epvm_
.SetExtensionPref(kExt1
, kPref2
, kRegular
, CreateVal("val4"));
188 epvm_
.SetExtensionPref(kExt3
, kPref2
, kRegular
, CreateVal("val5"));
190 epvm_
.UnregisterExtension(kExt3
);
192 EXPECT_EQ("val2", GetValue(kPref1
, false));
193 EXPECT_EQ("val4", GetValue(kPref2
, false));
196 // Tests uninstalling an extension that was winning for only some preferences.
197 TEST_F(ExtensionPrefValueMapTest
, UninstallExtensionFromMiddle
) {
198 RegisterExtension(kExt1
, CreateTime(10));
199 RegisterExtension(kExt2
, CreateTime(20));
200 RegisterExtension(kExt3
, CreateTime(30));
202 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val1"));
203 epvm_
.SetExtensionPref(kExt2
, kPref1
, kRegular
, CreateVal("val2"));
204 epvm_
.SetExtensionPref(kExt3
, kPref1
, kRegular
, CreateVal("val3"));
206 epvm_
.SetExtensionPref(kExt1
, kPref2
, kRegular
, CreateVal("val4"));
207 epvm_
.SetExtensionPref(kExt2
, kPref2
, kRegular
, CreateVal("val5"));
209 epvm_
.SetExtensionPref(kExt1
, kPref3
, kRegular
, CreateVal("val6"));
211 epvm_
.SetExtensionPref(kExt2
, kPref4
, kRegular
, CreateVal("val7"));
213 epvm_
.UnregisterExtension(kExt2
);
215 EXPECT_EQ("val3", GetValue(kPref1
, false));
216 EXPECT_EQ("val4", GetValue(kPref2
, false));
217 EXPECT_EQ("val6", GetValue(kPref3
, false));
218 EXPECT_EQ(std::string(), GetValue(kPref4
, false));
221 // Tests triggering of notifications to registered observers.
222 TEST_F(ExtensionPrefValueMapTest
, NotifyWhenNeeded
) {
224 using testing::StrEq
;
226 RegisterExtension(kExt1
, CreateTime(10));
228 ExtensionPrefValueMapObserverMock observer
;
229 epvm_
.AddObserver(&observer
);
231 EXPECT_CALL(observer
, OnPrefValueChanged(std::string(kPref1
)));
232 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val1"));
233 Mock::VerifyAndClearExpectations(&observer
);
235 // Write the same value again.
236 EXPECT_CALL(observer
, OnPrefValueChanged(std::string(kPref1
))).Times(0);
237 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val1"));
238 Mock::VerifyAndClearExpectations(&observer
);
240 // Override incognito value.
241 EXPECT_CALL(observer
, OnPrefValueChanged(std::string(kPref1
)));
242 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val2"));
243 Mock::VerifyAndClearExpectations(&observer
);
245 // Override non-incognito value.
246 EXPECT_CALL(observer
, OnPrefValueChanged(std::string(kPref1
)));
247 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val3"));
248 Mock::VerifyAndClearExpectations(&observer
);
251 EXPECT_CALL(observer
, OnPrefValueChanged(std::string(kPref1
)));
252 epvm_
.SetExtensionState(kExt1
, false);
253 Mock::VerifyAndClearExpectations(&observer
);
256 EXPECT_CALL(observer
, OnPrefValueChanged(std::string(kPref1
)));
257 epvm_
.SetExtensionState(kExt1
, true);
258 Mock::VerifyAndClearExpectations(&observer
);
261 EXPECT_CALL(observer
, OnPrefValueChanged(std::string(kPref1
)));
262 epvm_
.UnregisterExtension(kExt1
);
263 Mock::VerifyAndClearExpectations(&observer
);
265 epvm_
.RemoveObserver(&observer
);
267 // Write new value --> no notification after removing observer.
268 EXPECT_CALL(observer
, OnPrefValueChanged(std::string(kPref1
))).Times(0);
269 RegisterExtension(kExt1
, CreateTime(10));
270 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val4"));
271 Mock::VerifyAndClearExpectations(&observer
);
274 // Tests disabling an extension.
275 TEST_F(ExtensionPrefValueMapTest
, DisableExt
) {
276 RegisterExtension(kExt1
, CreateTime(10));
278 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val1"));
279 epvm_
.SetExtensionState(kExt1
, false);
280 EXPECT_EQ(std::string(), GetValue(kPref1
, false));
283 // Tests disabling and reenabling an extension.
284 TEST_F(ExtensionPrefValueMapTest
, ReenableExt
) {
285 RegisterExtension(kExt1
, CreateTime(10));
287 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
, CreateVal("val1"));
288 epvm_
.SetExtensionState(kExt1
, false);
289 epvm_
.SetExtensionState(kExt1
, true);
290 EXPECT_EQ("val1", GetValue(kPref1
, false));
293 struct OverrideIncognitoTestCase
{
294 OverrideIncognitoTestCase(bool enable_ext1_in_incognito
,
295 bool enable_ext2_in_incognito
,
296 int val_ext1_regular
,
297 int val_ext1_regular_only
,
298 int val_ext1_incognito_pers
,
299 int val_ext1_incognito_sess
,
300 int val_ext2_regular
,
301 int val_ext2_regular_only
,
302 int val_ext2_incognito_pers
,
303 int val_ext2_incognito_sess
,
304 int effective_value_regular
,
305 int effective_value_incognito
)
306 : enable_ext1_in_incognito_(enable_ext1_in_incognito
),
307 enable_ext2_in_incognito_(enable_ext2_in_incognito
),
308 val_ext1_regular_(val_ext1_regular
),
309 val_ext1_regular_only_(val_ext1_regular_only
),
310 val_ext1_incognito_pers_(val_ext1_incognito_pers
),
311 val_ext1_incognito_sess_(val_ext1_incognito_sess
),
312 val_ext2_regular_(val_ext2_regular
),
313 val_ext2_regular_only_(val_ext2_regular_only
),
314 val_ext2_incognito_pers_(val_ext2_incognito_pers
),
315 val_ext2_incognito_sess_(val_ext2_incognito_sess
),
316 effective_value_regular_(effective_value_regular
),
317 effective_value_incognito_(effective_value_incognito
) {}
319 bool enable_ext1_in_incognito_
;
320 bool enable_ext2_in_incognito_
;
322 // pers. = persistent
323 // sess. = session only
324 int val_ext1_regular_
; // pref value of extension 1
325 int val_ext1_regular_only_
; // pref value of extension 1 regular-only.
326 int val_ext1_incognito_pers_
; // pref value of extension 1 incognito pers.
327 int val_ext1_incognito_sess_
; // pref value of extension 1 incognito sess.
328 int val_ext2_regular_
; // pref value of extension 2
329 int val_ext2_regular_only_
; // pref value of extension 2 regular-only.
330 int val_ext2_incognito_pers_
; // pref value of extension 2 incognito pers.
331 int val_ext2_incognito_sess_
; // pref value of extension 2 incognito sess.
332 int effective_value_regular_
; // desired winner regular
333 int effective_value_incognito_
; // desired winner incognito
336 class ExtensionPrefValueMapTestIncognitoTests
337 : public ExtensionPrefValueMapTestBase
<
338 testing::TestWithParam
<OverrideIncognitoTestCase
> > {
341 TEST_P(ExtensionPrefValueMapTestIncognitoTests
, OverrideIncognito
) {
342 OverrideIncognitoTestCase test
= GetParam();
343 const char* strings
[] = {
355 const bool kEnabled
= true;
356 epvm_
.RegisterExtension(
357 kExt1
, CreateTime(10), kEnabled
, test
.enable_ext1_in_incognito_
);
358 epvm_
.RegisterExtension(
359 kExt2
, CreateTime(20), kEnabled
, test
.enable_ext2_in_incognito_
);
360 if (test
.val_ext1_regular_
) {
361 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegular
,
362 CreateVal(strings
[test
.val_ext1_regular_
]));
364 if (test
.val_ext1_regular_only_
) {
365 epvm_
.SetExtensionPref(kExt1
, kPref1
, kRegularOnly
,
366 CreateVal(strings
[test
.val_ext1_regular_only_
]));
368 if (test
.val_ext1_incognito_pers_
) {
369 epvm_
.SetExtensionPref(kExt1
, kPref1
, kIncognitoPersistent
,
370 CreateVal(strings
[test
.val_ext1_incognito_pers_
]));
372 if (test
.val_ext1_incognito_sess_
) {
373 epvm_
.SetExtensionPref(kExt1
, kPref1
, kIncognitoSessionOnly
,
374 CreateVal(strings
[test
.val_ext1_incognito_sess_
]));
376 if (test
.val_ext2_regular_
) {
377 epvm_
.SetExtensionPref(kExt2
, kPref1
, kRegular
,
378 CreateVal(strings
[test
.val_ext2_regular_
]));
380 if (test
.val_ext2_regular_only_
) {
381 epvm_
.SetExtensionPref(kExt2
, kPref1
, kRegularOnly
,
382 CreateVal(strings
[test
.val_ext2_regular_only_
]));
384 if (test
.val_ext2_incognito_pers_
) {
385 epvm_
.SetExtensionPref(kExt2
, kPref1
, kIncognitoPersistent
,
386 CreateVal(strings
[test
.val_ext2_incognito_pers_
]));
388 if (test
.val_ext2_incognito_sess_
) {
389 epvm_
.SetExtensionPref(kExt2
, kPref1
, kIncognitoSessionOnly
,
390 CreateVal(strings
[test
.val_ext2_incognito_sess_
]));
393 EXPECT_EQ(strings
[test
.effective_value_regular_
], GetValue(kPref1
, false));
394 EXPECT_EQ(strings
[test
.effective_value_incognito_
], GetValue(kPref1
, true));
395 epvm_
.UnregisterExtension(kExt1
);
396 epvm_
.UnregisterExtension(kExt2
);
399 INSTANTIATE_TEST_CASE_P(
400 ExtensionPrefValueMapTestIncognitoTestsInstance
,
401 ExtensionPrefValueMapTestIncognitoTests
,
403 // e.g. (true, 1, 0, 0, 0, 0, 0, 7, 0, 1, 7), means:
404 // ext1 regular is set to "val1", ext2 incognito persistent is set to
406 // --> the winning regular value is "val1", the winning incognito
408 OverrideIncognitoTestCase(true, true, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1),
409 OverrideIncognitoTestCase(true, true, 1, 2, 0, 0, 0, 0, 0, 0, 2, 1),
410 OverrideIncognitoTestCase(true, true, 1, 0, 3, 0, 0, 0, 0, 0, 1, 3),
411 OverrideIncognitoTestCase(true, true, 1, 0, 0, 4, 0, 0, 0, 0, 1, 4),
412 OverrideIncognitoTestCase(true, true, 1, 0, 3, 4, 0, 0, 0, 0, 1, 4),
413 OverrideIncognitoTestCase(true, true, 1, 2, 3, 0, 0, 0, 0, 0, 2, 3),
414 OverrideIncognitoTestCase(true, true, 1, 0, 0, 0, 5, 0, 0, 0, 5, 5),
415 OverrideIncognitoTestCase(true, true, 1, 2, 3, 0, 5, 0, 0, 0, 5, 5),
416 OverrideIncognitoTestCase(true, true, 1, 0, 0, 0, 0, 6, 0, 0, 6, 1),
417 OverrideIncognitoTestCase(true, true, 1, 0, 3, 0, 5, 6, 0, 0, 6, 5),
418 OverrideIncognitoTestCase(true, true, 1, 0, 0, 4, 5, 6, 0, 0, 6, 5),
419 OverrideIncognitoTestCase(true, true, 1, 0, 0, 0, 0, 0, 7, 0, 1, 7),
420 OverrideIncognitoTestCase(true, true, 1, 2, 0, 0, 5, 0, 7, 0, 5, 7),
421 OverrideIncognitoTestCase(true, true, 1, 2, 0, 0, 5, 0, 0, 8, 5, 8),
422 OverrideIncognitoTestCase(true, true, 1, 2, 0, 0, 5, 0, 7, 8, 5, 8),
423 OverrideIncognitoTestCase(true, true, 1, 2, 3, 0, 0, 6, 7, 0, 6, 7),
424 // Same tests as above but w/o incognito permission.
425 OverrideIncognitoTestCase(false, false, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0),
426 OverrideIncognitoTestCase(false, false, 1, 2, 0, 0, 0, 0, 0, 0, 2, 0),
427 OverrideIncognitoTestCase(false, false, 1, 0, 3, 0, 0, 0, 0, 0, 1, 0),
428 OverrideIncognitoTestCase(false, false, 1, 0, 0, 4, 0, 0, 0, 0, 1, 0),
429 OverrideIncognitoTestCase(false, false, 1, 0, 3, 4, 0, 0, 0, 0, 1, 0),
430 OverrideIncognitoTestCase(false, false, 1, 2, 3, 0, 0, 0, 0, 0, 2, 0),
431 OverrideIncognitoTestCase(false, false, 1, 0, 0, 0, 5, 0, 0, 0, 5, 0),
432 OverrideIncognitoTestCase(false, false, 1, 2, 3, 0, 5, 0, 0, 0, 5, 0),
433 OverrideIncognitoTestCase(false, false, 1, 0, 0, 0, 0, 6, 0, 0, 6, 0),
434 OverrideIncognitoTestCase(false, false, 1, 0, 3, 0, 5, 6, 0, 0, 6, 0),
435 OverrideIncognitoTestCase(false, false, 1, 0, 0, 4, 5, 6, 0, 0, 6, 0),
436 OverrideIncognitoTestCase(false, false, 1, 0, 0, 0, 0, 0, 7, 0, 1, 0),
437 OverrideIncognitoTestCase(false, false, 1, 2, 0, 0, 5, 0, 7, 0, 5, 0),
438 OverrideIncognitoTestCase(false, false, 1, 2, 0, 0, 5, 0, 0, 8, 5, 0),
439 OverrideIncognitoTestCase(false, false, 1, 2, 0, 0, 5, 0, 7, 8, 5, 0),
440 OverrideIncognitoTestCase(false, false, 1, 2, 3, 0, 0, 6, 7, 0, 6, 0)