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.
5 #include "base/command_line.h"
6 #include "base/json/json_file_value_serializer.h"
7 #include "base/logging.h"
8 #include "base/path_service.h"
9 #include "base/strings/utf_string_conversions.h"
10 #include "chrome/common/chrome_paths.h"
11 #include "chrome/common/chrome_switches.h"
12 #include "chrome/common/extensions/extension_test_util.h"
13 #include "chrome/common/extensions/features/feature_channel.h"
14 #include "chrome/common/extensions/permissions/chrome_permission_message_provider.h"
15 #include "chrome/grit/generated_resources.h"
16 #include "extensions/common/error_utils.h"
17 #include "extensions/common/extension.h"
18 #include "extensions/common/extension_builder.h"
19 #include "extensions/common/permissions/permission_message_provider.h"
20 #include "extensions/common/permissions/permission_message_util.h"
21 #include "extensions/common/permissions/permission_set.h"
22 #include "extensions/common/permissions/permissions_data.h"
23 #include "extensions/common/permissions/permissions_info.h"
24 #include "extensions/common/permissions/socket_permission.h"
25 #include "extensions/common/value_builder.h"
26 #include "extensions/strings/grit/extensions_strings.h"
27 #include "testing/gtest/include/gtest/gtest.h"
28 #include "ui/base/l10n/l10n_util.h"
30 using extension_test_util::LoadManifest;
32 namespace extensions {
36 static void AddPattern(URLPatternSet* extent, const std::string& pattern) {
37 int schemes = URLPattern::SCHEME_ALL;
38 extent->AddPattern(URLPattern(schemes, pattern));
41 size_t IndexOf(const std::vector<base::string16>& warnings,
42 const std::string& warning) {
43 for (size_t i = 0; i < warnings.size(); ++i) {
44 if (warnings[i] == base::ASCIIToUTF16(warning))
48 return warnings.size();
51 bool Contains(const std::vector<base::string16>& warnings,
52 const std::string& warning) {
53 return IndexOf(warnings, warning) != warnings.size();
59 TEST(PermissionsTest, GetByID) {
60 PermissionsInfo* info = PermissionsInfo::GetInstance();
61 APIPermissionSet apis = info->GetAll();
62 for (APIPermissionSet::const_iterator i = apis.begin();
63 i != apis.end(); ++i) {
64 EXPECT_EQ(i->id(), i->info()->id());
68 // Tests that GetByName works with normal permission names and aliases.
69 TEST(PermissionsTest, GetByName) {
70 PermissionsInfo* info = PermissionsInfo::GetInstance();
71 EXPECT_EQ(APIPermission::kTab, info->GetByName("tabs")->id());
72 EXPECT_EQ(APIPermission::kManagement,
73 info->GetByName("management")->id());
74 EXPECT_FALSE(info->GetByName("alsdkfjasldkfj"));
77 TEST(PermissionsTest, GetAll) {
79 PermissionsInfo* info = PermissionsInfo::GetInstance();
80 APIPermissionSet apis = info->GetAll();
81 for (APIPermissionSet::const_iterator api = apis.begin();
82 api != apis.end(); ++api) {
83 // Make sure only the valid permission IDs get returned.
84 EXPECT_NE(APIPermission::kInvalid, api->id());
85 EXPECT_NE(APIPermission::kUnknown, api->id());
88 EXPECT_EQ(count, info->get_permission_count());
91 TEST(PermissionsTest, GetAllByName) {
92 std::set<std::string> names;
93 names.insert("background");
94 names.insert("management");
96 // This is an alias of kTab
97 names.insert("windows");
99 // This unknown name should get dropped.
100 names.insert("sdlkfjasdlkfj");
102 APIPermissionSet expected;
103 expected.insert(APIPermission::kBackground);
104 expected.insert(APIPermission::kManagement);
105 expected.insert(APIPermission::kTab);
108 PermissionsInfo::GetInstance()->GetAllByName(names));
111 // Tests that the aliases are properly mapped.
112 TEST(PermissionsTest, Aliases) {
113 PermissionsInfo* info = PermissionsInfo::GetInstance();
114 // tabs: tabs, windows
115 std::string tabs_name = "tabs";
116 EXPECT_EQ(tabs_name, info->GetByID(APIPermission::kTab)->name());
117 EXPECT_EQ(APIPermission::kTab, info->GetByName("tabs")->id());
118 EXPECT_EQ(APIPermission::kTab, info->GetByName("windows")->id());
120 // unlimitedStorage: unlimitedStorage, unlimited_storage
121 std::string storage_name = "unlimitedStorage";
122 EXPECT_EQ(storage_name, info->GetByID(
123 APIPermission::kUnlimitedStorage)->name());
124 EXPECT_EQ(APIPermission::kUnlimitedStorage,
125 info->GetByName("unlimitedStorage")->id());
126 EXPECT_EQ(APIPermission::kUnlimitedStorage,
127 info->GetByName("unlimited_storage")->id());
130 TEST(PermissionsTest, EffectiveHostPermissions) {
131 scoped_refptr<Extension> extension;
132 scoped_refptr<const PermissionSet> permissions;
134 extension = LoadManifest("effective_host_permissions", "empty.json");
135 permissions = extension->permissions_data()->active_permissions();
137 extension->permissions_data()
138 ->GetEffectiveHostPermissions()
142 permissions->HasEffectiveAccessToURL(GURL("http://www.google.com")));
143 EXPECT_FALSE(permissions->HasEffectiveAccessToAllHosts());
145 extension = LoadManifest("effective_host_permissions", "one_host.json");
146 permissions = extension->permissions_data()->active_permissions();
147 EXPECT_TRUE(permissions->HasEffectiveAccessToURL(
148 GURL("http://www.google.com")));
149 EXPECT_FALSE(permissions->HasEffectiveAccessToURL(
150 GURL("https://www.google.com")));
151 EXPECT_FALSE(permissions->HasEffectiveAccessToAllHosts());
153 extension = LoadManifest("effective_host_permissions",
154 "one_host_wildcard.json");
155 permissions = extension->permissions_data()->active_permissions();
156 EXPECT_TRUE(permissions->HasEffectiveAccessToURL(GURL("http://google.com")));
157 EXPECT_TRUE(permissions->HasEffectiveAccessToURL(
158 GURL("http://foo.google.com")));
159 EXPECT_FALSE(permissions->HasEffectiveAccessToAllHosts());
161 extension = LoadManifest("effective_host_permissions", "two_hosts.json");
162 permissions = extension->permissions_data()->active_permissions();
163 EXPECT_TRUE(permissions->HasEffectiveAccessToURL(
164 GURL("http://www.google.com")));
165 EXPECT_TRUE(permissions->HasEffectiveAccessToURL(
166 GURL("http://www.reddit.com")));
167 EXPECT_FALSE(permissions->HasEffectiveAccessToAllHosts());
169 extension = LoadManifest("effective_host_permissions",
170 "https_not_considered.json");
171 permissions = extension->permissions_data()->active_permissions();
172 EXPECT_TRUE(permissions->HasEffectiveAccessToURL(GURL("http://google.com")));
173 EXPECT_TRUE(permissions->HasEffectiveAccessToURL(GURL("https://google.com")));
174 EXPECT_FALSE(permissions->HasEffectiveAccessToAllHosts());
176 extension = LoadManifest("effective_host_permissions",
177 "two_content_scripts.json");
178 permissions = extension->permissions_data()->active_permissions();
179 EXPECT_TRUE(permissions->HasEffectiveAccessToURL(GURL("http://google.com")));
180 EXPECT_TRUE(permissions->HasEffectiveAccessToURL(
181 GURL("http://www.reddit.com")));
182 EXPECT_TRUE(permissions->HasEffectiveAccessToURL(
183 GURL("http://news.ycombinator.com")));
184 EXPECT_FALSE(permissions->HasEffectiveAccessToAllHosts());
186 extension = LoadManifest("effective_host_permissions", "all_hosts.json");
187 permissions = extension->permissions_data()->active_permissions();
188 EXPECT_TRUE(permissions->HasEffectiveAccessToURL(GURL("http://test/")));
189 EXPECT_FALSE(permissions->HasEffectiveAccessToURL(GURL("https://test/")));
191 permissions->HasEffectiveAccessToURL(GURL("http://www.google.com")));
192 EXPECT_TRUE(permissions->HasEffectiveAccessToAllHosts());
194 extension = LoadManifest("effective_host_permissions", "all_hosts2.json");
195 permissions = extension->permissions_data()->active_permissions();
196 EXPECT_TRUE(permissions->HasEffectiveAccessToURL(GURL("http://test/")));
198 permissions->HasEffectiveAccessToURL(GURL("http://www.google.com")));
199 EXPECT_TRUE(permissions->HasEffectiveAccessToAllHosts());
201 extension = LoadManifest("effective_host_permissions", "all_hosts3.json");
202 permissions = extension->permissions_data()->active_permissions();
203 EXPECT_FALSE(permissions->HasEffectiveAccessToURL(GURL("http://test/")));
204 EXPECT_TRUE(permissions->HasEffectiveAccessToURL(GURL("https://test/")));
206 permissions->HasEffectiveAccessToURL(GURL("http://www.google.com")));
207 EXPECT_TRUE(permissions->HasEffectiveAccessToAllHosts());
210 TEST(PermissionsTest, ExplicitAccessToOrigin) {
211 APIPermissionSet apis;
212 ManifestPermissionSet manifest_permissions;
213 URLPatternSet explicit_hosts;
214 URLPatternSet scriptable_hosts;
216 AddPattern(&explicit_hosts, "http://*.google.com/*");
217 // The explicit host paths should get set to /*.
218 AddPattern(&explicit_hosts, "http://www.example.com/a/particular/path/*");
220 scoped_refptr<PermissionSet> perm_set = new PermissionSet(
221 apis, manifest_permissions, explicit_hosts, scriptable_hosts);
222 ASSERT_TRUE(perm_set->HasExplicitAccessToOrigin(
223 GURL("http://www.google.com/")));
224 ASSERT_TRUE(perm_set->HasExplicitAccessToOrigin(
225 GURL("http://test.google.com/")));
226 ASSERT_TRUE(perm_set->HasExplicitAccessToOrigin(
227 GURL("http://www.example.com")));
228 ASSERT_TRUE(perm_set->HasEffectiveAccessToURL(
229 GURL("http://www.example.com")));
230 ASSERT_FALSE(perm_set->HasExplicitAccessToOrigin(
231 GURL("http://test.example.com")));
234 TEST(PermissionsTest, CreateUnion) {
235 APIPermission* permission = NULL;
237 ManifestPermissionSet manifest_permissions;
238 APIPermissionSet apis1;
239 APIPermissionSet apis2;
240 APIPermissionSet expected_apis;
242 URLPatternSet explicit_hosts1;
243 URLPatternSet explicit_hosts2;
244 URLPatternSet expected_explicit_hosts;
246 URLPatternSet scriptable_hosts1;
247 URLPatternSet scriptable_hosts2;
248 URLPatternSet expected_scriptable_hosts;
250 URLPatternSet effective_hosts;
252 scoped_refptr<PermissionSet> set1;
253 scoped_refptr<PermissionSet> set2;
254 scoped_refptr<PermissionSet> union_set;
256 const APIPermissionInfo* permission_info =
257 PermissionsInfo::GetInstance()->GetByID(APIPermission::kSocket);
258 permission = permission_info->CreateAPIPermission();
260 scoped_ptr<base::ListValue> value(new base::ListValue());
261 value->Append(new base::StringValue("tcp-connect:*.example.com:80"));
262 value->Append(new base::StringValue("udp-bind::8080"));
263 value->Append(new base::StringValue("udp-send-to::8888"));
264 ASSERT_TRUE(permission->FromValue(value.get(), NULL, NULL));
267 // Union with an empty set.
268 apis1.insert(APIPermission::kTab);
269 apis1.insert(APIPermission::kBackground);
270 apis1.insert(permission->Clone());
271 expected_apis.insert(APIPermission::kTab);
272 expected_apis.insert(APIPermission::kBackground);
273 expected_apis.insert(permission);
275 AddPattern(&explicit_hosts1, "http://*.google.com/*");
276 AddPattern(&expected_explicit_hosts, "http://*.google.com/*");
277 AddPattern(&effective_hosts, "http://*.google.com/*");
279 set1 = new PermissionSet(apis1, manifest_permissions,
280 explicit_hosts1, scriptable_hosts1);
281 set2 = new PermissionSet(apis2, manifest_permissions,
282 explicit_hosts2, scriptable_hosts2);
283 union_set = PermissionSet::CreateUnion(set1.get(), set2.get());
284 EXPECT_TRUE(set1->Contains(*set2.get()));
285 EXPECT_TRUE(set1->Contains(*union_set.get()));
286 EXPECT_FALSE(set2->Contains(*set1.get()));
287 EXPECT_FALSE(set2->Contains(*union_set.get()));
288 EXPECT_TRUE(union_set->Contains(*set1.get()));
289 EXPECT_TRUE(union_set->Contains(*set2.get()));
291 EXPECT_FALSE(union_set->HasEffectiveFullAccess());
292 EXPECT_EQ(expected_apis, union_set->apis());
293 EXPECT_EQ(expected_explicit_hosts, union_set->explicit_hosts());
294 EXPECT_EQ(expected_scriptable_hosts, union_set->scriptable_hosts());
295 EXPECT_EQ(expected_explicit_hosts, union_set->effective_hosts());
297 // Now use a real second set.
298 apis2.insert(APIPermission::kTab);
299 apis2.insert(APIPermission::kProxy);
300 apis2.insert(APIPermission::kClipboardWrite);
301 apis2.insert(APIPermission::kPlugin);
303 permission = permission_info->CreateAPIPermission();
305 scoped_ptr<base::ListValue> value(new base::ListValue());
306 value->Append(new base::StringValue("tcp-connect:*.example.com:80"));
307 value->Append(new base::StringValue("udp-send-to::8899"));
308 ASSERT_TRUE(permission->FromValue(value.get(), NULL, NULL));
310 apis2.insert(permission);
312 expected_apis.insert(APIPermission::kTab);
313 expected_apis.insert(APIPermission::kProxy);
314 expected_apis.insert(APIPermission::kClipboardWrite);
315 expected_apis.insert(APIPermission::kPlugin);
317 permission = permission_info->CreateAPIPermission();
319 scoped_ptr<base::ListValue> value(new base::ListValue());
320 value->Append(new base::StringValue("tcp-connect:*.example.com:80"));
321 value->Append(new base::StringValue("udp-bind::8080"));
322 value->Append(new base::StringValue("udp-send-to::8888"));
323 value->Append(new base::StringValue("udp-send-to::8899"));
324 ASSERT_TRUE(permission->FromValue(value.get(), NULL, NULL));
326 // Insert a new permission socket permisssion which will replace the old one.
327 expected_apis.insert(permission);
329 AddPattern(&explicit_hosts2, "http://*.example.com/*");
330 AddPattern(&scriptable_hosts2, "http://*.google.com/*");
331 AddPattern(&expected_explicit_hosts, "http://*.example.com/*");
332 AddPattern(&expected_scriptable_hosts, "http://*.google.com/*");
334 URLPatternSet::CreateUnion(
335 explicit_hosts2, scriptable_hosts2, &effective_hosts);
337 set2 = new PermissionSet(apis2, manifest_permissions,
338 explicit_hosts2, scriptable_hosts2);
339 union_set = PermissionSet::CreateUnion(set1.get(), set2.get());
341 EXPECT_FALSE(set1->Contains(*set2.get()));
342 EXPECT_FALSE(set1->Contains(*union_set.get()));
343 EXPECT_FALSE(set2->Contains(*set1.get()));
344 EXPECT_FALSE(set2->Contains(*union_set.get()));
345 EXPECT_TRUE(union_set->Contains(*set1.get()));
346 EXPECT_TRUE(union_set->Contains(*set2.get()));
348 EXPECT_TRUE(union_set->HasEffectiveFullAccess());
349 EXPECT_TRUE(union_set->HasEffectiveAccessToAllHosts());
350 EXPECT_EQ(expected_apis, union_set->apis());
351 EXPECT_EQ(expected_explicit_hosts, union_set->explicit_hosts());
352 EXPECT_EQ(expected_scriptable_hosts, union_set->scriptable_hosts());
353 EXPECT_EQ(effective_hosts, union_set->effective_hosts());
356 TEST(PermissionsTest, CreateIntersection) {
357 APIPermission* permission = NULL;
359 ManifestPermissionSet manifest_permissions;
360 APIPermissionSet apis1;
361 APIPermissionSet apis2;
362 APIPermissionSet expected_apis;
364 URLPatternSet explicit_hosts1;
365 URLPatternSet explicit_hosts2;
366 URLPatternSet expected_explicit_hosts;
368 URLPatternSet scriptable_hosts1;
369 URLPatternSet scriptable_hosts2;
370 URLPatternSet expected_scriptable_hosts;
372 URLPatternSet effective_hosts;
374 scoped_refptr<PermissionSet> set1;
375 scoped_refptr<PermissionSet> set2;
376 scoped_refptr<PermissionSet> new_set;
378 const APIPermissionInfo* permission_info =
379 PermissionsInfo::GetInstance()->GetByID(APIPermission::kSocket);
381 // Intersection with an empty set.
382 apis1.insert(APIPermission::kTab);
383 apis1.insert(APIPermission::kBackground);
384 permission = permission_info->CreateAPIPermission();
386 scoped_ptr<base::ListValue> value(new base::ListValue());
387 value->Append(new base::StringValue("tcp-connect:*.example.com:80"));
388 value->Append(new base::StringValue("udp-bind::8080"));
389 value->Append(new base::StringValue("udp-send-to::8888"));
390 ASSERT_TRUE(permission->FromValue(value.get(), NULL, NULL));
392 apis1.insert(permission);
394 AddPattern(&explicit_hosts1, "http://*.google.com/*");
395 AddPattern(&scriptable_hosts1, "http://www.reddit.com/*");
397 set1 = new PermissionSet(apis1, manifest_permissions,
398 explicit_hosts1, scriptable_hosts1);
399 set2 = new PermissionSet(apis2, manifest_permissions,
400 explicit_hosts2, scriptable_hosts2);
401 new_set = PermissionSet::CreateIntersection(set1.get(), set2.get());
402 EXPECT_TRUE(set1->Contains(*new_set.get()));
403 EXPECT_TRUE(set2->Contains(*new_set.get()));
404 EXPECT_TRUE(set1->Contains(*set2.get()));
405 EXPECT_FALSE(set2->Contains(*set1.get()));
406 EXPECT_FALSE(new_set->Contains(*set1.get()));
407 EXPECT_TRUE(new_set->Contains(*set2.get()));
409 EXPECT_TRUE(new_set->IsEmpty());
410 EXPECT_FALSE(new_set->HasEffectiveFullAccess());
411 EXPECT_EQ(expected_apis, new_set->apis());
412 EXPECT_EQ(expected_explicit_hosts, new_set->explicit_hosts());
413 EXPECT_EQ(expected_scriptable_hosts, new_set->scriptable_hosts());
414 EXPECT_EQ(expected_explicit_hosts, new_set->effective_hosts());
416 // Now use a real second set.
417 apis2.insert(APIPermission::kTab);
418 apis2.insert(APIPermission::kProxy);
419 apis2.insert(APIPermission::kClipboardWrite);
420 apis2.insert(APIPermission::kPlugin);
421 permission = permission_info->CreateAPIPermission();
423 scoped_ptr<base::ListValue> value(new base::ListValue());
424 value->Append(new base::StringValue("udp-bind::8080"));
425 value->Append(new base::StringValue("udp-send-to::8888"));
426 value->Append(new base::StringValue("udp-send-to::8899"));
427 ASSERT_TRUE(permission->FromValue(value.get(), NULL, NULL));
429 apis2.insert(permission);
431 expected_apis.insert(APIPermission::kTab);
432 permission = permission_info->CreateAPIPermission();
434 scoped_ptr<base::ListValue> value(new base::ListValue());
435 value->Append(new base::StringValue("udp-bind::8080"));
436 value->Append(new base::StringValue("udp-send-to::8888"));
437 ASSERT_TRUE(permission->FromValue(value.get(), NULL, NULL));
439 expected_apis.insert(permission);
441 AddPattern(&explicit_hosts2, "http://*.example.com/*");
442 AddPattern(&explicit_hosts2, "http://*.google.com/*");
443 AddPattern(&scriptable_hosts2, "http://*.google.com/*");
444 AddPattern(&expected_explicit_hosts, "http://*.google.com/*");
446 effective_hosts.ClearPatterns();
447 AddPattern(&effective_hosts, "http://*.google.com/*");
449 set2 = new PermissionSet(apis2, manifest_permissions,
450 explicit_hosts2, scriptable_hosts2);
451 new_set = PermissionSet::CreateIntersection(set1.get(), set2.get());
453 EXPECT_TRUE(set1->Contains(*new_set.get()));
454 EXPECT_TRUE(set2->Contains(*new_set.get()));
455 EXPECT_FALSE(set1->Contains(*set2.get()));
456 EXPECT_FALSE(set2->Contains(*set1.get()));
457 EXPECT_FALSE(new_set->Contains(*set1.get()));
458 EXPECT_FALSE(new_set->Contains(*set2.get()));
460 EXPECT_FALSE(new_set->HasEffectiveFullAccess());
461 EXPECT_FALSE(new_set->HasEffectiveAccessToAllHosts());
462 EXPECT_EQ(expected_apis, new_set->apis());
463 EXPECT_EQ(expected_explicit_hosts, new_set->explicit_hosts());
464 EXPECT_EQ(expected_scriptable_hosts, new_set->scriptable_hosts());
465 EXPECT_EQ(effective_hosts, new_set->effective_hosts());
468 TEST(PermissionsTest, CreateDifference) {
469 APIPermission* permission = NULL;
471 ManifestPermissionSet manifest_permissions;
472 APIPermissionSet apis1;
473 APIPermissionSet apis2;
474 APIPermissionSet expected_apis;
476 URLPatternSet explicit_hosts1;
477 URLPatternSet explicit_hosts2;
478 URLPatternSet expected_explicit_hosts;
480 URLPatternSet scriptable_hosts1;
481 URLPatternSet scriptable_hosts2;
482 URLPatternSet expected_scriptable_hosts;
484 URLPatternSet effective_hosts;
486 scoped_refptr<PermissionSet> set1;
487 scoped_refptr<PermissionSet> set2;
488 scoped_refptr<PermissionSet> new_set;
490 const APIPermissionInfo* permission_info =
491 PermissionsInfo::GetInstance()->GetByID(APIPermission::kSocket);
493 // Difference with an empty set.
494 apis1.insert(APIPermission::kTab);
495 apis1.insert(APIPermission::kBackground);
496 permission = permission_info->CreateAPIPermission();
498 scoped_ptr<base::ListValue> value(new base::ListValue());
499 value->Append(new base::StringValue("tcp-connect:*.example.com:80"));
500 value->Append(new base::StringValue("udp-bind::8080"));
501 value->Append(new base::StringValue("udp-send-to::8888"));
502 ASSERT_TRUE(permission->FromValue(value.get(), NULL, NULL));
504 apis1.insert(permission);
506 AddPattern(&explicit_hosts1, "http://*.google.com/*");
507 AddPattern(&scriptable_hosts1, "http://www.reddit.com/*");
509 set1 = new PermissionSet(apis1, manifest_permissions,
510 explicit_hosts1, scriptable_hosts1);
511 set2 = new PermissionSet(apis2, manifest_permissions,
512 explicit_hosts2, scriptable_hosts2);
513 new_set = PermissionSet::CreateDifference(set1.get(), set2.get());
514 EXPECT_EQ(*set1.get(), *new_set.get());
516 // Now use a real second set.
517 apis2.insert(APIPermission::kTab);
518 apis2.insert(APIPermission::kProxy);
519 apis2.insert(APIPermission::kClipboardWrite);
520 apis2.insert(APIPermission::kPlugin);
521 permission = permission_info->CreateAPIPermission();
523 scoped_ptr<base::ListValue> value(new base::ListValue());
524 value->Append(new base::StringValue("tcp-connect:*.example.com:80"));
525 value->Append(new base::StringValue("udp-send-to::8899"));
526 ASSERT_TRUE(permission->FromValue(value.get(), NULL, NULL));
528 apis2.insert(permission);
530 expected_apis.insert(APIPermission::kBackground);
531 permission = permission_info->CreateAPIPermission();
533 scoped_ptr<base::ListValue> value(new base::ListValue());
534 value->Append(new base::StringValue("udp-bind::8080"));
535 value->Append(new base::StringValue("udp-send-to::8888"));
536 ASSERT_TRUE(permission->FromValue(value.get(), NULL, NULL));
538 expected_apis.insert(permission);
540 AddPattern(&explicit_hosts2, "http://*.example.com/*");
541 AddPattern(&explicit_hosts2, "http://*.google.com/*");
542 AddPattern(&scriptable_hosts2, "http://*.google.com/*");
543 AddPattern(&expected_scriptable_hosts, "http://www.reddit.com/*");
545 effective_hosts.ClearPatterns();
546 AddPattern(&effective_hosts, "http://www.reddit.com/*");
548 set2 = new PermissionSet(apis2, manifest_permissions,
549 explicit_hosts2, scriptable_hosts2);
550 new_set = PermissionSet::CreateDifference(set1.get(), set2.get());
552 EXPECT_TRUE(set1->Contains(*new_set.get()));
553 EXPECT_FALSE(set2->Contains(*new_set.get()));
555 EXPECT_FALSE(new_set->HasEffectiveFullAccess());
556 EXPECT_FALSE(new_set->HasEffectiveAccessToAllHosts());
557 EXPECT_EQ(expected_apis, new_set->apis());
558 EXPECT_EQ(expected_explicit_hosts, new_set->explicit_hosts());
559 EXPECT_EQ(expected_scriptable_hosts, new_set->scriptable_hosts());
560 EXPECT_EQ(effective_hosts, new_set->effective_hosts());
562 // |set3| = |set1| - |set2| --> |set3| intersect |set2| == empty_set
563 set1 = PermissionSet::CreateIntersection(new_set.get(), set2.get());
564 EXPECT_TRUE(set1->IsEmpty());
567 TEST(PermissionsTest, IsPrivilegeIncrease) {
569 const char* base_name;
570 bool expect_increase;
572 { "allhosts1", false }, // all -> all
573 { "allhosts2", false }, // all -> one
574 { "allhosts3", true }, // one -> all
575 { "hosts1", false }, // http://a,http://b -> http://a,http://b
576 { "hosts2", true }, // http://a,http://b -> https://a,http://*.b
577 { "hosts3", false }, // http://a,http://b -> http://a
578 { "hosts4", true }, // http://a -> http://a,http://b
579 { "hosts5", false }, // http://a,b,c -> http://a,b,c + https://a,b,c
580 { "hosts6", false }, // http://a.com -> http://a.com + http://a.co.uk
581 { "permissions1", false }, // tabs -> tabs
582 { "permissions2", true }, // tabs -> tabs,bookmarks
583 { "permissions3", true }, // http://a -> http://a,tabs
584 { "permissions5", true }, // bookmarks -> bookmarks,history
585 { "equivalent_warnings", false }, // tabs --> tabs, webNavigation
586 #if !defined(OS_CHROMEOS) // plugins aren't allowed in ChromeOS
587 { "permissions4", false }, // plugin -> plugin,tabs
588 { "plugin1", false }, // plugin -> plugin
589 { "plugin2", false }, // plugin -> none
590 { "plugin3", true }, // none -> plugin
592 { "storage", false }, // none -> storage
593 { "notifications", false }, // none -> notifications
594 { "platformapp1", false }, // host permissions for platform apps
595 { "platformapp2", true }, // API permissions for platform apps
596 { "media_galleries1", true }, // all -> read|all
597 { "media_galleries2", true }, // read|all -> read|delete|copyTo|all
598 { "media_galleries3", true }, // all -> read|delete|all
599 { "media_galleries4", false }, // read|all -> all
600 { "media_galleries5", false }, // read|copyTo|delete|all -> read|all
601 { "media_galleries6", false }, // read|all -> read|all
602 { "media_galleries7", true }, // read|delete|all -> read|copyTo|delete|all
603 { "sockets1", true }, // none -> tcp:*:*
604 { "sockets2", false }, // tcp:*:* -> tcp:*:*
605 { "sockets3", true }, // tcp:a.com:80 -> tcp:*:*
608 for (size_t i = 0; i < ARRAYSIZE_UNSAFE(kTests); ++i) {
609 scoped_refptr<Extension> old_extension(
610 LoadManifest("allow_silent_upgrade",
611 std::string(kTests[i].base_name) + "_old.json"));
612 scoped_refptr<Extension> new_extension(
613 LoadManifest("allow_silent_upgrade",
614 std::string(kTests[i].base_name) + "_new.json"));
616 EXPECT_TRUE(new_extension.get()) << kTests[i].base_name << "_new.json";
617 if (!new_extension.get())
620 scoped_refptr<const PermissionSet> old_p(
621 old_extension->permissions_data()->active_permissions());
622 scoped_refptr<const PermissionSet> new_p(
623 new_extension->permissions_data()->active_permissions());
624 Manifest::Type extension_type = old_extension->GetType();
626 bool increased = PermissionMessageProvider::Get()->IsPrivilegeIncrease(
627 old_p.get(), new_p.get(), extension_type);
628 EXPECT_EQ(kTests[i].expect_increase, increased) << kTests[i].base_name;
632 TEST(PermissionsTest, PermissionMessages) {
633 // Ensure that all permissions that needs to show install UI actually have
634 // strings associated with them.
635 APIPermissionSet skip;
637 // These are considered "nuisance" or "trivial" permissions that don't need
639 skip.insert(APIPermission::kActiveTab);
640 skip.insert(APIPermission::kAlarms);
641 skip.insert(APIPermission::kAlphaEnabled);
642 skip.insert(APIPermission::kAlwaysOnTopWindows);
643 skip.insert(APIPermission::kAppView);
644 skip.insert(APIPermission::kAudio);
645 skip.insert(APIPermission::kBrowsingData);
646 skip.insert(APIPermission::kCastStreaming);
647 skip.insert(APIPermission::kCommandsAccessibility);
648 skip.insert(APIPermission::kContextMenus);
649 skip.insert(APIPermission::kCopresencePrivate);
650 skip.insert(APIPermission::kDiagnostics);
651 skip.insert(APIPermission::kDns);
652 skip.insert(APIPermission::kDownloadsShelf);
653 skip.insert(APIPermission::kEmbeddedExtensionOptions);
654 skip.insert(APIPermission::kFontSettings);
655 skip.insert(APIPermission::kFullscreen);
656 skip.insert(APIPermission::kGcm);
657 skip.insert(APIPermission::kIdle);
658 skip.insert(APIPermission::kIdltest);
659 skip.insert(APIPermission::kLogPrivate);
660 skip.insert(APIPermission::kNotifications);
661 skip.insert(APIPermission::kNotificationProvider);
662 skip.insert(APIPermission::kOverrideEscFullscreen);
663 skip.insert(APIPermission::kPointerLock);
664 skip.insert(APIPermission::kPower);
665 skip.insert(APIPermission::kPushMessaging);
666 skip.insert(APIPermission::kSessions);
667 skip.insert(APIPermission::kStorage);
668 skip.insert(APIPermission::kSystemCpu);
669 skip.insert(APIPermission::kSystemDisplay);
670 skip.insert(APIPermission::kSystemMemory);
671 skip.insert(APIPermission::kSystemNetwork);
672 skip.insert(APIPermission::kSystemStorage);
673 skip.insert(APIPermission::kTts);
674 skip.insert(APIPermission::kUnlimitedStorage);
675 skip.insert(APIPermission::kWebcamPrivate);
676 skip.insert(APIPermission::kWebView);
677 skip.insert(APIPermission::kWindowShape);
679 // These permissions are restricted to extensions force-installed by policy
680 // and don't require a prompt, i.e. they're restricted to location 'policy'.
681 skip.insert(APIPermission::kEnterprisePlatformKeys);
683 // TODO(erikkay) add a string for this permission.
684 skip.insert(APIPermission::kBackground);
686 skip.insert(APIPermission::kClipboardWrite);
688 // The cookie permission does nothing unless you have associated host
690 skip.insert(APIPermission::kCookie);
692 // These are warned as part of host permission checks.
693 skip.insert(APIPermission::kDeclarativeContent);
694 skip.insert(APIPermission::kPageCapture);
695 skip.insert(APIPermission::kProxy);
696 skip.insert(APIPermission::kTabCapture);
697 skip.insert(APIPermission::kWebRequest);
698 skip.insert(APIPermission::kWebRequestBlocking);
700 // This permission requires explicit user action (context menu handler)
701 // so we won't prompt for it for now.
702 skip.insert(APIPermission::kFileBrowserHandler);
704 // These permissions require explicit user action (configuration dialog)
705 // so we don't prompt for them at install time.
706 skip.insert(APIPermission::kMediaGalleries);
708 // If you've turned on the experimental command-line flag, we don't need
709 // to warn you further.
710 skip.insert(APIPermission::kExperimental);
712 // The Identity API has its own server-driven permission prompts.
713 skip.insert(APIPermission::kIdentity);
715 // These are private.
716 skip.insert(APIPermission::kAccessibilityPrivate);
717 skip.insert(APIPermission::kAutoTestPrivate);
718 skip.insert(APIPermission::kBookmarkManagerPrivate);
719 skip.insert(APIPermission::kBrailleDisplayPrivate);
720 skip.insert(APIPermission::kCast);
721 skip.insert(APIPermission::kCastStreaming);
722 skip.insert(APIPermission::kChromeosInfoPrivate);
723 skip.insert(APIPermission::kCloudPrintPrivate);
724 skip.insert(APIPermission::kCommandLinePrivate);
725 skip.insert(APIPermission::kDeveloperPrivate);
726 skip.insert(APIPermission::kDial);
727 skip.insert(APIPermission::kDownloadsInternal);
728 skip.insert(APIPermission::kEasyUnlockPrivate);
729 skip.insert(APIPermission::kEchoPrivate);
730 skip.insert(APIPermission::kEnterprisePlatformKeysPrivate);
731 skip.insert(APIPermission::kFeedbackPrivate);
732 skip.insert(APIPermission::kFileBrowserHandlerInternal);
733 skip.insert(APIPermission::kFileManagerPrivate);
734 skip.insert(APIPermission::kFirstRunPrivate);
735 skip.insert(APIPermission::kGcdPrivate);
736 skip.insert(APIPermission::kHotwordPrivate);
737 skip.insert(APIPermission::kIdentityPrivate);
738 skip.insert(APIPermission::kInfobars);
739 skip.insert(APIPermission::kInputMethodPrivate);
740 skip.insert(APIPermission::kMediaGalleriesPrivate);
741 skip.insert(APIPermission::kMediaPlayerPrivate);
742 skip.insert(APIPermission::kMetricsPrivate);
743 skip.insert(APIPermission::kMDns);
744 skip.insert(APIPermission::kPreferencesPrivate);
745 skip.insert(APIPermission::kPrincipalsPrivate);
746 skip.insert(APIPermission::kImageWriterPrivate);
747 skip.insert(APIPermission::kReadingListPrivate);
748 skip.insert(APIPermission::kRtcPrivate);
749 skip.insert(APIPermission::kStreamsPrivate);
750 skip.insert(APIPermission::kSyncedNotificationsPrivate);
751 skip.insert(APIPermission::kSystemPrivate);
752 skip.insert(APIPermission::kTabCaptureForTab);
753 skip.insert(APIPermission::kTerminalPrivate);
754 skip.insert(APIPermission::kVirtualKeyboardPrivate);
755 skip.insert(APIPermission::kWallpaperPrivate);
756 skip.insert(APIPermission::kWebrtcAudioPrivate);
757 skip.insert(APIPermission::kWebrtcLoggingPrivate);
758 skip.insert(APIPermission::kWebstorePrivate);
760 // Warned as part of host permissions.
761 skip.insert(APIPermission::kDevtools);
764 skip.insert(APIPermission::kBrowser);
765 skip.insert(APIPermission::kFileSystem);
766 skip.insert(APIPermission::kFileSystemProvider);
767 skip.insert(APIPermission::kFileSystemRetainEntries);
768 skip.insert(APIPermission::kFileSystemWrite);
769 skip.insert(APIPermission::kSocket);
770 skip.insert(APIPermission::kUsbDevice);
772 // We already have a generic message for declaring externally_connectable.
773 skip.insert(APIPermission::kExternallyConnectableAllUrls);
775 PermissionsInfo* info = PermissionsInfo::GetInstance();
776 APIPermissionSet permissions = info->GetAll();
777 for (APIPermissionSet::const_iterator i = permissions.begin();
778 i != permissions.end(); ++i) {
779 const APIPermissionInfo* permission_info = i->info();
780 EXPECT_TRUE(permission_info != NULL);
782 if (skip.count(i->id())) {
783 EXPECT_EQ(PermissionMessage::kNone, permission_info->message_id())
784 << "unexpected message_id for " << permission_info->name();
786 EXPECT_NE(PermissionMessage::kNone, permission_info->message_id())
787 << "missing message_id for " << permission_info->name();
792 TEST(PermissionsTest, FileSystemPermissionMessages) {
793 APIPermissionSet api_permissions;
794 api_permissions.insert(APIPermission::kFileSystemWrite);
795 api_permissions.insert(APIPermission::kFileSystemDirectory);
796 scoped_refptr<PermissionSet> permissions(
797 new PermissionSet(api_permissions, ManifestPermissionSet(),
798 URLPatternSet(), URLPatternSet()));
799 PermissionMessages messages =
800 PermissionMessageProvider::Get()->GetPermissionMessages(
801 permissions.get(), Manifest::TYPE_PLATFORM_APP);
802 ASSERT_EQ(1u, messages.size());
803 std::sort(messages.begin(), messages.end());
804 std::set<PermissionMessage::ID> ids;
805 for (PermissionMessages::const_iterator it = messages.begin();
806 it != messages.end(); ++it) {
807 ids.insert(it->id());
809 EXPECT_TRUE(ContainsKey(ids, PermissionMessage::kFileSystemDirectory));
812 // The file system permissions have a special-case hack to show a warning for
813 // write and directory at the same time.
814 // TODO(sammc): Remove this. See http://crbug.com/284849.
815 TEST(PermissionsTest, FileSystemImplicitPermissions) {
816 APIPermissionSet apis;
817 apis.insert(APIPermission::kFileSystemWrite);
818 apis.AddImpliedPermissions();
820 EXPECT_EQ(apis.find(APIPermission::kFileSystemWrite)->id(),
821 APIPermission::kFileSystemWrite);
822 EXPECT_EQ(apis.size(), 1u);
824 apis.erase(APIPermission::kFileSystemWrite);
825 apis.insert(APIPermission::kFileSystemDirectory);
826 apis.AddImpliedPermissions();
828 EXPECT_EQ(apis.find(APIPermission::kFileSystemDirectory)->id(),
829 APIPermission::kFileSystemDirectory);
830 EXPECT_EQ(apis.size(), 1u);
832 apis.insert(APIPermission::kFileSystemWrite);
833 apis.AddImpliedPermissions();
835 EXPECT_EQ(apis.find(APIPermission::kFileSystemWrite)->id(),
836 APIPermission::kFileSystemWrite);
837 EXPECT_EQ(apis.find(APIPermission::kFileSystemDirectory)->id(),
838 APIPermission::kFileSystemDirectory);
839 EXPECT_EQ(apis.find(APIPermission::kFileSystemWriteDirectory)->id(),
840 APIPermission::kFileSystemWriteDirectory);
841 EXPECT_EQ(apis.size(), 3u);
844 TEST(PermissionsTest, HiddenFileSystemPermissionMessages) {
845 APIPermissionSet api_permissions;
846 api_permissions.insert(APIPermission::kFileSystemWrite);
847 api_permissions.insert(APIPermission::kFileSystemDirectory);
848 api_permissions.insert(APIPermission::kFileSystemWriteDirectory);
849 scoped_refptr<PermissionSet> permissions(
850 new PermissionSet(api_permissions, ManifestPermissionSet(),
851 URLPatternSet(), URLPatternSet()));
852 PermissionMessages messages =
853 PermissionMessageProvider::Get()->GetPermissionMessages(
854 permissions.get(), Manifest::TYPE_PLATFORM_APP);
855 ASSERT_EQ(1u, messages.size());
856 EXPECT_EQ(PermissionMessage::kFileSystemWriteDirectory, messages[0].id());
859 TEST(PermissionsTest, SuppressedPermissionMessages) {
861 // Tabs warning suppresses favicon warning.
862 APIPermissionSet api_permissions;
863 api_permissions.insert(APIPermission::kTab);
865 hosts.AddPattern(URLPattern(URLPattern::SCHEME_CHROMEUI,
866 "chrome://favicon/"));
867 scoped_refptr<PermissionSet> permissions(
868 new PermissionSet(api_permissions, ManifestPermissionSet(),
869 hosts, URLPatternSet()));
870 PermissionMessages messages =
871 PermissionMessageProvider::Get()->GetPermissionMessages(
872 permissions.get(), Manifest::TYPE_EXTENSION);
873 EXPECT_EQ(1u, messages.size());
874 EXPECT_EQ(PermissionMessage::kTabs, messages[0].id());
877 // History warning suppresses favicon warning.
878 APIPermissionSet api_permissions;
879 api_permissions.insert(APIPermission::kHistory);
881 hosts.AddPattern(URLPattern(URLPattern::SCHEME_CHROMEUI,
882 "chrome://favicon/"));
883 scoped_refptr<PermissionSet> permissions(
884 new PermissionSet(api_permissions, ManifestPermissionSet(),
885 hosts, URLPatternSet()));
886 PermissionMessages messages =
887 PermissionMessageProvider::Get()->GetPermissionMessages(
888 permissions.get(), Manifest::TYPE_EXTENSION);
889 EXPECT_EQ(1u, messages.size());
890 EXPECT_EQ(PermissionMessage::kBrowsingHistory, messages[0].id());
893 // All sites warning suppresses tabs warning.
894 APIPermissionSet api_permissions;
896 hosts.AddPattern(URLPattern(URLPattern::SCHEME_CHROMEUI, "*://*/*"));
897 api_permissions.insert(APIPermission::kTab);
898 scoped_refptr<PermissionSet> permissions(new PermissionSet(
899 api_permissions, ManifestPermissionSet(), hosts, URLPatternSet()));
900 PermissionMessages messages =
901 PermissionMessageProvider::Get()->GetPermissionMessages(
902 permissions.get(), Manifest::TYPE_EXTENSION);
903 EXPECT_EQ(1u, messages.size());
904 EXPECT_EQ(PermissionMessage::kHostsAll, messages[0].id());
907 // All sites warning suppresses topSites warning.
908 APIPermissionSet api_permissions;
910 hosts.AddPattern(URLPattern(URLPattern::SCHEME_CHROMEUI, "*://*/*"));
911 api_permissions.insert(APIPermission::kTopSites);
912 scoped_refptr<PermissionSet> permissions(new PermissionSet(
913 api_permissions, ManifestPermissionSet(), hosts, URLPatternSet()));
914 PermissionMessages messages =
915 PermissionMessageProvider::Get()->GetPermissionMessages(
916 permissions.get(), Manifest::TYPE_EXTENSION);
917 EXPECT_EQ(1u, messages.size());
918 EXPECT_EQ(PermissionMessage::kHostsAll, messages[0].id());
921 // All sites warning suppresses declarativeWebRequest warning.
922 APIPermissionSet api_permissions;
924 hosts.AddPattern(URLPattern(URLPattern::SCHEME_CHROMEUI, "*://*/*"));
925 api_permissions.insert(APIPermission::kDeclarativeWebRequest);
926 scoped_refptr<PermissionSet> permissions(new PermissionSet(
927 api_permissions, ManifestPermissionSet(), hosts, URLPatternSet()));
928 PermissionMessages messages =
929 PermissionMessageProvider::Get()->GetPermissionMessages(
930 permissions.get(), Manifest::TYPE_EXTENSION);
931 EXPECT_EQ(1u, messages.size());
932 EXPECT_EQ(PermissionMessage::kHostsAll, messages[0].id());
935 // BrowsingHistory warning suppresses all history read/write warnings.
936 APIPermissionSet api_permissions;
937 api_permissions.insert(APIPermission::kHistory);
938 api_permissions.insert(APIPermission::kTab);
939 api_permissions.insert(APIPermission::kTopSites);
940 api_permissions.insert(APIPermission::kProcesses);
941 api_permissions.insert(APIPermission::kWebNavigation);
942 scoped_refptr<PermissionSet> permissions(
943 new PermissionSet(api_permissions, ManifestPermissionSet(),
944 URLPatternSet(), URLPatternSet()));
945 PermissionMessages messages =
946 PermissionMessageProvider::Get()->GetPermissionMessages(
947 permissions.get(), Manifest::TYPE_EXTENSION);
948 EXPECT_EQ(1u, messages.size());
949 EXPECT_EQ(PermissionMessage::kBrowsingHistory, messages[0].id());
952 // Tabs warning suppresses all read-only history warnings.
953 APIPermissionSet api_permissions;
954 api_permissions.insert(APIPermission::kTab);
955 api_permissions.insert(APIPermission::kTopSites);
956 api_permissions.insert(APIPermission::kProcesses);
957 api_permissions.insert(APIPermission::kWebNavigation);
958 scoped_refptr<PermissionSet> permissions(
959 new PermissionSet(api_permissions, ManifestPermissionSet(),
960 URLPatternSet(), URLPatternSet()));
961 PermissionMessages messages =
962 PermissionMessageProvider::Get()->GetPermissionMessages(
963 permissions.get(), Manifest::TYPE_EXTENSION);
964 EXPECT_EQ(1u, messages.size());
965 EXPECT_EQ(PermissionMessage::kTabs, messages[0].id());
969 TEST(PermissionsTest, AccessToDevicesMessages) {
971 APIPermissionSet api_permissions;
972 api_permissions.insert(APIPermission::kUsb);
973 scoped_refptr<PermissionSet> permissions(
974 new PermissionSet(api_permissions,
975 ManifestPermissionSet(),
978 std::vector<base::string16> messages =
979 PermissionMessageProvider::Get()->GetWarningMessages(
980 permissions.get(), Manifest::TYPE_EXTENSION);
981 EXPECT_EQ(1u, messages.size());
982 EXPECT_EQ(l10n_util::GetStringUTF16(IDS_EXTENSION_PROMPT_WARNING_USB),
986 // Testing that multiple permissions will show the one message.
987 APIPermissionSet api_permissions;
988 api_permissions.insert(APIPermission::kUsb);
989 api_permissions.insert(APIPermission::kUsb);
990 scoped_refptr<PermissionSet> permissions(
991 new PermissionSet(api_permissions,
992 ManifestPermissionSet(),
995 std::vector<base::string16> messages =
996 PermissionMessageProvider::Get()->GetWarningMessages(
997 permissions.get(), Manifest::TYPE_EXTENSION);
998 EXPECT_EQ(1u, messages.size());
999 EXPECT_EQ(l10n_util::GetStringUTF16(IDS_EXTENSION_PROMPT_WARNING_USB),
1003 APIPermissionSet api_permissions;
1004 api_permissions.insert(APIPermission::kSerial);
1005 scoped_refptr<PermissionSet> permissions(
1006 new PermissionSet(api_permissions,
1007 ManifestPermissionSet(),
1010 std::vector<base::string16> messages =
1011 PermissionMessageProvider::Get()->GetWarningMessages(
1012 permissions.get(), Manifest::TYPE_EXTENSION);
1013 EXPECT_EQ(1u, messages.size());
1014 EXPECT_EQ(l10n_util::GetStringUTF16(IDS_EXTENSION_PROMPT_WARNING_SERIAL),
1018 APIPermissionSet api_permissions;
1019 api_permissions.insert(APIPermission::kUsb);
1020 api_permissions.insert(APIPermission::kSerial);
1021 scoped_refptr<PermissionSet> permissions(
1022 new PermissionSet(api_permissions,
1023 ManifestPermissionSet(),
1026 std::vector<base::string16> messages =
1027 PermissionMessageProvider::Get()->GetWarningMessages(
1028 permissions.get(), Manifest::TYPE_EXTENSION);
1029 EXPECT_EQ(1u, messages.size());
1031 l10n_util::GetStringUTF16(IDS_EXTENSION_PROMPT_WARNING_USB_SERIAL),
1035 // Testing that the same permission(s) will show one message.
1036 APIPermissionSet api_permissions;
1037 api_permissions.insert(APIPermission::kUsb);
1038 api_permissions.insert(APIPermission::kSerial);
1039 api_permissions.insert(APIPermission::kUsb);
1040 scoped_refptr<PermissionSet> permissions(
1041 new PermissionSet(api_permissions,
1042 ManifestPermissionSet(),
1045 std::vector<base::string16> messages =
1046 PermissionMessageProvider::Get()->GetWarningMessages(
1047 permissions.get(), Manifest::TYPE_EXTENSION);
1048 EXPECT_EQ(1u, messages.size());
1050 l10n_util::GetStringUTF16(IDS_EXTENSION_PROMPT_WARNING_USB_SERIAL),
1054 scoped_refptr<Extension> extension =
1055 LoadManifest("permissions", "access_to_devices_bluetooth.json");
1056 const PermissionMessageProvider* provider =
1057 PermissionMessageProvider::Get();
1058 PermissionSet* set = const_cast<PermissionSet*>(
1059 extension->permissions_data()->active_permissions().get());
1060 std::vector<base::string16> warnings =
1061 provider->GetWarningMessages(set, extension->GetType());
1062 EXPECT_EQ(1u, warnings.size());
1063 EXPECT_EQ(l10n_util::GetStringUTF16(IDS_EXTENSION_PROMPT_WARNING_BLUETOOTH),
1066 // Test Bluetooth and Serial
1067 set->apis_.insert(APIPermission::kSerial);
1068 warnings = provider->GetWarningMessages(set, extension->GetType());
1069 EXPECT_EQ(1u, warnings.size());
1070 EXPECT_EQ(l10n_util::GetStringUTF16(
1071 IDS_EXTENSION_PROMPT_WARNING_BLUETOOTH_SERIAL),
1073 set->apis_.erase(APIPermission::kSerial);
1075 // Test USB and Bluetooth
1076 set->apis_.insert(APIPermission::kUsb);
1077 warnings = provider->GetWarningMessages(set, extension->GetType());
1078 EXPECT_EQ(1u, warnings.size());
1080 l10n_util::GetStringUTF16(IDS_EXTENSION_PROMPT_WARNING_USB_BLUETOOTH),
1083 // Test USB, Bluetooth and Serial
1084 set->apis_.insert(APIPermission::kSerial);
1085 warnings = provider->GetWarningMessages(set, extension->GetType());
1086 EXPECT_EQ(1u, warnings.size());
1088 l10n_util::GetStringUTF16(IDS_EXTENSION_PROMPT_WARNING_ALL_DEVICES),
1093 TEST(PermissionsTest, MergedFileSystemPermissionComparison) {
1094 APIPermissionSet write_api_permissions;
1095 write_api_permissions.insert(APIPermission::kFileSystemWrite);
1096 scoped_refptr<PermissionSet> write_permissions(
1097 new PermissionSet(write_api_permissions, ManifestPermissionSet(),
1098 URLPatternSet(), URLPatternSet()));
1100 APIPermissionSet directory_api_permissions;
1101 directory_api_permissions.insert(APIPermission::kFileSystemDirectory);
1102 scoped_refptr<PermissionSet> directory_permissions(
1103 new PermissionSet(directory_api_permissions, ManifestPermissionSet(),
1104 URLPatternSet(), URLPatternSet()));
1106 APIPermissionSet write_directory_api_permissions;
1107 write_directory_api_permissions.insert(
1108 APIPermission::kFileSystemWriteDirectory);
1109 scoped_refptr<PermissionSet> write_directory_permissions(
1110 new PermissionSet(write_directory_api_permissions,
1111 ManifestPermissionSet(),
1115 const PermissionMessageProvider* provider = PermissionMessageProvider::Get();
1116 EXPECT_FALSE(provider->IsPrivilegeIncrease(write_directory_permissions.get(),
1117 write_permissions.get(),
1118 Manifest::TYPE_PLATFORM_APP));
1119 EXPECT_FALSE(provider->IsPrivilegeIncrease(write_directory_permissions.get(),
1120 directory_permissions.get(),
1121 Manifest::TYPE_PLATFORM_APP));
1122 EXPECT_TRUE(provider->IsPrivilegeIncrease(write_permissions.get(),
1123 directory_permissions.get(),
1124 Manifest::TYPE_PLATFORM_APP));
1125 EXPECT_TRUE(provider->IsPrivilegeIncrease(write_permissions.get(),
1126 write_directory_permissions.get(),
1127 Manifest::TYPE_PLATFORM_APP));
1128 EXPECT_FALSE(provider->IsPrivilegeIncrease(directory_permissions.get(),
1129 write_permissions.get(),
1130 Manifest::TYPE_PLATFORM_APP));
1131 EXPECT_TRUE(provider->IsPrivilegeIncrease(directory_permissions.get(),
1132 write_directory_permissions.get(),
1133 Manifest::TYPE_PLATFORM_APP));
1136 TEST(PermissionsTest, GetWarningMessages_ManyHosts) {
1137 scoped_refptr<Extension> extension;
1139 extension = LoadManifest("permissions", "many-hosts.json");
1140 std::vector<base::string16> warnings =
1141 extension->permissions_data()->GetPermissionMessageStrings();
1142 ASSERT_EQ(1u, warnings.size());
1144 "Read and change your data on encrypted.google.com and "
1146 base::UTF16ToUTF8(warnings[0]));
1149 TEST(PermissionsTest, GetWarningMessages_Plugins) {
1150 scoped_refptr<Extension> extension;
1151 scoped_refptr<PermissionSet> permissions;
1153 extension = LoadManifest("permissions", "plugins.json");
1154 std::vector<base::string16> warnings =
1155 extension->permissions_data()->GetPermissionMessageStrings();
1156 // We don't parse the plugins key on Chrome OS, so it should not ask for any
1158 #if defined(OS_CHROMEOS)
1159 ASSERT_EQ(0u, warnings.size());
1161 ASSERT_EQ(1u, warnings.size());
1163 "Read and change all your data on your computer and the websites "
1165 base::UTF16ToUTF8(warnings[0]));
1169 TEST(PermissionsTest, GetWarningMessages_AudioVideo) {
1170 // Both audio and video present.
1171 scoped_refptr<Extension> extension =
1172 LoadManifest("permissions", "audio-video.json");
1173 const PermissionMessageProvider* provider = PermissionMessageProvider::Get();
1174 PermissionSet* set = const_cast<PermissionSet*>(
1175 extension->permissions_data()->active_permissions().get());
1176 std::vector<base::string16> warnings =
1177 provider->GetWarningMessages(set, extension->GetType());
1178 EXPECT_FALSE(Contains(warnings, "Use your microphone"));
1179 EXPECT_FALSE(Contains(warnings, "Use your camera"));
1180 EXPECT_TRUE(Contains(warnings, "Use your microphone and camera"));
1181 size_t combined_index = IndexOf(warnings, "Use your microphone and camera");
1182 size_t combined_size = warnings.size();
1184 // Just audio present.
1185 set->apis_.erase(APIPermission::kVideoCapture);
1186 warnings = provider->GetWarningMessages(set, extension->GetType());
1187 EXPECT_EQ(combined_size, warnings.size());
1188 EXPECT_EQ(combined_index, IndexOf(warnings, "Use your microphone"));
1189 EXPECT_FALSE(Contains(warnings, "Use your camera"));
1190 EXPECT_FALSE(Contains(warnings, "Use your microphone and camera"));
1192 // Just video present.
1193 set->apis_.erase(APIPermission::kAudioCapture);
1194 set->apis_.insert(APIPermission::kVideoCapture);
1195 warnings = provider->GetWarningMessages(set, extension->GetType());
1196 EXPECT_EQ(combined_size, warnings.size());
1197 EXPECT_FALSE(Contains(warnings, "Use your microphone"));
1198 EXPECT_FALSE(Contains(warnings, "Use your microphone and camera"));
1199 EXPECT_TRUE(Contains(warnings, "Use your camera"));
1202 TEST(PermissionsTest, GetWarningMessages_CombinedSessions) {
1204 APIPermissionSet api_permissions;
1205 api_permissions.insert(APIPermission::kTab);
1206 api_permissions.insert(APIPermission::kTopSites);
1207 api_permissions.insert(APIPermission::kProcesses);
1208 api_permissions.insert(APIPermission::kWebNavigation);
1209 api_permissions.insert(APIPermission::kSessions);
1210 scoped_refptr<PermissionSet> permissions(
1211 new PermissionSet(api_permissions, ManifestPermissionSet(),
1212 URLPatternSet(), URLPatternSet()));
1213 std::vector<base::string16> messages =
1214 PermissionMessageProvider::Get()->GetWarningMessages(
1215 permissions.get(), Manifest::TYPE_EXTENSION);
1216 EXPECT_EQ(1u, messages.size());
1217 EXPECT_EQ(l10n_util::GetStringUTF16(
1218 IDS_EXTENSION_PROMPT_WARNING_HISTORY_READ_AND_SESSIONS),
1222 APIPermissionSet api_permissions;
1223 api_permissions.insert(APIPermission::kHistory);
1224 api_permissions.insert(APIPermission::kTab);
1225 api_permissions.insert(APIPermission::kTopSites);
1226 api_permissions.insert(APIPermission::kProcesses);
1227 api_permissions.insert(APIPermission::kWebNavigation);
1228 api_permissions.insert(APIPermission::kSessions);
1229 scoped_refptr<PermissionSet> permissions(
1230 new PermissionSet(api_permissions, ManifestPermissionSet(),
1231 URLPatternSet(), URLPatternSet()));
1232 std::vector<base::string16> messages =
1233 PermissionMessageProvider::Get()->GetWarningMessages(
1234 permissions.get(), Manifest::TYPE_EXTENSION);
1235 EXPECT_EQ(1u, messages.size());
1236 EXPECT_EQ(l10n_util::GetStringUTF16(
1237 IDS_EXTENSION_PROMPT_WARNING_HISTORY_WRITE_AND_SESSIONS),
1242 TEST(PermissionsTest, GetWarningMessages_DeclarativeWebRequest) {
1243 // Test that if the declarativeWebRequest permission is present
1244 // in combination with all hosts permission, then only the warning
1245 // for host permissions is shown, because that covers the use of
1246 // declarativeWebRequest.
1248 // Until Declarative Web Request is in stable, let's make sure it is enabled
1249 // on the current channel.
1250 ScopedCurrentChannel sc(chrome::VersionInfo::CHANNEL_CANARY);
1252 // First verify that declarativeWebRequest produces a message when host
1253 // permissions do not cover all hosts.
1254 scoped_refptr<Extension> extension =
1255 LoadManifest("permissions", "web_request_not_all_host_permissions.json");
1256 const PermissionMessageProvider* provider = PermissionMessageProvider::Get();
1257 const PermissionSet* set =
1258 extension->permissions_data()->active_permissions().get();
1259 std::vector<base::string16> warnings =
1260 provider->GetWarningMessages(set, extension->GetType());
1261 EXPECT_TRUE(Contains(warnings, "Block parts of web pages"));
1262 EXPECT_FALSE(Contains(
1263 warnings, "Read and change all your data on the websites you visit"));
1265 // Now verify that declarativeWebRequest does not produce a message when host
1266 // permissions do cover all hosts.
1268 LoadManifest("permissions", "web_request_all_host_permissions.json");
1269 set = extension->permissions_data()->active_permissions().get();
1270 warnings = provider->GetWarningMessages(set, extension->GetType());
1271 EXPECT_FALSE(Contains(warnings, "Block parts of web pages"));
1272 EXPECT_TRUE(Contains(
1273 warnings, "Read and change all your data on the websites you visit"));
1276 TEST(PermissionsTest, GetWarningMessages_Serial) {
1277 scoped_refptr<Extension> extension =
1278 LoadManifest("permissions", "serial.json");
1280 EXPECT_TRUE(extension->is_platform_app());
1282 extension->permissions_data()->HasAPIPermission(APIPermission::kSerial));
1283 std::vector<base::string16> warnings =
1284 extension->permissions_data()->GetPermissionMessageStrings();
1285 EXPECT_TRUE(Contains(warnings, "Access your serial devices"));
1286 ASSERT_EQ(1u, warnings.size());
1289 TEST(PermissionsTest, GetWarningMessages_Socket_AnyHost) {
1290 ScopedCurrentChannel channel(chrome::VersionInfo::CHANNEL_DEV);
1292 scoped_refptr<Extension> extension =
1293 LoadManifest("permissions", "socket_any_host.json");
1294 EXPECT_TRUE(extension->is_platform_app());
1296 extension->permissions_data()->HasAPIPermission(APIPermission::kSocket));
1297 std::vector<base::string16> warnings =
1298 extension->permissions_data()->GetPermissionMessageStrings();
1299 EXPECT_EQ(1u, warnings.size());
1300 EXPECT_TRUE(Contains(warnings, "Exchange data with any computer "
1301 "on the local network or internet"));
1304 TEST(PermissionsTest, GetWarningMessages_Socket_OneDomainTwoHostnames) {
1305 ScopedCurrentChannel channel(chrome::VersionInfo::CHANNEL_DEV);
1307 scoped_refptr<Extension> extension =
1308 LoadManifest("permissions", "socket_one_domain_two_hostnames.json");
1309 EXPECT_TRUE(extension->is_platform_app());
1311 extension->permissions_data()->HasAPIPermission(APIPermission::kSocket));
1312 std::vector<base::string16> warnings =
1313 extension->permissions_data()->GetPermissionMessageStrings();
1315 // Verify the warnings, including support for unicode characters, the fact
1316 // that domain host warnings come before specific host warnings, and the fact
1317 // that domains and hostnames are in alphabetical order regardless of the
1318 // order in the manifest file.
1319 EXPECT_EQ(2u, warnings.size());
1320 if (warnings.size() > 0)
1321 EXPECT_EQ(warnings[0],
1322 base::UTF8ToUTF16("Exchange data with any computer in the domain "
1324 if (warnings.size() > 1)
1325 EXPECT_EQ(warnings[1],
1326 base::UTF8ToUTF16("Exchange data with the computers named: "
1327 "b\xC3\xA5r.example.com foo.example.com"));
1328 // "\xC3\xA5" = UTF-8 for lowercase A with ring above
1331 TEST(PermissionsTest, GetWarningMessages_Socket_TwoDomainsOneHostname) {
1332 ScopedCurrentChannel channel(chrome::VersionInfo::CHANNEL_DEV);
1334 scoped_refptr<Extension> extension =
1335 LoadManifest("permissions", "socket_two_domains_one_hostname.json");
1336 EXPECT_TRUE(extension->is_platform_app());
1338 extension->permissions_data()->HasAPIPermission(APIPermission::kSocket));
1339 std::vector<base::string16> warnings =
1340 extension->permissions_data()->GetPermissionMessageStrings();
1342 // Verify the warnings, including the fact that domain host warnings come
1343 // before specific host warnings and the fact that domains and hostnames are
1344 // in alphabetical order regardless of the order in the manifest file.
1345 EXPECT_EQ(2u, warnings.size());
1346 if (warnings.size() > 0)
1347 EXPECT_EQ(warnings[0],
1348 base::UTF8ToUTF16("Exchange data with any computer in the "
1349 "domains: example.com foo.example.org"));
1350 if (warnings.size() > 1)
1351 EXPECT_EQ(warnings[1],
1352 base::UTF8ToUTF16("Exchange data with the computer named "
1353 "bar.example.org"));
1356 TEST(PermissionsTest, GetWarningMessages_PlatformApppHosts) {
1357 scoped_refptr<Extension> extension;
1359 extension = LoadManifest("permissions", "platform_app_hosts.json");
1360 EXPECT_TRUE(extension->is_platform_app());
1361 std::vector<base::string16> warnings =
1362 extension->permissions_data()->GetPermissionMessageStrings();
1363 ASSERT_EQ(0u, warnings.size());
1365 extension = LoadManifest("permissions", "platform_app_all_urls.json");
1366 EXPECT_TRUE(extension->is_platform_app());
1367 warnings = extension->permissions_data()->GetPermissionMessageStrings();
1368 ASSERT_EQ(0u, warnings.size());
1371 bool ShowsAllHostsWarning(const std::string& pattern) {
1372 scoped_refptr<Extension> extension =
1374 .SetManifest(DictionaryBuilder()
1375 .Set("name", "TLDWildCardTest")
1376 .Set("version", "0.1.0")
1377 .Set("permissions", ListBuilder().Append(pattern))
1381 std::vector<base::string16> warnings =
1382 extension->permissions_data()->GetPermissionMessageStrings();
1384 if (warnings.empty())
1388 l10n_util::GetStringUTF16(IDS_EXTENSION_PROMPT_WARNING_ALL_HOSTS)) {
1395 TEST(PermissionsTest, GetWarningMessages_TLDWildcardTreatedAsAllHosts) {
1396 EXPECT_TRUE(ShowsAllHostsWarning("http://*.com/*")); // most popular.
1397 EXPECT_TRUE(ShowsAllHostsWarning("http://*.org/*")); // sanity check.
1398 EXPECT_TRUE(ShowsAllHostsWarning("http://*.co.uk/*")); // eTLD.
1399 EXPECT_TRUE(ShowsAllHostsWarning("http://*.de/*")); // foreign country tld.
1401 // We should still show the normal permissions (i.e., "Can access your data on
1402 // *.rdcronin.com") for things that are not TLDs.
1403 EXPECT_FALSE(ShowsAllHostsWarning("http://*.rdcronin.com/*"));
1405 // Pseudo-TLDs, like appspot.com, should not show all hosts.
1406 EXPECT_FALSE(ShowsAllHostsWarning("http://*.appspot.com/*"));
1408 // Non-TLDs should be likewise exempt.
1409 EXPECT_FALSE(ShowsAllHostsWarning("http://*.notarealtld/*"));
1411 // Our internal checks use "foo", so let's make sure we're not messing
1412 // something up with it.
1413 EXPECT_FALSE(ShowsAllHostsWarning("http://*.foo.com"));
1414 EXPECT_FALSE(ShowsAllHostsWarning("http://foo.com"));
1415 // This will fail if foo becomes a recognized TLD. Which could be soon.
1416 // Update as needed.
1417 EXPECT_FALSE(ShowsAllHostsWarning("http://*.foo"));
1420 TEST(PermissionsTest, GetDistinctHosts) {
1421 URLPatternSet explicit_hosts;
1422 std::set<std::string> expected;
1423 expected.insert("www.foo.com");
1424 expected.insert("www.bar.com");
1425 expected.insert("www.baz.com");
1428 SCOPED_TRACE("no dupes");
1430 // Simple list with no dupes.
1431 explicit_hosts.AddPattern(
1432 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.com/path"));
1433 explicit_hosts.AddPattern(
1434 URLPattern(URLPattern::SCHEME_HTTP, "http://www.bar.com/path"));
1435 explicit_hosts.AddPattern(
1436 URLPattern(URLPattern::SCHEME_HTTP, "http://www.baz.com/path"));
1438 permission_message_util::GetDistinctHosts(
1439 explicit_hosts, true, true));
1443 SCOPED_TRACE("two dupes");
1446 explicit_hosts.AddPattern(
1447 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.com/path"));
1448 explicit_hosts.AddPattern(
1449 URLPattern(URLPattern::SCHEME_HTTP, "http://www.baz.com/path"));
1451 permission_message_util::GetDistinctHosts(
1452 explicit_hosts, true, true));
1456 SCOPED_TRACE("schemes differ");
1458 // Add a pattern that differs only by scheme. This should be filtered out.
1459 explicit_hosts.AddPattern(
1460 URLPattern(URLPattern::SCHEME_HTTPS, "https://www.bar.com/path"));
1462 permission_message_util::GetDistinctHosts(
1463 explicit_hosts, true, true));
1467 SCOPED_TRACE("paths differ");
1469 // Add some dupes by path.
1470 explicit_hosts.AddPattern(
1471 URLPattern(URLPattern::SCHEME_HTTP, "http://www.bar.com/pathypath"));
1473 permission_message_util::GetDistinctHosts(
1474 explicit_hosts, true, true));
1478 SCOPED_TRACE("subdomains differ");
1480 // We don't do anything special for subdomains.
1481 explicit_hosts.AddPattern(
1482 URLPattern(URLPattern::SCHEME_HTTP, "http://monkey.www.bar.com/path"));
1483 explicit_hosts.AddPattern(
1484 URLPattern(URLPattern::SCHEME_HTTP, "http://bar.com/path"));
1486 expected.insert("monkey.www.bar.com");
1487 expected.insert("bar.com");
1490 permission_message_util::GetDistinctHosts(
1491 explicit_hosts, true, true));
1495 SCOPED_TRACE("RCDs differ");
1497 // Now test for RCD uniquing.
1498 explicit_hosts.AddPattern(
1499 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.com/path"));
1500 explicit_hosts.AddPattern(
1501 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.co.uk/path"));
1502 explicit_hosts.AddPattern(
1503 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.de/path"));
1504 explicit_hosts.AddPattern(
1505 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.ca.us/path"));
1506 explicit_hosts.AddPattern(
1507 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.net/path"));
1508 explicit_hosts.AddPattern(
1509 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.com.my/path"));
1511 // This is an unknown RCD, which shouldn't be uniqued out.
1512 explicit_hosts.AddPattern(
1513 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.xyzzy/path"));
1514 // But it should only occur once.
1515 explicit_hosts.AddPattern(
1516 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.xyzzy/path"));
1518 expected.insert("www.foo.xyzzy");
1521 permission_message_util::GetDistinctHosts(
1522 explicit_hosts, true, true));
1526 SCOPED_TRACE("wildcards");
1528 explicit_hosts.AddPattern(
1529 URLPattern(URLPattern::SCHEME_HTTP, "http://*.google.com/*"));
1531 expected.insert("*.google.com");
1534 permission_message_util::GetDistinctHosts(
1535 explicit_hosts, true, true));
1539 SCOPED_TRACE("scriptable hosts");
1541 APIPermissionSet empty_perms;
1542 explicit_hosts.ClearPatterns();
1543 URLPatternSet scriptable_hosts;
1546 explicit_hosts.AddPattern(
1547 URLPattern(URLPattern::SCHEME_HTTP, "http://*.google.com/*"));
1548 scriptable_hosts.AddPattern(
1549 URLPattern(URLPattern::SCHEME_HTTP, "http://*.example.com/*"));
1551 expected.insert("*.google.com");
1552 expected.insert("*.example.com");
1554 scoped_refptr<PermissionSet> perm_set(new PermissionSet(
1555 empty_perms, ManifestPermissionSet(),
1556 explicit_hosts, scriptable_hosts));
1558 permission_message_util::GetDistinctHosts(
1559 perm_set->effective_hosts(), true, true));
1563 // We don't display warnings for file URLs because they are off by default.
1564 SCOPED_TRACE("file urls");
1566 explicit_hosts.ClearPatterns();
1569 explicit_hosts.AddPattern(
1570 URLPattern(URLPattern::SCHEME_FILE, "file:///*"));
1573 permission_message_util::GetDistinctHosts(
1574 explicit_hosts, true, true));
1578 TEST(PermissionsTest, GetDistinctHosts_ComIsBestRcd) {
1579 URLPatternSet explicit_hosts;
1580 explicit_hosts.AddPattern(
1581 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.ca/path"));
1582 explicit_hosts.AddPattern(
1583 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.org/path"));
1584 explicit_hosts.AddPattern(
1585 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.co.uk/path"));
1586 explicit_hosts.AddPattern(
1587 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.net/path"));
1588 explicit_hosts.AddPattern(
1589 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.jp/path"));
1590 explicit_hosts.AddPattern(
1591 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.com/path"));
1593 std::set<std::string> expected;
1594 expected.insert("www.foo.com");
1596 permission_message_util::GetDistinctHosts(
1597 explicit_hosts, true, true));
1600 TEST(PermissionsTest, GetDistinctHosts_NetIs2ndBestRcd) {
1601 URLPatternSet explicit_hosts;
1602 explicit_hosts.AddPattern(
1603 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.ca/path"));
1604 explicit_hosts.AddPattern(
1605 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.org/path"));
1606 explicit_hosts.AddPattern(
1607 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.co.uk/path"));
1608 explicit_hosts.AddPattern(
1609 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.net/path"));
1610 explicit_hosts.AddPattern(
1611 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.jp/path"));
1612 // No http://www.foo.com/path
1614 std::set<std::string> expected;
1615 expected.insert("www.foo.net");
1617 permission_message_util::GetDistinctHosts(
1618 explicit_hosts, true, true));
1621 TEST(PermissionsTest, GetDistinctHosts_OrgIs3rdBestRcd) {
1622 URLPatternSet explicit_hosts;
1623 explicit_hosts.AddPattern(
1624 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.ca/path"));
1625 explicit_hosts.AddPattern(
1626 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.org/path"));
1627 explicit_hosts.AddPattern(
1628 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.co.uk/path"));
1629 // No http://www.foo.net/path
1630 explicit_hosts.AddPattern(
1631 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.jp/path"));
1632 // No http://www.foo.com/path
1634 std::set<std::string> expected;
1635 expected.insert("www.foo.org");
1637 permission_message_util::GetDistinctHosts(
1638 explicit_hosts, true, true));
1641 TEST(PermissionsTest, GetDistinctHosts_FirstInListIs4thBestRcd) {
1642 URLPatternSet explicit_hosts;
1643 explicit_hosts.AddPattern(
1644 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.ca/path"));
1645 // No http://www.foo.org/path
1646 explicit_hosts.AddPattern(
1647 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.co.uk/path"));
1648 // No http://www.foo.net/path
1649 explicit_hosts.AddPattern(
1650 URLPattern(URLPattern::SCHEME_HTTP, "http://www.foo.jp/path"));
1651 // No http://www.foo.com/path
1653 std::set<std::string> expected;
1654 expected.insert("www.foo.ca");
1656 permission_message_util::GetDistinctHosts(
1657 explicit_hosts, true, true));
1660 TEST(PermissionsTest, IsHostPrivilegeIncrease) {
1661 Manifest::Type type = Manifest::TYPE_EXTENSION;
1662 const PermissionMessageProvider* provider = PermissionMessageProvider::Get();
1663 ManifestPermissionSet empty_manifest_permissions;
1664 URLPatternSet elist1;
1665 URLPatternSet elist2;
1666 URLPatternSet slist1;
1667 URLPatternSet slist2;
1668 scoped_refptr<PermissionSet> set1;
1669 scoped_refptr<PermissionSet> set2;
1670 APIPermissionSet empty_perms;
1672 URLPattern(URLPattern::SCHEME_HTTP, "http://www.google.com.hk/path"));
1674 URLPattern(URLPattern::SCHEME_HTTP, "http://www.google.com/path"));
1676 // Test that the host order does not matter.
1678 URLPattern(URLPattern::SCHEME_HTTP, "http://www.google.com/path"));
1680 URLPattern(URLPattern::SCHEME_HTTP, "http://www.google.com.hk/path"));
1682 set1 = new PermissionSet(empty_perms, empty_manifest_permissions,
1684 set2 = new PermissionSet(empty_perms, empty_manifest_permissions,
1687 EXPECT_FALSE(provider->IsPrivilegeIncrease(set1.get(), set2.get(), type));
1688 EXPECT_FALSE(provider->IsPrivilegeIncrease(set2.get(), set1.get(), type));
1690 // Test that paths are ignored.
1691 elist2.ClearPatterns();
1693 URLPattern(URLPattern::SCHEME_HTTP, "http://www.google.com/*"));
1694 set2 = new PermissionSet(empty_perms, empty_manifest_permissions,
1696 EXPECT_FALSE(provider->IsPrivilegeIncrease(set1.get(), set2.get(), type));
1697 EXPECT_FALSE(provider->IsPrivilegeIncrease(set2.get(), set1.get(), type));
1699 // Test that RCDs are ignored.
1700 elist2.ClearPatterns();
1702 URLPattern(URLPattern::SCHEME_HTTP, "http://www.google.com.hk/*"));
1703 set2 = new PermissionSet(empty_perms, empty_manifest_permissions,
1705 EXPECT_FALSE(provider->IsPrivilegeIncrease(set1.get(), set2.get(), type));
1706 EXPECT_FALSE(provider->IsPrivilegeIncrease(set2.get(), set1.get(), type));
1708 // Test that subdomain wildcards are handled properly.
1709 elist2.ClearPatterns();
1711 URLPattern(URLPattern::SCHEME_HTTP, "http://*.google.com.hk/*"));
1712 set2 = new PermissionSet(empty_perms, empty_manifest_permissions,
1714 EXPECT_TRUE(provider->IsPrivilegeIncrease(set1.get(), set2.get(), type));
1715 // TODO(jstritar): Does not match subdomains properly. http://crbug.com/65337
1716 // EXPECT_FALSE(provider->IsPrivilegeIncrease(set2, set1, type));
1718 // Test that different domains count as different hosts.
1719 elist2.ClearPatterns();
1721 URLPattern(URLPattern::SCHEME_HTTP, "http://www.google.com/path"));
1723 URLPattern(URLPattern::SCHEME_HTTP, "http://www.example.org/path"));
1724 set2 = new PermissionSet(empty_perms, empty_manifest_permissions,
1726 EXPECT_TRUE(provider->IsPrivilegeIncrease(set1.get(), set2.get(), type));
1727 EXPECT_FALSE(provider->IsPrivilegeIncrease(set2.get(), set1.get(), type));
1729 // Test that different subdomains count as different hosts.
1730 elist2.ClearPatterns();
1732 URLPattern(URLPattern::SCHEME_HTTP, "http://mail.google.com/*"));
1733 set2 = new PermissionSet(empty_perms, empty_manifest_permissions,
1735 EXPECT_TRUE(provider->IsPrivilegeIncrease(set1.get(), set2.get(), type));
1736 EXPECT_TRUE(provider->IsPrivilegeIncrease(set2.get(), set1.get(), type));
1738 // Test that platform apps do not have host permissions increases.
1739 type = Manifest::TYPE_PLATFORM_APP;
1740 EXPECT_FALSE(provider->IsPrivilegeIncrease(set1.get(), set2.get(), type));
1741 EXPECT_FALSE(provider->IsPrivilegeIncrease(set2.get(), set1.get(), type));
1744 TEST(PermissionsTest, GetAPIsAsStrings) {
1745 APIPermissionSet apis;
1746 URLPatternSet empty_set;
1748 apis.insert(APIPermission::kProxy);
1749 apis.insert(APIPermission::kBackground);
1750 apis.insert(APIPermission::kNotifications);
1751 apis.insert(APIPermission::kTab);
1753 scoped_refptr<PermissionSet> perm_set = new PermissionSet(
1754 apis, ManifestPermissionSet(), empty_set, empty_set);
1755 std::set<std::string> api_names = perm_set->GetAPIsAsStrings();
1757 // The result is correct if it has the same number of elements
1758 // and we can convert it back to the id set.
1759 EXPECT_EQ(4u, api_names.size());
1761 PermissionsInfo::GetInstance()->GetAllByName(api_names));
1764 TEST(PermissionsTest, IsEmpty) {
1765 APIPermissionSet empty_apis;
1766 URLPatternSet empty_extent;
1768 scoped_refptr<PermissionSet> empty = new PermissionSet();
1769 EXPECT_TRUE(empty->IsEmpty());
1770 scoped_refptr<PermissionSet> perm_set;
1772 perm_set = new PermissionSet(empty_apis, ManifestPermissionSet(),
1773 empty_extent, empty_extent);
1774 EXPECT_TRUE(perm_set->IsEmpty());
1776 APIPermissionSet non_empty_apis;
1777 non_empty_apis.insert(APIPermission::kBackground);
1778 perm_set = new PermissionSet(non_empty_apis, ManifestPermissionSet(),
1779 empty_extent, empty_extent);
1780 EXPECT_FALSE(perm_set->IsEmpty());
1782 // Try non standard host
1783 URLPatternSet non_empty_extent;
1784 AddPattern(&non_empty_extent, "http://www.google.com/*");
1786 perm_set = new PermissionSet(empty_apis, ManifestPermissionSet(),
1787 non_empty_extent, empty_extent);
1788 EXPECT_FALSE(perm_set->IsEmpty());
1790 perm_set = new PermissionSet(empty_apis, ManifestPermissionSet(),
1791 empty_extent, non_empty_extent);
1792 EXPECT_FALSE(perm_set->IsEmpty());
1795 TEST(PermissionsTest, ImpliedPermissions) {
1796 URLPatternSet empty_extent;
1797 APIPermissionSet apis;
1798 apis.insert(APIPermission::kFileBrowserHandler);
1799 EXPECT_EQ(1U, apis.size());
1801 scoped_refptr<PermissionSet> perm_set;
1802 perm_set = new PermissionSet(apis, ManifestPermissionSet(),
1803 empty_extent, empty_extent);
1804 EXPECT_EQ(2U, perm_set->apis().size());
1807 TEST(PermissionsTest, SyncFileSystemPermission) {
1808 scoped_refptr<Extension> extension = LoadManifest(
1809 "permissions", "sync_file_system.json");
1810 APIPermissionSet apis;
1811 apis.insert(APIPermission::kSyncFileSystem);
1812 EXPECT_TRUE(extension->is_platform_app());
1813 EXPECT_TRUE(extension->permissions_data()->HasAPIPermission(
1814 APIPermission::kSyncFileSystem));
1815 std::vector<base::string16> warnings =
1816 extension->permissions_data()->GetPermissionMessageStrings();
1817 EXPECT_TRUE(Contains(warnings, "Store data in your Google Drive account"));
1818 ASSERT_EQ(1u, warnings.size());
1821 // Make sure that we don't crash when we're trying to show the permissions
1822 // even though chrome://thumb (and everything that's not chrome://favicon with
1823 // a chrome:// scheme) is not a valid permission.
1824 // More details here: crbug/246314.
1825 TEST(PermissionsTest, ChromeURLs) {
1826 URLPatternSet allowed_hosts;
1827 allowed_hosts.AddPattern(
1828 URLPattern(URLPattern::SCHEME_ALL, "http://www.google.com/"));
1829 allowed_hosts.AddPattern(
1830 URLPattern(URLPattern::SCHEME_ALL, "chrome://favicon/"));
1831 allowed_hosts.AddPattern(
1832 URLPattern(URLPattern::SCHEME_ALL, "chrome://thumb/"));
1833 scoped_refptr<PermissionSet> permissions(
1834 new PermissionSet(APIPermissionSet(), ManifestPermissionSet(),
1835 allowed_hosts, URLPatternSet()));
1836 PermissionMessageProvider::Get()->GetPermissionMessages(
1837 permissions.get(), Manifest::TYPE_EXTENSION);
1840 TEST(PermissionsTest, IsPrivilegeIncrease_DeclarativeWebRequest) {
1841 scoped_refptr<Extension> extension(
1842 LoadManifest("permissions", "permissions_all_urls.json"));
1843 scoped_refptr<const PermissionSet> permissions(
1844 extension->permissions_data()->active_permissions());
1846 scoped_refptr<Extension> extension_dwr(
1847 LoadManifest("permissions", "web_request_all_host_permissions.json"));
1848 scoped_refptr<const PermissionSet> permissions_dwr(
1849 extension_dwr->permissions_data()->active_permissions());
1851 EXPECT_FALSE(PermissionMessageProvider::Get()->
1852 IsPrivilegeIncrease(permissions.get(),
1853 permissions_dwr.get(),
1854 extension->GetType()));
1857 } // namespace extensions