1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #include <algorithm> 6 #include <set> 7 #include <vector> 8 9 #include "base/at_exit.h" 10 #include "base/basictypes.h" 11 #include "base/bind.h" 12 #include "base/command_line.h" 13 #include "base/file_util.h" 14 #include "base/files/file_enumerator.h" 15 #include "base/files/scoped_temp_dir.h" 16 #include "base/json/json_file_value_serializer.h" 17 #include "base/json/json_reader.h" 18 #include "base/json/json_string_value_serializer.h" 19 #include "base/memory/scoped_ptr.h" 20 #include "base/memory/weak_ptr.h" 21 #include "base/message_loop/message_loop.h" 22 #include "base/prefs/scoped_user_pref_update.h" 23 #include "base/stl_util.h" 24 #include "base/strings/string16.h" 25 #include "base/strings/string_number_conversions.h" 26 #include "base/strings/string_util.h" 27 #include "base/strings/utf_string_conversions.h" 28 #include "base/version.h" 29 #include "chrome/browser/browser_process.h" 30 #include "chrome/browser/chrome_notification_types.h" 31 #include "chrome/browser/extensions/app_sync_data.h" 32 #include "chrome/browser/extensions/blacklist.h" 33 #include "chrome/browser/extensions/chrome_app_sorting.h" 34 #include "chrome/browser/extensions/component_loader.h" 35 #include "chrome/browser/extensions/crx_installer.h" 36 #include "chrome/browser/extensions/default_apps.h" 37 #include "chrome/browser/extensions/extension_creator.h" 38 #include "chrome/browser/extensions/extension_error_reporter.h" 39 #include "chrome/browser/extensions/extension_error_ui.h" 40 #include "chrome/browser/extensions/extension_notification_observer.h" 41 #include "chrome/browser/extensions/extension_service.h" 42 #include "chrome/browser/extensions/extension_service_test_base.h" 43 #include "chrome/browser/extensions/extension_special_storage_policy.h" 44 #include "chrome/browser/extensions/extension_sync_data.h" 45 #include "chrome/browser/extensions/extension_sync_service.h" 46 #include "chrome/browser/extensions/extension_util.h" 47 #include "chrome/browser/extensions/external_install_ui.h" 48 #include "chrome/browser/extensions/external_policy_loader.h" 49 #include "chrome/browser/extensions/external_pref_loader.h" 50 #include "chrome/browser/extensions/external_provider_impl.h" 51 #include "chrome/browser/extensions/fake_safe_browsing_database_manager.h" 52 #include "chrome/browser/extensions/installed_loader.h" 53 #include "chrome/browser/extensions/pack_extension_job.h" 54 #include "chrome/browser/extensions/pending_extension_info.h" 55 #include "chrome/browser/extensions/pending_extension_manager.h" 56 #include "chrome/browser/extensions/test_blacklist.h" 57 #include "chrome/browser/extensions/test_extension_system.h" 58 #include "chrome/browser/extensions/unpacked_installer.h" 59 #include "chrome/browser/extensions/updater/extension_updater.h" 60 #include "chrome/browser/prefs/pref_service_syncable.h" 61 #include "chrome/browser/sync/profile_sync_service.h" 62 #include "chrome/browser/sync/profile_sync_service_factory.h" 63 #include "chrome/common/chrome_constants.h" 64 #include "chrome/common/chrome_switches.h" 65 #include "chrome/common/extensions/api/plugins/plugins_handler.h" 66 #include "chrome/common/extensions/manifest_handlers/app_launch_info.h" 67 #include "chrome/common/extensions/manifest_handlers/content_scripts_handler.h" 68 #include "chrome/common/extensions/manifest_url_handler.h" 69 #include "chrome/common/pref_names.h" 70 #include "chrome/common/url_constants.h" 71 #include "chrome/test/base/scoped_browser_locale.h" 72 #include "chrome/test/base/testing_profile.h" 73 #include "components/pref_registry/pref_registry_syncable.h" 74 #include "content/public/browser/dom_storage_context.h" 75 #include "content/public/browser/gpu_data_manager.h" 76 #include "content/public/browser/indexed_db_context.h" 77 #include "content/public/browser/notification_registrar.h" 78 #include "content/public/browser/notification_service.h" 79 #include "content/public/browser/plugin_service.h" 80 #include "content/public/browser/render_process_host.h" 81 #include "content/public/browser/storage_partition.h" 82 #include "content/public/common/content_constants.h" 83 #include "content/public/test/test_utils.h" 84 #include "extensions/browser/extension_registry.h" 85 #include "extensions/browser/extension_system.h" 86 #include "extensions/browser/external_provider_interface.h" 87 #include "extensions/browser/install_flag.h" 88 #include "extensions/browser/management_policy.h" 89 #include "extensions/browser/pref_names.h" 90 #include "extensions/browser/test_management_policy.h" 91 #include "extensions/common/constants.h" 92 #include "extensions/common/extension.h" 93 #include "extensions/common/extension_builder.h" 94 #include "extensions/common/extension_l10n_util.h" 95 #include "extensions/common/extension_resource.h" 96 #include "extensions/common/feature_switch.h" 97 #include "extensions/common/manifest_constants.h" 98 #include "extensions/common/manifest_handlers/background_info.h" 99 #include "extensions/common/permissions/permission_set.h" 100 #include "extensions/common/permissions/permissions_data.h" 101 #include "extensions/common/switches.h" 102 #include "extensions/common/url_pattern.h" 103 #include "extensions/common/value_builder.h" 104 #include "gpu/config/gpu_info.h" 105 #include "grit/browser_resources.h" 106 #include "net/cookies/canonical_cookie.h" 107 #include "net/cookies/cookie_monster.h" 108 #include "net/cookies/cookie_options.h" 109 #include "net/url_request/url_request_context.h" 110 #include "net/url_request/url_request_context_getter.h" 111 #include "sync/api/fake_sync_change_processor.h" 112 #include "sync/api/string_ordinal.h" 113 #include "sync/api/sync_data.h" 114 #include "sync/api/sync_error_factory.h" 115 #include "sync/api/sync_error_factory_mock.h" 116 #include "sync/api/syncable_service.h" 117 #include "sync/protocol/app_specifics.pb.h" 118 #include "sync/protocol/extension_specifics.pb.h" 119 #include "sync/protocol/sync.pb.h" 120 #include "testing/gtest/include/gtest/gtest.h" 121 #include "testing/platform_test.h" 122 #include "url/gurl.h" 123 #include "webkit/browser/database/database_tracker.h" 124 #include "webkit/browser/quota/quota_manager.h" 125 #include "webkit/common/database/database_identifier.h" 126 127 #if defined(OS_CHROMEOS) 128 #include "chrome/browser/chromeos/login/users/user_manager.h" 129 #include "chrome/browser/chromeos/settings/cros_settings.h" 130 #include "chrome/browser/chromeos/settings/device_settings_service.h" 131 #endif 132 133 // The blacklist tests rely on safe browsing. 134 #if defined(FULL_SAFE_BROWSING) || defined(MOBILE_SAFE_BROWSING) 135 #define ENABLE_BLACKLIST_TESTS 136 #endif 137 138 using base::DictionaryValue; 139 using base::ListValue; 140 using base::Value; 141 using content::BrowserContext; 142 using content::BrowserThread; 143 using content::DOMStorageContext; 144 using content::IndexedDBContext; 145 using content::PluginService; 146 using extensions::APIPermission; 147 using extensions::APIPermissionSet; 148 using extensions::AppSorting; 149 using extensions::Blacklist; 150 using extensions::CrxInstaller; 151 using extensions::Extension; 152 using extensions::ExtensionCreator; 153 using extensions::ExtensionPrefs; 154 using extensions::ExtensionRegistry; 155 using extensions::ExtensionResource; 156 using extensions::ExtensionSystem; 157 using extensions::FakeSafeBrowsingDatabaseManager; 158 using extensions::FeatureSwitch; 159 using extensions::Manifest; 160 using extensions::PermissionSet; 161 using extensions::TestExtensionSystem; 162 using extensions::UnloadedExtensionInfo; 163 using extensions::URLPatternSet; 164 165 namespace keys = extensions::manifest_keys; 166 167 namespace { 168 169 // Extension ids used during testing. 170 const char good0[] = "behllobkkfkfnphdnhnkndlbkcpglgmj"; 171 const char good1[] = "hpiknbiabeeppbpihjehijgoemciehgk"; 172 const char good2[] = "bjafgdebaacbbbecmhlhpofkepfkgcpa"; 173 const char all_zero[] = "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"; 174 const char good2048[] = "nmgjhmhbleinmjpbdhgajfjkbijcmgbh"; 175 const char good_crx[] = "ldnnhddmnhbkjipkidpdiheffobcpfmf"; 176 const char hosted_app[] = "kbmnembihfiondgfjekmnmcbddelicoi"; 177 const char page_action[] = "obcimlgaoabeegjmmpldobjndiealpln"; 178 const char theme_crx[] = "iamefpfkojoapidjnbafmgkgncegbkad"; 179 const char theme2_crx[] = "pjpgmfcmabopnnfonnhmdjglfpjjfkbf"; 180 const char permissions_crx[] = "eagpmdpfmaekmmcejjbmjoecnejeiiin"; 181 const char unpacked[] = "cbcdidchbppangcjoddlpdjlenngjldk"; 182 const char updates_from_webstore[] = "akjooamlhcgeopfifcmlggaebeocgokj"; 183 184 struct ExtensionsOrder { 185 bool operator()(const scoped_refptr<const Extension>& a, 186 const scoped_refptr<const Extension>& b) { 187 return a->name() < b->name(); 188 } 189 }; 190 191 static std::vector<base::string16> GetErrors() { 192 const std::vector<base::string16>* errors = 193 ExtensionErrorReporter::GetInstance()->GetErrors(); 194 std::vector<base::string16> ret_val; 195 196 for (std::vector<base::string16>::const_iterator iter = errors->begin(); 197 iter != errors->end(); ++iter) { 198 std::string utf8_error = base::UTF16ToUTF8(*iter); 199 if (utf8_error.find(".svn") == std::string::npos) { 200 ret_val.push_back(*iter); 201 } 202 } 203 204 // The tests rely on the errors being in a certain order, which can vary 205 // depending on how filesystem iteration works. 206 std::stable_sort(ret_val.begin(), ret_val.end()); 207 208 return ret_val; 209 } 210 211 static void AddPattern(URLPatternSet* extent, const std::string& pattern) { 212 int schemes = URLPattern::SCHEME_ALL; 213 extent->AddPattern(URLPattern(schemes, pattern)); 214 } 215 216 base::FilePath GetTemporaryFile() { 217 base::FilePath temp_file; 218 CHECK(base::CreateTemporaryFile(&temp_file)); 219 return temp_file; 220 } 221 222 bool WaitForCountNotificationsCallback(int *count) { 223 return --(*count) == 0; 224 } 225 226 } // namespace 227 228 class MockExtensionProvider : public extensions::ExternalProviderInterface { 229 public: 230 MockExtensionProvider( 231 VisitorInterface* visitor, 232 Manifest::Location location) 233 : location_(location), visitor_(visitor), visit_count_(0) { 234 } 235 236 virtual ~MockExtensionProvider() {} 237 238 void UpdateOrAddExtension(const std::string& id, 239 const std::string& version, 240 const base::FilePath& path) { 241 extension_map_[id] = std::make_pair(version, path); 242 } 243 244 void RemoveExtension(const std::string& id) { 245 extension_map_.erase(id); 246 } 247 248 // ExternalProvider implementation: 249 virtual void VisitRegisteredExtension() OVERRIDE { 250 visit_count_++; 251 for (DataMap::const_iterator i = extension_map_.begin(); 252 i != extension_map_.end(); ++i) { 253 Version version(i->second.first); 254 255 visitor_->OnExternalExtensionFileFound( 256 i->first, &version, i->second.second, location_, 257 Extension::NO_FLAGS, false); 258 } 259 visitor_->OnExternalProviderReady(this); 260 } 261 262 virtual bool HasExtension(const std::string& id) const OVERRIDE { 263 return extension_map_.find(id) != extension_map_.end(); 264 } 265 266 virtual bool GetExtensionDetails( 267 const std::string& id, 268 Manifest::Location* location, 269 scoped_ptr<Version>* version) const OVERRIDE { 270 DataMap::const_iterator it = extension_map_.find(id); 271 if (it == extension_map_.end()) 272 return false; 273 274 if (version) 275 version->reset(new Version(it->second.first)); 276 277 if (location) 278 *location = location_; 279 280 return true; 281 } 282 283 virtual bool IsReady() const OVERRIDE { 284 return true; 285 } 286 287 virtual void ServiceShutdown() OVERRIDE { 288 } 289 290 int visit_count() const { return visit_count_; } 291 void set_visit_count(int visit_count) { 292 visit_count_ = visit_count; 293 } 294 295 private: 296 typedef std::map< std::string, std::pair<std::string, base::FilePath> > 297 DataMap; 298 DataMap extension_map_; 299 Manifest::Location location_; 300 VisitorInterface* visitor_; 301 302 // visit_count_ tracks the number of calls to VisitRegisteredExtension(). 303 // Mutable because it must be incremented on each call to 304 // VisitRegisteredExtension(), which must be a const method to inherit 305 // from the class being mocked. 306 mutable int visit_count_; 307 308 DISALLOW_COPY_AND_ASSIGN(MockExtensionProvider); 309 }; 310 311 class MockProviderVisitor 312 : public extensions::ExternalProviderInterface::VisitorInterface { 313 public: 314 // The provider will return |fake_base_path| from 315 // GetBaseCrxFilePath(). User can test the behavior with 316 // and without an empty path using this parameter. 317 explicit MockProviderVisitor(base::FilePath fake_base_path) 318 : ids_found_(0), 319 fake_base_path_(fake_base_path), 320 expected_creation_flags_(Extension::NO_FLAGS) { 321 profile_.reset(new TestingProfile); 322 } 323 324 MockProviderVisitor(base::FilePath fake_base_path, 325 int expected_creation_flags) 326 : ids_found_(0), 327 fake_base_path_(fake_base_path), 328 expected_creation_flags_(expected_creation_flags) { 329 } 330 331 int Visit(const std::string& json_data) { 332 // Give the test json file to the provider for parsing. 333 provider_.reset(new extensions::ExternalProviderImpl( 334 this, 335 new extensions::ExternalTestingLoader(json_data, fake_base_path_), 336 profile_.get(), 337 Manifest::EXTERNAL_PREF, 338 Manifest::EXTERNAL_PREF_DOWNLOAD, 339 Extension::NO_FLAGS)); 340 341 // We also parse the file into a dictionary to compare what we get back 342 // from the provider. 343 JSONStringValueSerializer serializer(json_data); 344 base::Value* json_value = serializer.Deserialize(NULL, NULL); 345 346 if (!json_value || !json_value->IsType(base::Value::TYPE_DICTIONARY)) { 347 NOTREACHED() << "Unable to deserialize json data"; 348 return -1; 349 } else { 350 base::DictionaryValue* external_extensions = 351 static_cast<base::DictionaryValue*>(json_value); 352 prefs_.reset(external_extensions); 353 } 354 355 // Reset our counter. 356 ids_found_ = 0; 357 // Ask the provider to look up all extensions and return them. 358 provider_->VisitRegisteredExtension(); 359 360 return ids_found_; 361 } 362 363 virtual bool OnExternalExtensionFileFound(const std::string& id, 364 const Version* version, 365 const base::FilePath& path, 366 Manifest::Location unused, 367 int creation_flags, 368 bool mark_acknowledged) OVERRIDE { 369 EXPECT_EQ(expected_creation_flags_, creation_flags); 370 371 ++ids_found_; 372 base::DictionaryValue* pref; 373 // This tests is to make sure that the provider only notifies us of the 374 // values we gave it. So if the id we doesn't exist in our internal 375 // dictionary then something is wrong. 376 EXPECT_TRUE(prefs_->GetDictionary(id, &pref)) 377 << "Got back ID (" << id.c_str() << ") we weren't expecting"; 378 379 EXPECT_TRUE(path.IsAbsolute()); 380 if (!fake_base_path_.empty()) 381 EXPECT_TRUE(fake_base_path_.IsParent(path)); 382 383 if (pref) { 384 EXPECT_TRUE(provider_->HasExtension(id)); 385 386 // Ask provider if the extension we got back is registered. 387 Manifest::Location location = Manifest::INVALID_LOCATION; 388 scoped_ptr<Version> v1; 389 base::FilePath crx_path; 390 391 EXPECT_TRUE(provider_->GetExtensionDetails(id, NULL, &v1)); 392 EXPECT_STREQ(version->GetString().c_str(), v1->GetString().c_str()); 393 394 scoped_ptr<Version> v2; 395 EXPECT_TRUE(provider_->GetExtensionDetails(id, &location, &v2)); 396 EXPECT_STREQ(version->GetString().c_str(), v1->GetString().c_str()); 397 EXPECT_STREQ(version->GetString().c_str(), v2->GetString().c_str()); 398 EXPECT_EQ(Manifest::EXTERNAL_PREF, location); 399 400 // Remove it so we won't count it ever again. 401 prefs_->Remove(id, NULL); 402 } 403 return true; 404 } 405 406 virtual bool OnExternalExtensionUpdateUrlFound( 407 const std::string& id, 408 const std::string& install_parameter, 409 const GURL& update_url, 410 Manifest::Location location, 411 int creation_flags, 412 bool mark_acknowledged) OVERRIDE { 413 ++ids_found_; 414 base::DictionaryValue* pref; 415 // This tests is to make sure that the provider only notifies us of the 416 // values we gave it. So if the id we doesn't exist in our internal 417 // dictionary then something is wrong. 418 EXPECT_TRUE(prefs_->GetDictionary(id, &pref)) 419 << L"Got back ID (" << id.c_str() << ") we weren't expecting"; 420 EXPECT_EQ(Manifest::EXTERNAL_PREF_DOWNLOAD, location); 421 422 if (pref) { 423 EXPECT_TRUE(provider_->HasExtension(id)); 424 425 // External extensions with update URLs do not have versions. 426 scoped_ptr<Version> v1; 427 Manifest::Location location1 = Manifest::INVALID_LOCATION; 428 EXPECT_TRUE(provider_->GetExtensionDetails(id, &location1, &v1)); 429 EXPECT_FALSE(v1.get()); 430 EXPECT_EQ(Manifest::EXTERNAL_PREF_DOWNLOAD, location1); 431 432 std::string parsed_install_parameter; 433 pref->GetString("install_parameter", &parsed_install_parameter); 434 EXPECT_EQ(parsed_install_parameter, install_parameter); 435 436 // Remove it so we won't count it again. 437 prefs_->Remove(id, NULL); 438 } 439 return true; 440 } 441 442 virtual void OnExternalProviderReady( 443 const extensions::ExternalProviderInterface* provider) OVERRIDE { 444 EXPECT_EQ(provider, provider_.get()); 445 EXPECT_TRUE(provider->IsReady()); 446 } 447 448 private: 449 int ids_found_; 450 base::FilePath fake_base_path_; 451 int expected_creation_flags_; 452 scoped_ptr<extensions::ExternalProviderImpl> provider_; 453 scoped_ptr<base::DictionaryValue> prefs_; 454 scoped_ptr<TestingProfile> profile_; 455 456 DISALLOW_COPY_AND_ASSIGN(MockProviderVisitor); 457 }; 458 459 class ExtensionServiceTest : public extensions::ExtensionServiceTestBase, 460 public content::NotificationObserver { 461 public: 462 ExtensionServiceTest() 463 : unloaded_reason_(UnloadedExtensionInfo::REASON_UNDEFINED), 464 installed_(NULL), 465 was_update_(false), 466 override_external_install_prompt_( 467 FeatureSwitch::prompt_for_external_extensions(), 468 false), 469 expected_extensions_count_(0) { 470 registrar_.Add(this, 471 chrome::NOTIFICATION_EXTENSION_LOADED_DEPRECATED, 472 content::NotificationService::AllSources()); 473 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_UNLOADED_DEPRECATED, 474 content::NotificationService::AllSources()); 475 registrar_.Add(this, 476 chrome::NOTIFICATION_EXTENSION_INSTALLED_DEPRECATED, 477 content::NotificationService::AllSources()); 478 } 479 480 virtual void Observe(int type, 481 const content::NotificationSource& source, 482 const content::NotificationDetails& details) OVERRIDE { 483 switch (type) { 484 case chrome::NOTIFICATION_EXTENSION_LOADED_DEPRECATED: { 485 const Extension* extension = 486 content::Details<const Extension>(details).ptr(); 487 loaded_.push_back(make_scoped_refptr(extension)); 488 // The tests rely on the errors being in a certain order, which can vary 489 // depending on how filesystem iteration works. 490 std::stable_sort(loaded_.begin(), loaded_.end(), ExtensionsOrder()); 491 break; 492 } 493 494 case chrome::NOTIFICATION_EXTENSION_UNLOADED_DEPRECATED: { 495 UnloadedExtensionInfo* unloaded_info = 496 content::Details<UnloadedExtensionInfo>(details).ptr(); 497 const Extension* e = unloaded_info->extension; 498 unloaded_id_ = e->id(); 499 unloaded_reason_ = unloaded_info->reason; 500 extensions::ExtensionList::iterator i = 501 std::find(loaded_.begin(), loaded_.end(), e); 502 // TODO(erikkay) fix so this can be an assert. Right now the tests 503 // are manually calling clear() on loaded_, so this isn't doable. 504 if (i == loaded_.end()) 505 return; 506 loaded_.erase(i); 507 break; 508 } 509 case chrome::NOTIFICATION_EXTENSION_INSTALLED_DEPRECATED: { 510 const extensions::InstalledExtensionInfo* installed_info = 511 content::Details<const extensions::InstalledExtensionInfo>(details) 512 .ptr(); 513 installed_ = installed_info->extension; 514 was_update_ = installed_info->is_update; 515 old_name_ = installed_info->old_name; 516 break; 517 } 518 519 default: 520 DCHECK(false); 521 } 522 } 523 524 void AddMockExternalProvider( 525 extensions::ExternalProviderInterface* provider) { 526 service()->AddProviderForTesting(provider); 527 } 528 529 void MockSyncStartFlare(bool* was_called, 530 syncer::ModelType* model_type_passed_in, 531 syncer::ModelType model_type) { 532 *was_called = true; 533 *model_type_passed_in = model_type; 534 } 535 536 protected: 537 // Paths to some of the fake extensions. 538 base::FilePath good0_path() { 539 return data_dir() 540 .AppendASCII("good") 541 .AppendASCII("Extensions") 542 .AppendASCII(good0) 543 .AppendASCII("1.0.0.0"); 544 } 545 546 base::FilePath good1_path() { 547 return data_dir() 548 .AppendASCII("good") 549 .AppendASCII("Extensions") 550 .AppendASCII(good1) 551 .AppendASCII("2"); 552 } 553 554 base::FilePath good2_path() { 555 return data_dir() 556 .AppendASCII("good") 557 .AppendASCII("Extensions") 558 .AppendASCII(good2) 559 .AppendASCII("1.0"); 560 } 561 562 void TestExternalProvider(MockExtensionProvider* provider, 563 Manifest::Location location); 564 565 void PackCRX(const base::FilePath& dir_path, 566 const base::FilePath& pem_path, 567 const base::FilePath& crx_path) { 568 // Use the existing pem key, if provided. 569 base::FilePath pem_output_path; 570 if (pem_path.value().empty()) { 571 pem_output_path = crx_path.DirName().AppendASCII("temp.pem"); 572 } else { 573 ASSERT_TRUE(base::PathExists(pem_path)); 574 } 575 576 ASSERT_TRUE(base::DeleteFile(crx_path, false)); 577 578 scoped_ptr<ExtensionCreator> creator(new ExtensionCreator()); 579 ASSERT_TRUE(creator->Run(dir_path, 580 crx_path, 581 pem_path, 582 pem_output_path, 583 ExtensionCreator::kOverwriteCRX)); 584 585 ASSERT_TRUE(base::PathExists(crx_path)); 586 } 587 588 enum InstallState { 589 INSTALL_FAILED, 590 INSTALL_UPDATED, 591 INSTALL_NEW, 592 INSTALL_WITHOUT_LOAD, 593 }; 594 595 const Extension* PackAndInstallCRX(const base::FilePath& dir_path, 596 const base::FilePath& pem_path, 597 InstallState install_state, 598 int creation_flags) { 599 base::FilePath crx_path; 600 base::ScopedTempDir temp_dir; 601 EXPECT_TRUE(temp_dir.CreateUniqueTempDir()); 602 crx_path = temp_dir.path().AppendASCII("temp.crx"); 603 604 PackCRX(dir_path, pem_path, crx_path); 605 return InstallCRX(crx_path, install_state, creation_flags); 606 } 607 608 const Extension* PackAndInstallCRX(const base::FilePath& dir_path, 609 const base::FilePath& pem_path, 610 InstallState install_state) { 611 return PackAndInstallCRX(dir_path, pem_path, install_state, 612 Extension::NO_FLAGS); 613 } 614 615 const Extension* PackAndInstallCRX(const base::FilePath& dir_path, 616 InstallState install_state) { 617 return PackAndInstallCRX(dir_path, base::FilePath(), install_state, 618 Extension::NO_FLAGS); 619 } 620 621 // Attempts to install an extension. Use INSTALL_FAILED if the installation 622 // is expected to fail. 623 // If |install_state| is INSTALL_UPDATED, and |expected_old_name| is 624 // non-empty, expects that the existing extension's title was 625 // |expected_old_name|. 626 const Extension* InstallCRX(const base::FilePath& path, 627 InstallState install_state, 628 int creation_flags, 629 const std::string& expected_old_name) { 630 InstallCRXInternal(path, creation_flags); 631 return VerifyCrxInstall(path, install_state, expected_old_name); 632 } 633 634 // Attempts to install an extension. Use INSTALL_FAILED if the installation 635 // is expected to fail. 636 const Extension* InstallCRX(const base::FilePath& path, 637 InstallState install_state, 638 int creation_flags) { 639 return InstallCRX(path, install_state, creation_flags, std::string()); 640 } 641 642 // Attempts to install an extension. Use INSTALL_FAILED if the installation 643 // is expected to fail. 644 const Extension* InstallCRX(const base::FilePath& path, 645 InstallState install_state) { 646 return InstallCRX(path, install_state, Extension::NO_FLAGS); 647 } 648 649 const Extension* InstallCRXFromWebStore(const base::FilePath& path, 650 InstallState install_state) { 651 InstallCRXInternal(path, Extension::FROM_WEBSTORE); 652 return VerifyCrxInstall(path, install_state); 653 } 654 655 const Extension* InstallCRXWithLocation(const base::FilePath& crx_path, 656 Manifest::Location install_location, 657 InstallState install_state) { 658 EXPECT_TRUE(base::PathExists(crx_path)) 659 << "Path does not exist: "<< crx_path.value().c_str(); 660 // no client (silent install) 661 scoped_refptr<CrxInstaller> installer( 662 CrxInstaller::CreateSilent(service())); 663 installer->set_install_source(install_location); 664 665 content::WindowedNotificationObserver observer( 666 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 667 content::NotificationService::AllSources()); 668 installer->InstallCrx(crx_path); 669 observer.Wait(); 670 671 return VerifyCrxInstall(crx_path, install_state); 672 } 673 674 // Verifies the result of a CRX installation. Used by InstallCRX. Set the 675 // |install_state| to INSTALL_FAILED if the installation is expected to fail. 676 // Returns an Extension pointer if the install succeeded, NULL otherwise. 677 const Extension* VerifyCrxInstall(const base::FilePath& path, 678 InstallState install_state) { 679 return VerifyCrxInstall(path, install_state, std::string()); 680 } 681 682 // Verifies the result of a CRX installation. Used by InstallCRX. Set the 683 // |install_state| to INSTALL_FAILED if the installation is expected to fail. 684 // If |install_state| is INSTALL_UPDATED, and |expected_old_name| is 685 // non-empty, expects that the existing extension's title was 686 // |expected_old_name|. 687 // Returns an Extension pointer if the install succeeded, NULL otherwise. 688 const Extension* VerifyCrxInstall(const base::FilePath& path, 689 InstallState install_state, 690 const std::string& expected_old_name) { 691 std::vector<base::string16> errors = GetErrors(); 692 const Extension* extension = NULL; 693 if (install_state != INSTALL_FAILED) { 694 if (install_state == INSTALL_NEW) 695 ++expected_extensions_count_; 696 697 EXPECT_TRUE(installed_) << path.value(); 698 // If and only if INSTALL_UPDATED, it should have the is_update flag. 699 EXPECT_EQ(install_state == INSTALL_UPDATED, was_update_) 700 << path.value(); 701 // If INSTALL_UPDATED, old_name_ should match the given string. 702 if (install_state == INSTALL_UPDATED && !expected_old_name.empty()) 703 EXPECT_EQ(expected_old_name, old_name_); 704 EXPECT_EQ(0u, errors.size()) << path.value(); 705 706 if (install_state == INSTALL_WITHOUT_LOAD) { 707 EXPECT_EQ(0u, loaded_.size()) << path.value(); 708 } else { 709 EXPECT_EQ(1u, loaded_.size()) << path.value(); 710 size_t actual_extension_count = 711 registry()->enabled_extensions().size() + 712 registry()->disabled_extensions().size(); 713 EXPECT_EQ(expected_extensions_count_, actual_extension_count) << 714 path.value(); 715 extension = loaded_[0].get(); 716 EXPECT_TRUE(service()->GetExtensionById(extension->id(), false)) 717 << path.value(); 718 } 719 720 for (std::vector<base::string16>::iterator err = errors.begin(); 721 err != errors.end(); ++err) { 722 LOG(ERROR) << *err; 723 } 724 } else { 725 EXPECT_FALSE(installed_) << path.value(); 726 EXPECT_EQ(0u, loaded_.size()) << path.value(); 727 EXPECT_EQ(1u, errors.size()) << path.value(); 728 } 729 730 installed_ = NULL; 731 was_update_ = false; 732 old_name_ = ""; 733 loaded_.clear(); 734 ExtensionErrorReporter::GetInstance()->ClearErrors(); 735 return extension; 736 } 737 738 enum UpdateState { 739 FAILED_SILENTLY, 740 FAILED, 741 UPDATED, 742 INSTALLED, 743 ENABLED 744 }; 745 746 void BlackListWebGL() { 747 static const std::string json_blacklist = 748 "{\n" 749 " \"name\": \"gpu blacklist\",\n" 750 " \"version\": \"1.0\",\n" 751 " \"entries\": [\n" 752 " {\n" 753 " \"id\": 1,\n" 754 " \"features\": [\"webgl\"]\n" 755 " }\n" 756 " ]\n" 757 "}"; 758 gpu::GPUInfo gpu_info; 759 content::GpuDataManager::GetInstance()->InitializeForTesting( 760 json_blacklist, gpu_info); 761 } 762 763 // Helper method to set up a WindowedNotificationObserver to wait for a 764 // specific CrxInstaller to finish if we don't know the value of the 765 // |installer| yet. 766 static bool IsCrxInstallerDone(extensions::CrxInstaller** installer, 767 const content::NotificationSource& source, 768 const content::NotificationDetails& details) { 769 return content::Source<extensions::CrxInstaller>(source).ptr() == 770 *installer; 771 } 772 773 void UpdateExtension(const std::string& id, 774 const base::FilePath& in_path, 775 UpdateState expected_state) { 776 ASSERT_TRUE(base::PathExists(in_path)); 777 778 // We need to copy this to a temporary location because Update() will delete 779 // it. 780 base::FilePath path = temp_dir().path(); 781 path = path.Append(in_path.BaseName()); 782 ASSERT_TRUE(base::CopyFile(in_path, path)); 783 784 int previous_enabled_extension_count = 785 registry()->enabled_extensions().size(); 786 int previous_installed_extension_count = 787 previous_enabled_extension_count + 788 registry()->disabled_extensions().size(); 789 790 extensions::CrxInstaller* installer = NULL; 791 content::WindowedNotificationObserver observer( 792 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 793 base::Bind(&IsCrxInstallerDone, &installer)); 794 service()->UpdateExtension(id, path, true, &installer); 795 796 if (installer) 797 observer.Wait(); 798 else 799 base::RunLoop().RunUntilIdle(); 800 801 std::vector<base::string16> errors = GetErrors(); 802 int error_count = errors.size(); 803 int enabled_extension_count = registry()->enabled_extensions().size(); 804 int installed_extension_count = 805 enabled_extension_count + registry()->disabled_extensions().size(); 806 807 int expected_error_count = (expected_state == FAILED) ? 1 : 0; 808 EXPECT_EQ(expected_error_count, error_count) << path.value(); 809 810 if (expected_state <= FAILED) { 811 EXPECT_EQ(previous_enabled_extension_count, 812 enabled_extension_count); 813 EXPECT_EQ(previous_installed_extension_count, 814 installed_extension_count); 815 } else { 816 int expected_installed_extension_count = 817 (expected_state >= INSTALLED) ? 1 : 0; 818 int expected_enabled_extension_count = 819 (expected_state >= ENABLED) ? 1 : 0; 820 EXPECT_EQ(expected_installed_extension_count, 821 installed_extension_count); 822 EXPECT_EQ(expected_enabled_extension_count, 823 enabled_extension_count); 824 } 825 826 // Update() should the temporary input file. 827 EXPECT_FALSE(base::PathExists(path)); 828 } 829 830 void TerminateExtension(const std::string& id) { 831 const Extension* extension = service()->GetInstalledExtension(id); 832 if (!extension) { 833 ADD_FAILURE(); 834 return; 835 } 836 service()->TrackTerminatedExtensionForTest(extension); 837 } 838 839 size_t GetPrefKeyCount() { 840 const base::DictionaryValue* dict = 841 profile()->GetPrefs()->GetDictionary("extensions.settings"); 842 if (!dict) { 843 ADD_FAILURE(); 844 return 0; 845 } 846 return dict->size(); 847 } 848 849 void UninstallExtension(const std::string& id, bool use_helper) { 850 // Verify that the extension is installed. 851 base::FilePath extension_path = extensions_install_dir().AppendASCII(id); 852 EXPECT_TRUE(base::PathExists(extension_path)); 853 size_t pref_key_count = GetPrefKeyCount(); 854 EXPECT_GT(pref_key_count, 0u); 855 ValidateIntegerPref(id, "state", Extension::ENABLED); 856 857 // Uninstall it. 858 if (use_helper) { 859 EXPECT_TRUE(ExtensionService::UninstallExtensionHelper(service(), id)); 860 } else { 861 EXPECT_TRUE(service()->UninstallExtension(id, false, NULL)); 862 } 863 --expected_extensions_count_; 864 865 // We should get an unload notification. 866 EXPECT_FALSE(unloaded_id_.empty()); 867 EXPECT_EQ(id, unloaded_id_); 868 869 // Verify uninstalled state. 870 size_t new_pref_key_count = GetPrefKeyCount(); 871 if (new_pref_key_count == pref_key_count) { 872 ValidateIntegerPref(id, "location", 873 Extension::EXTERNAL_EXTENSION_UNINSTALLED); 874 } else { 875 EXPECT_EQ(new_pref_key_count, pref_key_count - 1); 876 } 877 878 // The extension should not be in the service anymore. 879 EXPECT_FALSE(service()->GetInstalledExtension(id)); 880 base::RunLoop().RunUntilIdle(); 881 882 // The directory should be gone. 883 EXPECT_FALSE(base::PathExists(extension_path)); 884 } 885 886 void ValidatePrefKeyCount(size_t count) { 887 EXPECT_EQ(count, GetPrefKeyCount()); 888 } 889 890 testing::AssertionResult ValidateBooleanPref( 891 const std::string& extension_id, 892 const std::string& pref_path, 893 bool expected_val) { 894 std::string msg = "while checking: "; 895 msg += extension_id; 896 msg += " "; 897 msg += pref_path; 898 msg += " == "; 899 msg += expected_val ? "true" : "false"; 900 901 PrefService* prefs = profile()->GetPrefs(); 902 const base::DictionaryValue* dict = 903 prefs->GetDictionary("extensions.settings"); 904 if (!dict) { 905 return testing::AssertionFailure() 906 << "extension.settings does not exist " << msg; 907 } 908 909 const base::DictionaryValue* pref = NULL; 910 if (!dict->GetDictionary(extension_id, &pref)) { 911 return testing::AssertionFailure() 912 << "extension pref does not exist " << msg; 913 } 914 915 bool val; 916 if (!pref->GetBoolean(pref_path, &val)) { 917 return testing::AssertionFailure() 918 << pref_path << " pref not found " << msg; 919 } 920 921 return expected_val == val 922 ? testing::AssertionSuccess() 923 : testing::AssertionFailure() << "base::Value is incorrect " << msg; 924 } 925 926 bool IsPrefExist(const std::string& extension_id, 927 const std::string& pref_path) { 928 const base::DictionaryValue* dict = 929 profile()->GetPrefs()->GetDictionary("extensions.settings"); 930 if (dict == NULL) return false; 931 const base::DictionaryValue* pref = NULL; 932 if (!dict->GetDictionary(extension_id, &pref)) { 933 return false; 934 } 935 if (pref == NULL) { 936 return false; 937 } 938 bool val; 939 if (!pref->GetBoolean(pref_path, &val)) { 940 return false; 941 } 942 return true; 943 } 944 945 void ValidateIntegerPref(const std::string& extension_id, 946 const std::string& pref_path, 947 int expected_val) { 948 std::string msg = " while checking: "; 949 msg += extension_id; 950 msg += " "; 951 msg += pref_path; 952 msg += " == "; 953 msg += base::IntToString(expected_val); 954 955 PrefService* prefs = profile()->GetPrefs(); 956 const base::DictionaryValue* dict = 957 prefs->GetDictionary("extensions.settings"); 958 ASSERT_TRUE(dict != NULL) << msg; 959 const base::DictionaryValue* pref = NULL; 960 ASSERT_TRUE(dict->GetDictionary(extension_id, &pref)) << msg; 961 EXPECT_TRUE(pref != NULL) << msg; 962 int val; 963 ASSERT_TRUE(pref->GetInteger(pref_path, &val)) << msg; 964 EXPECT_EQ(expected_val, val) << msg; 965 } 966 967 void ValidateStringPref(const std::string& extension_id, 968 const std::string& pref_path, 969 const std::string& expected_val) { 970 std::string msg = " while checking: "; 971 msg += extension_id; 972 msg += ".manifest."; 973 msg += pref_path; 974 msg += " == "; 975 msg += expected_val; 976 977 const base::DictionaryValue* dict = 978 profile()->GetPrefs()->GetDictionary("extensions.settings"); 979 ASSERT_TRUE(dict != NULL) << msg; 980 const base::DictionaryValue* pref = NULL; 981 std::string manifest_path = extension_id + ".manifest"; 982 ASSERT_TRUE(dict->GetDictionary(manifest_path, &pref)) << msg; 983 EXPECT_TRUE(pref != NULL) << msg; 984 std::string val; 985 ASSERT_TRUE(pref->GetString(pref_path, &val)) << msg; 986 EXPECT_EQ(expected_val, val) << msg; 987 } 988 989 void SetPref(const std::string& extension_id, 990 const std::string& pref_path, 991 base::Value* value, 992 const std::string& msg) { 993 DictionaryPrefUpdate update(profile()->GetPrefs(), "extensions.settings"); 994 base::DictionaryValue* dict = update.Get(); 995 ASSERT_TRUE(dict != NULL) << msg; 996 base::DictionaryValue* pref = NULL; 997 ASSERT_TRUE(dict->GetDictionary(extension_id, &pref)) << msg; 998 EXPECT_TRUE(pref != NULL) << msg; 999 pref->Set(pref_path, value); 1000 } 1001 1002 void SetPrefInteg(const std::string& extension_id, 1003 const std::string& pref_path, 1004 int value) { 1005 std::string msg = " while setting: "; 1006 msg += extension_id; 1007 msg += " "; 1008 msg += pref_path; 1009 msg += " = "; 1010 msg += base::IntToString(value); 1011 1012 SetPref(extension_id, pref_path, new base::FundamentalValue(value), msg); 1013 } 1014 1015 void SetPrefBool(const std::string& extension_id, 1016 const std::string& pref_path, 1017 bool value) { 1018 std::string msg = " while setting: "; 1019 msg += extension_id + " " + pref_path; 1020 msg += " = "; 1021 msg += (value ? "true" : "false"); 1022 1023 SetPref(extension_id, pref_path, new base::FundamentalValue(value), msg); 1024 } 1025 1026 void ClearPref(const std::string& extension_id, 1027 const std::string& pref_path) { 1028 std::string msg = " while clearing: "; 1029 msg += extension_id + " " + pref_path; 1030 1031 DictionaryPrefUpdate update(profile()->GetPrefs(), "extensions.settings"); 1032 base::DictionaryValue* dict = update.Get(); 1033 ASSERT_TRUE(dict != NULL) << msg; 1034 base::DictionaryValue* pref = NULL; 1035 ASSERT_TRUE(dict->GetDictionary(extension_id, &pref)) << msg; 1036 EXPECT_TRUE(pref != NULL) << msg; 1037 pref->Remove(pref_path, NULL); 1038 } 1039 1040 void SetPrefStringSet(const std::string& extension_id, 1041 const std::string& pref_path, 1042 const std::set<std::string>& value) { 1043 std::string msg = " while setting: "; 1044 msg += extension_id + " " + pref_path; 1045 1046 base::ListValue* list_value = new base::ListValue(); 1047 for (std::set<std::string>::const_iterator iter = value.begin(); 1048 iter != value.end(); ++iter) 1049 list_value->Append(new base::StringValue(*iter)); 1050 1051 SetPref(extension_id, pref_path, list_value, msg); 1052 } 1053 1054 void InitPluginService() { 1055 #if defined(ENABLE_PLUGINS) 1056 PluginService::GetInstance()->Init(); 1057 #endif 1058 } 1059 1060 void InitializeExtensionSyncService() { 1061 extension_sync_service_.reset(new ExtensionSyncService( 1062 profile(), ExtensionPrefs::Get(browser_context()), service())); 1063 } 1064 1065 extensions::ManagementPolicy* GetManagementPolicy() { 1066 return ExtensionSystem::Get(browser_context())->management_policy(); 1067 } 1068 1069 ExtensionSyncService* extension_sync_service() { 1070 return extension_sync_service_.get(); 1071 } 1072 1073 protected: 1074 scoped_ptr<ExtensionSyncService> extension_sync_service_; 1075 extensions::ExtensionList loaded_; 1076 std::string unloaded_id_; 1077 UnloadedExtensionInfo::Reason unloaded_reason_; 1078 const Extension* installed_; 1079 bool was_update_; 1080 std::string old_name_; 1081 FeatureSwitch::ScopedOverride override_external_install_prompt_; 1082 1083 private: 1084 // Create a CrxInstaller and install the CRX file. 1085 // Instead of calling this method yourself, use InstallCRX(), which does extra 1086 // error checking. 1087 void InstallCRXInternal(const base::FilePath& crx_path) { 1088 InstallCRXInternal(crx_path, Extension::NO_FLAGS); 1089 } 1090 1091 void InstallCRXInternal(const base::FilePath& crx_path, int creation_flags) { 1092 ASSERT_TRUE(base::PathExists(crx_path)) 1093 << "Path does not exist: "<< crx_path.value().c_str(); 1094 scoped_refptr<CrxInstaller> installer( 1095 CrxInstaller::CreateSilent(service())); 1096 installer->set_creation_flags(creation_flags); 1097 if (!(creation_flags & Extension::WAS_INSTALLED_BY_DEFAULT)) 1098 installer->set_allow_silent_install(true); 1099 1100 content::WindowedNotificationObserver observer( 1101 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 1102 content::Source<extensions::CrxInstaller>(installer)); 1103 1104 installer->InstallCrx(crx_path); 1105 1106 observer.Wait(); 1107 } 1108 1109 size_t expected_extensions_count_; 1110 content::NotificationRegistrar registrar_; 1111 }; 1112 1113 // Receives notifications from a PackExtensionJob, indicating either that 1114 // packing succeeded or that there was some error. 1115 class PackExtensionTestClient : public extensions::PackExtensionJob::Client { 1116 public: 1117 PackExtensionTestClient(const base::FilePath& expected_crx_path, 1118 const base::FilePath& expected_private_key_path); 1119 virtual void OnPackSuccess(const base::FilePath& crx_path, 1120 const base::FilePath& private_key_path) OVERRIDE; 1121 virtual void OnPackFailure(const std::string& error_message, 1122 ExtensionCreator::ErrorType type) OVERRIDE; 1123 1124 private: 1125 const base::FilePath expected_crx_path_; 1126 const base::FilePath expected_private_key_path_; 1127 DISALLOW_COPY_AND_ASSIGN(PackExtensionTestClient); 1128 }; 1129 1130 PackExtensionTestClient::PackExtensionTestClient( 1131 const base::FilePath& expected_crx_path, 1132 const base::FilePath& expected_private_key_path) 1133 : expected_crx_path_(expected_crx_path), 1134 expected_private_key_path_(expected_private_key_path) {} 1135 1136 // If packing succeeded, we make sure that the package names match our 1137 // expectations. 1138 void PackExtensionTestClient::OnPackSuccess( 1139 const base::FilePath& crx_path, 1140 const base::FilePath& private_key_path) { 1141 // We got the notification and processed it; we don't expect any further tasks 1142 // to be posted to the current thread, so we should stop blocking and continue 1143 // on with the rest of the test. 1144 // This call to |Quit()| matches the call to |Run()| in the 1145 // |PackPunctuatedExtension| test. 1146 base::MessageLoop::current()->Quit(); 1147 EXPECT_EQ(expected_crx_path_.value(), crx_path.value()); 1148 EXPECT_EQ(expected_private_key_path_.value(), private_key_path.value()); 1149 ASSERT_TRUE(base::PathExists(private_key_path)); 1150 } 1151 1152 // The tests are designed so that we never expect to see a packing error. 1153 void PackExtensionTestClient::OnPackFailure(const std::string& error_message, 1154 ExtensionCreator::ErrorType type) { 1155 if (type == ExtensionCreator::kCRXExists) 1156 FAIL() << "Packing should not fail."; 1157 else 1158 FAIL() << "Existing CRX should have been overwritten."; 1159 } 1160 1161 // Test loading good extensions from the profile directory. 1162 TEST_F(ExtensionServiceTest, LoadAllExtensionsFromDirectorySuccess) { 1163 InitPluginService(); 1164 InitializeGoodInstalledExtensionService(); 1165 service()->Init(); 1166 1167 uint32 expected_num_extensions = 3u; 1168 ASSERT_EQ(expected_num_extensions, loaded_.size()); 1169 1170 EXPECT_EQ(std::string(good0), loaded_[0]->id()); 1171 EXPECT_EQ(std::string("My extension 1"), 1172 loaded_[0]->name()); 1173 EXPECT_EQ(std::string("The first extension that I made."), 1174 loaded_[0]->description()); 1175 EXPECT_EQ(Manifest::INTERNAL, loaded_[0]->location()); 1176 EXPECT_TRUE(service()->GetExtensionById(loaded_[0]->id(), false)); 1177 EXPECT_EQ(expected_num_extensions, registry()->enabled_extensions().size()); 1178 1179 ValidatePrefKeyCount(3); 1180 ValidateIntegerPref(good0, "state", Extension::ENABLED); 1181 ValidateIntegerPref(good0, "location", Manifest::INTERNAL); 1182 ValidateIntegerPref(good1, "state", Extension::ENABLED); 1183 ValidateIntegerPref(good1, "location", Manifest::INTERNAL); 1184 ValidateIntegerPref(good2, "state", Extension::ENABLED); 1185 ValidateIntegerPref(good2, "location", Manifest::INTERNAL); 1186 1187 URLPatternSet expected_patterns; 1188 AddPattern(&expected_patterns, "file:///*"); 1189 AddPattern(&expected_patterns, "http://*.google.com/*"); 1190 AddPattern(&expected_patterns, "https://*.google.com/*"); 1191 const Extension* extension = loaded_[0].get(); 1192 const extensions::UserScriptList& scripts = 1193 extensions::ContentScriptsInfo::GetContentScripts(extension); 1194 ASSERT_EQ(2u, scripts.size()); 1195 EXPECT_EQ(expected_patterns, scripts[0].url_patterns()); 1196 EXPECT_EQ(2u, scripts[0].js_scripts().size()); 1197 ExtensionResource resource00(extension->id(), 1198 scripts[0].js_scripts()[0].extension_root(), 1199 scripts[0].js_scripts()[0].relative_path()); 1200 base::FilePath expected_path = 1201 base::MakeAbsoluteFilePath(extension->path().AppendASCII("script1.js")); 1202 EXPECT_TRUE(resource00.ComparePathWithDefault(expected_path)); 1203 ExtensionResource resource01(extension->id(), 1204 scripts[0].js_scripts()[1].extension_root(), 1205 scripts[0].js_scripts()[1].relative_path()); 1206 expected_path = 1207 base::MakeAbsoluteFilePath(extension->path().AppendASCII("script2.js")); 1208 EXPECT_TRUE(resource01.ComparePathWithDefault(expected_path)); 1209 EXPECT_TRUE(!extensions::PluginInfo::HasPlugins(extension)); 1210 EXPECT_EQ(1u, scripts[1].url_patterns().patterns().size()); 1211 EXPECT_EQ("http://*.news.com/*", 1212 scripts[1].url_patterns().begin()->GetAsString()); 1213 ExtensionResource resource10(extension->id(), 1214 scripts[1].js_scripts()[0].extension_root(), 1215 scripts[1].js_scripts()[0].relative_path()); 1216 expected_path = 1217 extension->path().AppendASCII("js_files").AppendASCII("script3.js"); 1218 expected_path = base::MakeAbsoluteFilePath(expected_path); 1219 EXPECT_TRUE(resource10.ComparePathWithDefault(expected_path)); 1220 1221 expected_patterns.ClearPatterns(); 1222 AddPattern(&expected_patterns, "http://*.google.com/*"); 1223 AddPattern(&expected_patterns, "https://*.google.com/*"); 1224 EXPECT_EQ( 1225 expected_patterns, 1226 extension->permissions_data()->active_permissions()->explicit_hosts()); 1227 1228 EXPECT_EQ(std::string(good1), loaded_[1]->id()); 1229 EXPECT_EQ(std::string("My extension 2"), loaded_[1]->name()); 1230 EXPECT_EQ(std::string(), loaded_[1]->description()); 1231 EXPECT_EQ(loaded_[1]->GetResourceURL("background.html"), 1232 extensions::BackgroundInfo::GetBackgroundURL(loaded_[1].get())); 1233 EXPECT_EQ(0u, 1234 extensions::ContentScriptsInfo::GetContentScripts(loaded_[1].get()) 1235 .size()); 1236 1237 // We don't parse the plugins section on Chrome OS. 1238 #if defined(OS_CHROMEOS) 1239 EXPECT_TRUE(!extensions::PluginInfo::HasPlugins(loaded_[1].get())); 1240 #else 1241 ASSERT_TRUE(extensions::PluginInfo::HasPlugins(loaded_[1].get())); 1242 const std::vector<extensions::PluginInfo>* plugins = 1243 extensions::PluginInfo::GetPlugins(loaded_[1].get()); 1244 ASSERT_TRUE(plugins); 1245 ASSERT_EQ(2u, plugins->size()); 1246 EXPECT_EQ(loaded_[1]->path().AppendASCII("content_plugin.dll").value(), 1247 plugins->at(0).path.value()); 1248 EXPECT_TRUE(plugins->at(0).is_public); 1249 EXPECT_EQ(loaded_[1]->path().AppendASCII("extension_plugin.dll").value(), 1250 plugins->at(1).path.value()); 1251 EXPECT_FALSE(plugins->at(1).is_public); 1252 #endif 1253 1254 EXPECT_EQ(Manifest::INTERNAL, loaded_[1]->location()); 1255 1256 int index = expected_num_extensions - 1; 1257 EXPECT_EQ(std::string(good2), loaded_[index]->id()); 1258 EXPECT_EQ(std::string("My extension 3"), loaded_[index]->name()); 1259 EXPECT_EQ(std::string(), loaded_[index]->description()); 1260 EXPECT_EQ(0u, 1261 extensions::ContentScriptsInfo::GetContentScripts( 1262 loaded_[index].get()).size()); 1263 EXPECT_EQ(Manifest::INTERNAL, loaded_[index]->location()); 1264 }; 1265 1266 // Test loading bad extensions from the profile directory. 1267 TEST_F(ExtensionServiceTest, LoadAllExtensionsFromDirectoryFail) { 1268 // Initialize the test dir with a bad Preferences/extensions. 1269 base::FilePath source_install_dir = 1270 data_dir().AppendASCII("bad").AppendASCII("Extensions"); 1271 base::FilePath pref_path = 1272 source_install_dir.DirName().Append(chrome::kPreferencesFilename); 1273 1274 InitializeInstalledExtensionService(pref_path, source_install_dir); 1275 1276 service()->Init(); 1277 1278 ASSERT_EQ(4u, GetErrors().size()); 1279 ASSERT_EQ(0u, loaded_.size()); 1280 1281 EXPECT_TRUE(MatchPattern(base::UTF16ToUTF8(GetErrors()[0]), 1282 std::string("Could not load extension from '*'. ") + 1283 extensions::manifest_errors::kManifestUnreadable)) << 1284 base::UTF16ToUTF8(GetErrors()[0]); 1285 1286 EXPECT_TRUE(MatchPattern(base::UTF16ToUTF8(GetErrors()[1]), 1287 std::string("Could not load extension from '*'. ") + 1288 extensions::manifest_errors::kManifestUnreadable)) << 1289 base::UTF16ToUTF8(GetErrors()[1]); 1290 1291 EXPECT_TRUE(MatchPattern(base::UTF16ToUTF8(GetErrors()[2]), 1292 std::string("Could not load extension from '*'. ") + 1293 extensions::manifest_errors::kMissingFile)) << 1294 base::UTF16ToUTF8(GetErrors()[2]); 1295 1296 EXPECT_TRUE(MatchPattern(base::UTF16ToUTF8(GetErrors()[3]), 1297 std::string("Could not load extension from '*'. ") + 1298 extensions::manifest_errors::kManifestUnreadable)) << 1299 base::UTF16ToUTF8(GetErrors()[3]); 1300 }; 1301 1302 // Test various cases for delayed install because of missing imports. 1303 TEST_F(ExtensionServiceTest, PendingImports) { 1304 InitPluginService(); 1305 1306 base::FilePath source_install_dir = 1307 data_dir().AppendASCII("pending_updates_with_imports").AppendASCII( 1308 "Extensions"); 1309 base::FilePath pref_path = 1310 source_install_dir.DirName().Append(chrome::kPreferencesFilename); 1311 1312 InitializeInstalledExtensionService(pref_path, source_install_dir); 1313 1314 // Verify there are no pending extensions initially. 1315 EXPECT_FALSE(service()->pending_extension_manager()->HasPendingExtensions()); 1316 1317 service()->Init(); 1318 // Wait for GarbageCollectExtensions task to complete. 1319 base::RunLoop().RunUntilIdle(); 1320 1321 // These extensions are used by the extensions we test below, they must be 1322 // installed. 1323 EXPECT_TRUE(base::PathExists(extensions_install_dir().AppendASCII( 1324 "bjafgdebaacbbbecmhlhpofkepfkgcpa/1.0"))); 1325 EXPECT_TRUE(base::PathExists(extensions_install_dir().AppendASCII( 1326 "hpiknbiabeeppbpihjehijgoemciehgk/2"))); 1327 1328 // Each of these extensions should have been rejected because of dependencies 1329 // that cannot be satisfied. 1330 ExtensionPrefs* prefs = ExtensionPrefs::Get(profile()); 1331 EXPECT_FALSE( 1332 prefs->GetDelayedInstallInfo("aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa")); 1333 EXPECT_FALSE( 1334 prefs->GetInstalledExtensionInfo("aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa")); 1335 EXPECT_FALSE( 1336 prefs->GetDelayedInstallInfo("bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb")); 1337 EXPECT_FALSE( 1338 prefs->GetInstalledExtensionInfo("bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb")); 1339 EXPECT_FALSE( 1340 prefs->GetDelayedInstallInfo("cccccccccccccccccccccccccccccccc")); 1341 EXPECT_FALSE( 1342 prefs->GetInstalledExtensionInfo("cccccccccccccccccccccccccccccccc")); 1343 1344 // Make sure the import started for the extension with a dependency. 1345 EXPECT_TRUE( 1346 prefs->GetDelayedInstallInfo("behllobkkfkfnphdnhnkndlbkcpglgmj")); 1347 EXPECT_EQ(ExtensionPrefs::DELAY_REASON_WAIT_FOR_IMPORTS, 1348 prefs->GetDelayedInstallReason("behllobkkfkfnphdnhnkndlbkcpglgmj")); 1349 1350 EXPECT_FALSE(base::PathExists(extensions_install_dir().AppendASCII( 1351 "behllobkkfkfnphdnhnkndlbkcpglgmj/1.0.0.0"))); 1352 1353 EXPECT_TRUE(service()->pending_extension_manager()->HasPendingExtensions()); 1354 std::string pending_id("eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee"); 1355 EXPECT_TRUE(service()->pending_extension_manager()->IsIdPending(pending_id)); 1356 // Remove it because we are not testing the pending extension manager's 1357 // ability to download and install extensions. 1358 EXPECT_TRUE(service()->pending_extension_manager()->Remove(pending_id)); 1359 } 1360 1361 // Test installing extensions. This test tries to install few extensions using 1362 // crx files. If you need to change those crx files, feel free to repackage 1363 // them, throw away the key used and change the id's above. 1364 TEST_F(ExtensionServiceTest, InstallExtension) { 1365 InitializeEmptyExtensionService(); 1366 1367 // Extensions not enabled. 1368 service()->set_extensions_enabled(false); 1369 base::FilePath path = data_dir().AppendASCII("good.crx"); 1370 InstallCRX(path, INSTALL_FAILED); 1371 service()->set_extensions_enabled(true); 1372 1373 ValidatePrefKeyCount(0); 1374 1375 // A simple extension that should install without error. 1376 path = data_dir().AppendASCII("good.crx"); 1377 InstallCRX(path, INSTALL_NEW); 1378 // TODO(erikkay): verify the contents of the installed extension. 1379 1380 int pref_count = 0; 1381 ValidatePrefKeyCount(++pref_count); 1382 ValidateIntegerPref(good_crx, "state", Extension::ENABLED); 1383 ValidateIntegerPref(good_crx, "location", Manifest::INTERNAL); 1384 1385 // An extension with page actions. 1386 path = data_dir().AppendASCII("page_action.crx"); 1387 InstallCRX(path, INSTALL_NEW); 1388 ValidatePrefKeyCount(++pref_count); 1389 ValidateIntegerPref(page_action, "state", Extension::ENABLED); 1390 ValidateIntegerPref(page_action, "location", Manifest::INTERNAL); 1391 1392 // Bad signature. 1393 path = data_dir().AppendASCII("bad_signature.crx"); 1394 InstallCRX(path, INSTALL_FAILED); 1395 ValidatePrefKeyCount(pref_count); 1396 1397 // 0-length extension file. 1398 path = data_dir().AppendASCII("not_an_extension.crx"); 1399 InstallCRX(path, INSTALL_FAILED); 1400 ValidatePrefKeyCount(pref_count); 1401 1402 // Bad magic number. 1403 path = data_dir().AppendASCII("bad_magic.crx"); 1404 InstallCRX(path, INSTALL_FAILED); 1405 ValidatePrefKeyCount(pref_count); 1406 1407 // Packed extensions may have folders or files that have underscores. 1408 // This will only cause a warning, rather than a fatal error. 1409 path = data_dir().AppendASCII("bad_underscore.crx"); 1410 InstallCRX(path, INSTALL_NEW); 1411 ValidatePrefKeyCount(++pref_count); 1412 1413 // A test for an extension with a 2048-bit public key. 1414 path = data_dir().AppendASCII("good2048.crx"); 1415 InstallCRX(path, INSTALL_NEW); 1416 ValidatePrefKeyCount(++pref_count); 1417 ValidateIntegerPref(good2048, "state", Extension::ENABLED); 1418 ValidateIntegerPref(good2048, "location", Manifest::INTERNAL); 1419 1420 // TODO(erikkay): add more tests for many of the failure cases. 1421 // TODO(erikkay): add tests for upgrade cases. 1422 } 1423 1424 struct MockExtensionRegistryObserver 1425 : public extensions::ExtensionRegistryObserver { 1426 virtual void OnExtensionWillBeInstalled( 1427 content::BrowserContext* browser_context, 1428 const Extension* extension, 1429 bool is_update, 1430 bool from_ephemeral, 1431 const std::string& old_name) OVERRIDE { 1432 last_extension_installed = extension->id(); 1433 } 1434 1435 virtual void OnExtensionUninstalled(content::BrowserContext* browser_context, 1436 const Extension* extension) OVERRIDE { 1437 last_extension_uninstalled = extension->id(); 1438 } 1439 1440 std::string last_extension_installed; 1441 std::string last_extension_uninstalled; 1442 }; 1443 1444 // Test that correct notifications are sent to ExtensionRegistryObserver on 1445 // extension install and uninstall. 1446 TEST_F(ExtensionServiceTest, InstallObserverNotified) { 1447 InitializeEmptyExtensionService(); 1448 1449 extensions::ExtensionRegistry* registry( 1450 extensions::ExtensionRegistry::Get(profile())); 1451 MockExtensionRegistryObserver observer; 1452 registry->AddObserver(&observer); 1453 1454 // A simple extension that should install without error. 1455 ASSERT_TRUE(observer.last_extension_installed.empty()); 1456 base::FilePath path = data_dir().AppendASCII("good.crx"); 1457 InstallCRX(path, INSTALL_NEW); 1458 ASSERT_EQ(good_crx, observer.last_extension_installed); 1459 1460 // Uninstall the extension. 1461 ASSERT_TRUE(observer.last_extension_uninstalled.empty()); 1462 UninstallExtension(good_crx, false); 1463 ASSERT_EQ(good_crx, observer.last_extension_uninstalled); 1464 1465 registry->RemoveObserver(&observer); 1466 } 1467 1468 // Tests that flags passed to OnExternalExtensionFileFound() make it to the 1469 // extension object. 1470 TEST_F(ExtensionServiceTest, InstallingExternalExtensionWithFlags) { 1471 const char kPrefFromBookmark[] = "from_bookmark"; 1472 1473 InitializeEmptyExtensionService(); 1474 1475 base::FilePath path = data_dir().AppendASCII("good.crx"); 1476 service()->set_extensions_enabled(true); 1477 1478 // Register and install an external extension. 1479 Version version("1.0.0.0"); 1480 content::WindowedNotificationObserver observer( 1481 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 1482 content::NotificationService::AllSources()); 1483 if (service()->OnExternalExtensionFileFound(good_crx, 1484 &version, 1485 path, 1486 Manifest::EXTERNAL_PREF, 1487 Extension::FROM_BOOKMARK, 1488 false /* mark_acknowledged */)) { 1489 observer.Wait(); 1490 } 1491 1492 const Extension* extension = service()->GetExtensionById(good_crx, false); 1493 ASSERT_TRUE(extension); 1494 ASSERT_TRUE(extension->from_bookmark()); 1495 ASSERT_TRUE(ValidateBooleanPref(good_crx, kPrefFromBookmark, true)); 1496 1497 // Upgrade to version 2.0, the flag should be preserved. 1498 path = data_dir().AppendASCII("good2.crx"); 1499 UpdateExtension(good_crx, path, ENABLED); 1500 ASSERT_TRUE(ValidateBooleanPref(good_crx, kPrefFromBookmark, true)); 1501 extension = service()->GetExtensionById(good_crx, false); 1502 ASSERT_TRUE(extension); 1503 ASSERT_TRUE(extension->from_bookmark()); 1504 } 1505 1506 // Test the handling of Extension::EXTERNAL_EXTENSION_UNINSTALLED 1507 TEST_F(ExtensionServiceTest, UninstallingExternalExtensions) { 1508 InitializeEmptyExtensionService(); 1509 1510 base::FilePath path = data_dir().AppendASCII("good.crx"); 1511 service()->set_extensions_enabled(true); 1512 1513 // Install an external extension. 1514 Version version("1.0.0.0"); 1515 content::WindowedNotificationObserver observer( 1516 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 1517 content::NotificationService::AllSources()); 1518 if (service()->OnExternalExtensionFileFound(good_crx, 1519 &version, 1520 path, 1521 Manifest::EXTERNAL_PREF, 1522 Extension::NO_FLAGS, 1523 false)) { 1524 observer.Wait(); 1525 } 1526 1527 ASSERT_TRUE(service()->GetExtensionById(good_crx, false)); 1528 1529 // Uninstall it and check that its killbit gets set. 1530 UninstallExtension(good_crx, false); 1531 ValidateIntegerPref(good_crx, "location", 1532 Extension::EXTERNAL_EXTENSION_UNINSTALLED); 1533 1534 // Try to re-install it externally. This should fail because of the killbit. 1535 service()->OnExternalExtensionFileFound(good_crx, 1536 &version, 1537 path, 1538 Manifest::EXTERNAL_PREF, 1539 Extension::NO_FLAGS, 1540 false); 1541 base::RunLoop().RunUntilIdle(); 1542 ASSERT_TRUE(NULL == service()->GetExtensionById(good_crx, false)); 1543 ValidateIntegerPref(good_crx, "location", 1544 Extension::EXTERNAL_EXTENSION_UNINSTALLED); 1545 1546 version = Version("1.0.0.1"); 1547 // Repeat the same thing with a newer version of the extension. 1548 path = data_dir().AppendASCII("good2.crx"); 1549 service()->OnExternalExtensionFileFound(good_crx, 1550 &version, 1551 path, 1552 Manifest::EXTERNAL_PREF, 1553 Extension::NO_FLAGS, 1554 false); 1555 base::RunLoop().RunUntilIdle(); 1556 ASSERT_TRUE(NULL == service()->GetExtensionById(good_crx, false)); 1557 ValidateIntegerPref(good_crx, "location", 1558 Extension::EXTERNAL_EXTENSION_UNINSTALLED); 1559 1560 // Try adding the same extension from an external update URL. 1561 ASSERT_FALSE(service()->pending_extension_manager()->AddFromExternalUpdateUrl( 1562 good_crx, 1563 std::string(), 1564 GURL("http:://fake.update/url"), 1565 Manifest::EXTERNAL_PREF_DOWNLOAD, 1566 Extension::NO_FLAGS, 1567 false)); 1568 1569 ASSERT_FALSE(service()->pending_extension_manager()->IsIdPending(good_crx)); 1570 } 1571 1572 // Test that uninstalling an external extension does not crash when 1573 // the extension could not be loaded. 1574 // This extension shown in preferences file requires an experimental permission. 1575 // It could not be loaded without such permission. 1576 TEST_F(ExtensionServiceTest, UninstallingNotLoadedExtension) { 1577 base::FilePath source_install_dir = 1578 data_dir().AppendASCII("good").AppendASCII("Extensions"); 1579 // The preference contains an external extension 1580 // that requires 'experimental' permission. 1581 base::FilePath pref_path = source_install_dir 1582 .DirName() 1583 .AppendASCII("PreferencesExperimental"); 1584 1585 // Aforementioned extension will not be loaded if 1586 // there is no '--enable-experimental-extension-apis' command line flag. 1587 InitializeInstalledExtensionService(pref_path, source_install_dir); 1588 1589 service()->Init(); 1590 1591 // Check and try to uninstall it. 1592 // If we don't check whether the extension is loaded before we uninstall it 1593 // in CheckExternalUninstall, a crash will happen here because we will get or 1594 // dereference a NULL pointer (extension) inside UninstallExtension. 1595 MockExtensionProvider provider(NULL, Manifest::EXTERNAL_REGISTRY); 1596 service()->OnExternalProviderReady(&provider); 1597 } 1598 1599 // Test that external extensions with incorrect IDs are not installed. 1600 TEST_F(ExtensionServiceTest, FailOnWrongId) { 1601 InitializeEmptyExtensionService(); 1602 base::FilePath path = data_dir().AppendASCII("good.crx"); 1603 service()->set_extensions_enabled(true); 1604 1605 Version version("1.0.0.0"); 1606 1607 const std::string wrong_id = all_zero; 1608 const std::string correct_id = good_crx; 1609 ASSERT_NE(correct_id, wrong_id); 1610 1611 // Install an external extension with an ID from the external 1612 // source that is not equal to the ID in the extension manifest. 1613 content::WindowedNotificationObserver observer( 1614 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 1615 content::NotificationService::AllSources()); 1616 service()->OnExternalExtensionFileFound(wrong_id, 1617 &version, 1618 path, 1619 Manifest::EXTERNAL_PREF, 1620 Extension::NO_FLAGS, 1621 false); 1622 1623 observer.Wait(); 1624 ASSERT_FALSE(service()->GetExtensionById(good_crx, false)); 1625 1626 // Try again with the right ID. Expect success. 1627 content::WindowedNotificationObserver observer2( 1628 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 1629 content::NotificationService::AllSources()); 1630 if (service()->OnExternalExtensionFileFound(correct_id, 1631 &version, 1632 path, 1633 Manifest::EXTERNAL_PREF, 1634 Extension::NO_FLAGS, 1635 false)) { 1636 observer2.Wait(); 1637 } 1638 ASSERT_TRUE(service()->GetExtensionById(good_crx, false)); 1639 } 1640 1641 // Test that external extensions with incorrect versions are not installed. 1642 TEST_F(ExtensionServiceTest, FailOnWrongVersion) { 1643 InitializeEmptyExtensionService(); 1644 base::FilePath path = data_dir().AppendASCII("good.crx"); 1645 service()->set_extensions_enabled(true); 1646 1647 // Install an external extension with a version from the external 1648 // source that is not equal to the version in the extension manifest. 1649 Version wrong_version("1.2.3.4"); 1650 content::WindowedNotificationObserver observer( 1651 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 1652 content::NotificationService::AllSources()); 1653 service()->OnExternalExtensionFileFound(good_crx, 1654 &wrong_version, 1655 path, 1656 Manifest::EXTERNAL_PREF, 1657 Extension::NO_FLAGS, 1658 false); 1659 1660 observer.Wait(); 1661 ASSERT_FALSE(service()->GetExtensionById(good_crx, false)); 1662 1663 // Try again with the right version. Expect success. 1664 service()->pending_extension_manager()->Remove(good_crx); 1665 Version correct_version("1.0.0.0"); 1666 content::WindowedNotificationObserver observer2( 1667 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 1668 content::NotificationService::AllSources()); 1669 if (service()->OnExternalExtensionFileFound(good_crx, 1670 &correct_version, 1671 path, 1672 Manifest::EXTERNAL_PREF, 1673 Extension::NO_FLAGS, 1674 false)) { 1675 observer2.Wait(); 1676 } 1677 ASSERT_TRUE(service()->GetExtensionById(good_crx, false)); 1678 } 1679 1680 // Install a user script (they get converted automatically to an extension) 1681 TEST_F(ExtensionServiceTest, InstallUserScript) { 1682 // The details of script conversion are tested elsewhere, this just tests 1683 // integration with ExtensionService. 1684 InitializeEmptyExtensionService(); 1685 1686 base::FilePath path = data_dir().AppendASCII("user_script_basic.user.js"); 1687 1688 ASSERT_TRUE(base::PathExists(path)); 1689 scoped_refptr<CrxInstaller> installer(CrxInstaller::CreateSilent(service())); 1690 installer->set_allow_silent_install(true); 1691 installer->InstallUserScript( 1692 path, 1693 GURL("http://www.aaronboodman.com/scripts/user_script_basic.user.js")); 1694 1695 base::RunLoop().RunUntilIdle(); 1696 std::vector<base::string16> errors = GetErrors(); 1697 EXPECT_TRUE(installed_) << "Nothing was installed."; 1698 EXPECT_FALSE(was_update_) << path.value(); 1699 ASSERT_EQ(1u, loaded_.size()) << "Nothing was loaded."; 1700 EXPECT_EQ(0u, errors.size()) << "There were errors: " 1701 << JoinString(errors, ','); 1702 EXPECT_TRUE(service()->GetExtensionById(loaded_[0]->id(), false)) 1703 << path.value(); 1704 1705 installed_ = NULL; 1706 was_update_ = false; 1707 loaded_.clear(); 1708 ExtensionErrorReporter::GetInstance()->ClearErrors(); 1709 } 1710 1711 // Extensions don't install during shutdown. 1712 TEST_F(ExtensionServiceTest, InstallExtensionDuringShutdown) { 1713 InitializeEmptyExtensionService(); 1714 1715 // Simulate shutdown. 1716 service()->set_browser_terminating_for_test(true); 1717 1718 base::FilePath path = data_dir().AppendASCII("good.crx"); 1719 scoped_refptr<CrxInstaller> installer(CrxInstaller::CreateSilent(service())); 1720 installer->set_allow_silent_install(true); 1721 installer->InstallCrx(path); 1722 base::RunLoop().RunUntilIdle(); 1723 1724 EXPECT_FALSE(installed_) << "Extension installed during shutdown."; 1725 ASSERT_EQ(0u, loaded_.size()) << "Extension loaded during shutdown."; 1726 } 1727 1728 // This tests that the granted permissions preferences are correctly set when 1729 // installing an extension. 1730 TEST_F(ExtensionServiceTest, GrantedPermissions) { 1731 InitializeEmptyExtensionService(); 1732 base::FilePath path = data_dir().AppendASCII("permissions"); 1733 1734 base::FilePath pem_path = path.AppendASCII("unknown.pem"); 1735 path = path.AppendASCII("unknown"); 1736 1737 ASSERT_TRUE(base::PathExists(pem_path)); 1738 ASSERT_TRUE(base::PathExists(path)); 1739 1740 ExtensionPrefs* prefs = ExtensionPrefs::Get(profile()); 1741 1742 APIPermissionSet expected_api_perms; 1743 URLPatternSet expected_host_perms; 1744 1745 // Make sure there aren't any granted permissions before the 1746 // extension is installed. 1747 scoped_refptr<PermissionSet> known_perms( 1748 prefs->GetGrantedPermissions(permissions_crx)); 1749 EXPECT_FALSE(known_perms.get()); 1750 1751 const Extension* extension = PackAndInstallCRX(path, pem_path, INSTALL_NEW); 1752 1753 EXPECT_EQ(0u, GetErrors().size()); 1754 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 1755 EXPECT_EQ(permissions_crx, extension->id()); 1756 1757 // Verify that the valid API permissions have been recognized. 1758 expected_api_perms.insert(APIPermission::kTab); 1759 1760 AddPattern(&expected_host_perms, "http://*.google.com/*"); 1761 AddPattern(&expected_host_perms, "https://*.google.com/*"); 1762 AddPattern(&expected_host_perms, "http://*.google.com.hk/*"); 1763 AddPattern(&expected_host_perms, "http://www.example.com/*"); 1764 1765 known_perms = prefs->GetGrantedPermissions(extension->id()); 1766 EXPECT_TRUE(known_perms.get()); 1767 EXPECT_FALSE(known_perms->IsEmpty()); 1768 EXPECT_EQ(expected_api_perms, known_perms->apis()); 1769 EXPECT_FALSE(known_perms->HasEffectiveFullAccess()); 1770 EXPECT_EQ(expected_host_perms, known_perms->effective_hosts()); 1771 } 1772 1773 1774 #if !defined(OS_CHROMEOS) 1775 // This tests that the granted permissions preferences are correctly set for 1776 // default apps. 1777 TEST_F(ExtensionServiceTest, DefaultAppsGrantedPermissions) { 1778 InitializeEmptyExtensionService(); 1779 base::FilePath path = data_dir().AppendASCII("permissions"); 1780 1781 base::FilePath pem_path = path.AppendASCII("unknown.pem"); 1782 path = path.AppendASCII("unknown"); 1783 1784 ASSERT_TRUE(base::PathExists(pem_path)); 1785 ASSERT_TRUE(base::PathExists(path)); 1786 1787 ExtensionPrefs* prefs = ExtensionPrefs::Get(profile()); 1788 1789 APIPermissionSet expected_api_perms; 1790 URLPatternSet expected_host_perms; 1791 1792 // Make sure there aren't any granted permissions before the 1793 // extension is installed. 1794 scoped_refptr<PermissionSet> known_perms( 1795 prefs->GetGrantedPermissions(permissions_crx)); 1796 EXPECT_FALSE(known_perms.get()); 1797 1798 const Extension* extension = PackAndInstallCRX( 1799 path, pem_path, INSTALL_NEW, Extension::WAS_INSTALLED_BY_DEFAULT); 1800 1801 EXPECT_EQ(0u, GetErrors().size()); 1802 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 1803 EXPECT_EQ(permissions_crx, extension->id()); 1804 1805 // Verify that the valid API permissions have been recognized. 1806 expected_api_perms.insert(APIPermission::kTab); 1807 1808 known_perms = prefs->GetGrantedPermissions(extension->id()); 1809 EXPECT_TRUE(known_perms.get()); 1810 EXPECT_FALSE(known_perms->IsEmpty()); 1811 EXPECT_EQ(expected_api_perms, known_perms->apis()); 1812 EXPECT_FALSE(known_perms->HasEffectiveFullAccess()); 1813 } 1814 #endif 1815 1816 #if !defined(OS_POSIX) || defined(OS_MACOSX) 1817 // Tests that the granted permissions full_access bit gets set correctly when 1818 // an extension contains an NPAPI plugin. 1819 // Only run this on platforms that support NPAPI plugins. 1820 TEST_F(ExtensionServiceTest, GrantedFullAccessPermissions) { 1821 InitPluginService(); 1822 1823 InitializeEmptyExtensionService(); 1824 1825 ASSERT_TRUE(base::PathExists(good1_path())); 1826 const Extension* extension = PackAndInstallCRX(good1_path(), INSTALL_NEW); 1827 EXPECT_EQ(0u, GetErrors().size()); 1828 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 1829 ExtensionPrefs* prefs = ExtensionPrefs::Get(profile()); 1830 1831 scoped_refptr<PermissionSet> permissions( 1832 prefs->GetGrantedPermissions(extension->id())); 1833 EXPECT_FALSE(permissions->IsEmpty()); 1834 EXPECT_TRUE(permissions->HasEffectiveFullAccess()); 1835 EXPECT_FALSE(permissions->apis().empty()); 1836 EXPECT_TRUE(permissions->HasAPIPermission(APIPermission::kPlugin)); 1837 1838 // Full access implies full host access too... 1839 EXPECT_TRUE(permissions->HasEffectiveAccessToAllHosts()); 1840 } 1841 #endif 1842 1843 // Tests that the extension is disabled when permissions are missing from 1844 // the extension's granted permissions preferences. (This simulates updating 1845 // the browser to a version which recognizes more permissions). 1846 TEST_F(ExtensionServiceTest, GrantedAPIAndHostPermissions) { 1847 InitializeEmptyExtensionService(); 1848 1849 base::FilePath path = 1850 data_dir().AppendASCII("permissions").AppendASCII("unknown"); 1851 1852 ASSERT_TRUE(base::PathExists(path)); 1853 1854 const Extension* extension = PackAndInstallCRX(path, INSTALL_NEW); 1855 1856 EXPECT_EQ(0u, GetErrors().size()); 1857 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 1858 std::string extension_id = extension->id(); 1859 1860 ExtensionPrefs* prefs = ExtensionPrefs::Get(profile()); 1861 1862 APIPermissionSet expected_api_permissions; 1863 URLPatternSet expected_host_permissions; 1864 1865 expected_api_permissions.insert(APIPermission::kTab); 1866 AddPattern(&expected_host_permissions, "http://*.google.com/*"); 1867 AddPattern(&expected_host_permissions, "https://*.google.com/*"); 1868 AddPattern(&expected_host_permissions, "http://*.google.com.hk/*"); 1869 AddPattern(&expected_host_permissions, "http://www.example.com/*"); 1870 1871 std::set<std::string> host_permissions; 1872 1873 // Test that the extension is disabled when an API permission is missing from 1874 // the extension's granted api permissions preference. (This simulates 1875 // updating the browser to a version which recognizes a new API permission). 1876 SetPref(extension_id, "granted_permissions.api", 1877 new base::ListValue(), "granted_permissions.api"); 1878 service()->ReloadExtensionsForTest(); 1879 1880 EXPECT_EQ(1u, registry()->disabled_extensions().size()); 1881 extension = registry()->disabled_extensions().begin()->get(); 1882 1883 ASSERT_TRUE(prefs->IsExtensionDisabled(extension_id)); 1884 ASSERT_FALSE(service()->IsExtensionEnabled(extension_id)); 1885 ASSERT_TRUE(prefs->DidExtensionEscalatePermissions(extension_id)); 1886 1887 // Now grant and re-enable the extension, making sure the prefs are updated. 1888 service()->GrantPermissionsAndEnableExtension(extension); 1889 1890 ASSERT_FALSE(prefs->IsExtensionDisabled(extension_id)); 1891 ASSERT_TRUE(service()->IsExtensionEnabled(extension_id)); 1892 ASSERT_FALSE(prefs->DidExtensionEscalatePermissions(extension_id)); 1893 1894 scoped_refptr<PermissionSet> current_perms( 1895 prefs->GetGrantedPermissions(extension_id)); 1896 ASSERT_TRUE(current_perms.get()); 1897 ASSERT_FALSE(current_perms->IsEmpty()); 1898 ASSERT_FALSE(current_perms->HasEffectiveFullAccess()); 1899 ASSERT_EQ(expected_api_permissions, current_perms->apis()); 1900 ASSERT_EQ(expected_host_permissions, current_perms->effective_hosts()); 1901 1902 // Tests that the extension is disabled when a host permission is missing from 1903 // the extension's granted host permissions preference. (This simulates 1904 // updating the browser to a version which recognizes additional host 1905 // permissions). 1906 host_permissions.clear(); 1907 current_perms = NULL; 1908 1909 host_permissions.insert("http://*.google.com/*"); 1910 host_permissions.insert("https://*.google.com/*"); 1911 host_permissions.insert("http://*.google.com.hk/*"); 1912 1913 base::ListValue* api_permissions = new base::ListValue(); 1914 api_permissions->Append( 1915 new base::StringValue("tabs")); 1916 SetPref(extension_id, "granted_permissions.api", 1917 api_permissions, "granted_permissions.api"); 1918 SetPrefStringSet( 1919 extension_id, "granted_permissions.scriptable_host", host_permissions); 1920 1921 service()->ReloadExtensionsForTest(); 1922 1923 EXPECT_EQ(1u, registry()->disabled_extensions().size()); 1924 extension = registry()->disabled_extensions().begin()->get(); 1925 1926 ASSERT_TRUE(prefs->IsExtensionDisabled(extension_id)); 1927 ASSERT_FALSE(service()->IsExtensionEnabled(extension_id)); 1928 ASSERT_TRUE(prefs->DidExtensionEscalatePermissions(extension_id)); 1929 1930 // Now grant and re-enable the extension, making sure the prefs are updated. 1931 service()->GrantPermissionsAndEnableExtension(extension); 1932 1933 ASSERT_TRUE(service()->IsExtensionEnabled(extension_id)); 1934 ASSERT_FALSE(prefs->DidExtensionEscalatePermissions(extension_id)); 1935 1936 current_perms = prefs->GetGrantedPermissions(extension_id); 1937 ASSERT_TRUE(current_perms.get()); 1938 ASSERT_FALSE(current_perms->IsEmpty()); 1939 ASSERT_FALSE(current_perms->HasEffectiveFullAccess()); 1940 ASSERT_EQ(expected_api_permissions, current_perms->apis()); 1941 ASSERT_EQ(expected_host_permissions, current_perms->effective_hosts()); 1942 } 1943 1944 // Test Packaging and installing an extension. 1945 TEST_F(ExtensionServiceTest, PackExtension) { 1946 InitializeEmptyExtensionService(); 1947 base::FilePath input_directory = 1948 data_dir() 1949 .AppendASCII("good") 1950 .AppendASCII("Extensions") 1951 .AppendASCII("behllobkkfkfnphdnhnkndlbkcpglgmj") 1952 .AppendASCII("1.0.0.0"); 1953 1954 base::ScopedTempDir temp_dir; 1955 ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); 1956 base::FilePath output_directory = temp_dir.path(); 1957 1958 base::FilePath crx_path(output_directory.AppendASCII("ex1.crx")); 1959 base::FilePath privkey_path(output_directory.AppendASCII("privkey.pem")); 1960 1961 scoped_ptr<ExtensionCreator> creator(new ExtensionCreator()); 1962 ASSERT_TRUE(creator->Run(input_directory, crx_path, base::FilePath(), 1963 privkey_path, ExtensionCreator::kNoRunFlags)); 1964 ASSERT_TRUE(base::PathExists(crx_path)); 1965 ASSERT_TRUE(base::PathExists(privkey_path)); 1966 1967 // Repeat the run with the pem file gone, and no special flags 1968 // Should refuse to overwrite the existing crx. 1969 base::DeleteFile(privkey_path, false); 1970 ASSERT_FALSE(creator->Run(input_directory, crx_path, base::FilePath(), 1971 privkey_path, ExtensionCreator::kNoRunFlags)); 1972 1973 // OK, now try it with a flag to overwrite existing crx. Should work. 1974 ASSERT_TRUE(creator->Run(input_directory, crx_path, base::FilePath(), 1975 privkey_path, ExtensionCreator::kOverwriteCRX)); 1976 1977 // Repeat the run allowing existing crx, but the existing pem is still 1978 // an error. Should fail. 1979 ASSERT_FALSE(creator->Run(input_directory, crx_path, base::FilePath(), 1980 privkey_path, ExtensionCreator::kOverwriteCRX)); 1981 1982 ASSERT_TRUE(base::PathExists(privkey_path)); 1983 InstallCRX(crx_path, INSTALL_NEW); 1984 1985 // Try packing with invalid paths. 1986 creator.reset(new ExtensionCreator()); 1987 ASSERT_FALSE( 1988 creator->Run(base::FilePath(), base::FilePath(), base::FilePath(), 1989 base::FilePath(), ExtensionCreator::kOverwriteCRX)); 1990 1991 // Try packing an empty directory. Should fail because an empty directory is 1992 // not a valid extension. 1993 base::ScopedTempDir temp_dir2; 1994 ASSERT_TRUE(temp_dir2.CreateUniqueTempDir()); 1995 creator.reset(new ExtensionCreator()); 1996 ASSERT_FALSE(creator->Run(temp_dir2.path(), crx_path, privkey_path, 1997 base::FilePath(), ExtensionCreator::kOverwriteCRX)); 1998 1999 // Try packing with an invalid manifest. 2000 std::string invalid_manifest_content = "I am not a manifest."; 2001 ASSERT_TRUE(base::WriteFile( 2002 temp_dir2.path().Append(extensions::kManifestFilename), 2003 invalid_manifest_content.c_str(), invalid_manifest_content.size())); 2004 creator.reset(new ExtensionCreator()); 2005 ASSERT_FALSE(creator->Run(temp_dir2.path(), crx_path, privkey_path, 2006 base::FilePath(), ExtensionCreator::kOverwriteCRX)); 2007 2008 // Try packing with a private key that is a valid key, but invalid for the 2009 // extension. 2010 base::FilePath bad_private_key_dir = 2011 data_dir().AppendASCII("bad_private_key"); 2012 crx_path = output_directory.AppendASCII("bad_private_key.crx"); 2013 privkey_path = data_dir().AppendASCII("bad_private_key.pem"); 2014 ASSERT_FALSE(creator->Run(bad_private_key_dir, crx_path, base::FilePath(), 2015 privkey_path, ExtensionCreator::kOverwriteCRX)); 2016 } 2017 2018 // Test Packaging and installing an extension whose name contains punctuation. 2019 TEST_F(ExtensionServiceTest, PackPunctuatedExtension) { 2020 InitializeEmptyExtensionService(); 2021 base::FilePath input_directory = data_dir() 2022 .AppendASCII("good") 2023 .AppendASCII("Extensions") 2024 .AppendASCII(good0) 2025 .AppendASCII("1.0.0.0"); 2026 2027 base::ScopedTempDir temp_dir; 2028 ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); 2029 2030 // Extension names containing punctuation, and the expected names for the 2031 // packed extensions. 2032 const base::FilePath punctuated_names[] = { 2033 base::FilePath(FILE_PATH_LITERAL("this.extensions.name.has.periods")), 2034 base::FilePath(FILE_PATH_LITERAL(".thisextensionsnamestartswithaperiod")), 2035 base::FilePath(FILE_PATH_LITERAL("thisextensionhasaslashinitsname/")). 2036 NormalizePathSeparators(), 2037 }; 2038 const base::FilePath expected_crx_names[] = { 2039 base::FilePath(FILE_PATH_LITERAL("this.extensions.name.has.periods.crx")), 2040 base::FilePath( 2041 FILE_PATH_LITERAL(".thisextensionsnamestartswithaperiod.crx")), 2042 base::FilePath(FILE_PATH_LITERAL("thisextensionhasaslashinitsname.crx")), 2043 }; 2044 const base::FilePath expected_private_key_names[] = { 2045 base::FilePath(FILE_PATH_LITERAL("this.extensions.name.has.periods.pem")), 2046 base::FilePath( 2047 FILE_PATH_LITERAL(".thisextensionsnamestartswithaperiod.pem")), 2048 base::FilePath(FILE_PATH_LITERAL("thisextensionhasaslashinitsname.pem")), 2049 }; 2050 2051 for (size_t i = 0; i < arraysize(punctuated_names); ++i) { 2052 SCOPED_TRACE(punctuated_names[i].value().c_str()); 2053 base::FilePath output_dir = temp_dir.path().Append(punctuated_names[i]); 2054 2055 // Copy the extension into the output directory, as PackExtensionJob doesn't 2056 // let us choose where to output the packed extension. 2057 ASSERT_TRUE(base::CopyDirectory(input_directory, output_dir, true)); 2058 2059 base::FilePath expected_crx_path = 2060 temp_dir.path().Append(expected_crx_names[i]); 2061 base::FilePath expected_private_key_path = 2062 temp_dir.path().Append(expected_private_key_names[i]); 2063 PackExtensionTestClient pack_client(expected_crx_path, 2064 expected_private_key_path); 2065 scoped_refptr<extensions::PackExtensionJob> packer( 2066 new extensions::PackExtensionJob(&pack_client, output_dir, 2067 base::FilePath(), 2068 ExtensionCreator::kOverwriteCRX)); 2069 packer->Start(); 2070 2071 // The packer will post a notification task to the current thread's message 2072 // loop when it is finished. We manually run the loop here so that we 2073 // block and catch the notification; otherwise, the process would exit. 2074 // This call to |Run()| is matched by a call to |Quit()| in the 2075 // |PackExtensionTestClient|'s notification handling code. 2076 base::MessageLoop::current()->Run(); 2077 2078 if (HasFatalFailure()) 2079 return; 2080 2081 InstallCRX(expected_crx_path, INSTALL_NEW); 2082 } 2083 } 2084 2085 TEST_F(ExtensionServiceTest, PackExtensionContainingKeyFails) { 2086 InitializeEmptyExtensionService(); 2087 2088 base::ScopedTempDir extension_temp_dir; 2089 ASSERT_TRUE(extension_temp_dir.CreateUniqueTempDir()); 2090 base::FilePath input_directory = extension_temp_dir.path().AppendASCII("ext"); 2091 ASSERT_TRUE( 2092 base::CopyDirectory(data_dir() 2093 .AppendASCII("good") 2094 .AppendASCII("Extensions") 2095 .AppendASCII("behllobkkfkfnphdnhnkndlbkcpglgmj") 2096 .AppendASCII("1.0.0.0"), 2097 input_directory, 2098 /*recursive=*/true)); 2099 2100 base::ScopedTempDir output_temp_dir; 2101 ASSERT_TRUE(output_temp_dir.CreateUniqueTempDir()); 2102 base::FilePath output_directory = output_temp_dir.path(); 2103 2104 base::FilePath crx_path(output_directory.AppendASCII("ex1.crx")); 2105 base::FilePath privkey_path(output_directory.AppendASCII("privkey.pem")); 2106 2107 // Pack the extension once to get a private key. 2108 scoped_ptr<ExtensionCreator> creator(new ExtensionCreator()); 2109 ASSERT_TRUE(creator->Run(input_directory, crx_path, base::FilePath(), 2110 privkey_path, ExtensionCreator::kNoRunFlags)) 2111 << creator->error_message(); 2112 ASSERT_TRUE(base::PathExists(crx_path)); 2113 ASSERT_TRUE(base::PathExists(privkey_path)); 2114 2115 base::DeleteFile(crx_path, false); 2116 // Move the pem file into the extension. 2117 base::Move(privkey_path, 2118 input_directory.AppendASCII("privkey.pem")); 2119 2120 // This pack should fail because of the contained private key. 2121 EXPECT_FALSE(creator->Run(input_directory, crx_path, base::FilePath(), 2122 privkey_path, ExtensionCreator::kNoRunFlags)); 2123 EXPECT_THAT(creator->error_message(), 2124 testing::ContainsRegex( 2125 "extension includes the key file.*privkey.pem")); 2126 } 2127 2128 // Test Packaging and installing an extension using an openssl generated key. 2129 // The openssl is generated with the following: 2130 // > openssl genrsa -out privkey.pem 1024 2131 // > openssl pkcs8 -topk8 -nocrypt -in privkey.pem -out privkey_asn1.pem 2132 // The privkey.pem is a PrivateKey, and the pcks8 -topk8 creates a 2133 // PrivateKeyInfo ASN.1 structure, we our RSAPrivateKey expects. 2134 TEST_F(ExtensionServiceTest, PackExtensionOpenSSLKey) { 2135 InitializeEmptyExtensionService(); 2136 base::FilePath input_directory = 2137 data_dir() 2138 .AppendASCII("good") 2139 .AppendASCII("Extensions") 2140 .AppendASCII("behllobkkfkfnphdnhnkndlbkcpglgmj") 2141 .AppendASCII("1.0.0.0"); 2142 base::FilePath privkey_path( 2143 data_dir().AppendASCII("openssl_privkey_asn1.pem")); 2144 ASSERT_TRUE(base::PathExists(privkey_path)); 2145 2146 base::ScopedTempDir temp_dir; 2147 ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); 2148 base::FilePath output_directory = temp_dir.path(); 2149 2150 base::FilePath crx_path(output_directory.AppendASCII("ex1.crx")); 2151 2152 scoped_ptr<ExtensionCreator> creator(new ExtensionCreator()); 2153 ASSERT_TRUE(creator->Run(input_directory, crx_path, privkey_path, 2154 base::FilePath(), ExtensionCreator::kOverwriteCRX)); 2155 2156 InstallCRX(crx_path, INSTALL_NEW); 2157 } 2158 2159 #if defined(THREAD_SANITIZER) 2160 // Flaky under Tsan. http://crbug.com/377702 2161 #define MAYBE_InstallTheme DISABLED_InstallTheme 2162 #else 2163 #define MAYBE_InstallTheme InstallTheme 2164 #endif 2165 2166 TEST_F(ExtensionServiceTest, MAYBE_InstallTheme) { 2167 InitializeEmptyExtensionService(); 2168 service()->Init(); 2169 2170 // A theme. 2171 base::FilePath path = data_dir().AppendASCII("theme.crx"); 2172 InstallCRX(path, INSTALL_NEW); 2173 int pref_count = 0; 2174 ValidatePrefKeyCount(++pref_count); 2175 ValidateIntegerPref(theme_crx, "state", Extension::ENABLED); 2176 ValidateIntegerPref(theme_crx, "location", Manifest::INTERNAL); 2177 2178 // A theme when extensions are disabled. Themes can be installed, even when 2179 // extensions are disabled. 2180 service()->set_extensions_enabled(false); 2181 path = data_dir().AppendASCII("theme2.crx"); 2182 InstallCRX(path, INSTALL_NEW); 2183 ValidatePrefKeyCount(++pref_count); 2184 ValidateIntegerPref(theme2_crx, "state", Extension::ENABLED); 2185 ValidateIntegerPref(theme2_crx, "location", Manifest::INTERNAL); 2186 2187 // A theme with extension elements. Themes cannot have extension elements, 2188 // so any such elements (like content scripts) should be ignored. 2189 service()->set_extensions_enabled(true); 2190 { 2191 path = data_dir().AppendASCII("theme_with_extension.crx"); 2192 const Extension* extension = InstallCRX(path, INSTALL_NEW); 2193 ValidatePrefKeyCount(++pref_count); 2194 ASSERT_TRUE(extension); 2195 EXPECT_TRUE(extension->is_theme()); 2196 EXPECT_EQ( 2197 0u, 2198 extensions::ContentScriptsInfo::GetContentScripts(extension).size()); 2199 } 2200 2201 // A theme with image resources missing (misspelt path). 2202 path = data_dir().AppendASCII("theme_missing_image.crx"); 2203 InstallCRX(path, INSTALL_FAILED); 2204 ValidatePrefKeyCount(pref_count); 2205 } 2206 2207 TEST_F(ExtensionServiceTest, LoadLocalizedTheme) { 2208 // Load. 2209 InitializeEmptyExtensionService(); 2210 service()->Init(); 2211 2212 base::FilePath extension_path = data_dir().AppendASCII("theme_i18n"); 2213 2214 extensions::UnpackedInstaller::Create(service())->Load(extension_path); 2215 base::RunLoop().RunUntilIdle(); 2216 EXPECT_EQ(0u, GetErrors().size()); 2217 ASSERT_EQ(1u, loaded_.size()); 2218 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 2219 const Extension* theme = registry()->enabled_extensions().begin()->get(); 2220 EXPECT_EQ("name", theme->name()); 2221 EXPECT_EQ("description", theme->description()); 2222 2223 // Cleanup the "Cached Theme.pak" file. Ideally, this would be installed in a 2224 // temporary directory, but it automatically installs to the extension's 2225 // directory, and we don't want to copy the whole extension for a unittest. 2226 base::FilePath theme_file = extension_path.Append(chrome::kThemePackFilename); 2227 ASSERT_TRUE(base::PathExists(theme_file)); 2228 ASSERT_TRUE(base::DeleteFile(theme_file, false)); // Not recursive. 2229 } 2230 2231 // Tests that we can change the ID of an unpacked extension by adding a key 2232 // to its manifest. 2233 TEST_F(ExtensionServiceTest, UnpackedExtensionCanChangeID) { 2234 InitializeEmptyExtensionService(); 2235 2236 base::ScopedTempDir temp; 2237 ASSERT_TRUE(temp.CreateUniqueTempDir()); 2238 2239 base::FilePath extension_path = temp.path(); 2240 base::FilePath manifest_path = 2241 extension_path.Append(extensions::kManifestFilename); 2242 base::FilePath manifest_no_key = 2243 data_dir().AppendASCII("unpacked").AppendASCII("manifest_no_key.json"); 2244 2245 base::FilePath manifest_with_key = 2246 data_dir().AppendASCII("unpacked").AppendASCII("manifest_with_key.json"); 2247 2248 ASSERT_TRUE(base::PathExists(manifest_no_key)); 2249 ASSERT_TRUE(base::PathExists(manifest_with_key)); 2250 2251 // Load the unpacked extension with no key. 2252 base::CopyFile(manifest_no_key, manifest_path); 2253 extensions::UnpackedInstaller::Create(service())->Load(extension_path); 2254 2255 base::RunLoop().RunUntilIdle(); 2256 EXPECT_EQ(0u, GetErrors().size()); 2257 ASSERT_EQ(1u, loaded_.size()); 2258 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 2259 2260 // Add the key to the manifest. 2261 base::CopyFile(manifest_with_key, manifest_path); 2262 loaded_.clear(); 2263 2264 // Reload the extensions. 2265 service()->ReloadExtensionsForTest(); 2266 const Extension* extension = service()->GetExtensionById(unpacked, false); 2267 EXPECT_EQ(unpacked, extension->id()); 2268 ASSERT_EQ(1u, loaded_.size()); 2269 2270 // TODO(jstritar): Right now this just makes sure we don't crash and burn, but 2271 // we should also test that preferences are preserved. 2272 } 2273 2274 #if defined(OS_POSIX) 2275 TEST_F(ExtensionServiceTest, UnpackedExtensionMayContainSymlinkedFiles) { 2276 base::FilePath source_data_dir = 2277 data_dir().AppendASCII("unpacked").AppendASCII("symlinks_allowed"); 2278 2279 // Paths to test data files. 2280 base::FilePath source_manifest = source_data_dir.AppendASCII("manifest.json"); 2281 ASSERT_TRUE(base::PathExists(source_manifest)); 2282 base::FilePath source_icon = source_data_dir.AppendASCII("icon.png"); 2283 ASSERT_TRUE(base::PathExists(source_icon)); 2284 2285 // Set up the temporary extension directory. 2286 base::ScopedTempDir temp; 2287 ASSERT_TRUE(temp.CreateUniqueTempDir()); 2288 base::FilePath extension_path = temp.path(); 2289 base::FilePath manifest = extension_path.Append( 2290 extensions::kManifestFilename); 2291 base::FilePath icon_symlink = extension_path.AppendASCII("icon.png"); 2292 base::CopyFile(source_manifest, manifest); 2293 base::CreateSymbolicLink(source_icon, icon_symlink); 2294 2295 // Load extension. 2296 InitializeEmptyExtensionService(); 2297 extensions::UnpackedInstaller::Create(service())->Load(extension_path); 2298 base::RunLoop().RunUntilIdle(); 2299 2300 EXPECT_TRUE(GetErrors().empty()); 2301 ASSERT_EQ(1u, loaded_.size()); 2302 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 2303 } 2304 #endif 2305 2306 TEST_F(ExtensionServiceTest, UnpackedExtensionMayNotHaveUnderscore) { 2307 InitializeEmptyExtensionService(); 2308 base::FilePath extension_path = data_dir().AppendASCII("underscore_name"); 2309 extensions::UnpackedInstaller::Create(service())->Load(extension_path); 2310 base::RunLoop().RunUntilIdle(); 2311 EXPECT_EQ(1u, GetErrors().size()); 2312 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 2313 } 2314 2315 TEST_F(ExtensionServiceTest, InstallLocalizedTheme) { 2316 InitializeEmptyExtensionService(); 2317 service()->Init(); 2318 2319 base::FilePath theme_path = data_dir().AppendASCII("theme_i18n"); 2320 2321 const Extension* theme = PackAndInstallCRX(theme_path, INSTALL_NEW); 2322 2323 EXPECT_EQ(0u, GetErrors().size()); 2324 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 2325 EXPECT_EQ("name", theme->name()); 2326 EXPECT_EQ("description", theme->description()); 2327 } 2328 2329 TEST_F(ExtensionServiceTest, InstallApps) { 2330 InitializeEmptyExtensionService(); 2331 2332 // An empty app. 2333 const Extension* app = 2334 PackAndInstallCRX(data_dir().AppendASCII("app1"), INSTALL_NEW); 2335 int pref_count = 0; 2336 ValidatePrefKeyCount(++pref_count); 2337 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 2338 ValidateIntegerPref(app->id(), "state", Extension::ENABLED); 2339 ValidateIntegerPref(app->id(), "location", Manifest::INTERNAL); 2340 2341 // Another app with non-overlapping extent. Should succeed. 2342 PackAndInstallCRX(data_dir().AppendASCII("app2"), INSTALL_NEW); 2343 ValidatePrefKeyCount(++pref_count); 2344 2345 // A third app whose extent overlaps the first. Should fail. 2346 PackAndInstallCRX(data_dir().AppendASCII("app3"), INSTALL_FAILED); 2347 ValidatePrefKeyCount(pref_count); 2348 } 2349 2350 // Tests that file access is OFF by default. 2351 TEST_F(ExtensionServiceTest, DefaultFileAccess) { 2352 InitializeEmptyExtensionService(); 2353 const Extension* extension = PackAndInstallCRX( 2354 data_dir().AppendASCII("permissions").AppendASCII("files"), INSTALL_NEW); 2355 EXPECT_EQ(0u, GetErrors().size()); 2356 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 2357 EXPECT_FALSE( 2358 ExtensionPrefs::Get(profile())->AllowFileAccess(extension->id())); 2359 } 2360 2361 TEST_F(ExtensionServiceTest, UpdateApps) { 2362 InitializeEmptyExtensionService(); 2363 base::FilePath extensions_path = data_dir().AppendASCII("app_update"); 2364 2365 // First install v1 of a hosted app. 2366 const Extension* extension = 2367 InstallCRX(extensions_path.AppendASCII("v1.crx"), INSTALL_NEW); 2368 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 2369 std::string id = extension->id(); 2370 ASSERT_EQ(std::string("1"), extension->version()->GetString()); 2371 2372 // Now try updating to v2. 2373 UpdateExtension(id, 2374 extensions_path.AppendASCII("v2.crx"), 2375 ENABLED); 2376 ASSERT_EQ(std::string("2"), 2377 service()->GetExtensionById(id, false)->version()->GetString()); 2378 } 2379 2380 // Verifies that the NTP page and launch ordinals are kept when updating apps. 2381 TEST_F(ExtensionServiceTest, UpdateAppsRetainOrdinals) { 2382 InitializeEmptyExtensionService(); 2383 AppSorting* sorting = ExtensionPrefs::Get(profile())->app_sorting(); 2384 base::FilePath extensions_path = data_dir().AppendASCII("app_update"); 2385 2386 // First install v1 of a hosted app. 2387 const Extension* extension = 2388 InstallCRX(extensions_path.AppendASCII("v1.crx"), INSTALL_NEW); 2389 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 2390 std::string id = extension->id(); 2391 ASSERT_EQ(std::string("1"), extension->version()->GetString()); 2392 2393 // Modify the ordinals so we can distinguish them from the defaults. 2394 syncer::StringOrdinal new_page_ordinal = 2395 sorting->GetPageOrdinal(id).CreateAfter(); 2396 syncer::StringOrdinal new_launch_ordinal = 2397 sorting->GetAppLaunchOrdinal(id).CreateBefore(); 2398 2399 sorting->SetPageOrdinal(id, new_page_ordinal); 2400 sorting->SetAppLaunchOrdinal(id, new_launch_ordinal); 2401 2402 // Now try updating to v2. 2403 UpdateExtension(id, extensions_path.AppendASCII("v2.crx"), ENABLED); 2404 ASSERT_EQ(std::string("2"), 2405 service()->GetExtensionById(id, false)->version()->GetString()); 2406 2407 // Verify that the ordinals match. 2408 ASSERT_TRUE(new_page_ordinal.Equals(sorting->GetPageOrdinal(id))); 2409 ASSERT_TRUE(new_launch_ordinal.Equals(sorting->GetAppLaunchOrdinal(id))); 2410 } 2411 2412 // Ensures that the CWS has properly initialized ordinals. 2413 TEST_F(ExtensionServiceTest, EnsureCWSOrdinalsInitialized) { 2414 InitializeEmptyExtensionService(); 2415 service()->component_loader()->Add( 2416 IDR_WEBSTORE_MANIFEST, base::FilePath(FILE_PATH_LITERAL("web_store"))); 2417 service()->Init(); 2418 2419 AppSorting* sorting = ExtensionPrefs::Get(profile())->app_sorting(); 2420 EXPECT_TRUE( 2421 sorting->GetPageOrdinal(extension_misc::kWebStoreAppId).IsValid()); 2422 EXPECT_TRUE( 2423 sorting->GetAppLaunchOrdinal(extension_misc::kWebStoreAppId).IsValid()); 2424 } 2425 2426 TEST_F(ExtensionServiceTest, InstallAppsWithUnlimitedStorage) { 2427 InitializeEmptyExtensionService(); 2428 EXPECT_TRUE(registry()->enabled_extensions().is_empty()); 2429 2430 int pref_count = 0; 2431 2432 // Install app1 with unlimited storage. 2433 const Extension* extension = 2434 PackAndInstallCRX(data_dir().AppendASCII("app1"), INSTALL_NEW); 2435 ValidatePrefKeyCount(++pref_count); 2436 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 2437 const std::string id1 = extension->id(); 2438 EXPECT_TRUE(extension->permissions_data()->HasAPIPermission( 2439 APIPermission::kUnlimitedStorage)); 2440 EXPECT_TRUE(extension->web_extent().MatchesURL( 2441 extensions::AppLaunchInfo::GetFullLaunchURL(extension))); 2442 const GURL origin1( 2443 extensions::AppLaunchInfo::GetFullLaunchURL(extension).GetOrigin()); 2444 EXPECT_TRUE(profile()->GetExtensionSpecialStoragePolicy()->IsStorageUnlimited( 2445 origin1)); 2446 2447 // Install app2 from the same origin with unlimited storage. 2448 extension = PackAndInstallCRX(data_dir().AppendASCII("app2"), INSTALL_NEW); 2449 ValidatePrefKeyCount(++pref_count); 2450 ASSERT_EQ(2u, registry()->enabled_extensions().size()); 2451 const std::string id2 = extension->id(); 2452 EXPECT_TRUE(extension->permissions_data()->HasAPIPermission( 2453 APIPermission::kUnlimitedStorage)); 2454 EXPECT_TRUE(extension->web_extent().MatchesURL( 2455 extensions::AppLaunchInfo::GetFullLaunchURL(extension))); 2456 const GURL origin2( 2457 extensions::AppLaunchInfo::GetFullLaunchURL(extension).GetOrigin()); 2458 EXPECT_EQ(origin1, origin2); 2459 EXPECT_TRUE(profile()->GetExtensionSpecialStoragePolicy()->IsStorageUnlimited( 2460 origin2)); 2461 2462 // Uninstall one of them, unlimited storage should still be granted 2463 // to the origin. 2464 UninstallExtension(id1, false); 2465 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 2466 EXPECT_TRUE(profile()->GetExtensionSpecialStoragePolicy()->IsStorageUnlimited( 2467 origin1)); 2468 2469 // Uninstall the other, unlimited storage should be revoked. 2470 UninstallExtension(id2, false); 2471 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 2472 EXPECT_FALSE( 2473 profile()->GetExtensionSpecialStoragePolicy()->IsStorageUnlimited( 2474 origin2)); 2475 } 2476 2477 TEST_F(ExtensionServiceTest, InstallAppsAndCheckStorageProtection) { 2478 InitializeEmptyExtensionService(); 2479 EXPECT_TRUE(registry()->enabled_extensions().is_empty()); 2480 2481 int pref_count = 0; 2482 2483 const Extension* extension = 2484 PackAndInstallCRX(data_dir().AppendASCII("app1"), INSTALL_NEW); 2485 ValidatePrefKeyCount(++pref_count); 2486 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 2487 EXPECT_TRUE(extension->is_app()); 2488 const std::string id1 = extension->id(); 2489 const GURL origin1( 2490 extensions::AppLaunchInfo::GetFullLaunchURL(extension).GetOrigin()); 2491 EXPECT_TRUE(profile()->GetExtensionSpecialStoragePolicy()->IsStorageProtected( 2492 origin1)); 2493 2494 // App 4 has a different origin (maps.google.com). 2495 extension = PackAndInstallCRX(data_dir().AppendASCII("app4"), INSTALL_NEW); 2496 ValidatePrefKeyCount(++pref_count); 2497 ASSERT_EQ(2u, registry()->enabled_extensions().size()); 2498 const std::string id2 = extension->id(); 2499 const GURL origin2( 2500 extensions::AppLaunchInfo::GetFullLaunchURL(extension).GetOrigin()); 2501 ASSERT_NE(origin1, origin2); 2502 EXPECT_TRUE(profile()->GetExtensionSpecialStoragePolicy()->IsStorageProtected( 2503 origin2)); 2504 2505 UninstallExtension(id1, false); 2506 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 2507 2508 UninstallExtension(id2, false); 2509 2510 EXPECT_TRUE(registry()->enabled_extensions().is_empty()); 2511 EXPECT_FALSE( 2512 profile()->GetExtensionSpecialStoragePolicy()->IsStorageProtected( 2513 origin1)); 2514 EXPECT_FALSE( 2515 profile()->GetExtensionSpecialStoragePolicy()->IsStorageProtected( 2516 origin2)); 2517 } 2518 2519 // Test that when an extension version is reinstalled, nothing happens. 2520 TEST_F(ExtensionServiceTest, Reinstall) { 2521 InitializeEmptyExtensionService(); 2522 2523 // A simple extension that should install without error. 2524 base::FilePath path = data_dir().AppendASCII("good.crx"); 2525 InstallCRX(path, INSTALL_NEW); 2526 2527 ValidatePrefKeyCount(1); 2528 ValidateIntegerPref(good_crx, "state", Extension::ENABLED); 2529 ValidateIntegerPref(good_crx, "location", Manifest::INTERNAL); 2530 2531 // Reinstall the same version, it should overwrite the previous one. 2532 InstallCRX(path, INSTALL_UPDATED); 2533 2534 ValidatePrefKeyCount(1); 2535 ValidateIntegerPref(good_crx, "state", Extension::ENABLED); 2536 ValidateIntegerPref(good_crx, "location", Manifest::INTERNAL); 2537 } 2538 2539 // Test that we can determine if extensions came from the 2540 // Chrome web store. 2541 TEST_F(ExtensionServiceTest, FromWebStore) { 2542 InitializeEmptyExtensionService(); 2543 2544 // A simple extension that should install without error. 2545 base::FilePath path = data_dir().AppendASCII("good.crx"); 2546 // Not from web store. 2547 const Extension* extension = InstallCRX(path, INSTALL_NEW); 2548 std::string id = extension->id(); 2549 2550 ValidatePrefKeyCount(1); 2551 ASSERT_TRUE(ValidateBooleanPref(good_crx, "from_webstore", false)); 2552 ASSERT_FALSE(extension->from_webstore()); 2553 2554 // Test install from web store. 2555 InstallCRXFromWebStore(path, INSTALL_UPDATED); // From web store. 2556 2557 ValidatePrefKeyCount(1); 2558 ASSERT_TRUE(ValidateBooleanPref(good_crx, "from_webstore", true)); 2559 2560 // Reload so extension gets reinitialized with new value. 2561 service()->ReloadExtensionsForTest(); 2562 extension = service()->GetExtensionById(id, false); 2563 ASSERT_TRUE(extension->from_webstore()); 2564 2565 // Upgrade to version 2.0 2566 path = data_dir().AppendASCII("good2.crx"); 2567 UpdateExtension(good_crx, path, ENABLED); 2568 ValidatePrefKeyCount(1); 2569 ASSERT_TRUE(ValidateBooleanPref(good_crx, "from_webstore", true)); 2570 } 2571 2572 // Test upgrading a signed extension. 2573 TEST_F(ExtensionServiceTest, UpgradeSignedGood) { 2574 InitializeEmptyExtensionService(); 2575 2576 base::FilePath path = data_dir().AppendASCII("good.crx"); 2577 const Extension* extension = InstallCRX(path, INSTALL_NEW); 2578 std::string id = extension->id(); 2579 2580 ASSERT_EQ("1.0.0.0", extension->version()->GetString()); 2581 ASSERT_EQ(0u, GetErrors().size()); 2582 2583 // Upgrade to version 1.0.0.1. 2584 // Also test that the extension's old and new title are correctly retrieved. 2585 path = data_dir().AppendASCII("good2.crx"); 2586 InstallCRX(path, INSTALL_UPDATED, Extension::NO_FLAGS, "My extension 1"); 2587 extension = service()->GetExtensionById(id, false); 2588 2589 ASSERT_EQ("1.0.0.1", extension->version()->GetString()); 2590 ASSERT_EQ("My updated extension 1", extension->name()); 2591 ASSERT_EQ(0u, GetErrors().size()); 2592 } 2593 2594 // Test upgrading a signed extension with a bad signature. 2595 TEST_F(ExtensionServiceTest, UpgradeSignedBad) { 2596 InitializeEmptyExtensionService(); 2597 2598 base::FilePath path = data_dir().AppendASCII("good.crx"); 2599 InstallCRX(path, INSTALL_NEW); 2600 2601 // Try upgrading with a bad signature. This should fail during the unpack, 2602 // because the key will not match the signature. 2603 path = data_dir().AppendASCII("bad_signature.crx"); 2604 InstallCRX(path, INSTALL_FAILED); 2605 } 2606 2607 // Test a normal update via the UpdateExtension API 2608 TEST_F(ExtensionServiceTest, UpdateExtension) { 2609 InitializeEmptyExtensionService(); 2610 2611 base::FilePath path = data_dir().AppendASCII("good.crx"); 2612 2613 const Extension* good = InstallCRX(path, INSTALL_NEW); 2614 ASSERT_EQ("1.0.0.0", good->VersionString()); 2615 ASSERT_EQ(good_crx, good->id()); 2616 2617 path = data_dir().AppendASCII("good2.crx"); 2618 UpdateExtension(good_crx, path, ENABLED); 2619 ASSERT_EQ( 2620 "1.0.0.1", 2621 service()->GetExtensionById(good_crx, false)->version()->GetString()); 2622 } 2623 2624 // Extensions should not be updated during browser shutdown. 2625 TEST_F(ExtensionServiceTest, UpdateExtensionDuringShutdown) { 2626 InitializeEmptyExtensionService(); 2627 2628 // Install an extension. 2629 base::FilePath path = data_dir().AppendASCII("good.crx"); 2630 const Extension* good = InstallCRX(path, INSTALL_NEW); 2631 ASSERT_EQ(good_crx, good->id()); 2632 2633 // Simulate shutdown. 2634 service()->set_browser_terminating_for_test(true); 2635 2636 // Update should fail and extension should not be updated. 2637 path = data_dir().AppendASCII("good2.crx"); 2638 bool updated = service()->UpdateExtension(good_crx, path, true, NULL); 2639 ASSERT_FALSE(updated); 2640 ASSERT_EQ( 2641 "1.0.0.0", 2642 service()->GetExtensionById(good_crx, false)->version()->GetString()); 2643 } 2644 2645 // Test updating a not-already-installed extension - this should fail 2646 TEST_F(ExtensionServiceTest, UpdateNotInstalledExtension) { 2647 InitializeEmptyExtensionService(); 2648 2649 base::FilePath path = data_dir().AppendASCII("good.crx"); 2650 UpdateExtension(good_crx, path, UPDATED); 2651 base::RunLoop().RunUntilIdle(); 2652 2653 ASSERT_EQ(0u, registry()->enabled_extensions().size()); 2654 ASSERT_FALSE(installed_); 2655 ASSERT_EQ(0u, loaded_.size()); 2656 } 2657 2658 // Makes sure you can't downgrade an extension via UpdateExtension 2659 TEST_F(ExtensionServiceTest, UpdateWillNotDowngrade) { 2660 InitializeEmptyExtensionService(); 2661 2662 base::FilePath path = data_dir().AppendASCII("good2.crx"); 2663 2664 const Extension* good = InstallCRX(path, INSTALL_NEW); 2665 ASSERT_EQ("1.0.0.1", good->VersionString()); 2666 ASSERT_EQ(good_crx, good->id()); 2667 2668 // Change path from good2.crx -> good.crx 2669 path = data_dir().AppendASCII("good.crx"); 2670 UpdateExtension(good_crx, path, FAILED); 2671 ASSERT_EQ( 2672 "1.0.0.1", 2673 service()->GetExtensionById(good_crx, false)->version()->GetString()); 2674 } 2675 2676 // Make sure calling update with an identical version does nothing 2677 TEST_F(ExtensionServiceTest, UpdateToSameVersionIsNoop) { 2678 InitializeEmptyExtensionService(); 2679 2680 base::FilePath path = data_dir().AppendASCII("good.crx"); 2681 2682 const Extension* good = InstallCRX(path, INSTALL_NEW); 2683 ASSERT_EQ(good_crx, good->id()); 2684 UpdateExtension(good_crx, path, FAILED_SILENTLY); 2685 } 2686 2687 // Tests that updating an extension does not clobber old state. 2688 TEST_F(ExtensionServiceTest, UpdateExtensionPreservesState) { 2689 InitializeEmptyExtensionService(); 2690 2691 base::FilePath path = data_dir().AppendASCII("good.crx"); 2692 2693 const Extension* good = InstallCRX(path, INSTALL_NEW); 2694 ASSERT_EQ("1.0.0.0", good->VersionString()); 2695 ASSERT_EQ(good_crx, good->id()); 2696 2697 // Disable it and allow it to run in incognito. These settings should carry 2698 // over to the updated version. 2699 service()->DisableExtension(good->id(), Extension::DISABLE_USER_ACTION); 2700 extensions::util::SetIsIncognitoEnabled(good->id(), profile(), true); 2701 ExtensionPrefs::Get(profile()) 2702 ->SetDidExtensionEscalatePermissions(good, true); 2703 2704 path = data_dir().AppendASCII("good2.crx"); 2705 UpdateExtension(good_crx, path, INSTALLED); 2706 ASSERT_EQ(1u, registry()->disabled_extensions().size()); 2707 const Extension* good2 = service()->GetExtensionById(good_crx, true); 2708 ASSERT_EQ("1.0.0.1", good2->version()->GetString()); 2709 EXPECT_TRUE(extensions::util::IsIncognitoEnabled(good2->id(), profile())); 2710 EXPECT_TRUE(ExtensionPrefs::Get(profile()) 2711 ->DidExtensionEscalatePermissions(good2->id())); 2712 } 2713 2714 // Tests that updating preserves extension location. 2715 TEST_F(ExtensionServiceTest, UpdateExtensionPreservesLocation) { 2716 InitializeEmptyExtensionService(); 2717 2718 base::FilePath path = data_dir().AppendASCII("good.crx"); 2719 2720 const Extension* good = 2721 InstallCRXWithLocation(path, Manifest::EXTERNAL_PREF, INSTALL_NEW); 2722 2723 ASSERT_EQ("1.0.0.0", good->VersionString()); 2724 ASSERT_EQ(good_crx, good->id()); 2725 2726 path = data_dir().AppendASCII("good2.crx"); 2727 UpdateExtension(good_crx, path, ENABLED); 2728 const Extension* good2 = service()->GetExtensionById(good_crx, false); 2729 ASSERT_EQ("1.0.0.1", good2->version()->GetString()); 2730 EXPECT_EQ(good2->location(), Manifest::EXTERNAL_PREF); 2731 } 2732 2733 // Makes sure that LOAD extension types can downgrade. 2734 TEST_F(ExtensionServiceTest, LoadExtensionsCanDowngrade) { 2735 InitializeEmptyExtensionService(); 2736 2737 base::ScopedTempDir temp; 2738 ASSERT_TRUE(temp.CreateUniqueTempDir()); 2739 2740 // We'll write the extension manifest dynamically to a temporary path 2741 // to make it easier to change the version number. 2742 base::FilePath extension_path = temp.path(); 2743 base::FilePath manifest_path = 2744 extension_path.Append(extensions::kManifestFilename); 2745 ASSERT_FALSE(base::PathExists(manifest_path)); 2746 2747 // Start with version 2.0. 2748 base::DictionaryValue manifest; 2749 manifest.SetString("version", "2.0"); 2750 manifest.SetString("name", "LOAD Downgrade Test"); 2751 manifest.SetInteger("manifest_version", 2); 2752 2753 JSONFileValueSerializer serializer(manifest_path); 2754 ASSERT_TRUE(serializer.Serialize(manifest)); 2755 2756 extensions::UnpackedInstaller::Create(service())->Load(extension_path); 2757 base::RunLoop().RunUntilIdle(); 2758 2759 EXPECT_EQ(0u, GetErrors().size()); 2760 ASSERT_EQ(1u, loaded_.size()); 2761 EXPECT_EQ(Manifest::UNPACKED, loaded_[0]->location()); 2762 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 2763 EXPECT_EQ("2.0", loaded_[0]->VersionString()); 2764 2765 // Now set the version number to 1.0, reload the extensions and verify that 2766 // the downgrade was accepted. 2767 manifest.SetString("version", "1.0"); 2768 ASSERT_TRUE(serializer.Serialize(manifest)); 2769 2770 extensions::UnpackedInstaller::Create(service())->Load(extension_path); 2771 base::RunLoop().RunUntilIdle(); 2772 2773 EXPECT_EQ(0u, GetErrors().size()); 2774 ASSERT_EQ(1u, loaded_.size()); 2775 EXPECT_EQ(Manifest::UNPACKED, loaded_[0]->location()); 2776 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 2777 EXPECT_EQ("1.0", loaded_[0]->VersionString()); 2778 } 2779 2780 #if !defined(OS_POSIX) || defined(OS_MACOSX) 2781 // LOAD extensions with plugins require approval. 2782 // Only run this on platforms that support NPAPI plugins. 2783 TEST_F(ExtensionServiceTest, LoadExtensionsWithPlugins) { 2784 base::FilePath extension_with_plugin_path = good1_path(); 2785 base::FilePath extension_no_plugin_path = good2_path(); 2786 2787 InitPluginService(); 2788 InitializeEmptyExtensionService(); 2789 InitializeProcessManager(); 2790 service()->set_show_extensions_prompts(true); 2791 2792 // Start by canceling any install prompts. 2793 CommandLine::ForCurrentProcess()->AppendSwitchASCII( 2794 switches::kAppsGalleryInstallAutoConfirmForTests, 2795 "cancel"); 2796 2797 // The extension that has a plugin should not install. 2798 extensions::UnpackedInstaller::Create(service()) 2799 ->Load(extension_with_plugin_path); 2800 base::RunLoop().RunUntilIdle(); 2801 EXPECT_EQ(0u, GetErrors().size()); 2802 EXPECT_EQ(0u, loaded_.size()); 2803 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 2804 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 2805 2806 // But the extension with no plugin should since there's no prompt. 2807 ExtensionErrorReporter::GetInstance()->ClearErrors(); 2808 extensions::UnpackedInstaller::Create(service()) 2809 ->Load(extension_no_plugin_path); 2810 base::RunLoop().RunUntilIdle(); 2811 EXPECT_EQ(0u, GetErrors().size()); 2812 EXPECT_EQ(1u, loaded_.size()); 2813 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 2814 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 2815 EXPECT_TRUE(registry()->enabled_extensions().Contains(good2)); 2816 2817 // The plugin extension should install if we accept the dialog. 2818 CommandLine::ForCurrentProcess()->AppendSwitchASCII( 2819 switches::kAppsGalleryInstallAutoConfirmForTests, 2820 "accept"); 2821 2822 ExtensionErrorReporter::GetInstance()->ClearErrors(); 2823 extensions::UnpackedInstaller::Create(service()) 2824 ->Load(extension_with_plugin_path); 2825 base::RunLoop().RunUntilIdle(); 2826 EXPECT_EQ(0u, GetErrors().size()); 2827 EXPECT_EQ(2u, loaded_.size()); 2828 EXPECT_EQ(2u, registry()->enabled_extensions().size()); 2829 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 2830 EXPECT_TRUE(registry()->enabled_extensions().Contains(good1)); 2831 EXPECT_TRUE(registry()->enabled_extensions().Contains(good2)); 2832 2833 // Make sure the granted permissions have been setup. 2834 scoped_refptr<PermissionSet> permissions( 2835 ExtensionPrefs::Get(profile())->GetGrantedPermissions(good1)); 2836 EXPECT_FALSE(permissions->IsEmpty()); 2837 EXPECT_TRUE(permissions->HasEffectiveFullAccess()); 2838 EXPECT_FALSE(permissions->apis().empty()); 2839 EXPECT_TRUE(permissions->HasAPIPermission(APIPermission::kPlugin)); 2840 2841 // We should be able to reload the extension without getting another prompt. 2842 loaded_.clear(); 2843 CommandLine::ForCurrentProcess()->AppendSwitchASCII( 2844 switches::kAppsGalleryInstallAutoConfirmForTests, 2845 "cancel"); 2846 2847 service()->ReloadExtension(good1); 2848 base::RunLoop().RunUntilIdle(); 2849 EXPECT_EQ(1u, loaded_.size()); 2850 EXPECT_EQ(2u, registry()->enabled_extensions().size()); 2851 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 2852 } 2853 #endif // !defined(OS_POSIX) || defined(OS_MACOSX) 2854 2855 namespace { 2856 2857 bool IsExtension(const Extension* extension) { 2858 return extension->GetType() == Manifest::TYPE_EXTENSION; 2859 } 2860 2861 #if defined(ENABLE_BLACKLIST_TESTS) 2862 std::set<std::string> StringSet(const std::string& s) { 2863 std::set<std::string> set; 2864 set.insert(s); 2865 return set; 2866 } 2867 std::set<std::string> StringSet(const std::string& s1, const std::string& s2) { 2868 std::set<std::string> set = StringSet(s1); 2869 set.insert(s2); 2870 return set; 2871 } 2872 #endif // defined(ENABLE_BLACKLIST_TESTS) 2873 2874 } // namespace 2875 2876 // Test adding a pending extension. 2877 TEST_F(ExtensionServiceTest, AddPendingExtensionFromSync) { 2878 InitializeEmptyExtensionService(); 2879 2880 const std::string kFakeId(all_zero); 2881 const GURL kFakeUpdateURL("http:://fake.update/url"); 2882 const bool kFakeInstallSilently(true); 2883 const bool kFakeRemoteInstall(false); 2884 2885 EXPECT_TRUE( 2886 service()->pending_extension_manager()->AddFromSync(kFakeId, 2887 kFakeUpdateURL, 2888 &IsExtension, 2889 kFakeInstallSilently, 2890 kFakeRemoteInstall)); 2891 2892 const extensions::PendingExtensionInfo* pending_extension_info; 2893 ASSERT_TRUE((pending_extension_info = 2894 service()->pending_extension_manager()->GetById(kFakeId))); 2895 EXPECT_EQ(kFakeUpdateURL, pending_extension_info->update_url()); 2896 EXPECT_EQ(&IsExtension, pending_extension_info->should_allow_install_); 2897 EXPECT_EQ(kFakeInstallSilently, pending_extension_info->install_silently()); 2898 // Use 2899 // EXPECT_TRUE(kFakeRemoteInstall == pending_extension_info->remote_install()) 2900 // instead of 2901 // EXPECT_EQ(kFakeRemoteInstall, pending_extension_info->remote_install()) 2902 // as gcc 4.7 issues the following warning on EXPECT_EQ(false, x), which is 2903 // turned into an error with -Werror=conversion-null: 2904 // converting 'false' to pointer type for argument 1 of 2905 // 'char testing::internal::IsNullLiteralHelper(testing::internal::Secret*)' 2906 // https://code.google.com/p/googletest/issues/detail?id=458 2907 EXPECT_TRUE(kFakeRemoteInstall == pending_extension_info->remote_install()); 2908 } 2909 2910 namespace { 2911 const char kGoodId[] = "ldnnhddmnhbkjipkidpdiheffobcpfmf"; 2912 const char kGoodUpdateURL[] = "http://good.update/url"; 2913 const bool kGoodIsFromSync = true; 2914 const bool kGoodInstallSilently = true; 2915 const bool kGoodRemoteInstall = false; 2916 } // namespace 2917 2918 // Test updating a pending extension. 2919 TEST_F(ExtensionServiceTest, UpdatePendingExtension) { 2920 InitializeEmptyExtensionService(); 2921 EXPECT_TRUE( 2922 service()->pending_extension_manager()->AddFromSync(kGoodId, 2923 GURL(kGoodUpdateURL), 2924 &IsExtension, 2925 kGoodInstallSilently, 2926 kGoodRemoteInstall)); 2927 EXPECT_TRUE(service()->pending_extension_manager()->IsIdPending(kGoodId)); 2928 2929 base::FilePath path = data_dir().AppendASCII("good.crx"); 2930 UpdateExtension(kGoodId, path, ENABLED); 2931 2932 EXPECT_FALSE(service()->pending_extension_manager()->IsIdPending(kGoodId)); 2933 2934 const Extension* extension = service()->GetExtensionById(kGoodId, true); 2935 ASSERT_TRUE(extension); 2936 } 2937 2938 namespace { 2939 2940 bool IsTheme(const Extension* extension) { 2941 return extension->is_theme(); 2942 } 2943 2944 } // namespace 2945 2946 // Test updating a pending theme. 2947 // Disabled due to ASAN failure. http://crbug.com/108320 2948 TEST_F(ExtensionServiceTest, DISABLED_UpdatePendingTheme) { 2949 InitializeEmptyExtensionService(); 2950 EXPECT_TRUE(service()->pending_extension_manager()->AddFromSync( 2951 theme_crx, GURL(), &IsTheme, false, false)); 2952 EXPECT_TRUE(service()->pending_extension_manager()->IsIdPending(theme_crx)); 2953 2954 base::FilePath path = data_dir().AppendASCII("theme.crx"); 2955 UpdateExtension(theme_crx, path, ENABLED); 2956 2957 EXPECT_FALSE(service()->pending_extension_manager()->IsIdPending(theme_crx)); 2958 2959 const Extension* extension = service()->GetExtensionById(theme_crx, true); 2960 ASSERT_TRUE(extension); 2961 2962 EXPECT_FALSE( 2963 ExtensionPrefs::Get(profile())->IsExtensionDisabled(extension->id())); 2964 EXPECT_TRUE(service()->IsExtensionEnabled(theme_crx)); 2965 } 2966 2967 #if defined(OS_CHROMEOS) 2968 // Always fails on ChromeOS: http://crbug.com/79737 2969 #define MAYBE_UpdatePendingExternalCrx DISABLED_UpdatePendingExternalCrx 2970 #else 2971 #define MAYBE_UpdatePendingExternalCrx UpdatePendingExternalCrx 2972 #endif 2973 // Test updating a pending CRX as if the source is an external extension 2974 // with an update URL. In this case we don't know if the CRX is a theme 2975 // or not. 2976 TEST_F(ExtensionServiceTest, MAYBE_UpdatePendingExternalCrx) { 2977 InitializeEmptyExtensionService(); 2978 EXPECT_TRUE(service()->pending_extension_manager()->AddFromExternalUpdateUrl( 2979 theme_crx, 2980 std::string(), 2981 GURL(), 2982 Manifest::EXTERNAL_PREF_DOWNLOAD, 2983 Extension::NO_FLAGS, 2984 false)); 2985 2986 EXPECT_TRUE(service()->pending_extension_manager()->IsIdPending(theme_crx)); 2987 2988 base::FilePath path = data_dir().AppendASCII("theme.crx"); 2989 UpdateExtension(theme_crx, path, ENABLED); 2990 2991 EXPECT_FALSE(service()->pending_extension_manager()->IsIdPending(theme_crx)); 2992 2993 const Extension* extension = service()->GetExtensionById(theme_crx, true); 2994 ASSERT_TRUE(extension); 2995 2996 EXPECT_FALSE( 2997 ExtensionPrefs::Get(profile())->IsExtensionDisabled(extension->id())); 2998 EXPECT_TRUE(service()->IsExtensionEnabled(extension->id())); 2999 EXPECT_FALSE( 3000 extensions::util::IsIncognitoEnabled(extension->id(), profile())); 3001 } 3002 3003 // Test updating a pending CRX as if the source is an external extension 3004 // with an update URL. The external update should overwrite a sync update, 3005 // but a sync update should not overwrite a non-sync update. 3006 TEST_F(ExtensionServiceTest, UpdatePendingExternalCrxWinsOverSync) { 3007 InitializeEmptyExtensionService(); 3008 3009 // Add a crx to be installed from the update mechanism. 3010 EXPECT_TRUE( 3011 service()->pending_extension_manager()->AddFromSync(kGoodId, 3012 GURL(kGoodUpdateURL), 3013 &IsExtension, 3014 kGoodInstallSilently, 3015 kGoodRemoteInstall)); 3016 3017 // Check that there is a pending crx, with is_from_sync set to true. 3018 const extensions::PendingExtensionInfo* pending_extension_info; 3019 ASSERT_TRUE((pending_extension_info = 3020 service()->pending_extension_manager()->GetById(kGoodId))); 3021 EXPECT_TRUE(pending_extension_info->is_from_sync()); 3022 3023 // Add a crx to be updated, with the same ID, from a non-sync source. 3024 EXPECT_TRUE(service()->pending_extension_manager()->AddFromExternalUpdateUrl( 3025 kGoodId, 3026 std::string(), 3027 GURL(kGoodUpdateURL), 3028 Manifest::EXTERNAL_PREF_DOWNLOAD, 3029 Extension::NO_FLAGS, 3030 false)); 3031 3032 // Check that there is a pending crx, with is_from_sync set to false. 3033 ASSERT_TRUE((pending_extension_info = 3034 service()->pending_extension_manager()->GetById(kGoodId))); 3035 EXPECT_FALSE(pending_extension_info->is_from_sync()); 3036 EXPECT_EQ(Manifest::EXTERNAL_PREF_DOWNLOAD, 3037 pending_extension_info->install_source()); 3038 3039 // Add a crx to be installed from the update mechanism. 3040 EXPECT_FALSE( 3041 service()->pending_extension_manager()->AddFromSync(kGoodId, 3042 GURL(kGoodUpdateURL), 3043 &IsExtension, 3044 kGoodInstallSilently, 3045 kGoodRemoteInstall)); 3046 3047 // Check that the external, non-sync update was not overridden. 3048 ASSERT_TRUE((pending_extension_info = 3049 service()->pending_extension_manager()->GetById(kGoodId))); 3050 EXPECT_FALSE(pending_extension_info->is_from_sync()); 3051 EXPECT_EQ(Manifest::EXTERNAL_PREF_DOWNLOAD, 3052 pending_extension_info->install_source()); 3053 } 3054 3055 // Updating a theme should fail if the updater is explicitly told that 3056 // the CRX is not a theme. 3057 TEST_F(ExtensionServiceTest, UpdatePendingCrxThemeMismatch) { 3058 InitializeEmptyExtensionService(); 3059 EXPECT_TRUE(service()->pending_extension_manager()->AddFromSync( 3060 theme_crx, GURL(), &IsExtension, true, false)); 3061 3062 EXPECT_TRUE(service()->pending_extension_manager()->IsIdPending(theme_crx)); 3063 3064 base::FilePath path = data_dir().AppendASCII("theme.crx"); 3065 UpdateExtension(theme_crx, path, FAILED_SILENTLY); 3066 3067 EXPECT_FALSE(service()->pending_extension_manager()->IsIdPending(theme_crx)); 3068 3069 const Extension* extension = service()->GetExtensionById(theme_crx, true); 3070 ASSERT_FALSE(extension); 3071 } 3072 3073 // TODO(akalin): Test updating a pending extension non-silently once 3074 // we can mock out ExtensionInstallUI and inject our version into 3075 // UpdateExtension(). 3076 3077 // Test updating a pending extension which fails the should-install test. 3078 TEST_F(ExtensionServiceTest, UpdatePendingExtensionFailedShouldInstallTest) { 3079 InitializeEmptyExtensionService(); 3080 // Add pending extension with a flipped is_theme. 3081 EXPECT_TRUE( 3082 service()->pending_extension_manager()->AddFromSync(kGoodId, 3083 GURL(kGoodUpdateURL), 3084 &IsTheme, 3085 kGoodInstallSilently, 3086 kGoodRemoteInstall)); 3087 EXPECT_TRUE(service()->pending_extension_manager()->IsIdPending(kGoodId)); 3088 3089 base::FilePath path = data_dir().AppendASCII("good.crx"); 3090 UpdateExtension(kGoodId, path, UPDATED); 3091 3092 // TODO(akalin): Figure out how to check that the extensions 3093 // directory is cleaned up properly in OnExtensionInstalled(). 3094 3095 EXPECT_FALSE(service()->pending_extension_manager()->IsIdPending(kGoodId)); 3096 } 3097 3098 // TODO(akalin): Figure out how to test that installs of pending 3099 // unsyncable extensions are blocked. 3100 3101 // Test updating a pending extension for one that is not pending. 3102 TEST_F(ExtensionServiceTest, UpdatePendingExtensionNotPending) { 3103 InitializeEmptyExtensionService(); 3104 3105 base::FilePath path = data_dir().AppendASCII("good.crx"); 3106 UpdateExtension(kGoodId, path, UPDATED); 3107 3108 EXPECT_FALSE(service()->pending_extension_manager()->IsIdPending(kGoodId)); 3109 } 3110 3111 // Test updating a pending extension for one that is already 3112 // installed. 3113 TEST_F(ExtensionServiceTest, UpdatePendingExtensionAlreadyInstalled) { 3114 InitializeEmptyExtensionService(); 3115 3116 base::FilePath path = data_dir().AppendASCII("good.crx"); 3117 const Extension* good = InstallCRX(path, INSTALL_NEW); 3118 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 3119 3120 EXPECT_FALSE(good->is_theme()); 3121 3122 // Use AddExtensionImpl() as AddFrom*() would balk. 3123 service()->pending_extension_manager()->AddExtensionImpl( 3124 good->id(), 3125 std::string(), 3126 extensions::ManifestURL::GetUpdateURL(good), 3127 Version(), 3128 &IsExtension, 3129 kGoodIsFromSync, 3130 kGoodInstallSilently, 3131 Manifest::INTERNAL, 3132 Extension::NO_FLAGS, 3133 false, 3134 kGoodRemoteInstall); 3135 UpdateExtension(good->id(), path, ENABLED); 3136 3137 EXPECT_FALSE(service()->pending_extension_manager()->IsIdPending(kGoodId)); 3138 } 3139 3140 #if defined(ENABLE_BLACKLIST_TESTS) 3141 // Tests blacklisting then unblacklisting extensions after the service has been 3142 // initialized. 3143 TEST_F(ExtensionServiceTest, SetUnsetBlacklistInPrefs) { 3144 extensions::TestBlacklist test_blacklist; 3145 // A profile with 3 extensions installed: good0, good1, and good2. 3146 InitializeGoodInstalledExtensionService(); 3147 test_blacklist.Attach(service()->blacklist_); 3148 service()->Init(); 3149 3150 const extensions::ExtensionSet& enabled_extensions = 3151 registry()->enabled_extensions(); 3152 const extensions::ExtensionSet& blacklisted_extensions = 3153 registry()->blacklisted_extensions(); 3154 3155 EXPECT_TRUE(enabled_extensions.Contains(good0) && 3156 !blacklisted_extensions.Contains(good0)); 3157 EXPECT_TRUE(enabled_extensions.Contains(good1) && 3158 !blacklisted_extensions.Contains(good1)); 3159 EXPECT_TRUE(enabled_extensions.Contains(good2) && 3160 !blacklisted_extensions.Contains(good2)); 3161 3162 EXPECT_FALSE(IsPrefExist(good0, "blacklist")); 3163 EXPECT_FALSE(IsPrefExist(good1, "blacklist")); 3164 EXPECT_FALSE(IsPrefExist(good2, "blacklist")); 3165 EXPECT_FALSE(IsPrefExist("invalid_id", "blacklist")); 3166 3167 // Blacklist good0 and good1 (and an invalid extension ID). 3168 test_blacklist.SetBlacklistState( 3169 good0, extensions::BLACKLISTED_MALWARE, true); 3170 test_blacklist.SetBlacklistState( 3171 good1, extensions::BLACKLISTED_MALWARE, true); 3172 test_blacklist.SetBlacklistState( 3173 "invalid_id", extensions::BLACKLISTED_MALWARE, true); 3174 base::RunLoop().RunUntilIdle(); 3175 3176 EXPECT_TRUE(!enabled_extensions.Contains(good0) && 3177 blacklisted_extensions.Contains(good0)); 3178 EXPECT_TRUE(!enabled_extensions.Contains(good1) && 3179 blacklisted_extensions.Contains(good1)); 3180 EXPECT_TRUE(enabled_extensions.Contains(good2) && 3181 !blacklisted_extensions.Contains(good2)); 3182 3183 EXPECT_TRUE(ValidateBooleanPref(good0, "blacklist", true)); 3184 EXPECT_TRUE(ValidateBooleanPref(good1, "blacklist", true)); 3185 EXPECT_FALSE(IsPrefExist(good2, "blacklist")); 3186 EXPECT_FALSE(IsPrefExist("invalid_id", "blacklist")); 3187 3188 // Un-blacklist good1 and blacklist good2. 3189 test_blacklist.Clear(false); 3190 test_blacklist.SetBlacklistState( 3191 good0, extensions::BLACKLISTED_MALWARE, true); 3192 test_blacklist.SetBlacklistState( 3193 good2, extensions::BLACKLISTED_MALWARE, true); 3194 test_blacklist.SetBlacklistState( 3195 "invalid_id", extensions::BLACKLISTED_MALWARE, true); 3196 base::RunLoop().RunUntilIdle(); 3197 3198 EXPECT_TRUE(!enabled_extensions.Contains(good0) && 3199 blacklisted_extensions.Contains(good0)); 3200 EXPECT_TRUE(enabled_extensions.Contains(good1) && 3201 !blacklisted_extensions.Contains(good1)); 3202 EXPECT_TRUE(!enabled_extensions.Contains(good2) && 3203 blacklisted_extensions.Contains(good2)); 3204 3205 EXPECT_TRUE(ValidateBooleanPref(good0, "blacklist", true)); 3206 EXPECT_FALSE(IsPrefExist(good1, "blacklist")); 3207 EXPECT_TRUE(ValidateBooleanPref(good2, "blacklist", true)); 3208 EXPECT_FALSE(IsPrefExist("invalid_id", "blacklist")); 3209 } 3210 #endif // defined(ENABLE_BLACKLIST_TESTS) 3211 3212 #if defined(ENABLE_BLACKLIST_TESTS) 3213 // Tests trying to install a blacklisted extension. 3214 TEST_F(ExtensionServiceTest, BlacklistedExtensionWillNotInstall) { 3215 scoped_refptr<FakeSafeBrowsingDatabaseManager> blacklist_db( 3216 new FakeSafeBrowsingDatabaseManager(true)); 3217 Blacklist::ScopedDatabaseManagerForTest scoped_blacklist_db(blacklist_db); 3218 3219 InitializeEmptyExtensionService(); 3220 service()->Init(); 3221 3222 // After blacklisting good_crx, we cannot install it. 3223 blacklist_db->SetUnsafe(good_crx).NotifyUpdate(); 3224 base::RunLoop().RunUntilIdle(); 3225 3226 base::FilePath path = data_dir().AppendASCII("good.crx"); 3227 // HACK: specify WAS_INSTALLED_BY_DEFAULT so that test machinery doesn't 3228 // decide to install this silently. Somebody should fix these tests, all 3229 // 6,000 lines of them. Hah! 3230 InstallCRX(path, INSTALL_FAILED, Extension::WAS_INSTALLED_BY_DEFAULT); 3231 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3232 } 3233 #endif // defined(ENABLE_BLACKLIST_TESTS) 3234 3235 #if defined(ENABLE_BLACKLIST_TESTS) 3236 // Unload blacklisted extension on policy change. 3237 TEST_F(ExtensionServiceTest, UnloadBlacklistedExtensionPolicy) { 3238 extensions::TestBlacklist test_blacklist; 3239 3240 // A profile with no extensions installed. 3241 InitializeEmptyExtensionService(); 3242 test_blacklist.Attach(service()->blacklist_); 3243 3244 base::FilePath path = data_dir().AppendASCII("good.crx"); 3245 3246 const Extension* good = InstallCRX(path, INSTALL_NEW); 3247 EXPECT_EQ(good_crx, good->id()); 3248 UpdateExtension(good_crx, path, FAILED_SILENTLY); 3249 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3250 3251 base::ListValue whitelist; 3252 PrefService* prefs = ExtensionPrefs::Get(profile())->pref_service(); 3253 whitelist.Append(new base::StringValue(good_crx)); 3254 prefs->Set(extensions::pref_names::kInstallAllowList, whitelist); 3255 3256 test_blacklist.SetBlacklistState( 3257 good_crx, extensions::BLACKLISTED_MALWARE, true); 3258 base::RunLoop().RunUntilIdle(); 3259 3260 // The good_crx is blacklisted and the whitelist doesn't negate it. 3261 ASSERT_TRUE(ValidateBooleanPref(good_crx, "blacklist", true)); 3262 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3263 } 3264 #endif // defined(ENABLE_BLACKLIST_TESTS) 3265 3266 #if defined(ENABLE_BLACKLIST_TESTS) 3267 // Tests that a blacklisted extension is eventually unloaded on startup, if it 3268 // wasn't already. 3269 TEST_F(ExtensionServiceTest, WillNotLoadBlacklistedExtensionsFromDirectory) { 3270 extensions::TestBlacklist test_blacklist; 3271 3272 // A profile with 3 extensions installed: good0, good1, and good2. 3273 InitializeGoodInstalledExtensionService(); 3274 test_blacklist.Attach(service()->blacklist_); 3275 3276 // Blacklist good1 before the service initializes. 3277 test_blacklist.SetBlacklistState( 3278 good1, extensions::BLACKLISTED_MALWARE, false); 3279 3280 // Load extensions. 3281 service()->Init(); 3282 ASSERT_EQ(3u, loaded_.size()); // hasn't had time to blacklist yet 3283 3284 base::RunLoop().RunUntilIdle(); 3285 3286 ASSERT_EQ(1u, registry()->blacklisted_extensions().size()); 3287 ASSERT_EQ(2u, registry()->enabled_extensions().size()); 3288 3289 ASSERT_TRUE(registry()->enabled_extensions().Contains(good0)); 3290 ASSERT_TRUE(registry()->blacklisted_extensions().Contains(good1)); 3291 ASSERT_TRUE(registry()->enabled_extensions().Contains(good2)); 3292 } 3293 #endif // defined(ENABLE_BLACKLIST_TESTS) 3294 3295 #if defined(ENABLE_BLACKLIST_TESTS) 3296 // Tests extensions blacklisted in prefs on startup; one still blacklisted by 3297 // safe browsing, the other not. The not-blacklisted one should recover. 3298 TEST_F(ExtensionServiceTest, BlacklistedInPrefsFromStartup) { 3299 extensions::TestBlacklist test_blacklist; 3300 3301 InitializeGoodInstalledExtensionService(); 3302 test_blacklist.Attach(service()->blacklist_); 3303 ExtensionPrefs::Get(profile())->SetExtensionBlacklisted(good0, true); 3304 ExtensionPrefs::Get(profile())->SetExtensionBlacklisted(good1, true); 3305 3306 test_blacklist.SetBlacklistState( 3307 good1, extensions::BLACKLISTED_MALWARE, false); 3308 3309 // Extension service hasn't loaded yet, but IsExtensionEnabled reads out of 3310 // prefs. Ensure it takes into account the blacklist state (crbug.com/373842). 3311 EXPECT_FALSE(service()->IsExtensionEnabled(good0)); 3312 EXPECT_FALSE(service()->IsExtensionEnabled(good1)); 3313 EXPECT_TRUE(service()->IsExtensionEnabled(good2)); 3314 3315 service()->Init(); 3316 3317 EXPECT_EQ(2u, registry()->blacklisted_extensions().size()); 3318 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3319 3320 EXPECT_TRUE(registry()->blacklisted_extensions().Contains(good0)); 3321 EXPECT_TRUE(registry()->blacklisted_extensions().Contains(good1)); 3322 EXPECT_TRUE(registry()->enabled_extensions().Contains(good2)); 3323 3324 // Give time for the blacklist to update. 3325 base::RunLoop().RunUntilIdle(); 3326 3327 EXPECT_EQ(1u, registry()->blacklisted_extensions().size()); 3328 EXPECT_EQ(2u, registry()->enabled_extensions().size()); 3329 3330 EXPECT_TRUE(registry()->enabled_extensions().Contains(good0)); 3331 EXPECT_TRUE(registry()->blacklisted_extensions().Contains(good1)); 3332 EXPECT_TRUE(registry()->enabled_extensions().Contains(good2)); 3333 } 3334 #endif // defined(ENABLE_BLACKLIST_TESTS) 3335 3336 #if defined(ENABLE_BLACKLIST_TESTS) 3337 // Extension is added to blacklist with BLACKLISTED_POTENTIALLY_UNWANTED state 3338 // after it is installed. It is then successfully re-enabled by the user. 3339 TEST_F(ExtensionServiceTest, GreylistedExtensionDisabled) { 3340 extensions::TestBlacklist test_blacklist; 3341 // A profile with 3 extensions installed: good0, good1, and good2. 3342 InitializeGoodInstalledExtensionService(); 3343 test_blacklist.Attach(service()->blacklist_); 3344 service()->Init(); 3345 3346 const extensions::ExtensionSet& enabled_extensions = 3347 registry()->enabled_extensions(); 3348 const extensions::ExtensionSet& disabled_extensions = 3349 registry()->disabled_extensions(); 3350 3351 EXPECT_TRUE(enabled_extensions.Contains(good0)); 3352 EXPECT_TRUE(enabled_extensions.Contains(good1)); 3353 EXPECT_TRUE(enabled_extensions.Contains(good2)); 3354 3355 // Blacklist good0 and good1 (and an invalid extension ID). 3356 test_blacklist.SetBlacklistState( 3357 good0, extensions::BLACKLISTED_CWS_POLICY_VIOLATION, true); 3358 test_blacklist.SetBlacklistState( 3359 good1, extensions::BLACKLISTED_POTENTIALLY_UNWANTED, true); 3360 test_blacklist.SetBlacklistState( 3361 "invalid_id", extensions::BLACKLISTED_MALWARE, true); 3362 base::RunLoop().RunUntilIdle(); 3363 3364 EXPECT_FALSE(enabled_extensions.Contains(good0)); 3365 EXPECT_TRUE(disabled_extensions.Contains(good0)); 3366 EXPECT_FALSE(enabled_extensions.Contains(good1)); 3367 EXPECT_TRUE(disabled_extensions.Contains(good1)); 3368 EXPECT_TRUE(enabled_extensions.Contains(good2)); 3369 EXPECT_FALSE(disabled_extensions.Contains(good2)); 3370 3371 ValidateIntegerPref( 3372 good0, "blacklist_state", extensions::BLACKLISTED_CWS_POLICY_VIOLATION); 3373 ValidateIntegerPref( 3374 good1, "blacklist_state", extensions::BLACKLISTED_POTENTIALLY_UNWANTED); 3375 3376 // Now user enables good0. 3377 service()->EnableExtension(good0); 3378 3379 EXPECT_TRUE(enabled_extensions.Contains(good0)); 3380 EXPECT_FALSE(disabled_extensions.Contains(good0)); 3381 EXPECT_FALSE(enabled_extensions.Contains(good1)); 3382 EXPECT_TRUE(disabled_extensions.Contains(good1)); 3383 3384 // Remove extensions from blacklist. 3385 test_blacklist.SetBlacklistState( 3386 good0, extensions::NOT_BLACKLISTED, true); 3387 test_blacklist.SetBlacklistState( 3388 good1, extensions::NOT_BLACKLISTED, true); 3389 base::RunLoop().RunUntilIdle(); 3390 3391 // All extensions are enabled. 3392 EXPECT_TRUE(enabled_extensions.Contains(good0)); 3393 EXPECT_FALSE(disabled_extensions.Contains(good0)); 3394 EXPECT_TRUE(enabled_extensions.Contains(good1)); 3395 EXPECT_FALSE(disabled_extensions.Contains(good1)); 3396 EXPECT_TRUE(enabled_extensions.Contains(good2)); 3397 EXPECT_FALSE(disabled_extensions.Contains(good2)); 3398 } 3399 #endif // defined(ENABLE_BLACKLIST_TESTS) 3400 3401 #if defined(ENABLE_BLACKLIST_TESTS) 3402 // When extension is removed from greylist, do not re-enable it if it is 3403 // disabled by user. 3404 TEST_F(ExtensionServiceTest, GreylistDontEnableManuallyDisabled) { 3405 extensions::TestBlacklist test_blacklist; 3406 // A profile with 3 extensions installed: good0, good1, and good2. 3407 InitializeGoodInstalledExtensionService(); 3408 test_blacklist.Attach(service()->blacklist_); 3409 service()->Init(); 3410 3411 const extensions::ExtensionSet& enabled_extensions = 3412 registry()->enabled_extensions(); 3413 const extensions::ExtensionSet& disabled_extensions = 3414 registry()->disabled_extensions(); 3415 3416 // Manually disable. 3417 service()->DisableExtension(good0, 3418 extensions::Extension::DISABLE_USER_ACTION); 3419 3420 test_blacklist.SetBlacklistState( 3421 good0, extensions::BLACKLISTED_CWS_POLICY_VIOLATION, true); 3422 test_blacklist.SetBlacklistState( 3423 good1, extensions::BLACKLISTED_POTENTIALLY_UNWANTED, true); 3424 test_blacklist.SetBlacklistState( 3425 good2, extensions::BLACKLISTED_SECURITY_VULNERABILITY, true); 3426 base::RunLoop().RunUntilIdle(); 3427 3428 // All extensions disabled. 3429 EXPECT_FALSE(enabled_extensions.Contains(good0)); 3430 EXPECT_TRUE(disabled_extensions.Contains(good0)); 3431 EXPECT_FALSE(enabled_extensions.Contains(good1)); 3432 EXPECT_TRUE(disabled_extensions.Contains(good1)); 3433 EXPECT_FALSE(enabled_extensions.Contains(good2)); 3434 EXPECT_TRUE(disabled_extensions.Contains(good2)); 3435 3436 // Greylisted extension can be enabled. 3437 service()->EnableExtension(good1); 3438 EXPECT_TRUE(enabled_extensions.Contains(good1)); 3439 EXPECT_FALSE(disabled_extensions.Contains(good1)); 3440 3441 // good1 is now manually disabled. 3442 service()->DisableExtension(good1, 3443 extensions::Extension::DISABLE_USER_ACTION); 3444 EXPECT_FALSE(enabled_extensions.Contains(good1)); 3445 EXPECT_TRUE(disabled_extensions.Contains(good1)); 3446 3447 // Remove extensions from blacklist. 3448 test_blacklist.SetBlacklistState( 3449 good0, extensions::NOT_BLACKLISTED, true); 3450 test_blacklist.SetBlacklistState( 3451 good1, extensions::NOT_BLACKLISTED, true); 3452 test_blacklist.SetBlacklistState( 3453 good2, extensions::NOT_BLACKLISTED, true); 3454 base::RunLoop().RunUntilIdle(); 3455 3456 // good0 and good1 remain disabled. 3457 EXPECT_FALSE(enabled_extensions.Contains(good0)); 3458 EXPECT_TRUE(disabled_extensions.Contains(good0)); 3459 EXPECT_FALSE(enabled_extensions.Contains(good1)); 3460 EXPECT_TRUE(disabled_extensions.Contains(good1)); 3461 EXPECT_TRUE(enabled_extensions.Contains(good2)); 3462 EXPECT_FALSE(disabled_extensions.Contains(good2)); 3463 } 3464 #endif // defined(ENABLE_BLACKLIST_TESTS) 3465 3466 #if defined(ENABLE_BLACKLIST_TESTS) 3467 // Blacklisted extension with unknown state are not enabled/disabled. 3468 TEST_F(ExtensionServiceTest, GreylistUnknownDontChange) { 3469 extensions::TestBlacklist test_blacklist; 3470 // A profile with 3 extensions installed: good0, good1, and good2. 3471 InitializeGoodInstalledExtensionService(); 3472 test_blacklist.Attach(service()->blacklist_); 3473 service()->Init(); 3474 3475 const extensions::ExtensionSet& enabled_extensions = 3476 registry()->enabled_extensions(); 3477 const extensions::ExtensionSet& disabled_extensions = 3478 registry()->disabled_extensions(); 3479 3480 test_blacklist.SetBlacklistState( 3481 good0, extensions::BLACKLISTED_CWS_POLICY_VIOLATION, true); 3482 test_blacklist.SetBlacklistState( 3483 good1, extensions::BLACKLISTED_POTENTIALLY_UNWANTED, true); 3484 base::RunLoop().RunUntilIdle(); 3485 3486 EXPECT_FALSE(enabled_extensions.Contains(good0)); 3487 EXPECT_TRUE(disabled_extensions.Contains(good0)); 3488 EXPECT_FALSE(enabled_extensions.Contains(good1)); 3489 EXPECT_TRUE(disabled_extensions.Contains(good1)); 3490 EXPECT_TRUE(enabled_extensions.Contains(good2)); 3491 EXPECT_FALSE(disabled_extensions.Contains(good2)); 3492 3493 test_blacklist.SetBlacklistState( 3494 good0, extensions::NOT_BLACKLISTED, true); 3495 test_blacklist.SetBlacklistState( 3496 good1, extensions::BLACKLISTED_UNKNOWN, true); 3497 test_blacklist.SetBlacklistState( 3498 good2, extensions::BLACKLISTED_UNKNOWN, true); 3499 base::RunLoop().RunUntilIdle(); 3500 3501 // good0 re-enabled, other remain as they were. 3502 EXPECT_TRUE(enabled_extensions.Contains(good0)); 3503 EXPECT_FALSE(disabled_extensions.Contains(good0)); 3504 EXPECT_FALSE(enabled_extensions.Contains(good1)); 3505 EXPECT_TRUE(disabled_extensions.Contains(good1)); 3506 EXPECT_TRUE(enabled_extensions.Contains(good2)); 3507 EXPECT_FALSE(disabled_extensions.Contains(good2)); 3508 } 3509 3510 // Tests that blacklisted extensions cannot be reloaded, both those loaded 3511 // before and after extension service startup. 3512 TEST_F(ExtensionServiceTest, ReloadBlacklistedExtension) { 3513 extensions::TestBlacklist test_blacklist; 3514 3515 InitializeGoodInstalledExtensionService(); 3516 test_blacklist.Attach(service()->blacklist_); 3517 3518 test_blacklist.SetBlacklistState( 3519 good1, extensions::BLACKLISTED_MALWARE, false); 3520 service()->Init(); 3521 test_blacklist.SetBlacklistState( 3522 good2, extensions::BLACKLISTED_MALWARE, false); 3523 base::RunLoop().RunUntilIdle(); 3524 3525 EXPECT_EQ(StringSet(good0), registry()->enabled_extensions().GetIDs()); 3526 EXPECT_EQ(StringSet(good1, good2), 3527 registry()->blacklisted_extensions().GetIDs()); 3528 3529 service()->ReloadExtension(good1); 3530 service()->ReloadExtension(good2); 3531 base::RunLoop().RunUntilIdle(); 3532 3533 EXPECT_EQ(StringSet(good0), registry()->enabled_extensions().GetIDs()); 3534 EXPECT_EQ(StringSet(good1, good2), 3535 registry()->blacklisted_extensions().GetIDs()); 3536 } 3537 3538 #endif // defined(ENABLE_BLACKLIST_TESTS) 3539 3540 // Will not install extension blacklisted by policy. 3541 TEST_F(ExtensionServiceTest, BlacklistedByPolicyWillNotInstall) { 3542 InitializeEmptyExtensionService(); 3543 3544 // Blacklist everything. 3545 { 3546 ListPrefUpdate update(profile()->GetPrefs(), 3547 extensions::pref_names::kInstallDenyList); 3548 base::ListValue* blacklist = update.Get(); 3549 blacklist->Append(new base::StringValue("*")); 3550 } 3551 3552 // Blacklist prevents us from installing good_crx. 3553 base::FilePath path = data_dir().AppendASCII("good.crx"); 3554 InstallCRX(path, INSTALL_FAILED); 3555 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3556 3557 // Now whitelist this particular extension. 3558 { 3559 ListPrefUpdate update(profile()->GetPrefs(), 3560 extensions::pref_names::kInstallAllowList); 3561 base::ListValue* whitelist = update.Get(); 3562 whitelist->Append(new base::StringValue(good_crx)); 3563 } 3564 3565 // Ensure we can now install good_crx. 3566 InstallCRX(path, INSTALL_NEW); 3567 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3568 } 3569 3570 // Extension blacklisted by policy get unloaded after installing. 3571 TEST_F(ExtensionServiceTest, BlacklistedByPolicyRemovedIfRunning) { 3572 InitializeEmptyExtensionService(); 3573 3574 // Install good_crx. 3575 base::FilePath path = data_dir().AppendASCII("good.crx"); 3576 InstallCRX(path, INSTALL_NEW); 3577 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3578 3579 { // Scope for pref update notification. 3580 PrefService* prefs = profile()->GetPrefs(); 3581 ListPrefUpdate update(prefs, extensions::pref_names::kInstallDenyList); 3582 base::ListValue* blacklist = update.Get(); 3583 ASSERT_TRUE(blacklist != NULL); 3584 3585 // Blacklist this extension. 3586 blacklist->Append(new base::StringValue(good_crx)); 3587 } 3588 3589 // Extension should not be running now. 3590 base::RunLoop().RunUntilIdle(); 3591 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3592 } 3593 3594 // Tests that component extensions are not blacklisted by policy. 3595 TEST_F(ExtensionServiceTest, ComponentExtensionWhitelisted) { 3596 InitializeEmptyExtensionService(); 3597 3598 // Blacklist everything. 3599 { 3600 ListPrefUpdate update(profile()->GetPrefs(), 3601 extensions::pref_names::kInstallDenyList); 3602 base::ListValue* blacklist = update.Get(); 3603 blacklist->Append(new base::StringValue("*")); 3604 } 3605 3606 // Install a component extension. 3607 base::FilePath path = data_dir() 3608 .AppendASCII("good") 3609 .AppendASCII("Extensions") 3610 .AppendASCII(good0) 3611 .AppendASCII("1.0.0.0"); 3612 std::string manifest; 3613 ASSERT_TRUE(base::ReadFileToString( 3614 path.Append(extensions::kManifestFilename), &manifest)); 3615 service()->component_loader()->Add(manifest, path); 3616 service()->Init(); 3617 3618 // Extension should be installed despite blacklist. 3619 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 3620 EXPECT_TRUE(service()->GetExtensionById(good0, false)); 3621 3622 // Poke external providers and make sure the extension is still present. 3623 service()->CheckForExternalUpdates(); 3624 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 3625 EXPECT_TRUE(service()->GetExtensionById(good0, false)); 3626 3627 // Extension should not be uninstalled on blacklist changes. 3628 { 3629 ListPrefUpdate update(profile()->GetPrefs(), 3630 extensions::pref_names::kInstallDenyList); 3631 base::ListValue* blacklist = update.Get(); 3632 blacklist->Append(new base::StringValue(good0)); 3633 } 3634 base::RunLoop().RunUntilIdle(); 3635 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 3636 EXPECT_TRUE(service()->GetExtensionById(good0, false)); 3637 } 3638 3639 // Tests that policy-installed extensions are not blacklisted by policy. 3640 TEST_F(ExtensionServiceTest, PolicyInstalledExtensionsWhitelisted) { 3641 InitializeEmptyExtensionService(); 3642 3643 { 3644 // Blacklist everything. 3645 ListPrefUpdate blacklist_update(profile()->GetPrefs(), 3646 extensions::pref_names::kInstallDenyList); 3647 base::ListValue* blacklist = blacklist_update.Get(); 3648 blacklist->AppendString("*"); 3649 3650 // Mark good.crx for force-installation. 3651 DictionaryPrefUpdate forcelist_update( 3652 profile()->GetPrefs(), extensions::pref_names::kInstallForceList); 3653 extensions::ExternalPolicyLoader::AddExtension( 3654 forcelist_update.Get(), good_crx, "http://example.com/update_url"); 3655 } 3656 3657 // Have policy force-install an extension. 3658 MockExtensionProvider* provider = 3659 new MockExtensionProvider(service(), Manifest::EXTERNAL_POLICY_DOWNLOAD); 3660 AddMockExternalProvider(provider); 3661 provider->UpdateOrAddExtension( 3662 good_crx, "1.0.0.0", data_dir().AppendASCII("good.crx")); 3663 3664 // Reloading extensions should find our externally registered extension 3665 // and install it. 3666 content::WindowedNotificationObserver observer( 3667 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 3668 content::NotificationService::AllSources()); 3669 service()->CheckForExternalUpdates(); 3670 observer.Wait(); 3671 3672 // Extension should be installed despite blacklist. 3673 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 3674 EXPECT_TRUE(service()->GetExtensionById(good_crx, false)); 3675 3676 // Blacklist update should not uninstall the extension. 3677 { 3678 ListPrefUpdate update(profile()->GetPrefs(), 3679 extensions::pref_names::kInstallDenyList); 3680 base::ListValue* blacklist = update.Get(); 3681 blacklist->Append(new base::StringValue(good0)); 3682 } 3683 base::RunLoop().RunUntilIdle(); 3684 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 3685 EXPECT_TRUE(service()->GetExtensionById(good_crx, false)); 3686 } 3687 3688 // Tests that extensions cannot be installed if the policy provider prohibits 3689 // it. This functionality is implemented in CrxInstaller::ConfirmInstall(). 3690 TEST_F(ExtensionServiceTest, ManagementPolicyProhibitsInstall) { 3691 InitializeEmptyExtensionService(); 3692 3693 GetManagementPolicy()->UnregisterAllProviders(); 3694 extensions::TestManagementPolicyProvider provider_( 3695 extensions::TestManagementPolicyProvider::PROHIBIT_LOAD); 3696 GetManagementPolicy()->RegisterProvider(&provider_); 3697 3698 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_FAILED); 3699 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3700 } 3701 3702 // Tests that extensions cannot be loaded from prefs if the policy provider 3703 // prohibits it. This functionality is implemented in InstalledLoader::Load(). 3704 TEST_F(ExtensionServiceTest, ManagementPolicyProhibitsLoadFromPrefs) { 3705 InitializeEmptyExtensionService(); 3706 3707 // Create a fake extension to be loaded as though it were read from prefs. 3708 base::FilePath path = 3709 data_dir().AppendASCII("management").AppendASCII("simple_extension"); 3710 base::DictionaryValue manifest; 3711 manifest.SetString(keys::kName, "simple_extension"); 3712 manifest.SetString(keys::kVersion, "1"); 3713 // UNPACKED is for extensions loaded from a directory. We use it here, even 3714 // though we're testing loading from prefs, so that we don't need to provide 3715 // an extension key. 3716 extensions::ExtensionInfo extension_info( 3717 &manifest, std::string(), path, Manifest::UNPACKED); 3718 3719 // Ensure we can load it with no management policy in place. 3720 GetManagementPolicy()->UnregisterAllProviders(); 3721 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3722 extensions::InstalledLoader(service()).Load(extension_info, false); 3723 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3724 3725 const Extension* extension = 3726 (registry()->enabled_extensions().begin())->get(); 3727 EXPECT_TRUE(service()->UninstallExtension(extension->id(), false, NULL)); 3728 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3729 3730 // Ensure we cannot load it if management policy prohibits installation. 3731 extensions::TestManagementPolicyProvider provider_( 3732 extensions::TestManagementPolicyProvider::PROHIBIT_LOAD); 3733 GetManagementPolicy()->RegisterProvider(&provider_); 3734 3735 extensions::InstalledLoader(service()).Load(extension_info, false); 3736 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3737 } 3738 3739 // Tests disabling an extension when prohibited by the ManagementPolicy. 3740 TEST_F(ExtensionServiceTest, ManagementPolicyProhibitsDisable) { 3741 InitializeEmptyExtensionService(); 3742 3743 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 3744 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3745 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 3746 3747 GetManagementPolicy()->UnregisterAllProviders(); 3748 extensions::TestManagementPolicyProvider provider( 3749 extensions::TestManagementPolicyProvider::PROHIBIT_MODIFY_STATUS); 3750 GetManagementPolicy()->RegisterProvider(&provider); 3751 3752 // Attempt to disable it. 3753 service()->DisableExtension(good_crx, Extension::DISABLE_USER_ACTION); 3754 3755 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3756 EXPECT_TRUE(service()->GetExtensionById(good_crx, false)); 3757 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 3758 } 3759 3760 // Tests uninstalling an extension when prohibited by the ManagementPolicy. 3761 TEST_F(ExtensionServiceTest, ManagementPolicyProhibitsUninstall) { 3762 InitializeEmptyExtensionService(); 3763 3764 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 3765 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3766 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 3767 3768 GetManagementPolicy()->UnregisterAllProviders(); 3769 extensions::TestManagementPolicyProvider provider( 3770 extensions::TestManagementPolicyProvider::PROHIBIT_MODIFY_STATUS); 3771 GetManagementPolicy()->RegisterProvider(&provider); 3772 3773 // Attempt to uninstall it. 3774 EXPECT_FALSE(service()->UninstallExtension(good_crx, false, NULL)); 3775 3776 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3777 EXPECT_TRUE(service()->GetExtensionById(good_crx, false)); 3778 } 3779 3780 // Tests that previously installed extensions that are now prohibited from 3781 // being installed are removed. 3782 TEST_F(ExtensionServiceTest, ManagementPolicyUnloadsAllProhibited) { 3783 InitializeEmptyExtensionService(); 3784 3785 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 3786 InstallCRX(data_dir().AppendASCII("page_action.crx"), INSTALL_NEW); 3787 EXPECT_EQ(2u, registry()->enabled_extensions().size()); 3788 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 3789 3790 GetManagementPolicy()->UnregisterAllProviders(); 3791 extensions::TestManagementPolicyProvider provider( 3792 extensions::TestManagementPolicyProvider::PROHIBIT_LOAD); 3793 GetManagementPolicy()->RegisterProvider(&provider); 3794 3795 // Run the policy check. 3796 service()->CheckManagementPolicy(); 3797 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3798 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 3799 } 3800 3801 // Tests that previously disabled extensions that are now required to be 3802 // enabled are re-enabled on reinstall. 3803 TEST_F(ExtensionServiceTest, ManagementPolicyRequiresEnable) { 3804 InitializeEmptyExtensionService(); 3805 3806 // Install, then disable, an extension. 3807 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 3808 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3809 service()->DisableExtension(good_crx, Extension::DISABLE_USER_ACTION); 3810 EXPECT_EQ(1u, registry()->disabled_extensions().size()); 3811 3812 // Register an ExtensionMnagementPolicy that requires the extension to remain 3813 // enabled. 3814 GetManagementPolicy()->UnregisterAllProviders(); 3815 extensions::TestManagementPolicyProvider provider( 3816 extensions::TestManagementPolicyProvider::MUST_REMAIN_ENABLED); 3817 GetManagementPolicy()->RegisterProvider(&provider); 3818 3819 // Reinstall the extension. 3820 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_UPDATED); 3821 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3822 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 3823 } 3824 3825 // Flaky on windows; http://crbug.com/309833 3826 #if defined(OS_WIN) 3827 #define MAYBE_ExternalExtensionAutoAcknowledgement DISABLED_ExternalExtensionAutoAcknowledgement 3828 #else 3829 #define MAYBE_ExternalExtensionAutoAcknowledgement ExternalExtensionAutoAcknowledgement 3830 #endif 3831 TEST_F(ExtensionServiceTest, MAYBE_ExternalExtensionAutoAcknowledgement) { 3832 InitializeEmptyExtensionService(); 3833 service()->set_extensions_enabled(true); 3834 3835 { 3836 // Register and install an external extension. 3837 MockExtensionProvider* provider = 3838 new MockExtensionProvider(service(), Manifest::EXTERNAL_PREF); 3839 AddMockExternalProvider(provider); 3840 provider->UpdateOrAddExtension( 3841 good_crx, "1.0.0.0", data_dir().AppendASCII("good.crx")); 3842 } 3843 { 3844 // Have policy force-install an extension. 3845 MockExtensionProvider* provider = new MockExtensionProvider( 3846 service(), Manifest::EXTERNAL_POLICY_DOWNLOAD); 3847 AddMockExternalProvider(provider); 3848 provider->UpdateOrAddExtension( 3849 page_action, "1.0.0.0", data_dir().AppendASCII("page_action.crx")); 3850 } 3851 3852 // Providers are set up. Let them run. 3853 int count = 2; 3854 content::WindowedNotificationObserver observer( 3855 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 3856 base::Bind(&WaitForCountNotificationsCallback, &count)); 3857 service()->CheckForExternalUpdates(); 3858 3859 observer.Wait(); 3860 3861 ASSERT_EQ(2u, registry()->enabled_extensions().size()); 3862 EXPECT_TRUE(service()->GetExtensionById(good_crx, false)); 3863 EXPECT_TRUE(service()->GetExtensionById(page_action, false)); 3864 ExtensionPrefs* prefs = ExtensionPrefs::Get(profile()); 3865 ASSERT_TRUE(!prefs->IsExternalExtensionAcknowledged(good_crx)); 3866 ASSERT_TRUE(prefs->IsExternalExtensionAcknowledged(page_action)); 3867 } 3868 3869 #if !defined(OS_CHROMEOS) 3870 // This tests if default apps are installed correctly. 3871 TEST_F(ExtensionServiceTest, DefaultAppsInstall) { 3872 InitializeEmptyExtensionService(); 3873 service()->set_extensions_enabled(true); 3874 3875 { 3876 std::string json_data = 3877 "{" 3878 " \"ldnnhddmnhbkjipkidpdiheffobcpfmf\" : {" 3879 " \"external_crx\": \"good.crx\"," 3880 " \"external_version\": \"1.0.0.0\"," 3881 " \"is_bookmark_app\": false" 3882 " }" 3883 "}"; 3884 default_apps::Provider* provider = new default_apps::Provider( 3885 profile(), 3886 service(), 3887 new extensions::ExternalTestingLoader(json_data, data_dir()), 3888 Manifest::INTERNAL, 3889 Manifest::INVALID_LOCATION, 3890 Extension::FROM_WEBSTORE | Extension::WAS_INSTALLED_BY_DEFAULT); 3891 3892 AddMockExternalProvider(provider); 3893 } 3894 3895 ASSERT_EQ(0u, registry()->enabled_extensions().size()); 3896 content::WindowedNotificationObserver observer( 3897 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 3898 content::NotificationService::AllSources()); 3899 service()->CheckForExternalUpdates(); 3900 observer.Wait(); 3901 3902 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 3903 EXPECT_TRUE(service()->GetExtensionById(good_crx, false)); 3904 const Extension* extension = service()->GetExtensionById(good_crx, false); 3905 EXPECT_TRUE(extension->from_webstore()); 3906 EXPECT_TRUE(extension->was_installed_by_default()); 3907 } 3908 #endif 3909 3910 // Tests disabling extensions 3911 TEST_F(ExtensionServiceTest, DisableExtension) { 3912 InitializeEmptyExtensionService(); 3913 3914 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 3915 EXPECT_TRUE(service()->GetExtensionById(good_crx, true)); 3916 EXPECT_TRUE(service()->GetExtensionById(good_crx, false)); 3917 3918 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3919 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 3920 EXPECT_EQ(0u, registry()->terminated_extensions().size()); 3921 EXPECT_EQ(0u, registry()->blacklisted_extensions().size()); 3922 3923 // Disable it. 3924 service()->DisableExtension(good_crx, Extension::DISABLE_USER_ACTION); 3925 3926 EXPECT_TRUE(service()->GetExtensionById(good_crx, true)); 3927 EXPECT_FALSE(service()->GetExtensionById(good_crx, false)); 3928 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3929 EXPECT_EQ(1u, registry()->disabled_extensions().size()); 3930 EXPECT_EQ(0u, registry()->terminated_extensions().size()); 3931 EXPECT_EQ(0u, registry()->blacklisted_extensions().size()); 3932 } 3933 3934 TEST_F(ExtensionServiceTest, TerminateExtension) { 3935 InitializeEmptyExtensionService(); 3936 3937 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 3938 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3939 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 3940 EXPECT_EQ(0u, registry()->terminated_extensions().size()); 3941 EXPECT_EQ(0u, registry()->blacklisted_extensions().size()); 3942 3943 TerminateExtension(good_crx); 3944 3945 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3946 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 3947 EXPECT_EQ(1u, registry()->terminated_extensions().size()); 3948 EXPECT_EQ(0u, registry()->blacklisted_extensions().size()); 3949 } 3950 3951 TEST_F(ExtensionServiceTest, DisableTerminatedExtension) { 3952 InitializeEmptyExtensionService(); 3953 3954 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 3955 TerminateExtension(good_crx); 3956 EXPECT_TRUE(registry()->GetExtensionById( 3957 good_crx, extensions::ExtensionRegistry::TERMINATED)); 3958 3959 // Disable it. 3960 service()->DisableExtension(good_crx, Extension::DISABLE_USER_ACTION); 3961 3962 EXPECT_FALSE(registry()->GetExtensionById( 3963 good_crx, extensions::ExtensionRegistry::TERMINATED)); 3964 EXPECT_TRUE(service()->GetExtensionById(good_crx, true)); 3965 3966 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3967 EXPECT_EQ(1u, registry()->disabled_extensions().size()); 3968 EXPECT_EQ(0u, registry()->terminated_extensions().size()); 3969 EXPECT_EQ(0u, registry()->blacklisted_extensions().size()); 3970 } 3971 3972 // Tests disabling all extensions (simulating --disable-extensions flag). 3973 TEST_F(ExtensionServiceTest, DisableAllExtensions) { 3974 InitializeEmptyExtensionService(); 3975 3976 base::FilePath path = data_dir().AppendASCII("good.crx"); 3977 InstallCRX(path, INSTALL_NEW); 3978 3979 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 3980 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 3981 3982 // Disable extensions. 3983 service()->set_extensions_enabled(false); 3984 service()->ReloadExtensionsForTest(); 3985 3986 // There shouldn't be extensions in either list. 3987 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3988 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 3989 3990 // This shouldn't do anything when all extensions are disabled. 3991 service()->EnableExtension(good_crx); 3992 service()->ReloadExtensionsForTest(); 3993 3994 // There still shouldn't be extensions in either list. 3995 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 3996 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 3997 3998 // And then re-enable the extensions. 3999 service()->set_extensions_enabled(true); 4000 service()->ReloadExtensionsForTest(); 4001 4002 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 4003 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 4004 } 4005 4006 // Tests reloading extensions. 4007 TEST_F(ExtensionServiceTest, ReloadExtensions) { 4008 InitializeEmptyExtensionService(); 4009 4010 // Simple extension that should install without error. 4011 base::FilePath path = data_dir().AppendASCII("good.crx"); 4012 InstallCRX(path, INSTALL_NEW, 4013 Extension::FROM_WEBSTORE | Extension::WAS_INSTALLED_BY_DEFAULT); 4014 const char* extension_id = good_crx; 4015 service()->DisableExtension(extension_id, Extension::DISABLE_USER_ACTION); 4016 4017 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 4018 EXPECT_EQ(1u, registry()->disabled_extensions().size()); 4019 4020 service()->ReloadExtensionsForTest(); 4021 4022 // The creation flags should not change when reloading the extension. 4023 const Extension* extension = service()->GetExtensionById(good_crx, true); 4024 EXPECT_TRUE(extension->from_webstore()); 4025 EXPECT_TRUE(extension->was_installed_by_default()); 4026 EXPECT_FALSE(extension->from_bookmark()); 4027 4028 // Extension counts shouldn't change. 4029 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 4030 EXPECT_EQ(1u, registry()->disabled_extensions().size()); 4031 4032 service()->EnableExtension(extension_id); 4033 4034 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 4035 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 4036 4037 // Need to clear |loaded_| manually before reloading as the 4038 // EnableExtension() call above inserted into it and 4039 // UnloadAllExtensions() doesn't send out notifications. 4040 loaded_.clear(); 4041 service()->ReloadExtensionsForTest(); 4042 4043 // Extension counts shouldn't change. 4044 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 4045 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 4046 } 4047 4048 // Tests reloading an extension. 4049 TEST_F(ExtensionServiceTest, ReloadExtension) { 4050 InitializeEmptyExtensionService(); 4051 InitializeProcessManager(); 4052 4053 // Simple extension that should install without error. 4054 const char* extension_id = "behllobkkfkfnphdnhnkndlbkcpglgmj"; 4055 base::FilePath ext = data_dir() 4056 .AppendASCII("good") 4057 .AppendASCII("Extensions") 4058 .AppendASCII(extension_id) 4059 .AppendASCII("1.0.0.0"); 4060 extensions::UnpackedInstaller::Create(service())->Load(ext); 4061 base::RunLoop().RunUntilIdle(); 4062 4063 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 4064 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 4065 4066 service()->ReloadExtension(extension_id); 4067 4068 // Extension should be disabled now, waiting to be reloaded. 4069 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 4070 EXPECT_EQ(1u, registry()->disabled_extensions().size()); 4071 EXPECT_EQ(Extension::DISABLE_RELOAD, 4072 ExtensionPrefs::Get(profile())->GetDisableReasons(extension_id)); 4073 4074 // Reloading again should not crash. 4075 service()->ReloadExtension(extension_id); 4076 4077 // Finish reloading 4078 base::RunLoop().RunUntilIdle(); 4079 4080 // Extension should be enabled again. 4081 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 4082 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 4083 } 4084 4085 TEST_F(ExtensionServiceTest, UninstallExtension) { 4086 InitializeEmptyExtensionService(); 4087 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 4088 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 4089 UninstallExtension(good_crx, false); 4090 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 4091 EXPECT_EQ(UnloadedExtensionInfo::REASON_UNINSTALL, unloaded_reason_); 4092 } 4093 4094 TEST_F(ExtensionServiceTest, UninstallTerminatedExtension) { 4095 InitializeEmptyExtensionService(); 4096 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 4097 TerminateExtension(good_crx); 4098 UninstallExtension(good_crx, false); 4099 EXPECT_EQ(UnloadedExtensionInfo::REASON_TERMINATE, unloaded_reason_); 4100 } 4101 4102 // Tests the uninstaller helper. 4103 TEST_F(ExtensionServiceTest, UninstallExtensionHelper) { 4104 InitializeEmptyExtensionService(); 4105 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 4106 UninstallExtension(good_crx, true); 4107 EXPECT_EQ(UnloadedExtensionInfo::REASON_UNINSTALL, unloaded_reason_); 4108 } 4109 4110 TEST_F(ExtensionServiceTest, UninstallExtensionHelperTerminated) { 4111 InitializeEmptyExtensionService(); 4112 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 4113 TerminateExtension(good_crx); 4114 UninstallExtension(good_crx, true); 4115 EXPECT_EQ(UnloadedExtensionInfo::REASON_TERMINATE, unloaded_reason_); 4116 } 4117 4118 // An extension disabled because of unsupported requirements should re-enabled 4119 // if updated to a version with supported requirements as long as there are no 4120 // other disable reasons. 4121 TEST_F(ExtensionServiceTest, UpgradingRequirementsEnabled) { 4122 InitializeEmptyExtensionService(); 4123 BlackListWebGL(); 4124 4125 base::FilePath path = data_dir().AppendASCII("requirements"); 4126 base::FilePath pem_path = 4127 data_dir().AppendASCII("requirements").AppendASCII("v1_good.pem"); 4128 const Extension* extension_v1 = PackAndInstallCRX(path.AppendASCII("v1_good"), 4129 pem_path, 4130 INSTALL_NEW); 4131 std::string id = extension_v1->id(); 4132 EXPECT_TRUE(service()->IsExtensionEnabled(id)); 4133 4134 base::FilePath v2_bad_requirements_crx = GetTemporaryFile(); 4135 4136 PackCRX(path.AppendASCII("v2_bad_requirements"), 4137 pem_path, 4138 v2_bad_requirements_crx); 4139 UpdateExtension(id, v2_bad_requirements_crx, INSTALLED); 4140 EXPECT_FALSE(service()->IsExtensionEnabled(id)); 4141 4142 base::FilePath v3_good_crx = GetTemporaryFile(); 4143 4144 PackCRX(path.AppendASCII("v3_good"), pem_path, v3_good_crx); 4145 UpdateExtension(id, v3_good_crx, ENABLED); 4146 EXPECT_TRUE(service()->IsExtensionEnabled(id)); 4147 } 4148 4149 // Extensions disabled through user action should stay disabled. 4150 TEST_F(ExtensionServiceTest, UpgradingRequirementsDisabled) { 4151 InitializeEmptyExtensionService(); 4152 BlackListWebGL(); 4153 4154 base::FilePath path = data_dir().AppendASCII("requirements"); 4155 base::FilePath pem_path = 4156 data_dir().AppendASCII("requirements").AppendASCII("v1_good.pem"); 4157 const Extension* extension_v1 = PackAndInstallCRX(path.AppendASCII("v1_good"), 4158 pem_path, 4159 INSTALL_NEW); 4160 std::string id = extension_v1->id(); 4161 service()->DisableExtension(id, Extension::DISABLE_USER_ACTION); 4162 EXPECT_FALSE(service()->IsExtensionEnabled(id)); 4163 4164 base::FilePath v2_bad_requirements_crx = GetTemporaryFile(); 4165 4166 PackCRX(path.AppendASCII("v2_bad_requirements"), 4167 pem_path, 4168 v2_bad_requirements_crx); 4169 UpdateExtension(id, v2_bad_requirements_crx, INSTALLED); 4170 EXPECT_FALSE(service()->IsExtensionEnabled(id)); 4171 4172 base::FilePath v3_good_crx = GetTemporaryFile(); 4173 4174 PackCRX(path.AppendASCII("v3_good"), pem_path, v3_good_crx); 4175 UpdateExtension(id, v3_good_crx, INSTALLED); 4176 EXPECT_FALSE(service()->IsExtensionEnabled(id)); 4177 } 4178 4179 // The extension should not re-enabled because it was disabled from a 4180 // permission increase. 4181 TEST_F(ExtensionServiceTest, UpgradingRequirementsPermissions) { 4182 InitializeEmptyExtensionService(); 4183 BlackListWebGL(); 4184 4185 base::FilePath path = data_dir().AppendASCII("requirements"); 4186 base::FilePath pem_path = 4187 data_dir().AppendASCII("requirements").AppendASCII("v1_good.pem"); 4188 const Extension* extension_v1 = PackAndInstallCRX(path.AppendASCII("v1_good"), 4189 pem_path, 4190 INSTALL_NEW); 4191 std::string id = extension_v1->id(); 4192 EXPECT_TRUE(service()->IsExtensionEnabled(id)); 4193 4194 base::FilePath v2_bad_requirements_and_permissions_crx = GetTemporaryFile(); 4195 4196 PackCRX(path.AppendASCII("v2_bad_requirements_and_permissions"), 4197 pem_path, 4198 v2_bad_requirements_and_permissions_crx); 4199 UpdateExtension(id, v2_bad_requirements_and_permissions_crx, INSTALLED); 4200 EXPECT_FALSE(service()->IsExtensionEnabled(id)); 4201 4202 base::FilePath v3_bad_permissions_crx = GetTemporaryFile(); 4203 4204 PackCRX(path.AppendASCII("v3_bad_permissions"), 4205 pem_path, 4206 v3_bad_permissions_crx); 4207 UpdateExtension(id, v3_bad_permissions_crx, INSTALLED); 4208 EXPECT_FALSE(service()->IsExtensionEnabled(id)); 4209 } 4210 4211 // Unpacked extensions are not allowed to be installed if they have unsupported 4212 // requirements. 4213 TEST_F(ExtensionServiceTest, UnpackedRequirements) { 4214 InitializeEmptyExtensionService(); 4215 BlackListWebGL(); 4216 4217 base::FilePath path = 4218 data_dir().AppendASCII("requirements").AppendASCII("v2_bad_requirements"); 4219 extensions::UnpackedInstaller::Create(service())->Load(path); 4220 base::RunLoop().RunUntilIdle(); 4221 EXPECT_EQ(1u, GetErrors().size()); 4222 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 4223 } 4224 4225 class ExtensionCookieCallback { 4226 public: 4227 ExtensionCookieCallback() 4228 : result_(false), 4229 weak_factory_(base::MessageLoop::current()) {} 4230 4231 void SetCookieCallback(bool result) { 4232 base::MessageLoop::current()->PostTask(FROM_HERE, 4233 base::Bind(&base::MessageLoop::Quit, weak_factory_.GetWeakPtr())); 4234 result_ = result; 4235 } 4236 4237 void GetAllCookiesCallback(const net::CookieList& list) { 4238 base::MessageLoop::current()->PostTask(FROM_HERE, 4239 base::Bind(&base::MessageLoop::Quit, weak_factory_.GetWeakPtr())); 4240 list_ = list; 4241 } 4242 net::CookieList list_; 4243 bool result_; 4244 base::WeakPtrFactory<base::MessageLoop> weak_factory_; 4245 }; 4246 4247 // Verifies extension state is removed upon uninstall. 4248 TEST_F(ExtensionServiceTest, ClearExtensionData) { 4249 InitializeEmptyExtensionService(); 4250 ExtensionCookieCallback callback; 4251 4252 // Load a test extension. 4253 base::FilePath path = data_dir(); 4254 path = path.AppendASCII("good.crx"); 4255 const Extension* extension = InstallCRX(path, INSTALL_NEW); 4256 ASSERT_TRUE(extension); 4257 GURL ext_url(extension->url()); 4258 std::string origin_id = webkit_database::GetIdentifierFromOrigin(ext_url); 4259 4260 // Set a cookie for the extension. 4261 net::CookieMonster* cookie_monster = profile() 4262 ->GetRequestContextForExtensions() 4263 ->GetURLRequestContext() 4264 ->cookie_store() 4265 ->GetCookieMonster(); 4266 ASSERT_TRUE(cookie_monster); 4267 net::CookieOptions options; 4268 cookie_monster->SetCookieWithOptionsAsync( 4269 ext_url, "dummy=value", options, 4270 base::Bind(&ExtensionCookieCallback::SetCookieCallback, 4271 base::Unretained(&callback))); 4272 base::RunLoop().RunUntilIdle(); 4273 EXPECT_TRUE(callback.result_); 4274 4275 cookie_monster->GetAllCookiesForURLAsync( 4276 ext_url, 4277 base::Bind(&ExtensionCookieCallback::GetAllCookiesCallback, 4278 base::Unretained(&callback))); 4279 base::RunLoop().RunUntilIdle(); 4280 EXPECT_EQ(1U, callback.list_.size()); 4281 4282 // Open a database. 4283 webkit_database::DatabaseTracker* db_tracker = 4284 BrowserContext::GetDefaultStoragePartition(profile()) 4285 ->GetDatabaseTracker(); 4286 base::string16 db_name = base::UTF8ToUTF16("db"); 4287 base::string16 description = base::UTF8ToUTF16("db_description"); 4288 int64 size; 4289 db_tracker->DatabaseOpened(origin_id, db_name, description, 1, &size); 4290 db_tracker->DatabaseClosed(origin_id, db_name); 4291 std::vector<webkit_database::OriginInfo> origins; 4292 db_tracker->GetAllOriginsInfo(&origins); 4293 EXPECT_EQ(1U, origins.size()); 4294 EXPECT_EQ(origin_id, origins[0].GetOriginIdentifier()); 4295 4296 // Create local storage. We only simulate this by creating the backing files. 4297 // Note: This test depends on details of how the dom_storage library 4298 // stores data in the host file system. 4299 base::FilePath lso_dir_path = 4300 profile()->GetPath().AppendASCII("Local Storage"); 4301 base::FilePath lso_file_path = lso_dir_path.AppendASCII(origin_id) 4302 .AddExtension(FILE_PATH_LITERAL(".localstorage")); 4303 EXPECT_TRUE(base::CreateDirectory(lso_dir_path)); 4304 EXPECT_EQ(0, base::WriteFile(lso_file_path, NULL, 0)); 4305 EXPECT_TRUE(base::PathExists(lso_file_path)); 4306 4307 // Create indexed db. Similarly, it is enough to only simulate this by 4308 // creating the directory on the disk. 4309 IndexedDBContext* idb_context = BrowserContext::GetDefaultStoragePartition( 4310 profile())->GetIndexedDBContext(); 4311 idb_context->SetTaskRunnerForTesting( 4312 base::MessageLoop::current()->message_loop_proxy().get()); 4313 base::FilePath idb_path = idb_context->GetFilePathForTesting(origin_id); 4314 EXPECT_TRUE(base::CreateDirectory(idb_path)); 4315 EXPECT_TRUE(base::DirectoryExists(idb_path)); 4316 4317 // Uninstall the extension. 4318 service()->UninstallExtension(good_crx, false, NULL); 4319 base::RunLoop().RunUntilIdle(); 4320 4321 // Check that the cookie is gone. 4322 cookie_monster->GetAllCookiesForURLAsync( 4323 ext_url, 4324 base::Bind(&ExtensionCookieCallback::GetAllCookiesCallback, 4325 base::Unretained(&callback))); 4326 base::RunLoop().RunUntilIdle(); 4327 EXPECT_EQ(0U, callback.list_.size()); 4328 4329 // The database should have vanished as well. 4330 origins.clear(); 4331 db_tracker->GetAllOriginsInfo(&origins); 4332 EXPECT_EQ(0U, origins.size()); 4333 4334 // Check that the LSO file has been removed. 4335 EXPECT_FALSE(base::PathExists(lso_file_path)); 4336 4337 // Check if the indexed db has disappeared too. 4338 EXPECT_FALSE(base::DirectoryExists(idb_path)); 4339 } 4340 4341 // Verifies app state is removed upon uninstall. 4342 TEST_F(ExtensionServiceTest, ClearAppData) { 4343 InitializeEmptyExtensionService(); 4344 ExtensionCookieCallback callback; 4345 4346 int pref_count = 0; 4347 4348 // Install app1 with unlimited storage. 4349 const Extension* extension = 4350 PackAndInstallCRX(data_dir().AppendASCII("app1"), INSTALL_NEW); 4351 ValidatePrefKeyCount(++pref_count); 4352 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 4353 const std::string id1 = extension->id(); 4354 EXPECT_TRUE(extension->permissions_data()->HasAPIPermission( 4355 APIPermission::kUnlimitedStorage)); 4356 const GURL origin1( 4357 extensions::AppLaunchInfo::GetFullLaunchURL(extension).GetOrigin()); 4358 EXPECT_TRUE(profile()->GetExtensionSpecialStoragePolicy()->IsStorageUnlimited( 4359 origin1)); 4360 std::string origin_id = webkit_database::GetIdentifierFromOrigin(origin1); 4361 4362 // Install app2 from the same origin with unlimited storage. 4363 extension = PackAndInstallCRX(data_dir().AppendASCII("app2"), INSTALL_NEW); 4364 ValidatePrefKeyCount(++pref_count); 4365 ASSERT_EQ(2u, registry()->enabled_extensions().size()); 4366 const std::string id2 = extension->id(); 4367 EXPECT_TRUE(extension->permissions_data()->HasAPIPermission( 4368 APIPermission::kUnlimitedStorage)); 4369 EXPECT_TRUE(extension->web_extent().MatchesURL( 4370 extensions::AppLaunchInfo::GetFullLaunchURL(extension))); 4371 const GURL origin2( 4372 extensions::AppLaunchInfo::GetFullLaunchURL(extension).GetOrigin()); 4373 EXPECT_EQ(origin1, origin2); 4374 EXPECT_TRUE(profile()->GetExtensionSpecialStoragePolicy()->IsStorageUnlimited( 4375 origin2)); 4376 4377 // Set a cookie for the extension. 4378 net::CookieMonster* cookie_monster = profile() 4379 ->GetRequestContext() 4380 ->GetURLRequestContext() 4381 ->cookie_store() 4382 ->GetCookieMonster(); 4383 ASSERT_TRUE(cookie_monster); 4384 net::CookieOptions options; 4385 cookie_monster->SetCookieWithOptionsAsync( 4386 origin1, "dummy=value", options, 4387 base::Bind(&ExtensionCookieCallback::SetCookieCallback, 4388 base::Unretained(&callback))); 4389 base::RunLoop().RunUntilIdle(); 4390 EXPECT_TRUE(callback.result_); 4391 4392 cookie_monster->GetAllCookiesForURLAsync( 4393 origin1, 4394 base::Bind(&ExtensionCookieCallback::GetAllCookiesCallback, 4395 base::Unretained(&callback))); 4396 base::RunLoop().RunUntilIdle(); 4397 EXPECT_EQ(1U, callback.list_.size()); 4398 4399 // Open a database. 4400 webkit_database::DatabaseTracker* db_tracker = 4401 BrowserContext::GetDefaultStoragePartition(profile()) 4402 ->GetDatabaseTracker(); 4403 base::string16 db_name = base::UTF8ToUTF16("db"); 4404 base::string16 description = base::UTF8ToUTF16("db_description"); 4405 int64 size; 4406 db_tracker->DatabaseOpened(origin_id, db_name, description, 1, &size); 4407 db_tracker->DatabaseClosed(origin_id, db_name); 4408 std::vector<webkit_database::OriginInfo> origins; 4409 db_tracker->GetAllOriginsInfo(&origins); 4410 EXPECT_EQ(1U, origins.size()); 4411 EXPECT_EQ(origin_id, origins[0].GetOriginIdentifier()); 4412 4413 // Create local storage. We only simulate this by creating the backing files. 4414 // Note: This test depends on details of how the dom_storage library 4415 // stores data in the host file system. 4416 base::FilePath lso_dir_path = 4417 profile()->GetPath().AppendASCII("Local Storage"); 4418 base::FilePath lso_file_path = lso_dir_path.AppendASCII(origin_id) 4419 .AddExtension(FILE_PATH_LITERAL(".localstorage")); 4420 EXPECT_TRUE(base::CreateDirectory(lso_dir_path)); 4421 EXPECT_EQ(0, base::WriteFile(lso_file_path, NULL, 0)); 4422 EXPECT_TRUE(base::PathExists(lso_file_path)); 4423 4424 // Create indexed db. Similarly, it is enough to only simulate this by 4425 // creating the directory on the disk. 4426 IndexedDBContext* idb_context = BrowserContext::GetDefaultStoragePartition( 4427 profile())->GetIndexedDBContext(); 4428 idb_context->SetTaskRunnerForTesting( 4429 base::MessageLoop::current()->message_loop_proxy().get()); 4430 base::FilePath idb_path = idb_context->GetFilePathForTesting(origin_id); 4431 EXPECT_TRUE(base::CreateDirectory(idb_path)); 4432 EXPECT_TRUE(base::DirectoryExists(idb_path)); 4433 4434 // Uninstall one of them, unlimited storage should still be granted 4435 // to the origin. 4436 UninstallExtension(id1, false); 4437 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 4438 EXPECT_TRUE(profile()->GetExtensionSpecialStoragePolicy()->IsStorageUnlimited( 4439 origin1)); 4440 4441 // Check that the cookie is still there. 4442 cookie_monster->GetAllCookiesForURLAsync( 4443 origin1, 4444 base::Bind(&ExtensionCookieCallback::GetAllCookiesCallback, 4445 base::Unretained(&callback))); 4446 base::RunLoop().RunUntilIdle(); 4447 EXPECT_EQ(1U, callback.list_.size()); 4448 4449 // Now uninstall the other. Storage should be cleared for the apps. 4450 UninstallExtension(id2, false); 4451 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 4452 EXPECT_FALSE( 4453 profile()->GetExtensionSpecialStoragePolicy()->IsStorageUnlimited( 4454 origin1)); 4455 4456 // Check that the cookie is gone. 4457 cookie_monster->GetAllCookiesForURLAsync( 4458 origin1, 4459 base::Bind(&ExtensionCookieCallback::GetAllCookiesCallback, 4460 base::Unretained(&callback))); 4461 base::RunLoop().RunUntilIdle(); 4462 EXPECT_EQ(0U, callback.list_.size()); 4463 4464 // The database should have vanished as well. 4465 origins.clear(); 4466 db_tracker->GetAllOriginsInfo(&origins); 4467 EXPECT_EQ(0U, origins.size()); 4468 4469 // Check that the LSO file has been removed. 4470 EXPECT_FALSE(base::PathExists(lso_file_path)); 4471 4472 // Check if the indexed db has disappeared too. 4473 EXPECT_FALSE(base::DirectoryExists(idb_path)); 4474 } 4475 4476 // Tests loading single extensions (like --load-extension) 4477 // Flaky crashes. http://crbug.com/231806 4478 TEST_F(ExtensionServiceTest, DISABLED_LoadExtension) { 4479 InitializeEmptyExtensionService(); 4480 4481 base::FilePath ext1 = data_dir() 4482 .AppendASCII("good") 4483 .AppendASCII("Extensions") 4484 .AppendASCII("behllobkkfkfnphdnhnkndlbkcpglgmj") 4485 .AppendASCII("1.0.0.0"); 4486 extensions::UnpackedInstaller::Create(service())->Load(ext1); 4487 base::RunLoop().RunUntilIdle(); 4488 EXPECT_EQ(0u, GetErrors().size()); 4489 ASSERT_EQ(1u, loaded_.size()); 4490 EXPECT_EQ(Manifest::UNPACKED, loaded_[0]->location()); 4491 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 4492 4493 ValidatePrefKeyCount(1); 4494 4495 base::FilePath no_manifest = 4496 data_dir() 4497 .AppendASCII("bad") 4498 // .AppendASCII("Extensions") 4499 .AppendASCII("cccccccccccccccccccccccccccccccc") 4500 .AppendASCII("1"); 4501 extensions::UnpackedInstaller::Create(service())->Load(no_manifest); 4502 base::RunLoop().RunUntilIdle(); 4503 EXPECT_EQ(1u, GetErrors().size()); 4504 ASSERT_EQ(1u, loaded_.size()); 4505 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 4506 4507 // Test uninstall. 4508 std::string id = loaded_[0]->id(); 4509 EXPECT_FALSE(unloaded_id_.length()); 4510 service()->UninstallExtension(id, false, NULL); 4511 base::RunLoop().RunUntilIdle(); 4512 EXPECT_EQ(id, unloaded_id_); 4513 ASSERT_EQ(0u, loaded_.size()); 4514 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 4515 } 4516 4517 // Tests that we generate IDs when they are not specified in the manifest for 4518 // --load-extension. 4519 TEST_F(ExtensionServiceTest, GenerateID) { 4520 InitializeEmptyExtensionService(); 4521 4522 base::FilePath no_id_ext = data_dir().AppendASCII("no_id"); 4523 extensions::UnpackedInstaller::Create(service())->Load(no_id_ext); 4524 base::RunLoop().RunUntilIdle(); 4525 EXPECT_EQ(0u, GetErrors().size()); 4526 ASSERT_EQ(1u, loaded_.size()); 4527 ASSERT_TRUE(Extension::IdIsValid(loaded_[0]->id())); 4528 EXPECT_EQ(loaded_[0]->location(), Manifest::UNPACKED); 4529 4530 ValidatePrefKeyCount(1); 4531 4532 std::string previous_id = loaded_[0]->id(); 4533 4534 // If we reload the same path, we should get the same extension ID. 4535 extensions::UnpackedInstaller::Create(service())->Load(no_id_ext); 4536 base::RunLoop().RunUntilIdle(); 4537 ASSERT_EQ(1u, loaded_.size()); 4538 ASSERT_EQ(previous_id, loaded_[0]->id()); 4539 } 4540 4541 TEST_F(ExtensionServiceTest, UnpackedValidatesLocales) { 4542 InitializeEmptyExtensionService(); 4543 4544 base::FilePath bad_locale = 4545 data_dir().AppendASCII("unpacked").AppendASCII("bad_messages_file"); 4546 extensions::UnpackedInstaller::Create(service())->Load(bad_locale); 4547 base::RunLoop().RunUntilIdle(); 4548 EXPECT_EQ(1u, GetErrors().size()); 4549 base::FilePath ms_messages_file = bad_locale.AppendASCII("_locales") 4550 .AppendASCII("ms") 4551 .AppendASCII("messages.json"); 4552 EXPECT_THAT(base::UTF16ToUTF8(GetErrors()[0]), testing::AllOf( 4553 testing::HasSubstr( 4554 base::UTF16ToUTF8(ms_messages_file.LossyDisplayName())), 4555 testing::HasSubstr("Dictionary keys must be quoted."))); 4556 ASSERT_EQ(0u, loaded_.size()); 4557 } 4558 4559 void ExtensionServiceTest::TestExternalProvider( 4560 MockExtensionProvider* provider, Manifest::Location location) { 4561 // Verify that starting with no providers loads no extensions. 4562 service()->Init(); 4563 ASSERT_EQ(0u, loaded_.size()); 4564 4565 provider->set_visit_count(0); 4566 4567 // Register a test extension externally using the mock registry provider. 4568 base::FilePath source_path = data_dir().AppendASCII("good.crx"); 4569 4570 // Add the extension. 4571 provider->UpdateOrAddExtension(good_crx, "1.0.0.0", source_path); 4572 4573 // Reloading extensions should find our externally registered extension 4574 // and install it. 4575 content::WindowedNotificationObserver observer( 4576 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 4577 content::NotificationService::AllSources()); 4578 service()->CheckForExternalUpdates(); 4579 observer.Wait(); 4580 4581 ASSERT_EQ(0u, GetErrors().size()); 4582 ASSERT_EQ(1u, loaded_.size()); 4583 ASSERT_EQ(location, loaded_[0]->location()); 4584 ASSERT_EQ("1.0.0.0", loaded_[0]->version()->GetString()); 4585 ValidatePrefKeyCount(1); 4586 ValidateIntegerPref(good_crx, "state", Extension::ENABLED); 4587 ValidateIntegerPref(good_crx, "location", location); 4588 4589 // Reload extensions without changing anything. The extension should be 4590 // loaded again. 4591 loaded_.clear(); 4592 service()->ReloadExtensionsForTest(); 4593 base::RunLoop().RunUntilIdle(); 4594 ASSERT_EQ(0u, GetErrors().size()); 4595 ASSERT_EQ(1u, loaded_.size()); 4596 ValidatePrefKeyCount(1); 4597 ValidateIntegerPref(good_crx, "state", Extension::ENABLED); 4598 ValidateIntegerPref(good_crx, "location", location); 4599 4600 // Now update the extension with a new version. We should get upgraded. 4601 source_path = source_path.DirName().AppendASCII("good2.crx"); 4602 provider->UpdateOrAddExtension(good_crx, "1.0.0.1", source_path); 4603 4604 loaded_.clear(); 4605 content::WindowedNotificationObserver observer_2( 4606 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 4607 content::NotificationService::AllSources()); 4608 service()->CheckForExternalUpdates(); 4609 observer_2.Wait(); 4610 ASSERT_EQ(0u, GetErrors().size()); 4611 ASSERT_EQ(1u, loaded_.size()); 4612 ASSERT_EQ("1.0.0.1", loaded_[0]->version()->GetString()); 4613 ValidatePrefKeyCount(1); 4614 ValidateIntegerPref(good_crx, "state", Extension::ENABLED); 4615 ValidateIntegerPref(good_crx, "location", location); 4616 4617 // Uninstall the extension and reload. Nothing should happen because the 4618 // preference should prevent us from reinstalling. 4619 std::string id = loaded_[0]->id(); 4620 bool no_uninstall = 4621 GetManagementPolicy()->MustRemainEnabled(loaded_[0].get(), NULL); 4622 service()->UninstallExtension(id, false, NULL); 4623 base::RunLoop().RunUntilIdle(); 4624 4625 base::FilePath install_path = extensions_install_dir().AppendASCII(id); 4626 if (no_uninstall) { 4627 // Policy controlled extensions should not have been touched by uninstall. 4628 ASSERT_TRUE(base::PathExists(install_path)); 4629 } else { 4630 // The extension should also be gone from the install directory. 4631 ASSERT_FALSE(base::PathExists(install_path)); 4632 loaded_.clear(); 4633 service()->CheckForExternalUpdates(); 4634 base::RunLoop().RunUntilIdle(); 4635 ASSERT_EQ(0u, loaded_.size()); 4636 ValidatePrefKeyCount(1); 4637 ValidateIntegerPref(good_crx, "state", 4638 Extension::EXTERNAL_EXTENSION_UNINSTALLED); 4639 ValidateIntegerPref(good_crx, "location", location); 4640 4641 // Now clear the preference and reinstall. 4642 SetPrefInteg(good_crx, "state", Extension::ENABLED); 4643 4644 loaded_.clear(); 4645 content::WindowedNotificationObserver observer( 4646 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 4647 content::NotificationService::AllSources()); 4648 service()->CheckForExternalUpdates(); 4649 observer.Wait(); 4650 ASSERT_EQ(1u, loaded_.size()); 4651 } 4652 ValidatePrefKeyCount(1); 4653 ValidateIntegerPref(good_crx, "state", Extension::ENABLED); 4654 ValidateIntegerPref(good_crx, "location", location); 4655 4656 if (GetManagementPolicy()->MustRemainEnabled(loaded_[0].get(), NULL)) { 4657 EXPECT_EQ(2, provider->visit_count()); 4658 } else { 4659 // Now test an externally triggered uninstall (deleting the registry key or 4660 // the pref entry). 4661 provider->RemoveExtension(good_crx); 4662 4663 loaded_.clear(); 4664 service()->OnExternalProviderReady(provider); 4665 base::RunLoop().RunUntilIdle(); 4666 ASSERT_EQ(0u, loaded_.size()); 4667 ValidatePrefKeyCount(0); 4668 4669 // The extension should also be gone from the install directory. 4670 ASSERT_FALSE(base::PathExists(install_path)); 4671 4672 // Now test the case where user uninstalls and then the extension is removed 4673 // from the external provider. 4674 content::WindowedNotificationObserver observer( 4675 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 4676 content::NotificationService::AllSources()); 4677 provider->UpdateOrAddExtension(good_crx, "1.0.0.1", source_path); 4678 service()->CheckForExternalUpdates(); 4679 observer.Wait(); 4680 4681 ASSERT_EQ(1u, loaded_.size()); 4682 ASSERT_EQ(0u, GetErrors().size()); 4683 4684 // User uninstalls. 4685 loaded_.clear(); 4686 service()->UninstallExtension(id, false, NULL); 4687 base::RunLoop().RunUntilIdle(); 4688 ASSERT_EQ(0u, loaded_.size()); 4689 4690 // Then remove the extension from the extension provider. 4691 provider->RemoveExtension(good_crx); 4692 4693 // Should still be at 0. 4694 loaded_.clear(); 4695 extensions::InstalledLoader(service()).LoadAllExtensions(); 4696 base::RunLoop().RunUntilIdle(); 4697 ASSERT_EQ(0u, loaded_.size()); 4698 ValidatePrefKeyCount(1); 4699 4700 EXPECT_EQ(5, provider->visit_count()); 4701 } 4702 } 4703 4704 // Tests the external installation feature 4705 #if defined(OS_WIN) 4706 TEST_F(ExtensionServiceTest, ExternalInstallRegistry) { 4707 // This should all work, even when normal extension installation is disabled. 4708 InitializeEmptyExtensionService(); 4709 service()->set_extensions_enabled(false); 4710 4711 // Now add providers. Extension system takes ownership of the objects. 4712 MockExtensionProvider* reg_provider = 4713 new MockExtensionProvider(service(), Manifest::EXTERNAL_REGISTRY); 4714 AddMockExternalProvider(reg_provider); 4715 TestExternalProvider(reg_provider, Manifest::EXTERNAL_REGISTRY); 4716 } 4717 #endif 4718 4719 TEST_F(ExtensionServiceTest, ExternalInstallPref) { 4720 InitializeEmptyExtensionService(); 4721 4722 // Now add providers. Extension system takes ownership of the objects. 4723 MockExtensionProvider* pref_provider = 4724 new MockExtensionProvider(service(), Manifest::EXTERNAL_PREF); 4725 4726 AddMockExternalProvider(pref_provider); 4727 TestExternalProvider(pref_provider, Manifest::EXTERNAL_PREF); 4728 } 4729 4730 TEST_F(ExtensionServiceTest, ExternalInstallPrefUpdateUrl) { 4731 // This should all work, even when normal extension installation is disabled. 4732 InitializeEmptyExtensionService(); 4733 service()->set_extensions_enabled(false); 4734 4735 // TODO(skerner): The mock provider is not a good model of a provider 4736 // that works with update URLs, because it adds file and version info. 4737 // Extend the mock to work with update URLs. This test checks the 4738 // behavior that is common to all external extension visitors. The 4739 // browser test ExtensionManagementTest.ExternalUrlUpdate tests that 4740 // what the visitor does results in an extension being downloaded and 4741 // installed. 4742 MockExtensionProvider* pref_provider = 4743 new MockExtensionProvider(service(), Manifest::EXTERNAL_PREF_DOWNLOAD); 4744 AddMockExternalProvider(pref_provider); 4745 TestExternalProvider(pref_provider, Manifest::EXTERNAL_PREF_DOWNLOAD); 4746 } 4747 4748 TEST_F(ExtensionServiceTest, ExternalInstallPolicyUpdateUrl) { 4749 // This should all work, even when normal extension installation is disabled. 4750 InitializeEmptyExtensionService(); 4751 service()->set_extensions_enabled(false); 4752 4753 // TODO(skerner): The mock provider is not a good model of a provider 4754 // that works with update URLs, because it adds file and version info. 4755 // Extend the mock to work with update URLs. This test checks the 4756 // behavior that is common to all external extension visitors. The 4757 // browser test ExtensionManagementTest.ExternalUrlUpdate tests that 4758 // what the visitor does results in an extension being downloaded and 4759 // installed. 4760 MockExtensionProvider* pref_provider = 4761 new MockExtensionProvider(service(), Manifest::EXTERNAL_POLICY_DOWNLOAD); 4762 AddMockExternalProvider(pref_provider); 4763 TestExternalProvider(pref_provider, Manifest::EXTERNAL_POLICY_DOWNLOAD); 4764 } 4765 4766 // Tests that external extensions get uninstalled when the external extension 4767 // providers can't account for them. 4768 TEST_F(ExtensionServiceTest, ExternalUninstall) { 4769 // Start the extensions service with one external extension already installed. 4770 base::FilePath source_install_dir = 4771 data_dir().AppendASCII("good").AppendASCII("Extensions"); 4772 base::FilePath pref_path = source_install_dir 4773 .DirName() 4774 .AppendASCII("PreferencesExternal"); 4775 4776 // This initializes the extensions service with no ExternalProviders. 4777 InitializeInstalledExtensionService(pref_path, source_install_dir); 4778 service()->set_extensions_enabled(false); 4779 4780 service()->Init(); 4781 4782 ASSERT_EQ(0u, GetErrors().size()); 4783 ASSERT_EQ(0u, loaded_.size()); 4784 4785 // Verify that it's not the disabled extensions flag causing it not to load. 4786 service()->set_extensions_enabled(true); 4787 service()->ReloadExtensionsForTest(); 4788 base::RunLoop().RunUntilIdle(); 4789 4790 ASSERT_EQ(0u, GetErrors().size()); 4791 ASSERT_EQ(0u, loaded_.size()); 4792 } 4793 4794 // Test that running multiple update checks simultaneously does not 4795 // keep the update from succeeding. 4796 TEST_F(ExtensionServiceTest, MultipleExternalUpdateCheck) { 4797 InitializeEmptyExtensionService(); 4798 4799 MockExtensionProvider* provider = 4800 new MockExtensionProvider(service(), Manifest::EXTERNAL_PREF); 4801 AddMockExternalProvider(provider); 4802 4803 // Verify that starting with no providers loads no extensions. 4804 service()->Init(); 4805 ASSERT_EQ(0u, loaded_.size()); 4806 4807 // Start two checks for updates. 4808 provider->set_visit_count(0); 4809 service()->CheckForExternalUpdates(); 4810 service()->CheckForExternalUpdates(); 4811 base::RunLoop().RunUntilIdle(); 4812 4813 // Two calls should cause two checks for external extensions. 4814 EXPECT_EQ(2, provider->visit_count()); 4815 EXPECT_EQ(0u, GetErrors().size()); 4816 EXPECT_EQ(0u, loaded_.size()); 4817 4818 // Register a test extension externally using the mock registry provider. 4819 base::FilePath source_path = data_dir().AppendASCII("good.crx"); 4820 provider->UpdateOrAddExtension(good_crx, "1.0.0.0", source_path); 4821 4822 // Two checks for external updates should find the extension, and install it 4823 // once. 4824 content::WindowedNotificationObserver observer( 4825 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 4826 content::NotificationService::AllSources()); 4827 provider->set_visit_count(0); 4828 service()->CheckForExternalUpdates(); 4829 service()->CheckForExternalUpdates(); 4830 observer.Wait(); 4831 EXPECT_EQ(2, provider->visit_count()); 4832 ASSERT_EQ(0u, GetErrors().size()); 4833 ASSERT_EQ(1u, loaded_.size()); 4834 ASSERT_EQ(Manifest::EXTERNAL_PREF, loaded_[0]->location()); 4835 ASSERT_EQ("1.0.0.0", loaded_[0]->version()->GetString()); 4836 ValidatePrefKeyCount(1); 4837 ValidateIntegerPref(good_crx, "state", Extension::ENABLED); 4838 ValidateIntegerPref(good_crx, "location", Manifest::EXTERNAL_PREF); 4839 4840 provider->RemoveExtension(good_crx); 4841 provider->set_visit_count(0); 4842 service()->CheckForExternalUpdates(); 4843 service()->CheckForExternalUpdates(); 4844 base::RunLoop().RunUntilIdle(); 4845 4846 // Two calls should cause two checks for external extensions. 4847 // Because the external source no longer includes good_crx, 4848 // good_crx will be uninstalled. So, expect that no extensions 4849 // are loaded. 4850 EXPECT_EQ(2, provider->visit_count()); 4851 EXPECT_EQ(0u, GetErrors().size()); 4852 EXPECT_EQ(0u, loaded_.size()); 4853 } 4854 4855 TEST_F(ExtensionServiceTest, ExternalPrefProvider) { 4856 InitializeEmptyExtensionService(); 4857 4858 // Test some valid extension records. 4859 // Set a base path to avoid erroring out on relative paths. 4860 // Paths starting with // are absolute on every platform we support. 4861 base::FilePath base_path(FILE_PATH_LITERAL("//base/path")); 4862 ASSERT_TRUE(base_path.IsAbsolute()); 4863 MockProviderVisitor visitor(base_path); 4864 std::string json_data = 4865 "{" 4866 " \"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa\": {" 4867 " \"external_crx\": \"RandomExtension.crx\"," 4868 " \"external_version\": \"1.0\"" 4869 " }," 4870 " \"bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb\": {" 4871 " \"external_crx\": \"RandomExtension2.crx\"," 4872 " \"external_version\": \"2.0\"" 4873 " }," 4874 " \"cccccccccccccccccccccccccccccccc\": {" 4875 " \"external_update_url\": \"http:\\\\foo.com/update\"," 4876 " \"install_parameter\": \"id\"" 4877 " }" 4878 "}"; 4879 EXPECT_EQ(3, visitor.Visit(json_data)); 4880 4881 // Simulate an external_extensions.json file that contains seven invalid 4882 // records: 4883 // - One that is missing the 'external_crx' key. 4884 // - One that is missing the 'external_version' key. 4885 // - One that is specifying .. in the path. 4886 // - One that specifies both a file and update URL. 4887 // - One that specifies no file or update URL. 4888 // - One that has an update URL that is not well formed. 4889 // - One that contains a malformed version. 4890 // - One that has an invalid id. 4891 // - One that has a non-dictionary value. 4892 // - One that has an integer 'external_version' instead of a string. 4893 // The final extension is valid, and we check that it is read to make sure 4894 // failures don't stop valid records from being read. 4895 json_data = 4896 "{" 4897 " \"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa\": {" 4898 " \"external_version\": \"1.0\"" 4899 " }," 4900 " \"bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb\": {" 4901 " \"external_crx\": \"RandomExtension.crx\"" 4902 " }," 4903 " \"cccccccccccccccccccccccccccccccc\": {" 4904 " \"external_crx\": \"..\\\\foo\\\\RandomExtension2.crx\"," 4905 " \"external_version\": \"2.0\"" 4906 " }," 4907 " \"dddddddddddddddddddddddddddddddd\": {" 4908 " \"external_crx\": \"RandomExtension2.crx\"," 4909 " \"external_version\": \"2.0\"," 4910 " \"external_update_url\": \"http:\\\\foo.com/update\"" 4911 " }," 4912 " \"eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee\": {" 4913 " }," 4914 " \"ffffffffffffffffffffffffffffffff\": {" 4915 " \"external_update_url\": \"This string is not a valid URL\"" 4916 " }," 4917 " \"gggggggggggggggggggggggggggggggg\": {" 4918 " \"external_crx\": \"RandomExtension3.crx\"," 4919 " \"external_version\": \"This is not a valid version!\"" 4920 " }," 4921 " \"This is not a valid id!\": {}," 4922 " \"hhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhh\": true," 4923 " \"iiiiiiiiiiiiiiiiiiiiiiiiiiiiiiii\": {" 4924 " \"external_crx\": \"RandomExtension4.crx\"," 4925 " \"external_version\": 1.0" 4926 " }," 4927 " \"pppppppppppppppppppppppppppppppp\": {" 4928 " \"external_crx\": \"RandomValidExtension.crx\"," 4929 " \"external_version\": \"1.0\"" 4930 " }" 4931 "}"; 4932 EXPECT_EQ(1, visitor.Visit(json_data)); 4933 4934 // Check that if a base path is not provided, use of a relative 4935 // path fails. 4936 base::FilePath empty; 4937 MockProviderVisitor visitor_no_relative_paths(empty); 4938 4939 // Use absolute paths. Expect success. 4940 json_data = 4941 "{" 4942 " \"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa\": {" 4943 " \"external_crx\": \"//RandomExtension1.crx\"," 4944 " \"external_version\": \"3.0\"" 4945 " }," 4946 " \"bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb\": {" 4947 " \"external_crx\": \"//path/to/RandomExtension2.crx\"," 4948 " \"external_version\": \"3.0\"" 4949 " }" 4950 "}"; 4951 EXPECT_EQ(2, visitor_no_relative_paths.Visit(json_data)); 4952 4953 // Use a relative path. Expect that it will error out. 4954 json_data = 4955 "{" 4956 " \"cccccccccccccccccccccccccccccccc\": {" 4957 " \"external_crx\": \"RandomExtension2.crx\"," 4958 " \"external_version\": \"3.0\"" 4959 " }" 4960 "}"; 4961 EXPECT_EQ(0, visitor_no_relative_paths.Visit(json_data)); 4962 4963 // Test supported_locales. 4964 json_data = 4965 "{" 4966 " \"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa\": {" 4967 " \"external_crx\": \"RandomExtension.crx\"," 4968 " \"external_version\": \"1.0\"," 4969 " \"supported_locales\": [ \"en\" ]" 4970 " }," 4971 " \"bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb\": {" 4972 " \"external_crx\": \"RandomExtension2.crx\"," 4973 " \"external_version\": \"2.0\"," 4974 " \"supported_locales\": [ \"en-GB\" ]" 4975 " }," 4976 " \"cccccccccccccccccccccccccccccccc\": {" 4977 " \"external_crx\": \"RandomExtension2.crx\"," 4978 " \"external_version\": \"3.0\"," 4979 " \"supported_locales\": [ \"en_US\", \"fr\" ]" 4980 " }" 4981 "}"; 4982 { 4983 ScopedBrowserLocale guard("en-US"); 4984 EXPECT_EQ(2, visitor.Visit(json_data)); 4985 } 4986 4987 // Test keep_if_present. 4988 json_data = 4989 "{" 4990 " \"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa\": {" 4991 " \"external_crx\": \"RandomExtension.crx\"," 4992 " \"external_version\": \"1.0\"," 4993 " \"keep_if_present\": true" 4994 " }" 4995 "}"; 4996 { 4997 EXPECT_EQ(0, visitor.Visit(json_data)); 4998 } 4999 5000 // Test is_bookmark_app. 5001 MockProviderVisitor from_bookmark_visitor( 5002 base_path, Extension::FROM_BOOKMARK); 5003 json_data = 5004 "{" 5005 " \"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa\": {" 5006 " \"external_crx\": \"RandomExtension.crx\"," 5007 " \"external_version\": \"1.0\"," 5008 " \"is_bookmark_app\": true" 5009 " }" 5010 "}"; 5011 EXPECT_EQ(1, from_bookmark_visitor.Visit(json_data)); 5012 5013 // Test is_from_webstore. 5014 MockProviderVisitor from_webstore_visitor( 5015 base_path, Extension::FROM_WEBSTORE); 5016 json_data = 5017 "{" 5018 " \"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa\": {" 5019 " \"external_crx\": \"RandomExtension.crx\"," 5020 " \"external_version\": \"1.0\"," 5021 " \"is_from_webstore\": true" 5022 " }" 5023 "}"; 5024 EXPECT_EQ(1, from_webstore_visitor.Visit(json_data)); 5025 5026 // Test was_installed_by_eom. 5027 MockProviderVisitor was_installed_by_eom_visitor( 5028 base_path, Extension::WAS_INSTALLED_BY_OEM); 5029 json_data = 5030 "{" 5031 " \"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa\": {" 5032 " \"external_crx\": \"RandomExtension.crx\"," 5033 " \"external_version\": \"1.0\"," 5034 " \"was_installed_by_oem\": true" 5035 " }" 5036 "}"; 5037 EXPECT_EQ(1, was_installed_by_eom_visitor.Visit(json_data)); 5038 } 5039 5040 // Test loading good extensions from the profile directory. 5041 TEST_F(ExtensionServiceTest, LoadAndRelocalizeExtensions) { 5042 // Ensure we're testing in "en" and leave global state untouched. 5043 extension_l10n_util::ScopedLocaleForTest testLocale("en"); 5044 5045 // Initialize the test dir with a good Preferences/extensions. 5046 base::FilePath source_install_dir = data_dir().AppendASCII("l10n"); 5047 base::FilePath pref_path = 5048 source_install_dir.Append(chrome::kPreferencesFilename); 5049 InitializeInstalledExtensionService(pref_path, source_install_dir); 5050 5051 service()->Init(); 5052 5053 ASSERT_EQ(3u, loaded_.size()); 5054 5055 // This was equal to "sr" on load. 5056 ValidateStringPref(loaded_[0]->id(), keys::kCurrentLocale, "en"); 5057 5058 // These are untouched by re-localization. 5059 ValidateStringPref(loaded_[1]->id(), keys::kCurrentLocale, "en"); 5060 EXPECT_FALSE(IsPrefExist(loaded_[1]->id(), keys::kCurrentLocale)); 5061 5062 // This one starts with Serbian name, and gets re-localized into English. 5063 EXPECT_EQ("My name is simple.", loaded_[0]->name()); 5064 5065 // These are untouched by re-localization. 5066 EXPECT_EQ("My name is simple.", loaded_[1]->name()); 5067 EXPECT_EQ("no l10n", loaded_[2]->name()); 5068 } 5069 5070 class ExtensionsReadyRecorder : public content::NotificationObserver { 5071 public: 5072 ExtensionsReadyRecorder() : ready_(false) { 5073 registrar_.Add(this, chrome::NOTIFICATION_EXTENSIONS_READY, 5074 content::NotificationService::AllSources()); 5075 } 5076 5077 void set_ready(bool value) { ready_ = value; } 5078 bool ready() { return ready_; } 5079 5080 private: 5081 virtual void Observe(int type, 5082 const content::NotificationSource& source, 5083 const content::NotificationDetails& details) OVERRIDE { 5084 switch (type) { 5085 case chrome::NOTIFICATION_EXTENSIONS_READY: 5086 ready_ = true; 5087 break; 5088 default: 5089 NOTREACHED(); 5090 } 5091 } 5092 5093 content::NotificationRegistrar registrar_; 5094 bool ready_; 5095 }; 5096 5097 // Test that we get enabled/disabled correctly for all the pref/command-line 5098 // combinations. We don't want to derive from the ExtensionServiceTest class 5099 // for this test, so we use ExtensionServiceTestSimple. 5100 // 5101 // Also tests that we always fire EXTENSIONS_READY, no matter whether we are 5102 // enabled or not. 5103 TEST(ExtensionServiceTestSimple, Enabledness) { 5104 // Make sure the PluginService singleton is destroyed at the end of the test. 5105 base::ShadowingAtExitManager at_exit_manager; 5106 #if defined(ENABLE_PLUGINS) 5107 content::PluginService::GetInstance()->Init(); 5108 content::PluginService::GetInstance()->DisablePluginsDiscoveryForTesting(); 5109 #endif 5110 5111 ExtensionErrorReporter::Init(false); // no noisy errors 5112 ExtensionsReadyRecorder recorder; 5113 scoped_ptr<TestingProfile> profile(new TestingProfile()); 5114 content::TestBrowserThreadBundle thread_bundle_; 5115 #if defined OS_CHROMEOS 5116 chromeos::ScopedTestDeviceSettingsService device_settings_service; 5117 chromeos::ScopedTestCrosSettings cros_settings; 5118 scoped_ptr<chromeos::ScopedTestUserManager> user_manager( 5119 new chromeos::ScopedTestUserManager); 5120 #endif 5121 scoped_ptr<CommandLine> command_line; 5122 base::FilePath install_dir = profile->GetPath() 5123 .AppendASCII(extensions::kInstallDirectoryName); 5124 5125 // By default, we are enabled. 5126 command_line.reset(new CommandLine(CommandLine::NO_PROGRAM)); 5127 ExtensionService* service = static_cast<extensions::TestExtensionSystem*>( 5128 ExtensionSystem::Get(profile.get()))-> 5129 CreateExtensionService( 5130 command_line.get(), 5131 install_dir, 5132 false); 5133 EXPECT_TRUE(service->extensions_enabled()); 5134 service->Init(); 5135 base::RunLoop().RunUntilIdle(); 5136 EXPECT_TRUE(recorder.ready()); 5137 #if defined OS_CHROMEOS 5138 user_manager.reset(); 5139 #endif 5140 5141 // If either the command line or pref is set, we are disabled. 5142 recorder.set_ready(false); 5143 profile.reset(new TestingProfile()); 5144 command_line->AppendSwitch(switches::kDisableExtensions); 5145 service = static_cast<extensions::TestExtensionSystem*>( 5146 ExtensionSystem::Get(profile.get()))-> 5147 CreateExtensionService( 5148 command_line.get(), 5149 install_dir, 5150 false); 5151 EXPECT_FALSE(service->extensions_enabled()); 5152 service->Init(); 5153 base::RunLoop().RunUntilIdle(); 5154 EXPECT_TRUE(recorder.ready()); 5155 5156 recorder.set_ready(false); 5157 profile.reset(new TestingProfile()); 5158 profile->GetPrefs()->SetBoolean(prefs::kDisableExtensions, true); 5159 service = static_cast<extensions::TestExtensionSystem*>( 5160 ExtensionSystem::Get(profile.get()))-> 5161 CreateExtensionService( 5162 command_line.get(), 5163 install_dir, 5164 false); 5165 EXPECT_FALSE(service->extensions_enabled()); 5166 service->Init(); 5167 base::RunLoop().RunUntilIdle(); 5168 EXPECT_TRUE(recorder.ready()); 5169 5170 recorder.set_ready(false); 5171 profile.reset(new TestingProfile()); 5172 profile->GetPrefs()->SetBoolean(prefs::kDisableExtensions, true); 5173 command_line.reset(new CommandLine(CommandLine::NO_PROGRAM)); 5174 service = static_cast<extensions::TestExtensionSystem*>( 5175 ExtensionSystem::Get(profile.get()))-> 5176 CreateExtensionService( 5177 command_line.get(), 5178 install_dir, 5179 false); 5180 EXPECT_FALSE(service->extensions_enabled()); 5181 service->Init(); 5182 base::RunLoop().RunUntilIdle(); 5183 EXPECT_TRUE(recorder.ready()); 5184 5185 // Explicitly delete all the resources used in this test. 5186 profile.reset(); 5187 service = NULL; 5188 // Execute any pending deletion tasks. 5189 base::RunLoop().RunUntilIdle(); 5190 } 5191 5192 // Test loading extensions that require limited and unlimited storage quotas. 5193 TEST_F(ExtensionServiceTest, StorageQuota) { 5194 InitializeEmptyExtensionService(); 5195 5196 base::FilePath extensions_path = data_dir().AppendASCII("storage_quota"); 5197 5198 base::FilePath limited_quota_ext = 5199 extensions_path.AppendASCII("limited_quota") 5200 .AppendASCII("1.0"); 5201 5202 // The old permission name for unlimited quota was "unlimited_storage", but 5203 // we changed it to "unlimitedStorage". This tests both versions. 5204 base::FilePath unlimited_quota_ext = 5205 extensions_path.AppendASCII("unlimited_quota") 5206 .AppendASCII("1.0"); 5207 base::FilePath unlimited_quota_ext2 = 5208 extensions_path.AppendASCII("unlimited_quota") 5209 .AppendASCII("2.0"); 5210 extensions::UnpackedInstaller::Create(service())->Load(limited_quota_ext); 5211 extensions::UnpackedInstaller::Create(service())->Load(unlimited_quota_ext); 5212 extensions::UnpackedInstaller::Create(service())->Load(unlimited_quota_ext2); 5213 base::RunLoop().RunUntilIdle(); 5214 5215 ASSERT_EQ(3u, loaded_.size()); 5216 EXPECT_TRUE(profile()); 5217 EXPECT_FALSE(profile()->IsOffTheRecord()); 5218 EXPECT_FALSE( 5219 profile()->GetExtensionSpecialStoragePolicy()->IsStorageUnlimited( 5220 loaded_[0]->url())); 5221 EXPECT_TRUE(profile()->GetExtensionSpecialStoragePolicy()->IsStorageUnlimited( 5222 loaded_[1]->url())); 5223 EXPECT_TRUE(profile()->GetExtensionSpecialStoragePolicy()->IsStorageUnlimited( 5224 loaded_[2]->url())); 5225 } 5226 5227 // Tests ComponentLoader::Add(). 5228 TEST_F(ExtensionServiceTest, ComponentExtensions) { 5229 InitializeEmptyExtensionService(); 5230 5231 // Component extensions should work even when extensions are disabled. 5232 service()->set_extensions_enabled(false); 5233 5234 base::FilePath path = data_dir() 5235 .AppendASCII("good") 5236 .AppendASCII("Extensions") 5237 .AppendASCII("behllobkkfkfnphdnhnkndlbkcpglgmj") 5238 .AppendASCII("1.0.0.0"); 5239 5240 std::string manifest; 5241 ASSERT_TRUE(base::ReadFileToString( 5242 path.Append(extensions::kManifestFilename), &manifest)); 5243 5244 service()->component_loader()->Add(manifest, path); 5245 service()->Init(); 5246 5247 // Note that we do not pump messages -- the extension should be loaded 5248 // immediately. 5249 5250 EXPECT_EQ(0u, GetErrors().size()); 5251 ASSERT_EQ(1u, loaded_.size()); 5252 EXPECT_EQ(Manifest::COMPONENT, loaded_[0]->location()); 5253 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 5254 5255 // Component extensions get a prefs entry on first install. 5256 ValidatePrefKeyCount(1); 5257 5258 // Reload all extensions, and make sure it comes back. 5259 std::string extension_id = (*registry()->enabled_extensions().begin())->id(); 5260 loaded_.clear(); 5261 service()->ReloadExtensionsForTest(); 5262 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 5263 EXPECT_EQ(extension_id, (*registry()->enabled_extensions().begin())->id()); 5264 } 5265 5266 TEST_F(ExtensionServiceTest, DeferredSyncStartupPreInstalledComponent) { 5267 InitializeEmptyExtensionService(); 5268 InitializeExtensionSyncService(); 5269 5270 bool flare_was_called = false; 5271 syncer::ModelType triggered_type(syncer::UNSPECIFIED); 5272 base::WeakPtrFactory<ExtensionServiceTest> factory(this); 5273 extension_sync_service()->SetSyncStartFlare( 5274 base::Bind(&ExtensionServiceTest::MockSyncStartFlare, 5275 factory.GetWeakPtr(), 5276 &flare_was_called, // Safe due to WeakPtrFactory scope. 5277 &triggered_type)); // Safe due to WeakPtrFactory scope. 5278 5279 // Install a component extension. 5280 std::string manifest; 5281 ASSERT_TRUE(base::ReadFileToString( 5282 good0_path().Append(extensions::kManifestFilename), &manifest)); 5283 service()->component_loader()->Add(manifest, good0_path()); 5284 ASSERT_FALSE(service()->is_ready()); 5285 service()->Init(); 5286 ASSERT_TRUE(service()->is_ready()); 5287 5288 // Extensions added before service is_ready() don't trigger sync startup. 5289 EXPECT_FALSE(flare_was_called); 5290 ASSERT_EQ(syncer::UNSPECIFIED, triggered_type); 5291 } 5292 5293 TEST_F(ExtensionServiceTest, DeferredSyncStartupPreInstalledNormal) { 5294 InitializeGoodInstalledExtensionService(); 5295 InitializeExtensionSyncService(); 5296 5297 bool flare_was_called = false; 5298 syncer::ModelType triggered_type(syncer::UNSPECIFIED); 5299 base::WeakPtrFactory<ExtensionServiceTest> factory(this); 5300 extension_sync_service()->SetSyncStartFlare( 5301 base::Bind(&ExtensionServiceTest::MockSyncStartFlare, 5302 factory.GetWeakPtr(), 5303 &flare_was_called, // Safe due to WeakPtrFactory scope. 5304 &triggered_type)); // Safe due to WeakPtrFactory scope. 5305 5306 ASSERT_FALSE(service()->is_ready()); 5307 service()->Init(); 5308 ASSERT_EQ(3u, loaded_.size()); 5309 ASSERT_TRUE(service()->is_ready()); 5310 5311 // Extensions added before service is_ready() don't trigger sync startup. 5312 EXPECT_FALSE(flare_was_called); 5313 ASSERT_EQ(syncer::UNSPECIFIED, triggered_type); 5314 } 5315 5316 TEST_F(ExtensionServiceTest, DeferredSyncStartupOnInstall) { 5317 InitializeEmptyExtensionService(); 5318 InitializeExtensionSyncService(); 5319 service()->Init(); 5320 ASSERT_TRUE(service()->is_ready()); 5321 5322 bool flare_was_called = false; 5323 syncer::ModelType triggered_type(syncer::UNSPECIFIED); 5324 base::WeakPtrFactory<ExtensionServiceTest> factory(this); 5325 extension_sync_service()->SetSyncStartFlare( 5326 base::Bind(&ExtensionServiceTest::MockSyncStartFlare, 5327 factory.GetWeakPtr(), 5328 &flare_was_called, // Safe due to WeakPtrFactory scope. 5329 &triggered_type)); // Safe due to WeakPtrFactory scope. 5330 5331 base::FilePath path = data_dir().AppendASCII("good.crx"); 5332 InstallCRX(path, INSTALL_NEW); 5333 5334 EXPECT_TRUE(flare_was_called); 5335 EXPECT_EQ(syncer::EXTENSIONS, triggered_type); 5336 5337 // Reset. 5338 flare_was_called = false; 5339 triggered_type = syncer::UNSPECIFIED; 5340 5341 // Once sync starts, flare should no longer be invoked. 5342 extension_sync_service()->MergeDataAndStartSyncing( 5343 syncer::EXTENSIONS, 5344 syncer::SyncDataList(), 5345 scoped_ptr<syncer::SyncChangeProcessor>( 5346 new syncer::FakeSyncChangeProcessor), 5347 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5348 path = data_dir().AppendASCII("page_action.crx"); 5349 InstallCRX(path, INSTALL_NEW); 5350 EXPECT_FALSE(flare_was_called); 5351 ASSERT_EQ(syncer::UNSPECIFIED, triggered_type); 5352 } 5353 5354 TEST_F(ExtensionServiceTest, DisableExtensionFromSync) { 5355 // Start the extensions service with one external extension already installed. 5356 base::FilePath source_install_dir = 5357 data_dir().AppendASCII("good").AppendASCII("Extensions"); 5358 base::FilePath pref_path = 5359 source_install_dir.DirName().Append(chrome::kPreferencesFilename); 5360 5361 InitializeInstalledExtensionService(pref_path, source_install_dir); 5362 InitializeExtensionSyncService(); 5363 5364 // The user has enabled sync. 5365 ProfileSyncService* sync_service = 5366 ProfileSyncServiceFactory::GetForProfile(profile()); 5367 sync_service->SetSyncSetupCompleted(); 5368 5369 service()->Init(); 5370 ASSERT_TRUE(service()->is_ready()); 5371 5372 ASSERT_EQ(3u, loaded_.size()); 5373 5374 // We start enabled. 5375 const Extension* extension = service()->GetExtensionById(good0, true); 5376 ASSERT_TRUE(extension); 5377 ASSERT_TRUE(service()->IsExtensionEnabled(good0)); 5378 extensions::ExtensionSyncData disable_good_crx( 5379 *extension, false, false, false); 5380 5381 // Then sync data arrives telling us to disable |good0|. 5382 syncer::SyncDataList sync_data; 5383 sync_data.push_back(disable_good_crx.GetSyncData()); 5384 extension_sync_service()->MergeDataAndStartSyncing( 5385 syncer::EXTENSIONS, 5386 sync_data, 5387 scoped_ptr<syncer::SyncChangeProcessor>( 5388 new syncer::FakeSyncChangeProcessor), 5389 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5390 ASSERT_FALSE(service()->IsExtensionEnabled(good0)); 5391 } 5392 5393 TEST_F(ExtensionServiceTest, DontDisableExtensionWithPendingEnableFromSync) { 5394 // Start the extensions service with one external extension already installed. 5395 base::FilePath source_install_dir = 5396 data_dir().AppendASCII("good").AppendASCII("Extensions"); 5397 base::FilePath pref_path = 5398 source_install_dir.DirName().Append(chrome::kPreferencesFilename); 5399 5400 InitializeInstalledExtensionService(pref_path, source_install_dir); 5401 InitializeExtensionSyncService(); 5402 5403 // The user has enabled sync. 5404 ProfileSyncService* sync_service = 5405 ProfileSyncServiceFactory::GetForProfile(profile()); 5406 sync_service->SetSyncSetupCompleted(); 5407 5408 service()->Init(); 5409 ASSERT_TRUE(service()->is_ready()); 5410 ASSERT_EQ(3u, loaded_.size()); 5411 5412 const Extension* extension = service()->GetExtensionById(good0, true); 5413 ASSERT_TRUE(service()->IsExtensionEnabled(good0)); 5414 5415 // Disable extension before first sync data arrives. 5416 service()->DisableExtension(good0, Extension::DISABLE_USER_ACTION); 5417 ASSERT_FALSE(service()->IsExtensionEnabled(good0)); 5418 5419 // Enable extension - this is now the most recent state. 5420 service()->EnableExtension(good0); 5421 ASSERT_TRUE(service()->IsExtensionEnabled(good0)); 5422 5423 // Now sync data comes in that says to disable good0. This should be 5424 // ignored. 5425 extensions::ExtensionSyncData disable_good_crx( 5426 *extension, false, false, false); 5427 syncer::SyncDataList sync_data; 5428 sync_data.push_back(disable_good_crx.GetSyncData()); 5429 extension_sync_service()->MergeDataAndStartSyncing( 5430 syncer::EXTENSIONS, 5431 sync_data, 5432 scoped_ptr<syncer::SyncChangeProcessor>( 5433 new syncer::FakeSyncChangeProcessor), 5434 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5435 5436 // The extension was enabled locally before the sync data arrived, so it 5437 // should still be enabled now. 5438 ASSERT_TRUE(service()->IsExtensionEnabled(good0)); 5439 } 5440 5441 TEST_F(ExtensionServiceTest, GetSyncData) { 5442 InitializeEmptyExtensionService(); 5443 InitializeExtensionSyncService(); 5444 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 5445 const Extension* extension = service()->GetInstalledExtension(good_crx); 5446 ASSERT_TRUE(extension); 5447 5448 extension_sync_service()->MergeDataAndStartSyncing( 5449 syncer::EXTENSIONS, 5450 syncer::SyncDataList(), 5451 scoped_ptr<syncer::SyncChangeProcessor>( 5452 new syncer::FakeSyncChangeProcessor), 5453 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5454 5455 syncer::SyncDataList list = 5456 extension_sync_service()->GetAllSyncData(syncer::EXTENSIONS); 5457 ASSERT_EQ(list.size(), 1U); 5458 extensions::ExtensionSyncData data(list[0]); 5459 EXPECT_EQ(extension->id(), data.id()); 5460 EXPECT_FALSE(data.uninstalled()); 5461 EXPECT_EQ(service()->IsExtensionEnabled(good_crx), data.enabled()); 5462 EXPECT_EQ(extensions::util::IsIncognitoEnabled(good_crx, profile()), 5463 data.incognito_enabled()); 5464 EXPECT_TRUE(data.version().Equals(*extension->version())); 5465 EXPECT_EQ(extensions::ManifestURL::GetUpdateURL(extension), 5466 data.update_url()); 5467 EXPECT_EQ(extension->name(), data.name()); 5468 } 5469 5470 TEST_F(ExtensionServiceTest, GetSyncDataTerminated) { 5471 InitializeEmptyExtensionService(); 5472 InitializeExtensionSyncService(); 5473 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 5474 TerminateExtension(good_crx); 5475 const Extension* extension = service()->GetInstalledExtension(good_crx); 5476 ASSERT_TRUE(extension); 5477 5478 syncer::FakeSyncChangeProcessor processor; 5479 extension_sync_service()->MergeDataAndStartSyncing( 5480 syncer::EXTENSIONS, 5481 syncer::SyncDataList(), 5482 scoped_ptr<syncer::SyncChangeProcessor>( 5483 new syncer::FakeSyncChangeProcessor), 5484 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5485 5486 syncer::SyncDataList list = 5487 extension_sync_service()->GetAllSyncData(syncer::EXTENSIONS); 5488 ASSERT_EQ(list.size(), 1U); 5489 extensions::ExtensionSyncData data(list[0]); 5490 EXPECT_EQ(extension->id(), data.id()); 5491 EXPECT_FALSE(data.uninstalled()); 5492 EXPECT_EQ(service()->IsExtensionEnabled(good_crx), data.enabled()); 5493 EXPECT_EQ(extensions::util::IsIncognitoEnabled(good_crx, profile()), 5494 data.incognito_enabled()); 5495 EXPECT_TRUE(data.version().Equals(*extension->version())); 5496 EXPECT_EQ(extensions::ManifestURL::GetUpdateURL(extension), 5497 data.update_url()); 5498 EXPECT_EQ(extension->name(), data.name()); 5499 } 5500 5501 TEST_F(ExtensionServiceTest, GetSyncDataFilter) { 5502 InitializeEmptyExtensionService(); 5503 InitializeExtensionSyncService(); 5504 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 5505 const Extension* extension = service()->GetInstalledExtension(good_crx); 5506 ASSERT_TRUE(extension); 5507 5508 syncer::FakeSyncChangeProcessor processor; 5509 extension_sync_service()->MergeDataAndStartSyncing( 5510 syncer::APPS, 5511 syncer::SyncDataList(), 5512 scoped_ptr<syncer::SyncChangeProcessor>( 5513 new syncer::FakeSyncChangeProcessor), 5514 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5515 5516 syncer::SyncDataList list = 5517 extension_sync_service()->GetAllSyncData(syncer::EXTENSIONS); 5518 ASSERT_EQ(list.size(), 0U); 5519 } 5520 5521 TEST_F(ExtensionServiceTest, GetSyncExtensionDataUserSettings) { 5522 InitializeEmptyExtensionService(); 5523 InitializeProcessManager(); 5524 InitializeExtensionSyncService(); 5525 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 5526 const Extension* extension = service()->GetInstalledExtension(good_crx); 5527 ASSERT_TRUE(extension); 5528 5529 syncer::FakeSyncChangeProcessor processor; 5530 extension_sync_service()->MergeDataAndStartSyncing( 5531 syncer::EXTENSIONS, 5532 syncer::SyncDataList(), 5533 scoped_ptr<syncer::SyncChangeProcessor>( 5534 new syncer::FakeSyncChangeProcessor), 5535 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5536 5537 { 5538 syncer::SyncDataList list = 5539 extension_sync_service()->GetAllSyncData(syncer::EXTENSIONS); 5540 ASSERT_EQ(list.size(), 1U); 5541 extensions::ExtensionSyncData data(list[0]); 5542 EXPECT_TRUE(data.enabled()); 5543 EXPECT_FALSE(data.incognito_enabled()); 5544 } 5545 5546 service()->DisableExtension(good_crx, Extension::DISABLE_USER_ACTION); 5547 { 5548 syncer::SyncDataList list = 5549 extension_sync_service()->GetAllSyncData(syncer::EXTENSIONS); 5550 ASSERT_EQ(list.size(), 1U); 5551 extensions::ExtensionSyncData data(list[0]); 5552 EXPECT_FALSE(data.enabled()); 5553 EXPECT_FALSE(data.incognito_enabled()); 5554 } 5555 5556 extensions::util::SetIsIncognitoEnabled(good_crx, profile(), true); 5557 { 5558 syncer::SyncDataList list = 5559 extension_sync_service()->GetAllSyncData(syncer::EXTENSIONS); 5560 ASSERT_EQ(list.size(), 1U); 5561 extensions::ExtensionSyncData data(list[0]); 5562 EXPECT_FALSE(data.enabled()); 5563 EXPECT_TRUE(data.incognito_enabled()); 5564 } 5565 5566 service()->EnableExtension(good_crx); 5567 { 5568 syncer::SyncDataList list = 5569 extension_sync_service()->GetAllSyncData(syncer::EXTENSIONS); 5570 ASSERT_EQ(list.size(), 1U); 5571 extensions::ExtensionSyncData data(list[0]); 5572 EXPECT_TRUE(data.enabled()); 5573 EXPECT_TRUE(data.incognito_enabled()); 5574 } 5575 } 5576 5577 TEST_F(ExtensionServiceTest, SyncForUninstalledExternalExtension) { 5578 InitializeEmptyExtensionService(); 5579 InitializeExtensionSyncService(); 5580 InstallCRXWithLocation( 5581 data_dir().AppendASCII("good.crx"), Manifest::EXTERNAL_PREF, INSTALL_NEW); 5582 const Extension* extension = service()->GetInstalledExtension(good_crx); 5583 ASSERT_TRUE(extension); 5584 5585 syncer::FakeSyncChangeProcessor processor; 5586 extension_sync_service()->MergeDataAndStartSyncing( 5587 syncer::EXTENSIONS, 5588 syncer::SyncDataList(), 5589 scoped_ptr<syncer::SyncChangeProcessor>( 5590 new syncer::FakeSyncChangeProcessor), 5591 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5592 5593 UninstallExtension(good_crx, false); 5594 EXPECT_TRUE( 5595 ExtensionPrefs::Get(profile())->IsExternalExtensionUninstalled(good_crx)); 5596 5597 sync_pb::EntitySpecifics specifics; 5598 sync_pb::AppSpecifics* app_specifics = specifics.mutable_app(); 5599 sync_pb::ExtensionSpecifics* extension_specifics = 5600 app_specifics->mutable_extension(); 5601 extension_specifics->set_id(good_crx); 5602 extension_specifics->set_version("1.0"); 5603 extension_specifics->set_enabled(true); 5604 5605 syncer::SyncData sync_data = 5606 syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); 5607 syncer::SyncChange sync_change(FROM_HERE, 5608 syncer::SyncChange::ACTION_UPDATE, 5609 sync_data); 5610 syncer::SyncChangeList list(1); 5611 list[0] = sync_change; 5612 5613 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 5614 EXPECT_TRUE( 5615 ExtensionPrefs::Get(profile())->IsExternalExtensionUninstalled(good_crx)); 5616 } 5617 5618 TEST_F(ExtensionServiceTest, GetSyncAppDataUserSettings) { 5619 InitializeEmptyExtensionService(); 5620 InitializeExtensionSyncService(); 5621 const Extension* app = 5622 PackAndInstallCRX(data_dir().AppendASCII("app"), INSTALL_NEW); 5623 ASSERT_TRUE(app); 5624 ASSERT_TRUE(app->is_app()); 5625 5626 syncer::FakeSyncChangeProcessor processor; 5627 extension_sync_service()->MergeDataAndStartSyncing( 5628 syncer::APPS, 5629 syncer::SyncDataList(), 5630 scoped_ptr<syncer::SyncChangeProcessor>( 5631 new syncer::FakeSyncChangeProcessor), 5632 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5633 5634 syncer::StringOrdinal initial_ordinal = 5635 syncer::StringOrdinal::CreateInitialOrdinal(); 5636 { 5637 syncer::SyncDataList list = 5638 extension_sync_service()->GetAllSyncData(syncer::APPS); 5639 ASSERT_EQ(list.size(), 1U); 5640 5641 extensions::AppSyncData app_sync_data(list[0]); 5642 EXPECT_TRUE(initial_ordinal.Equals(app_sync_data.app_launch_ordinal())); 5643 EXPECT_TRUE(initial_ordinal.Equals(app_sync_data.page_ordinal())); 5644 } 5645 5646 AppSorting* sorting = ExtensionPrefs::Get(profile())->app_sorting(); 5647 sorting->SetAppLaunchOrdinal(app->id(), initial_ordinal.CreateAfter()); 5648 { 5649 syncer::SyncDataList list = 5650 extension_sync_service()->GetAllSyncData(syncer::APPS); 5651 ASSERT_EQ(list.size(), 1U); 5652 5653 extensions::AppSyncData app_sync_data(list[0]); 5654 EXPECT_TRUE(initial_ordinal.LessThan(app_sync_data.app_launch_ordinal())); 5655 EXPECT_TRUE(initial_ordinal.Equals(app_sync_data.page_ordinal())); 5656 } 5657 5658 sorting->SetPageOrdinal(app->id(), initial_ordinal.CreateAfter()); 5659 { 5660 syncer::SyncDataList list = 5661 extension_sync_service()->GetAllSyncData(syncer::APPS); 5662 ASSERT_EQ(list.size(), 1U); 5663 5664 extensions::AppSyncData app_sync_data(list[0]); 5665 EXPECT_TRUE(initial_ordinal.LessThan(app_sync_data.app_launch_ordinal())); 5666 EXPECT_TRUE(initial_ordinal.LessThan(app_sync_data.page_ordinal())); 5667 } 5668 } 5669 5670 // TODO (rdevlin.cronin): The OnExtensionMoved() method has been removed from 5671 // ExtensionService, so this test probably needs a new home. Unfortunately, it 5672 // relies pretty heavily on things like InitializeExtension[Sync]Service() and 5673 // PackAndInstallCRX(). When we clean up a bit more, this should move out. 5674 TEST_F(ExtensionServiceTest, GetSyncAppDataUserSettingsOnExtensionMoved) { 5675 InitializeEmptyExtensionService(); 5676 InitializeExtensionSyncService(); 5677 const size_t kAppCount = 3; 5678 const Extension* apps[kAppCount]; 5679 apps[0] = PackAndInstallCRX(data_dir().AppendASCII("app1"), INSTALL_NEW); 5680 apps[1] = PackAndInstallCRX(data_dir().AppendASCII("app2"), INSTALL_NEW); 5681 apps[2] = PackAndInstallCRX(data_dir().AppendASCII("app4"), INSTALL_NEW); 5682 for (size_t i = 0; i < kAppCount; ++i) { 5683 ASSERT_TRUE(apps[i]); 5684 ASSERT_TRUE(apps[i]->is_app()); 5685 } 5686 5687 syncer::FakeSyncChangeProcessor processor; 5688 extension_sync_service()->MergeDataAndStartSyncing( 5689 syncer::APPS, 5690 syncer::SyncDataList(), 5691 scoped_ptr<syncer::SyncChangeProcessor>( 5692 new syncer::FakeSyncChangeProcessor), 5693 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5694 5695 ExtensionPrefs::Get(service()->GetBrowserContext()) 5696 ->app_sorting() 5697 ->OnExtensionMoved(apps[0]->id(), apps[1]->id(), apps[2]->id()); 5698 { 5699 syncer::SyncDataList list = 5700 extension_sync_service()->GetAllSyncData(syncer::APPS); 5701 ASSERT_EQ(list.size(), 3U); 5702 5703 extensions::AppSyncData data[kAppCount]; 5704 for (size_t i = 0; i < kAppCount; ++i) { 5705 data[i] = extensions::AppSyncData(list[i]); 5706 } 5707 5708 // The sync data is not always in the same order our apps were installed in, 5709 // so we do that sorting here so we can make sure the values are changed as 5710 // expected. 5711 syncer::StringOrdinal app_launch_ordinals[kAppCount]; 5712 for (size_t i = 0; i < kAppCount; ++i) { 5713 for (size_t j = 0; j < kAppCount; ++j) { 5714 if (apps[i]->id() == data[j].id()) 5715 app_launch_ordinals[i] = data[j].app_launch_ordinal(); 5716 } 5717 } 5718 5719 EXPECT_TRUE(app_launch_ordinals[1].LessThan(app_launch_ordinals[0])); 5720 EXPECT_TRUE(app_launch_ordinals[0].LessThan(app_launch_ordinals[2])); 5721 } 5722 } 5723 5724 TEST_F(ExtensionServiceTest, GetSyncDataList) { 5725 InitializeEmptyExtensionService(); 5726 InitializeExtensionSyncService(); 5727 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 5728 InstallCRX(data_dir().AppendASCII("page_action.crx"), INSTALL_NEW); 5729 InstallCRX(data_dir().AppendASCII("theme.crx"), INSTALL_NEW); 5730 InstallCRX(data_dir().AppendASCII("theme2.crx"), INSTALL_NEW); 5731 5732 syncer::FakeSyncChangeProcessor processor; 5733 extension_sync_service()->MergeDataAndStartSyncing( 5734 syncer::APPS, 5735 syncer::SyncDataList(), 5736 scoped_ptr<syncer::SyncChangeProcessor>( 5737 new syncer::FakeSyncChangeProcessor), 5738 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5739 extension_sync_service()->MergeDataAndStartSyncing( 5740 syncer::EXTENSIONS, 5741 syncer::SyncDataList(), 5742 scoped_ptr<syncer::SyncChangeProcessor>( 5743 new syncer::FakeSyncChangeProcessor), 5744 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5745 5746 service()->DisableExtension(page_action, Extension::DISABLE_USER_ACTION); 5747 TerminateExtension(theme2_crx); 5748 5749 EXPECT_EQ(0u, extension_sync_service()->GetAllSyncData(syncer::APPS).size()); 5750 EXPECT_EQ( 5751 2u, extension_sync_service()->GetAllSyncData(syncer::EXTENSIONS).size()); 5752 } 5753 5754 TEST_F(ExtensionServiceTest, ProcessSyncDataUninstall) { 5755 InitializeEmptyExtensionService(); 5756 InitializeExtensionSyncService(); 5757 syncer::FakeSyncChangeProcessor processor; 5758 extension_sync_service()->MergeDataAndStartSyncing( 5759 syncer::EXTENSIONS, 5760 syncer::SyncDataList(), 5761 scoped_ptr<syncer::SyncChangeProcessor>( 5762 new syncer::FakeSyncChangeProcessor), 5763 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5764 5765 sync_pb::EntitySpecifics specifics; 5766 sync_pb::ExtensionSpecifics* ext_specifics = specifics.mutable_extension(); 5767 ext_specifics->set_id(good_crx); 5768 ext_specifics->set_version("1.0"); 5769 syncer::SyncData sync_data = 5770 syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); 5771 syncer::SyncChange sync_change(FROM_HERE, 5772 syncer::SyncChange::ACTION_DELETE, 5773 sync_data); 5774 syncer::SyncChangeList list(1); 5775 list[0] = sync_change; 5776 5777 // Should do nothing. 5778 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 5779 EXPECT_FALSE(service()->GetExtensionById(good_crx, true)); 5780 5781 // Install the extension. 5782 base::FilePath extension_path = data_dir().AppendASCII("good.crx"); 5783 InstallCRX(extension_path, INSTALL_NEW); 5784 EXPECT_TRUE(service()->GetExtensionById(good_crx, true)); 5785 5786 // Should uninstall the extension. 5787 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 5788 EXPECT_FALSE(service()->GetExtensionById(good_crx, true)); 5789 5790 // Should again do nothing. 5791 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 5792 EXPECT_FALSE(service()->GetExtensionById(good_crx, true)); 5793 } 5794 5795 TEST_F(ExtensionServiceTest, ProcessSyncDataWrongType) { 5796 InitializeEmptyExtensionService(); 5797 InitializeExtensionSyncService(); 5798 5799 // Install the extension. 5800 base::FilePath extension_path = data_dir().AppendASCII("good.crx"); 5801 InstallCRX(extension_path, INSTALL_NEW); 5802 EXPECT_TRUE(service()->GetExtensionById(good_crx, true)); 5803 5804 sync_pb::EntitySpecifics specifics; 5805 sync_pb::AppSpecifics* app_specifics = specifics.mutable_app(); 5806 sync_pb::ExtensionSpecifics* extension_specifics = 5807 app_specifics->mutable_extension(); 5808 extension_specifics->set_id(good_crx); 5809 extension_specifics->set_version( 5810 service()->GetInstalledExtension(good_crx)->version()->GetString()); 5811 5812 { 5813 extension_specifics->set_enabled(true); 5814 syncer::SyncData sync_data = 5815 syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); 5816 syncer::SyncChange sync_change(FROM_HERE, 5817 syncer::SyncChange::ACTION_DELETE, 5818 sync_data); 5819 syncer::SyncChangeList list(1); 5820 list[0] = sync_change; 5821 5822 // Should do nothing 5823 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 5824 EXPECT_TRUE(service()->GetExtensionById(good_crx, true)); 5825 } 5826 5827 { 5828 extension_specifics->set_enabled(false); 5829 syncer::SyncData sync_data = 5830 syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); 5831 syncer::SyncChange sync_change(FROM_HERE, 5832 syncer::SyncChange::ACTION_UPDATE, 5833 sync_data); 5834 syncer::SyncChangeList list(1); 5835 list[0] = sync_change; 5836 5837 // Should again do nothing. 5838 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 5839 EXPECT_TRUE(service()->GetExtensionById(good_crx, false)); 5840 } 5841 } 5842 5843 TEST_F(ExtensionServiceTest, ProcessSyncDataSettings) { 5844 InitializeEmptyExtensionService(); 5845 InitializeProcessManager(); 5846 InitializeExtensionSyncService(); 5847 syncer::FakeSyncChangeProcessor processor; 5848 extension_sync_service()->MergeDataAndStartSyncing( 5849 syncer::EXTENSIONS, 5850 syncer::SyncDataList(), 5851 scoped_ptr<syncer::SyncChangeProcessor>( 5852 new syncer::FakeSyncChangeProcessor), 5853 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5854 5855 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 5856 EXPECT_TRUE(service()->IsExtensionEnabled(good_crx)); 5857 EXPECT_FALSE(extensions::util::IsIncognitoEnabled(good_crx, profile())); 5858 5859 sync_pb::EntitySpecifics specifics; 5860 sync_pb::ExtensionSpecifics* ext_specifics = specifics.mutable_extension(); 5861 ext_specifics->set_id(good_crx); 5862 ext_specifics->set_version( 5863 service()->GetInstalledExtension(good_crx)->version()->GetString()); 5864 ext_specifics->set_enabled(false); 5865 5866 { 5867 syncer::SyncData sync_data = 5868 syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); 5869 syncer::SyncChange sync_change(FROM_HERE, 5870 syncer::SyncChange::ACTION_UPDATE, 5871 sync_data); 5872 syncer::SyncChangeList list(1); 5873 list[0] = sync_change; 5874 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 5875 EXPECT_FALSE(service()->IsExtensionEnabled(good_crx)); 5876 EXPECT_FALSE(extensions::util::IsIncognitoEnabled(good_crx, profile())); 5877 } 5878 5879 { 5880 ext_specifics->set_enabled(true); 5881 ext_specifics->set_incognito_enabled(true); 5882 syncer::SyncData sync_data = 5883 syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); 5884 syncer::SyncChange sync_change(FROM_HERE, 5885 syncer::SyncChange::ACTION_UPDATE, 5886 sync_data); 5887 syncer::SyncChangeList list(1); 5888 list[0] = sync_change; 5889 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 5890 EXPECT_TRUE(service()->IsExtensionEnabled(good_crx)); 5891 EXPECT_TRUE(extensions::util::IsIncognitoEnabled(good_crx, profile())); 5892 } 5893 5894 { 5895 ext_specifics->set_enabled(false); 5896 ext_specifics->set_incognito_enabled(true); 5897 syncer::SyncData sync_data = 5898 syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); 5899 syncer::SyncChange sync_change(FROM_HERE, 5900 syncer::SyncChange::ACTION_UPDATE, 5901 sync_data); 5902 syncer::SyncChangeList list(1); 5903 list[0] = sync_change; 5904 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 5905 EXPECT_FALSE(service()->IsExtensionEnabled(good_crx)); 5906 EXPECT_TRUE(extensions::util::IsIncognitoEnabled(good_crx, profile())); 5907 } 5908 5909 EXPECT_FALSE(service()->pending_extension_manager()->IsIdPending(good_crx)); 5910 } 5911 5912 TEST_F(ExtensionServiceTest, ProcessSyncDataTerminatedExtension) { 5913 InitializeExtensionServiceWithUpdater(); 5914 InitializeExtensionSyncService(); 5915 syncer::FakeSyncChangeProcessor processor; 5916 extension_sync_service()->MergeDataAndStartSyncing( 5917 syncer::EXTENSIONS, 5918 syncer::SyncDataList(), 5919 scoped_ptr<syncer::SyncChangeProcessor>( 5920 new syncer::FakeSyncChangeProcessor), 5921 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5922 5923 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 5924 TerminateExtension(good_crx); 5925 EXPECT_TRUE(service()->IsExtensionEnabled(good_crx)); 5926 EXPECT_FALSE(extensions::util::IsIncognitoEnabled(good_crx, profile())); 5927 5928 sync_pb::EntitySpecifics specifics; 5929 sync_pb::ExtensionSpecifics* ext_specifics = specifics.mutable_extension(); 5930 ext_specifics->set_id(good_crx); 5931 ext_specifics->set_version( 5932 service()->GetInstalledExtension(good_crx)->version()->GetString()); 5933 ext_specifics->set_enabled(false); 5934 ext_specifics->set_incognito_enabled(true); 5935 syncer::SyncData sync_data = 5936 syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); 5937 syncer::SyncChange sync_change(FROM_HERE, 5938 syncer::SyncChange::ACTION_UPDATE, 5939 sync_data); 5940 syncer::SyncChangeList list(1); 5941 list[0] = sync_change; 5942 5943 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 5944 EXPECT_FALSE(service()->IsExtensionEnabled(good_crx)); 5945 EXPECT_TRUE(extensions::util::IsIncognitoEnabled(good_crx, profile())); 5946 5947 EXPECT_FALSE(service()->pending_extension_manager()->IsIdPending(good_crx)); 5948 } 5949 5950 TEST_F(ExtensionServiceTest, ProcessSyncDataVersionCheck) { 5951 InitializeExtensionServiceWithUpdater(); 5952 InitializeExtensionSyncService(); 5953 syncer::FakeSyncChangeProcessor processor; 5954 extension_sync_service()->MergeDataAndStartSyncing( 5955 syncer::EXTENSIONS, 5956 syncer::SyncDataList(), 5957 scoped_ptr<syncer::SyncChangeProcessor>( 5958 new syncer::FakeSyncChangeProcessor), 5959 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 5960 5961 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 5962 EXPECT_TRUE(service()->IsExtensionEnabled(good_crx)); 5963 EXPECT_FALSE(extensions::util::IsIncognitoEnabled(good_crx, profile())); 5964 5965 sync_pb::EntitySpecifics specifics; 5966 sync_pb::ExtensionSpecifics* ext_specifics = specifics.mutable_extension(); 5967 ext_specifics->set_id(good_crx); 5968 ext_specifics->set_enabled(true); 5969 5970 { 5971 ext_specifics->set_version( 5972 service()->GetInstalledExtension(good_crx)->version()->GetString()); 5973 syncer::SyncData sync_data = 5974 syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); 5975 syncer::SyncChange sync_change(FROM_HERE, 5976 syncer::SyncChange::ACTION_UPDATE, 5977 sync_data); 5978 syncer::SyncChangeList list(1); 5979 list[0] = sync_change; 5980 5981 // Should do nothing if extension version == sync version. 5982 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 5983 EXPECT_FALSE(service()->updater()->WillCheckSoon()); 5984 } 5985 5986 // Should do nothing if extension version > sync version (but see 5987 // the TODO in ProcessExtensionSyncData). 5988 { 5989 ext_specifics->set_version("0.0.0.0"); 5990 syncer::SyncData sync_data = 5991 syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); 5992 syncer::SyncChange sync_change(FROM_HERE, 5993 syncer::SyncChange::ACTION_UPDATE, 5994 sync_data); 5995 syncer::SyncChangeList list(1); 5996 list[0] = sync_change; 5997 5998 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 5999 EXPECT_FALSE(service()->updater()->WillCheckSoon()); 6000 } 6001 6002 // Should kick off an update if extension version < sync version. 6003 { 6004 ext_specifics->set_version("9.9.9.9"); 6005 syncer::SyncData sync_data = 6006 syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); 6007 syncer::SyncChange sync_change(FROM_HERE, 6008 syncer::SyncChange::ACTION_UPDATE, 6009 sync_data); 6010 syncer::SyncChangeList list(1); 6011 list[0] = sync_change; 6012 6013 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 6014 EXPECT_TRUE(service()->updater()->WillCheckSoon()); 6015 } 6016 6017 EXPECT_FALSE(service()->pending_extension_manager()->IsIdPending(good_crx)); 6018 } 6019 6020 TEST_F(ExtensionServiceTest, ProcessSyncDataNotInstalled) { 6021 InitializeExtensionServiceWithUpdater(); 6022 InitializeExtensionSyncService(); 6023 syncer::FakeSyncChangeProcessor processor; 6024 extension_sync_service()->MergeDataAndStartSyncing( 6025 syncer::EXTENSIONS, 6026 syncer::SyncDataList(), 6027 scoped_ptr<syncer::SyncChangeProcessor>( 6028 new syncer::FakeSyncChangeProcessor), 6029 scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); 6030 6031 sync_pb::EntitySpecifics specifics; 6032 sync_pb::ExtensionSpecifics* ext_specifics = specifics.mutable_extension(); 6033 ext_specifics->set_id(good_crx); 6034 ext_specifics->set_enabled(false); 6035 ext_specifics->set_incognito_enabled(true); 6036 ext_specifics->set_update_url("http://www.google.com/"); 6037 ext_specifics->set_version("1.2.3.4"); 6038 syncer::SyncData sync_data = 6039 syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); 6040 syncer::SyncChange sync_change(FROM_HERE, 6041 syncer::SyncChange::ACTION_UPDATE, 6042 sync_data); 6043 syncer::SyncChangeList list(1); 6044 list[0] = sync_change; 6045 6046 EXPECT_TRUE(service()->IsExtensionEnabled(good_crx)); 6047 EXPECT_FALSE(extensions::util::IsIncognitoEnabled(good_crx, profile())); 6048 extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); 6049 EXPECT_TRUE(service()->updater()->WillCheckSoon()); 6050 EXPECT_FALSE(service()->IsExtensionEnabled(good_crx)); 6051 EXPECT_TRUE(extensions::util::IsIncognitoEnabled(good_crx, profile())); 6052 6053 const extensions::PendingExtensionInfo* info; 6054 EXPECT_TRUE( 6055 (info = service()->pending_extension_manager()->GetById(good_crx))); 6056 EXPECT_EQ(ext_specifics->update_url(), info->update_url().spec()); 6057 EXPECT_TRUE(info->is_from_sync()); 6058 EXPECT_TRUE(info->install_silently()); 6059 EXPECT_EQ(Manifest::INTERNAL, info->install_source()); 6060 // TODO(akalin): Figure out a way to test |info.ShouldAllowInstall()|. 6061 } 6062 6063 TEST_F(ExtensionServiceTest, InstallPriorityExternalUpdateUrl) { 6064 InitializeEmptyExtensionService(); 6065 6066 base::FilePath path = data_dir().AppendASCII("good.crx"); 6067 InstallCRX(path, INSTALL_NEW); 6068 ValidatePrefKeyCount(1u); 6069 ValidateIntegerPref(good_crx, "state", Extension::ENABLED); 6070 ValidateIntegerPref(good_crx, "location", Manifest::INTERNAL); 6071 6072 extensions::PendingExtensionManager* pending = 6073 service()->pending_extension_manager(); 6074 EXPECT_FALSE(pending->IsIdPending(kGoodId)); 6075 6076 // Skip install when the location is the same. 6077 EXPECT_FALSE( 6078 service()->OnExternalExtensionUpdateUrlFound(kGoodId, 6079 std::string(), 6080 GURL(kGoodUpdateURL), 6081 Manifest::INTERNAL, 6082 Extension::NO_FLAGS, 6083 false)); 6084 EXPECT_FALSE(pending->IsIdPending(kGoodId)); 6085 6086 // Install when the location has higher priority. 6087 EXPECT_TRUE(service()->OnExternalExtensionUpdateUrlFound( 6088 kGoodId, 6089 std::string(), 6090 GURL(kGoodUpdateURL), 6091 Manifest::EXTERNAL_POLICY_DOWNLOAD, 6092 Extension::NO_FLAGS, 6093 false)); 6094 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6095 6096 // Try the low priority again. Should be rejected. 6097 EXPECT_FALSE(service()->OnExternalExtensionUpdateUrlFound( 6098 kGoodId, 6099 std::string(), 6100 GURL(kGoodUpdateURL), 6101 Manifest::EXTERNAL_PREF_DOWNLOAD, 6102 Extension::NO_FLAGS, 6103 false)); 6104 // The existing record should still be present in the pending extension 6105 // manager. 6106 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6107 6108 pending->Remove(kGoodId); 6109 6110 // Skip install when the location has the same priority as the installed 6111 // location. 6112 EXPECT_FALSE( 6113 service()->OnExternalExtensionUpdateUrlFound(kGoodId, 6114 std::string(), 6115 GURL(kGoodUpdateURL), 6116 Manifest::INTERNAL, 6117 Extension::NO_FLAGS, 6118 false)); 6119 6120 EXPECT_FALSE(pending->IsIdPending(kGoodId)); 6121 } 6122 6123 TEST_F(ExtensionServiceTest, InstallPriorityExternalLocalFile) { 6124 Version older_version("0.1.0.0"); 6125 Version newer_version("2.0.0.0"); 6126 6127 // We don't want the extension to be installed. A path that doesn't 6128 // point to a valid CRX ensures this. 6129 const base::FilePath kInvalidPathToCrx = base::FilePath(); 6130 6131 const int kCreationFlags = 0; 6132 const bool kDontMarkAcknowledged = false; 6133 6134 InitializeEmptyExtensionService(); 6135 6136 // The test below uses install source constants to test that 6137 // priority is enforced. It assumes a specific ranking of install 6138 // sources: Registry (EXTERNAL_REGISTRY) overrides external pref 6139 // (EXTERNAL_PREF), and external pref overrides user install (INTERNAL). 6140 // The following assertions verify these assumptions: 6141 ASSERT_EQ(Manifest::EXTERNAL_REGISTRY, 6142 Manifest::GetHigherPriorityLocation(Manifest::EXTERNAL_REGISTRY, 6143 Manifest::EXTERNAL_PREF)); 6144 ASSERT_EQ(Manifest::EXTERNAL_REGISTRY, 6145 Manifest::GetHigherPriorityLocation(Manifest::EXTERNAL_REGISTRY, 6146 Manifest::INTERNAL)); 6147 ASSERT_EQ(Manifest::EXTERNAL_PREF, 6148 Manifest::GetHigherPriorityLocation(Manifest::EXTERNAL_PREF, 6149 Manifest::INTERNAL)); 6150 6151 extensions::PendingExtensionManager* pending = 6152 service()->pending_extension_manager(); 6153 EXPECT_FALSE(pending->IsIdPending(kGoodId)); 6154 6155 { 6156 // Simulate an external source adding the extension as INTERNAL. 6157 content::WindowedNotificationObserver observer( 6158 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 6159 content::NotificationService::AllSources()); 6160 EXPECT_TRUE(service()->OnExternalExtensionFileFound(kGoodId, 6161 &older_version, 6162 kInvalidPathToCrx, 6163 Manifest::INTERNAL, 6164 kCreationFlags, 6165 kDontMarkAcknowledged)); 6166 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6167 observer.Wait(); 6168 VerifyCrxInstall(kInvalidPathToCrx, INSTALL_FAILED); 6169 } 6170 6171 { 6172 // Simulate an external source adding the extension as EXTERNAL_PREF. 6173 content::WindowedNotificationObserver observer( 6174 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 6175 content::NotificationService::AllSources()); 6176 EXPECT_TRUE(service()->OnExternalExtensionFileFound(kGoodId, 6177 &older_version, 6178 kInvalidPathToCrx, 6179 Manifest::EXTERNAL_PREF, 6180 kCreationFlags, 6181 kDontMarkAcknowledged)); 6182 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6183 observer.Wait(); 6184 VerifyCrxInstall(kInvalidPathToCrx, INSTALL_FAILED); 6185 } 6186 6187 // Simulate an external source adding as EXTERNAL_PREF again. 6188 // This is rejected because the version and the location are the same as 6189 // the previous installation, which is still pending. 6190 EXPECT_FALSE(service()->OnExternalExtensionFileFound(kGoodId, 6191 &older_version, 6192 kInvalidPathToCrx, 6193 Manifest::EXTERNAL_PREF, 6194 kCreationFlags, 6195 kDontMarkAcknowledged)); 6196 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6197 6198 // Try INTERNAL again. Should fail. 6199 EXPECT_FALSE(service()->OnExternalExtensionFileFound(kGoodId, 6200 &older_version, 6201 kInvalidPathToCrx, 6202 Manifest::INTERNAL, 6203 kCreationFlags, 6204 kDontMarkAcknowledged)); 6205 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6206 6207 { 6208 // Now the registry adds the extension. 6209 content::WindowedNotificationObserver observer( 6210 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 6211 content::NotificationService::AllSources()); 6212 EXPECT_TRUE( 6213 service()->OnExternalExtensionFileFound(kGoodId, 6214 &older_version, 6215 kInvalidPathToCrx, 6216 Manifest::EXTERNAL_REGISTRY, 6217 kCreationFlags, 6218 kDontMarkAcknowledged)); 6219 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6220 observer.Wait(); 6221 VerifyCrxInstall(kInvalidPathToCrx, INSTALL_FAILED); 6222 } 6223 6224 // Registry outranks both external pref and internal, so both fail. 6225 EXPECT_FALSE(service()->OnExternalExtensionFileFound(kGoodId, 6226 &older_version, 6227 kInvalidPathToCrx, 6228 Manifest::EXTERNAL_PREF, 6229 kCreationFlags, 6230 kDontMarkAcknowledged)); 6231 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6232 6233 EXPECT_FALSE(service()->OnExternalExtensionFileFound(kGoodId, 6234 &older_version, 6235 kInvalidPathToCrx, 6236 Manifest::INTERNAL, 6237 kCreationFlags, 6238 kDontMarkAcknowledged)); 6239 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6240 6241 pending->Remove(kGoodId); 6242 6243 // Install the extension. 6244 base::FilePath path = data_dir().AppendASCII("good.crx"); 6245 const Extension* ext = InstallCRX(path, INSTALL_NEW); 6246 ValidatePrefKeyCount(1u); 6247 ValidateIntegerPref(good_crx, "state", Extension::ENABLED); 6248 ValidateIntegerPref(good_crx, "location", Manifest::INTERNAL); 6249 6250 // Now test the logic of OnExternalExtensionFileFound() when the extension 6251 // being added is already installed. 6252 6253 // Tests assume |older_version| is less than the installed version, and 6254 // |newer_version| is greater. Verify this: 6255 ASSERT_TRUE(older_version.IsOlderThan(ext->VersionString())); 6256 ASSERT_TRUE(ext->version()->IsOlderThan(newer_version.GetString())); 6257 6258 // An external install for the same location should fail if the version is 6259 // older, or the same, and succeed if the version is newer. 6260 6261 // Older than the installed version... 6262 EXPECT_FALSE(service()->OnExternalExtensionFileFound(kGoodId, 6263 &older_version, 6264 kInvalidPathToCrx, 6265 Manifest::INTERNAL, 6266 kCreationFlags, 6267 kDontMarkAcknowledged)); 6268 EXPECT_FALSE(pending->IsIdPending(kGoodId)); 6269 6270 // Same version as the installed version... 6271 EXPECT_FALSE(service()->OnExternalExtensionFileFound(kGoodId, 6272 ext->version(), 6273 kInvalidPathToCrx, 6274 Manifest::INTERNAL, 6275 kCreationFlags, 6276 kDontMarkAcknowledged)); 6277 EXPECT_FALSE(pending->IsIdPending(kGoodId)); 6278 6279 // Newer than the installed version... 6280 EXPECT_TRUE(service()->OnExternalExtensionFileFound(kGoodId, 6281 &newer_version, 6282 kInvalidPathToCrx, 6283 Manifest::INTERNAL, 6284 kCreationFlags, 6285 kDontMarkAcknowledged)); 6286 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6287 6288 // An external install for a higher priority install source should succeed 6289 // if the version is greater. |older_version| is not... 6290 EXPECT_FALSE(service()->OnExternalExtensionFileFound(kGoodId, 6291 &older_version, 6292 kInvalidPathToCrx, 6293 Manifest::EXTERNAL_PREF, 6294 kCreationFlags, 6295 kDontMarkAcknowledged)); 6296 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6297 6298 // |newer_version| is newer. 6299 EXPECT_TRUE(service()->OnExternalExtensionFileFound(kGoodId, 6300 &newer_version, 6301 kInvalidPathToCrx, 6302 Manifest::EXTERNAL_PREF, 6303 kCreationFlags, 6304 kDontMarkAcknowledged)); 6305 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6306 6307 // An external install for an even higher priority install source should 6308 // succeed if the version is greater. 6309 EXPECT_TRUE( 6310 service()->OnExternalExtensionFileFound(kGoodId, 6311 &newer_version, 6312 kInvalidPathToCrx, 6313 Manifest::EXTERNAL_REGISTRY, 6314 kCreationFlags, 6315 kDontMarkAcknowledged)); 6316 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6317 6318 // Because EXTERNAL_PREF is a lower priority source than EXTERNAL_REGISTRY, 6319 // adding from external pref will now fail. 6320 EXPECT_FALSE(service()->OnExternalExtensionFileFound(kGoodId, 6321 &newer_version, 6322 kInvalidPathToCrx, 6323 Manifest::EXTERNAL_PREF, 6324 kCreationFlags, 6325 kDontMarkAcknowledged)); 6326 EXPECT_TRUE(pending->IsIdPending(kGoodId)); 6327 } 6328 6329 TEST_F(ExtensionServiceTest, ConcurrentExternalLocalFile) { 6330 Version kVersion123("1.2.3"); 6331 Version kVersion124("1.2.4"); 6332 Version kVersion125("1.2.5"); 6333 const base::FilePath kInvalidPathToCrx = base::FilePath(); 6334 const int kCreationFlags = 0; 6335 const bool kDontMarkAcknowledged = false; 6336 6337 InitializeEmptyExtensionService(); 6338 6339 extensions::PendingExtensionManager* pending = 6340 service()->pending_extension_manager(); 6341 EXPECT_FALSE(pending->IsIdPending(kGoodId)); 6342 6343 // An external provider starts installing from a local crx. 6344 EXPECT_TRUE(service()->OnExternalExtensionFileFound(kGoodId, 6345 &kVersion123, 6346 kInvalidPathToCrx, 6347 Manifest::EXTERNAL_PREF, 6348 kCreationFlags, 6349 kDontMarkAcknowledged)); 6350 const extensions::PendingExtensionInfo* info; 6351 EXPECT_TRUE((info = pending->GetById(kGoodId))); 6352 EXPECT_TRUE(info->version().IsValid()); 6353 EXPECT_TRUE(info->version().Equals(kVersion123)); 6354 6355 // Adding a newer version overrides the currently pending version. 6356 EXPECT_TRUE(service()->OnExternalExtensionFileFound(kGoodId, 6357 &kVersion124, 6358 kInvalidPathToCrx, 6359 Manifest::EXTERNAL_PREF, 6360 kCreationFlags, 6361 kDontMarkAcknowledged)); 6362 EXPECT_TRUE((info = pending->GetById(kGoodId))); 6363 EXPECT_TRUE(info->version().IsValid()); 6364 EXPECT_TRUE(info->version().Equals(kVersion124)); 6365 6366 // Adding an older version fails. 6367 EXPECT_FALSE(service()->OnExternalExtensionFileFound(kGoodId, 6368 &kVersion123, 6369 kInvalidPathToCrx, 6370 Manifest::EXTERNAL_PREF, 6371 kCreationFlags, 6372 kDontMarkAcknowledged)); 6373 EXPECT_TRUE((info = pending->GetById(kGoodId))); 6374 EXPECT_TRUE(info->version().IsValid()); 6375 EXPECT_TRUE(info->version().Equals(kVersion124)); 6376 6377 // Adding an older version fails even when coming from a higher-priority 6378 // location. 6379 EXPECT_FALSE( 6380 service()->OnExternalExtensionFileFound(kGoodId, 6381 &kVersion123, 6382 kInvalidPathToCrx, 6383 Manifest::EXTERNAL_REGISTRY, 6384 kCreationFlags, 6385 kDontMarkAcknowledged)); 6386 EXPECT_TRUE((info = pending->GetById(kGoodId))); 6387 EXPECT_TRUE(info->version().IsValid()); 6388 EXPECT_TRUE(info->version().Equals(kVersion124)); 6389 6390 // Adding the latest version from the webstore overrides a specific version. 6391 GURL kUpdateUrl("http://example.com/update"); 6392 EXPECT_TRUE(service()->OnExternalExtensionUpdateUrlFound( 6393 kGoodId, 6394 std::string(), 6395 kUpdateUrl, 6396 Manifest::EXTERNAL_POLICY_DOWNLOAD, 6397 Extension::NO_FLAGS, 6398 false)); 6399 EXPECT_TRUE((info = pending->GetById(kGoodId))); 6400 EXPECT_FALSE(info->version().IsValid()); 6401 } 6402 6403 // This makes sure we can package and install CRX files that use whitelisted 6404 // permissions. 6405 TEST_F(ExtensionServiceTest, InstallWhitelistedExtension) { 6406 std::string test_id = "hdkklepkcpckhnpgjnmbdfhehckloojk"; 6407 CommandLine::ForCurrentProcess()->AppendSwitchASCII( 6408 extensions::switches::kWhitelistedExtensionID, test_id); 6409 6410 InitializeEmptyExtensionService(); 6411 base::FilePath path = data_dir().AppendASCII("permissions"); 6412 base::FilePath pem_path = path 6413 .AppendASCII("whitelist.pem"); 6414 path = path 6415 .AppendASCII("whitelist"); 6416 6417 const Extension* extension = PackAndInstallCRX(path, pem_path, INSTALL_NEW); 6418 EXPECT_EQ(0u, GetErrors().size()); 6419 ASSERT_EQ(1u, registry()->enabled_extensions().size()); 6420 EXPECT_EQ(test_id, extension->id()); 6421 } 6422 6423 // Test that when multiple sources try to install an extension, 6424 // we consistently choose the right one. To make tests easy to read, 6425 // methods that fake requests to install crx files in several ways 6426 // are provided. 6427 class ExtensionSourcePriorityTest : public ExtensionServiceTest { 6428 public: 6429 virtual void SetUp() { 6430 ExtensionServiceTest::SetUp(); 6431 6432 // All tests use a single extension. Put the id and path in member vars 6433 // that all methods can read. 6434 crx_id_ = kGoodId; 6435 crx_path_ = data_dir().AppendASCII("good.crx"); 6436 } 6437 6438 // Fake an external source adding a URL to fetch an extension from. 6439 bool AddPendingExternalPrefUrl() { 6440 return service()->pending_extension_manager()->AddFromExternalUpdateUrl( 6441 crx_id_, 6442 std::string(), 6443 GURL(), 6444 Manifest::EXTERNAL_PREF_DOWNLOAD, 6445 Extension::NO_FLAGS, 6446 false); 6447 } 6448 6449 // Fake an external file from external_extensions.json. 6450 bool AddPendingExternalPrefFileInstall() { 6451 Version version("1.0.0.0"); 6452 6453 return service()->OnExternalExtensionFileFound(crx_id_, 6454 &version, 6455 crx_path_, 6456 Manifest::EXTERNAL_PREF, 6457 Extension::NO_FLAGS, 6458 false); 6459 } 6460 6461 // Fake a request from sync to install an extension. 6462 bool AddPendingSyncInstall() { 6463 return service()->pending_extension_manager()->AddFromSync( 6464 crx_id_, 6465 GURL(kGoodUpdateURL), 6466 &IsExtension, 6467 kGoodInstallSilently, 6468 kGoodRemoteInstall); 6469 } 6470 6471 // Fake a policy install. 6472 bool AddPendingPolicyInstall() { 6473 // Get path to the CRX with id |kGoodId|. 6474 return service()->OnExternalExtensionUpdateUrlFound( 6475 crx_id_, 6476 std::string(), 6477 GURL(), 6478 Manifest::EXTERNAL_POLICY_DOWNLOAD, 6479 Extension::NO_FLAGS, 6480 false); 6481 } 6482 6483 // Get the install source of a pending extension. 6484 Manifest::Location GetPendingLocation() { 6485 const extensions::PendingExtensionInfo* info; 6486 EXPECT_TRUE( 6487 (info = service()->pending_extension_manager()->GetById(crx_id_))); 6488 return info->install_source(); 6489 } 6490 6491 // Is an extension pending from a sync request? 6492 bool GetPendingIsFromSync() { 6493 const extensions::PendingExtensionInfo* info; 6494 EXPECT_TRUE( 6495 (info = service()->pending_extension_manager()->GetById(crx_id_))); 6496 return info->is_from_sync(); 6497 } 6498 6499 // Is the CRX id these tests use pending? 6500 bool IsCrxPending() { 6501 return service()->pending_extension_manager()->IsIdPending(crx_id_); 6502 } 6503 6504 // Is an extension installed? 6505 bool IsCrxInstalled() { 6506 return (service()->GetExtensionById(crx_id_, true) != NULL); 6507 } 6508 6509 protected: 6510 // All tests use a single extension. Making the id and path member 6511 // vars avoids pasing the same argument to every method. 6512 std::string crx_id_; 6513 base::FilePath crx_path_; 6514 }; 6515 6516 // Test that a pending request for installation of an external CRX from 6517 // an update URL overrides a pending request to install the same extension 6518 // from sync. 6519 TEST_F(ExtensionSourcePriorityTest, PendingExternalFileOverSync) { 6520 InitializeEmptyExtensionService(); 6521 6522 ASSERT_FALSE(IsCrxInstalled()); 6523 6524 // Install pending extension from sync. 6525 content::WindowedNotificationObserver observer( 6526 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 6527 content::NotificationService::AllSources()); 6528 EXPECT_TRUE(AddPendingSyncInstall()); 6529 ASSERT_EQ(Manifest::INTERNAL, GetPendingLocation()); 6530 EXPECT_TRUE(GetPendingIsFromSync()); 6531 ASSERT_FALSE(IsCrxInstalled()); 6532 6533 // Install pending as external prefs json would. 6534 AddPendingExternalPrefFileInstall(); 6535 ASSERT_EQ(Manifest::EXTERNAL_PREF, GetPendingLocation()); 6536 ASSERT_FALSE(IsCrxInstalled()); 6537 6538 // Another request from sync should be ignored. 6539 EXPECT_FALSE(AddPendingSyncInstall()); 6540 ASSERT_EQ(Manifest::EXTERNAL_PREF, GetPendingLocation()); 6541 ASSERT_FALSE(IsCrxInstalled()); 6542 6543 observer.Wait(); 6544 VerifyCrxInstall(crx_path_, INSTALL_NEW); 6545 ASSERT_TRUE(IsCrxInstalled()); 6546 } 6547 6548 // Test that an install of an external CRX from an update overrides 6549 // an install of the same extension from sync. 6550 TEST_F(ExtensionSourcePriorityTest, PendingExternalUrlOverSync) { 6551 InitializeEmptyExtensionService(); 6552 ASSERT_FALSE(IsCrxInstalled()); 6553 6554 EXPECT_TRUE(AddPendingSyncInstall()); 6555 ASSERT_EQ(Manifest::INTERNAL, GetPendingLocation()); 6556 EXPECT_TRUE(GetPendingIsFromSync()); 6557 ASSERT_FALSE(IsCrxInstalled()); 6558 6559 ASSERT_TRUE(AddPendingExternalPrefUrl()); 6560 ASSERT_EQ(Manifest::EXTERNAL_PREF_DOWNLOAD, GetPendingLocation()); 6561 EXPECT_FALSE(GetPendingIsFromSync()); 6562 ASSERT_FALSE(IsCrxInstalled()); 6563 6564 EXPECT_FALSE(AddPendingSyncInstall()); 6565 ASSERT_EQ(Manifest::EXTERNAL_PREF_DOWNLOAD, GetPendingLocation()); 6566 EXPECT_FALSE(GetPendingIsFromSync()); 6567 ASSERT_FALSE(IsCrxInstalled()); 6568 } 6569 6570 // Test that an external install request stops sync from installing 6571 // the same extension. 6572 TEST_F(ExtensionSourcePriorityTest, InstallExternalBlocksSyncRequest) { 6573 InitializeEmptyExtensionService(); 6574 ASSERT_FALSE(IsCrxInstalled()); 6575 6576 // External prefs starts an install. 6577 AddPendingExternalPrefFileInstall(); 6578 6579 // Crx installer was made, but has not yet run. 6580 ASSERT_FALSE(IsCrxInstalled()); 6581 6582 // Before the CRX installer runs, Sync requests that the same extension 6583 // be installed. Should fail, because an external source is pending. 6584 content::WindowedNotificationObserver observer( 6585 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 6586 content::NotificationService::AllSources()); 6587 ASSERT_FALSE(AddPendingSyncInstall()); 6588 6589 // Wait for the external source to install. 6590 observer.Wait(); 6591 VerifyCrxInstall(crx_path_, INSTALL_NEW); 6592 ASSERT_TRUE(IsCrxInstalled()); 6593 6594 // Now that the extension is installed, sync request should fail 6595 // because the extension is already installed. 6596 ASSERT_FALSE(AddPendingSyncInstall()); 6597 } 6598 6599 // Test that installing an external extension displays a GlobalError. 6600 TEST_F(ExtensionServiceTest, ExternalInstallGlobalError) { 6601 FeatureSwitch::ScopedOverride prompt( 6602 FeatureSwitch::prompt_for_external_extensions(), true); 6603 6604 InitializeEmptyExtensionService(); 6605 MockExtensionProvider* provider = 6606 new MockExtensionProvider(service(), Manifest::EXTERNAL_PREF); 6607 AddMockExternalProvider(provider); 6608 6609 service()->UpdateExternalExtensionAlert(); 6610 // Should return false, meaning there aren't any extensions that the user 6611 // needs to know about. 6612 EXPECT_FALSE(extensions::HasExternalInstallError(service())); 6613 6614 // This is a normal extension, installed normally. 6615 // This should NOT trigger an alert. 6616 service()->set_extensions_enabled(true); 6617 base::FilePath path = data_dir().AppendASCII("good.crx"); 6618 InstallCRX(path, INSTALL_NEW); 6619 6620 service()->CheckForExternalUpdates(); 6621 base::RunLoop().RunUntilIdle(); 6622 EXPECT_FALSE(extensions::HasExternalInstallError(service())); 6623 6624 // A hosted app, installed externally. 6625 // This should NOT trigger an alert. 6626 provider->UpdateOrAddExtension( 6627 hosted_app, "1.0.0.0", data_dir().AppendASCII("hosted_app.crx")); 6628 6629 content::WindowedNotificationObserver observer( 6630 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 6631 content::NotificationService::AllSources()); 6632 service()->CheckForExternalUpdates(); 6633 observer.Wait(); 6634 EXPECT_FALSE(extensions::HasExternalInstallError(service())); 6635 6636 // Another normal extension, but installed externally. 6637 // This SHOULD trigger an alert. 6638 provider->UpdateOrAddExtension( 6639 page_action, "1.0.0.0", data_dir().AppendASCII("page_action.crx")); 6640 6641 content::WindowedNotificationObserver observer2( 6642 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 6643 content::NotificationService::AllSources()); 6644 service()->CheckForExternalUpdates(); 6645 observer2.Wait(); 6646 EXPECT_TRUE(extensions::HasExternalInstallError(service())); 6647 } 6648 6649 // Test that external extensions are initially disabled, and that enabling 6650 // them clears the prompt. 6651 TEST_F(ExtensionServiceTest, ExternalInstallInitiallyDisabled) { 6652 FeatureSwitch::ScopedOverride prompt( 6653 FeatureSwitch::prompt_for_external_extensions(), true); 6654 6655 InitializeEmptyExtensionService(); 6656 MockExtensionProvider* provider = 6657 new MockExtensionProvider(service(), Manifest::EXTERNAL_PREF); 6658 AddMockExternalProvider(provider); 6659 6660 provider->UpdateOrAddExtension( 6661 page_action, "1.0.0.0", data_dir().AppendASCII("page_action.crx")); 6662 6663 content::WindowedNotificationObserver observer( 6664 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 6665 content::NotificationService::AllSources()); 6666 service()->CheckForExternalUpdates(); 6667 observer.Wait(); 6668 EXPECT_TRUE(extensions::HasExternalInstallError(service())); 6669 EXPECT_FALSE(service()->IsExtensionEnabled(page_action)); 6670 6671 const Extension* extension = 6672 registry()->disabled_extensions().GetByID(page_action); 6673 EXPECT_TRUE(extension); 6674 EXPECT_EQ(page_action, extension->id()); 6675 6676 service()->EnableExtension(page_action); 6677 EXPECT_FALSE(extensions::HasExternalInstallError(service())); 6678 EXPECT_TRUE(service()->IsExtensionEnabled(page_action)); 6679 } 6680 6681 // Test that installing multiple external extensions works. 6682 // Flaky on windows; http://crbug.com/295757 . 6683 #if defined(OS_WIN) 6684 #define MAYBE_ExternalInstallMultiple DISABLED_ExternalInstallMultiple 6685 #else 6686 #define MAYBE_ExternalInstallMultiple ExternalInstallMultiple 6687 #endif 6688 TEST_F(ExtensionServiceTest, MAYBE_ExternalInstallMultiple) { 6689 FeatureSwitch::ScopedOverride prompt( 6690 FeatureSwitch::prompt_for_external_extensions(), true); 6691 6692 InitializeEmptyExtensionService(); 6693 MockExtensionProvider* provider = 6694 new MockExtensionProvider(service(), Manifest::EXTERNAL_PREF); 6695 AddMockExternalProvider(provider); 6696 6697 provider->UpdateOrAddExtension( 6698 page_action, "1.0.0.0", data_dir().AppendASCII("page_action.crx")); 6699 provider->UpdateOrAddExtension( 6700 good_crx, "1.0.0.0", data_dir().AppendASCII("good.crx")); 6701 provider->UpdateOrAddExtension( 6702 theme_crx, "2.0", data_dir().AppendASCII("theme.crx")); 6703 6704 int count = 3; 6705 content::WindowedNotificationObserver observer( 6706 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 6707 base::Bind(&WaitForCountNotificationsCallback, &count)); 6708 service()->CheckForExternalUpdates(); 6709 observer.Wait(); 6710 EXPECT_TRUE(extensions::HasExternalInstallError(service())); 6711 EXPECT_FALSE(service()->IsExtensionEnabled(page_action)); 6712 EXPECT_FALSE(service()->IsExtensionEnabled(good_crx)); 6713 EXPECT_FALSE(service()->IsExtensionEnabled(theme_crx)); 6714 6715 service()->EnableExtension(page_action); 6716 EXPECT_TRUE(extensions::HasExternalInstallError(service())); 6717 EXPECT_FALSE(extensions::HasExternalInstallBubble(service())); 6718 service()->EnableExtension(theme_crx); 6719 EXPECT_TRUE(extensions::HasExternalInstallError(service())); 6720 EXPECT_FALSE(extensions::HasExternalInstallBubble(service())); 6721 service()->EnableExtension(good_crx); 6722 EXPECT_FALSE(extensions::HasExternalInstallError(service())); 6723 EXPECT_FALSE(extensions::HasExternalInstallBubble(service())); 6724 } 6725 6726 // Test that there is a bubble for external extensions that update 6727 // from the webstore if the profile is not new. 6728 TEST_F(ExtensionServiceTest, ExternalInstallUpdatesFromWebstoreOldProfile) { 6729 FeatureSwitch::ScopedOverride prompt( 6730 FeatureSwitch::prompt_for_external_extensions(), true); 6731 6732 // This sets up the ExtensionPrefs used by our ExtensionService to be 6733 // post-first run. 6734 ExtensionServiceInitParams params = CreateDefaultInitParams(); 6735 params.is_first_run = false; 6736 InitializeExtensionService(params); 6737 6738 base::FilePath crx_path = temp_dir().path().AppendASCII("webstore.crx"); 6739 PackCRX(data_dir().AppendASCII("update_from_webstore"), 6740 data_dir().AppendASCII("update_from_webstore.pem"), 6741 crx_path); 6742 6743 MockExtensionProvider* provider = 6744 new MockExtensionProvider(service(), Manifest::EXTERNAL_PREF); 6745 AddMockExternalProvider(provider); 6746 provider->UpdateOrAddExtension(updates_from_webstore, "1", crx_path); 6747 6748 content::WindowedNotificationObserver observer( 6749 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 6750 content::NotificationService::AllSources()); 6751 service()->CheckForExternalUpdates(); 6752 observer.Wait(); 6753 EXPECT_TRUE(extensions::HasExternalInstallError(service())); 6754 EXPECT_TRUE(extensions::HasExternalInstallBubble(service())); 6755 EXPECT_FALSE(service()->IsExtensionEnabled(updates_from_webstore)); 6756 } 6757 6758 // Test that there is no bubble for external extensions if the profile is new. 6759 TEST_F(ExtensionServiceTest, ExternalInstallUpdatesFromWebstoreNewProfile) { 6760 FeatureSwitch::ScopedOverride prompt( 6761 FeatureSwitch::prompt_for_external_extensions(), true); 6762 6763 InitializeEmptyExtensionService(); 6764 6765 base::FilePath crx_path = temp_dir().path().AppendASCII("webstore.crx"); 6766 PackCRX(data_dir().AppendASCII("update_from_webstore"), 6767 data_dir().AppendASCII("update_from_webstore.pem"), 6768 crx_path); 6769 6770 MockExtensionProvider* provider = 6771 new MockExtensionProvider(service(), Manifest::EXTERNAL_PREF); 6772 AddMockExternalProvider(provider); 6773 provider->UpdateOrAddExtension(updates_from_webstore, "1", crx_path); 6774 6775 content::WindowedNotificationObserver observer( 6776 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 6777 content::NotificationService::AllSources()); 6778 service()->CheckForExternalUpdates(); 6779 observer.Wait(); 6780 EXPECT_TRUE(extensions::HasExternalInstallError(service())); 6781 EXPECT_FALSE(extensions::HasExternalInstallBubble(service())); 6782 EXPECT_FALSE(service()->IsExtensionEnabled(updates_from_webstore)); 6783 } 6784 6785 TEST_F(ExtensionServiceTest, InstallBlacklistedExtension) { 6786 InitializeEmptyExtensionService(); 6787 6788 scoped_refptr<Extension> extension = extensions::ExtensionBuilder() 6789 .SetManifest(extensions::DictionaryBuilder() 6790 .Set("name", "extension") 6791 .Set("version", "1.0") 6792 .Set("manifest_version", 2).Build()) 6793 .Build(); 6794 ASSERT_TRUE(extension.get()); 6795 const std::string& id = extension->id(); 6796 6797 std::set<std::string> id_set; 6798 id_set.insert(id); 6799 extensions::ExtensionNotificationObserver notifications( 6800 content::NotificationService::AllSources(), id_set); 6801 6802 // Installation should be allowed but the extension should never have been 6803 // loaded and it should be blacklisted in prefs. 6804 service()->OnExtensionInstalled( 6805 extension.get(), 6806 syncer::StringOrdinal(), 6807 (extensions::kInstallFlagIsBlacklistedForMalware | 6808 extensions::kInstallFlagInstallImmediately)); 6809 base::RunLoop().RunUntilIdle(); 6810 6811 // Extension was installed but not loaded. 6812 EXPECT_TRUE(notifications.CheckNotifications( 6813 chrome::NOTIFICATION_EXTENSION_INSTALLED_DEPRECATED)); 6814 EXPECT_TRUE(service()->GetInstalledExtension(id)); 6815 6816 EXPECT_FALSE(registry()->enabled_extensions().Contains(id)); 6817 EXPECT_TRUE(registry()->blacklisted_extensions().Contains(id)); 6818 6819 EXPECT_TRUE(ExtensionPrefs::Get(profile())->IsExtensionBlacklisted(id)); 6820 EXPECT_TRUE( 6821 ExtensionPrefs::Get(profile())->IsBlacklistedExtensionAcknowledged(id)); 6822 } 6823 6824 TEST_F(ExtensionServiceTest, ReconcileKnownDisabledNoneDisabled) { 6825 // A profile with 3 extensions installed: good0, good1, and good2. 6826 InitializeGoodInstalledExtensionService(); 6827 6828 // Initializing shouldn't disable any extensions if none are known to be 6829 // disabled. 6830 service()->Init(); 6831 6832 extensions::ExtensionIdSet expected_extensions; 6833 expected_extensions.insert(good0); 6834 expected_extensions.insert(good1); 6835 expected_extensions.insert(good2); 6836 6837 extensions::ExtensionIdSet expected_disabled_extensions; 6838 6839 EXPECT_EQ(expected_extensions, registry()->enabled_extensions().GetIDs()); 6840 EXPECT_EQ(expected_disabled_extensions, 6841 registry()->disabled_extensions().GetIDs()); 6842 } 6843 6844 TEST_F(ExtensionServiceTest, ReconcileKnownDisabledWithSideEnable) { 6845 // A profile with 3 extensions installed: good0, good1, and good2. 6846 InitializeGoodInstalledExtensionService(); 6847 6848 ExtensionPrefs* extension_prefs = ExtensionPrefs::Get(profile()); 6849 6850 // Disable good1. 6851 extension_prefs->SetExtensionState(good1, Extension::DISABLED); 6852 6853 // Mark both good1 and good2 as "known_disabled" (effectively making good2 6854 // look as if it had been side-enabled). 6855 extensions::ExtensionIdSet known_disabled; 6856 known_disabled.insert(good1); 6857 known_disabled.insert(good2); 6858 extension_prefs->SetKnownDisabled(known_disabled); 6859 6860 // Initialize the service (which should disable good2 since it's known to be 6861 // disabled). 6862 service()->Init(); 6863 6864 extensions::ExtensionIdSet expected_extensions; 6865 expected_extensions.insert(good0); 6866 6867 extensions::ExtensionIdSet expected_disabled_extensions; 6868 expected_disabled_extensions.insert(good1); 6869 expected_disabled_extensions.insert(good2); 6870 6871 EXPECT_EQ(expected_extensions, registry()->enabled_extensions().GetIDs()); 6872 EXPECT_EQ(expected_disabled_extensions, 6873 registry()->disabled_extensions().GetIDs()); 6874 6875 // Make sure that re-enabling an extension sticks across calls to 6876 // ReconcileKnownDisabled(). 6877 service()->EnableExtension(good2); 6878 service()->ReconcileKnownDisabled(); 6879 expected_extensions.insert(good2); 6880 expected_disabled_extensions.erase(good2); 6881 6882 EXPECT_EQ(expected_extensions, registry()->enabled_extensions().GetIDs()); 6883 EXPECT_EQ(expected_disabled_extensions, 6884 registry()->disabled_extensions().GetIDs()); 6885 } 6886 6887 // Tests a profile being destroyed correctly disables extensions. 6888 TEST_F(ExtensionServiceTest, DestroyingProfileClearsExtensions) { 6889 InitializeEmptyExtensionService(); 6890 6891 InstallCRX(data_dir().AppendASCII("good.crx"), INSTALL_NEW); 6892 EXPECT_NE(UnloadedExtensionInfo::REASON_PROFILE_SHUTDOWN, unloaded_reason_); 6893 EXPECT_EQ(1u, registry()->enabled_extensions().size()); 6894 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 6895 EXPECT_EQ(0u, registry()->terminated_extensions().size()); 6896 EXPECT_EQ(0u, registry()->blacklisted_extensions().size()); 6897 6898 service()->Observe(chrome::NOTIFICATION_PROFILE_DESTRUCTION_STARTED, 6899 content::Source<Profile>(profile()), 6900 content::NotificationService::NoDetails()); 6901 EXPECT_EQ(UnloadedExtensionInfo::REASON_PROFILE_SHUTDOWN, unloaded_reason_); 6902 EXPECT_EQ(0u, registry()->enabled_extensions().size()); 6903 EXPECT_EQ(0u, registry()->disabled_extensions().size()); 6904 EXPECT_EQ(0u, registry()->terminated_extensions().size()); 6905 EXPECT_EQ(0u, registry()->blacklisted_extensions().size()); 6906 } 6907