| // Copyright (c) 2013 The Chromium Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| #include "chrome/browser/profile_resetter/profile_resetter.h" |
| |
| #include "base/json/json_string_value_serializer.h" |
| #include "base/prefs/pref_service.h" |
| #include "base/strings/utf_string_conversions.h" |
| #include "chrome/browser/content_settings/host_content_settings_map.h" |
| #include "chrome/browser/extensions/extension_service_unittest.h" |
| #include "chrome/browser/extensions/tab_helper.h" |
| #include "chrome/browser/notifications/desktop_notification_service.h" |
| #include "chrome/browser/notifications/desktop_notification_service_factory.h" |
| #include "chrome/browser/prefs/session_startup_pref.h" |
| #include "chrome/browser/profile_resetter/brandcode_config_fetcher.h" |
| #include "chrome/browser/profile_resetter/profile_resetter_test_base.h" |
| #include "chrome/browser/profile_resetter/resettable_settings_snapshot.h" |
| #include "chrome/browser/search_engines/template_url_service.h" |
| #include "chrome/browser/search_engines/template_url_service_factory.h" |
| #include "chrome/browser/themes/theme_service.h" |
| #include "chrome/browser/themes/theme_service_factory.h" |
| #include "chrome/browser/ui/tabs/tab_strip_model.h" |
| #include "chrome/common/extensions/extension.h" |
| #include "chrome/common/pref_names.h" |
| #include "chrome/test/base/browser_with_test_window_test.h" |
| #include "content/public/browser/web_contents.h" |
| #include "content/public/test/test_browser_thread.h" |
| #include "extensions/common/manifest_constants.h" |
| #include "net/http/http_response_headers.h" |
| #include "net/url_request/test_url_fetcher_factory.h" |
| |
| |
| namespace { |
| |
| const char kDistributionConfig[] = "{" |
| " \"homepage\" : \"http://www.foo.com\"," |
| " \"homepage_is_newtabpage\" : false," |
| " \"browser\" : {" |
| " \"show_home_button\" : true" |
| " }," |
| " \"session\" : {" |
| " \"restore_on_startup\" : 4," |
| " \"urls_to_restore_on_startup\" : [\"http://goo.gl\", \"http://foo.de\"]" |
| " }," |
| " \"search_provider_overrides\" : [" |
| " {" |
| " \"name\" : \"first\"," |
| " \"keyword\" : \"firstkey\"," |
| " \"search_url\" : \"http://www.foo.com/s?q={searchTerms}\"," |
| " \"favicon_url\" : \"http://www.foo.com/favicon.ico\"," |
| " \"suggest_url\" : \"http://www.foo.com/s?q={searchTerms}\"," |
| " \"encoding\" : \"UTF-8\"," |
| " \"id\" : 1001" |
| " }" |
| " ]," |
| " \"extensions\" : {" |
| " \"settings\" : {" |
| " \"placeholder_for_id\": {" |
| " }" |
| " }" |
| " }" |
| "}"; |
| |
| const char kXmlConfig[] = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>" |
| "<response protocol=\"3.0\" server=\"prod\">" |
| "<app appid=\"{8A69D345-D564-463C-AFF1-A69D9E530F96}\" status=\"ok\">" |
| "<data index=\"skipfirstrunui-importsearch-defaultbrowser\" " |
| "name=\"install\" status=\"ok\">" |
| "placeholder_for_data" |
| "</data>" |
| "</app>" |
| "</response>"; |
| |
| using extensions::Extension; |
| using extensions::Manifest; |
| |
| |
| // ProfileResetterTest -------------------------------------------------------- |
| |
| // ProfileResetterTest sets up the extension, WebData and TemplateURL services. |
| class ProfileResetterTest : public ExtensionServiceTestBase, |
| public ProfileResetterTestBase { |
| protected: |
| virtual void SetUp() OVERRIDE; |
| |
| TestingProfile* profile() { return profile_.get(); } |
| |
| static BrowserContextKeyedService* CreateTemplateURLService( |
| content::BrowserContext* context); |
| }; |
| |
| void ProfileResetterTest::SetUp() { |
| ExtensionServiceTestBase::SetUp(); |
| InitializeEmptyExtensionService(); |
| |
| profile()->CreateWebDataService(); |
| TemplateURLServiceFactory::GetInstance()->SetTestingFactory( |
| profile(), |
| &ProfileResetterTest::CreateTemplateURLService); |
| resetter_.reset(new ProfileResetter(profile())); |
| } |
| |
| // static |
| BrowserContextKeyedService* ProfileResetterTest::CreateTemplateURLService( |
| content::BrowserContext* context) { |
| return new TemplateURLService(static_cast<Profile*>(context)); |
| } |
| |
| |
| // PinnedTabsResetTest -------------------------------------------------------- |
| |
| class PinnedTabsResetTest : public BrowserWithTestWindowTest, |
| public ProfileResetterTestBase { |
| protected: |
| virtual void SetUp() OVERRIDE; |
| |
| content::WebContents* CreateWebContents(); |
| }; |
| |
| void PinnedTabsResetTest::SetUp() { |
| BrowserWithTestWindowTest::SetUp(); |
| resetter_.reset(new ProfileResetter(profile())); |
| } |
| |
| content::WebContents* PinnedTabsResetTest::CreateWebContents() { |
| return content::WebContents::Create( |
| content::WebContents::CreateParams(profile())); |
| } |
| |
| |
| // ConfigParserTest ----------------------------------------------------------- |
| |
| // URLFetcher delegate that simply records the upload data. |
| struct URLFetcherRequestListener : net::URLFetcherDelegate { |
| URLFetcherRequestListener(); |
| virtual ~URLFetcherRequestListener(); |
| |
| virtual void OnURLFetchComplete(const net::URLFetcher* source) OVERRIDE; |
| |
| std::string upload_data; |
| net::URLFetcherDelegate* real_delegate; |
| }; |
| |
| URLFetcherRequestListener::URLFetcherRequestListener() |
| : real_delegate(NULL) { |
| } |
| |
| URLFetcherRequestListener::~URLFetcherRequestListener() { |
| } |
| |
| void URLFetcherRequestListener::OnURLFetchComplete( |
| const net::URLFetcher* source) { |
| const net::TestURLFetcher* test_fetcher = |
| static_cast<const net::TestURLFetcher*>(source); |
| upload_data = test_fetcher->upload_data(); |
| DCHECK(real_delegate); |
| real_delegate->OnURLFetchComplete(source); |
| } |
| |
| class ConfigParserTest : public testing::Test { |
| protected: |
| ConfigParserTest(); |
| virtual ~ConfigParserTest(); |
| |
| scoped_ptr<BrandcodeConfigFetcher> WaitForRequest(const GURL& url); |
| |
| net::FakeURLFetcherFactory& factory() { return factory_; } |
| |
| private: |
| scoped_ptr<net::FakeURLFetcher> CreateFakeURLFetcher( |
| const GURL& url, |
| net::URLFetcherDelegate* fetcher_delegate, |
| const std::string& response_data, |
| bool success); |
| |
| MOCK_METHOD0(Callback, void(void)); |
| |
| base::MessageLoop loop_; |
| content::TestBrowserThread ui_thread_; |
| content::TestBrowserThread io_thread_; |
| URLFetcherRequestListener request_listener_; |
| net::FakeURLFetcherFactory factory_; |
| }; |
| |
| ConfigParserTest::ConfigParserTest() |
| : loop_(base::MessageLoop::TYPE_IO), |
| ui_thread_(content::BrowserThread::UI, &loop_), |
| io_thread_(content::BrowserThread::IO, &loop_), |
| factory_(NULL, base::Bind(&ConfigParserTest::CreateFakeURLFetcher, |
| base::Unretained(this))) { |
| } |
| |
| ConfigParserTest::~ConfigParserTest() {} |
| |
| scoped_ptr<BrandcodeConfigFetcher> ConfigParserTest::WaitForRequest( |
| const GURL& url) { |
| EXPECT_CALL(*this, Callback()); |
| scoped_ptr<BrandcodeConfigFetcher> fetcher( |
| new BrandcodeConfigFetcher(base::Bind(&ConfigParserTest::Callback, |
| base::Unretained(this)), |
| url, |
| "ABCD")); |
| base::MessageLoop::current()->RunUntilIdle(); |
| EXPECT_FALSE(fetcher->IsActive()); |
| // Look for the brand code in the request. |
| EXPECT_NE(std::string::npos, request_listener_.upload_data.find("ABCD")); |
| return fetcher.Pass(); |
| } |
| |
| scoped_ptr<net::FakeURLFetcher> ConfigParserTest::CreateFakeURLFetcher( |
| const GURL& url, |
| net::URLFetcherDelegate* fetcher_delegate, |
| const std::string& response_data, |
| bool success) { |
| request_listener_.real_delegate = fetcher_delegate; |
| scoped_ptr<net::FakeURLFetcher> fetcher( |
| new net::FakeURLFetcher(url, &request_listener_, response_data, success)); |
| scoped_refptr<net::HttpResponseHeaders> download_headers = |
| new net::HttpResponseHeaders(""); |
| download_headers->AddHeader("Content-Type: text/xml"); |
| fetcher->set_response_headers(download_headers); |
| return fetcher.Pass(); |
| } |
| |
| |
| // helper functions ----------------------------------------------------------- |
| |
| scoped_refptr<Extension> CreateExtension(const std::string& name, |
| const base::FilePath& path, |
| Manifest::Location location, |
| extensions::Manifest::Type type, |
| bool installed_by_default) { |
| DictionaryValue manifest; |
| manifest.SetString(extensions::manifest_keys::kVersion, "1.0.0.0"); |
| manifest.SetString(extensions::manifest_keys::kName, name); |
| switch (type) { |
| case extensions::Manifest::TYPE_THEME: |
| manifest.Set(extensions::manifest_keys::kTheme, new DictionaryValue); |
| break; |
| case extensions::Manifest::TYPE_HOSTED_APP: |
| manifest.SetString(extensions::manifest_keys::kLaunchWebURL, |
| "http://www.google.com"); |
| manifest.SetString(extensions::manifest_keys::kUpdateURL, |
| "http://clients2.google.com/service/update2/crx"); |
| break; |
| case extensions::Manifest::TYPE_EXTENSION: |
| // do nothing |
| break; |
| default: |
| NOTREACHED(); |
| } |
| manifest.SetString(extensions::manifest_keys::kOmniboxKeyword, name); |
| std::string error; |
| scoped_refptr<Extension> extension = Extension::Create( |
| path, |
| location, |
| manifest, |
| installed_by_default ? Extension::WAS_INSTALLED_BY_DEFAULT |
| : Extension::NO_FLAGS, |
| &error); |
| EXPECT_TRUE(extension.get() != NULL) << error; |
| return extension; |
| } |
| |
| void ReplaceString(std::string* str, |
| const std::string& placeholder, |
| const std::string& substitution) { |
| ASSERT_NE(static_cast<std::string*>(NULL), str); |
| size_t placeholder_pos = str->find(placeholder); |
| ASSERT_NE(std::string::npos, placeholder_pos); |
| str->replace(placeholder_pos, placeholder.size(), substitution); |
| } |
| |
| |
| /********************* Tests *********************/ |
| |
| TEST_F(ProfileResetterTest, ResetDefaultSearchEngine) { |
| // Search engine's logic is tested by |
| // TemplateURLServiceTest.ResetURLs. |
| PrefService* prefs = profile()->GetPrefs(); |
| DCHECK(prefs); |
| prefs->SetString(prefs::kLastPromptedGoogleURL, "http://www.foo.com/"); |
| |
| scoped_refptr<Extension> extension = CreateExtension( |
| "xxx", |
| base::FilePath(FILE_PATH_LITERAL("//nonexistent")), |
| Manifest::COMPONENT, |
| extensions::Manifest::TYPE_EXTENSION, |
| false); |
| service_->AddExtension(extension.get()); |
| |
| ResetAndWait(ProfileResetter::DEFAULT_SEARCH_ENGINE); |
| |
| // TemplateURLService should reset extension search engines. |
| TemplateURLService* model = |
| TemplateURLServiceFactory::GetForProfile(profile()); |
| TemplateURL* ext_url = model->GetTemplateURLForKeyword(ASCIIToUTF16("xxx")); |
| ASSERT_TRUE(ext_url); |
| EXPECT_TRUE(ext_url->IsExtensionKeyword()); |
| EXPECT_EQ(ASCIIToUTF16("xxx"), ext_url->keyword()); |
| EXPECT_EQ(ASCIIToUTF16("xxx"), ext_url->short_name()); |
| EXPECT_EQ("", prefs->GetString(prefs::kLastPromptedGoogleURL)); |
| } |
| |
| TEST_F(ProfileResetterTest, ResetDefaultSearchEngineNonOrganic) { |
| PrefService* prefs = profile()->GetPrefs(); |
| DCHECK(prefs); |
| prefs->SetString(prefs::kLastPromptedGoogleURL, "http://www.foo.com/"); |
| |
| ResetAndWait(ProfileResetter::DEFAULT_SEARCH_ENGINE, kDistributionConfig); |
| |
| TemplateURLService* model = |
| TemplateURLServiceFactory::GetForProfile(profile()); |
| EXPECT_EQ(1u, model->GetTemplateURLs().size()); |
| TemplateURL* default_engine = model->GetDefaultSearchProvider(); |
| ASSERT_NE(static_cast<TemplateURL*>(NULL), default_engine); |
| EXPECT_EQ(ASCIIToUTF16("first"), default_engine->short_name()); |
| EXPECT_EQ(ASCIIToUTF16("firstkey"), default_engine->keyword()); |
| EXPECT_EQ("http://www.foo.com/s?q={searchTerms}", default_engine->url()); |
| |
| EXPECT_EQ("", prefs->GetString(prefs::kLastPromptedGoogleURL)); |
| } |
| |
| TEST_F(ProfileResetterTest, ResetHomepage) { |
| PrefService* prefs = profile()->GetPrefs(); |
| DCHECK(prefs); |
| prefs->SetBoolean(prefs::kHomePageIsNewTabPage, false); |
| prefs->SetString(prefs::kHomePage, "http://google.com"); |
| prefs->SetBoolean(prefs::kShowHomeButton, true); |
| |
| ResetAndWait(ProfileResetter::HOMEPAGE); |
| |
| EXPECT_TRUE(prefs->GetBoolean(prefs::kHomePageIsNewTabPage)); |
| EXPECT_EQ(std::string(), prefs->GetString(prefs::kHomePage)); |
| EXPECT_FALSE(prefs->GetBoolean(prefs::kShowHomeButton)); |
| } |
| |
| TEST_F(ProfileResetterTest, ResetHomepageNonOrganic) { |
| PrefService* prefs = profile()->GetPrefs(); |
| DCHECK(prefs); |
| prefs->SetBoolean(prefs::kHomePageIsNewTabPage, true); |
| prefs->SetString(prefs::kHomePage, "http://google.com"); |
| prefs->SetBoolean(prefs::kShowHomeButton, false); |
| |
| ResetAndWait(ProfileResetter::HOMEPAGE, kDistributionConfig); |
| |
| EXPECT_FALSE(prefs->GetBoolean(prefs::kHomePageIsNewTabPage)); |
| EXPECT_EQ("http://www.foo.com", prefs->GetString(prefs::kHomePage)); |
| EXPECT_TRUE(prefs->GetBoolean(prefs::kShowHomeButton)); |
| } |
| |
| TEST_F(ProfileResetterTest, ResetContentSettings) { |
| HostContentSettingsMap* host_content_settings_map = |
| profile()->GetHostContentSettingsMap(); |
| DesktopNotificationService* notification_service = |
| DesktopNotificationServiceFactory::GetForProfile(profile()); |
| ContentSettingsPattern pattern = |
| ContentSettingsPattern::FromString("[*.]example.org"); |
| std::map<ContentSettingsType, ContentSetting> default_settings; |
| |
| for (int type = 0; type < CONTENT_SETTINGS_NUM_TYPES; ++type) { |
| if (type == CONTENT_SETTINGS_TYPE_NOTIFICATIONS) { |
| notification_service->SetDefaultContentSetting(CONTENT_SETTING_BLOCK); |
| notification_service->GrantPermission(GURL("http://foo.de")); |
| } else if (type == CONTENT_SETTINGS_TYPE_AUTO_SELECT_CERTIFICATE || |
| type == CONTENT_SETTINGS_TYPE_MIXEDSCRIPT || |
| type == CONTENT_SETTINGS_TYPE_PROTOCOL_HANDLERS) { |
| // These types are excluded because one can't call |
| // GetDefaultContentSetting() for them. |
| } else { |
| ContentSettingsType content_type = static_cast<ContentSettingsType>(type); |
| ContentSetting default_setting = |
| host_content_settings_map->GetDefaultContentSetting(content_type, |
| NULL); |
| default_settings[content_type] = default_setting; |
| ContentSetting wildcard_setting = |
| default_setting == CONTENT_SETTING_BLOCK ? CONTENT_SETTING_ALLOW |
| : CONTENT_SETTING_BLOCK; |
| ContentSetting site_setting = |
| default_setting == CONTENT_SETTING_ALLOW ? CONTENT_SETTING_ALLOW |
| : CONTENT_SETTING_BLOCK; |
| if (HostContentSettingsMap::IsSettingAllowedForType( |
| profile()->GetPrefs(), |
| wildcard_setting, |
| content_type)) { |
| host_content_settings_map->SetDefaultContentSetting( |
| content_type, |
| wildcard_setting); |
| } |
| if (!HostContentSettingsMap::ContentTypeHasCompoundValue(content_type) && |
| HostContentSettingsMap::IsSettingAllowedForType( |
| profile()->GetPrefs(), |
| site_setting, |
| content_type)) { |
| host_content_settings_map->SetContentSetting( |
| pattern, |
| ContentSettingsPattern::Wildcard(), |
| content_type, |
| std::string(), |
| site_setting); |
| ContentSettingsForOneType host_settings; |
| host_content_settings_map->GetSettingsForOneType( |
| content_type, std::string(), &host_settings); |
| EXPECT_EQ(2U, host_settings.size()); |
| } |
| } |
| } |
| |
| ResetAndWait(ProfileResetter::CONTENT_SETTINGS); |
| |
| for (int type = 0; type < CONTENT_SETTINGS_NUM_TYPES; ++type) { |
| if (type == CONTENT_SETTINGS_TYPE_NOTIFICATIONS) { |
| EXPECT_EQ(CONTENT_SETTING_ASK, |
| notification_service->GetDefaultContentSetting(NULL)); |
| EXPECT_EQ(CONTENT_SETTING_ASK, |
| notification_service->GetContentSetting(GURL("http://foo.de"))); |
| } else { |
| ContentSettingsType content_type = static_cast<ContentSettingsType>(type); |
| if (HostContentSettingsMap::ContentTypeHasCompoundValue(content_type) || |
| type == CONTENT_SETTINGS_TYPE_AUTO_SELECT_CERTIFICATE || |
| content_type == CONTENT_SETTINGS_TYPE_MIXEDSCRIPT || |
| content_type == CONTENT_SETTINGS_TYPE_PROTOCOL_HANDLERS) |
| continue; |
| ContentSetting default_setting = |
| host_content_settings_map->GetDefaultContentSetting(content_type, |
| NULL); |
| EXPECT_TRUE(default_settings.count(content_type)); |
| EXPECT_EQ(default_settings[content_type], default_setting); |
| if (!HostContentSettingsMap::ContentTypeHasCompoundValue(content_type)) { |
| ContentSetting site_setting = |
| host_content_settings_map->GetContentSetting( |
| GURL("example.org"), |
| GURL(), |
| content_type, |
| std::string()); |
| EXPECT_EQ(default_setting, site_setting); |
| } |
| |
| ContentSettingsForOneType host_settings; |
| host_content_settings_map->GetSettingsForOneType( |
| content_type, std::string(), &host_settings); |
| EXPECT_EQ(1U, host_settings.size()); |
| } |
| } |
| } |
| |
| TEST_F(ProfileResetterTest, ResetExtensionsByDisabling) { |
| service_->Init(); |
| |
| base::ScopedTempDir temp_dir; |
| ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); |
| |
| scoped_refptr<Extension> theme = |
| CreateExtension("example1", |
| temp_dir.path(), |
| Manifest::INVALID_LOCATION, |
| extensions::Manifest::TYPE_THEME, |
| false); |
| service_->FinishInstallationForTest(theme.get()); |
| // Let ThemeService finish creating the theme pack. |
| base::MessageLoop::current()->RunUntilIdle(); |
| |
| ThemeService* theme_service = |
| ThemeServiceFactory::GetForProfile(profile()); |
| EXPECT_FALSE(theme_service->UsingDefaultTheme()); |
| |
| scoped_refptr<Extension> ext2 = CreateExtension( |
| "example2", |
| base::FilePath(FILE_PATH_LITERAL("//nonexistent")), |
| Manifest::INVALID_LOCATION, |
| extensions::Manifest::TYPE_EXTENSION, |
| false); |
| service_->AddExtension(ext2.get()); |
| // Components and external policy extensions shouldn't be deleted. |
| scoped_refptr<Extension> ext3 = CreateExtension( |
| "example3", |
| base::FilePath(FILE_PATH_LITERAL("//nonexistent2")), |
| Manifest::COMPONENT, |
| extensions::Manifest::TYPE_EXTENSION, |
| false); |
| service_->AddExtension(ext3.get()); |
| scoped_refptr<Extension> ext4 = |
| CreateExtension("example4", |
| base::FilePath(FILE_PATH_LITERAL("//nonexistent3")), |
| Manifest::EXTERNAL_POLICY_DOWNLOAD, |
| extensions::Manifest::TYPE_EXTENSION, |
| false); |
| service_->AddExtension(ext4.get()); |
| EXPECT_EQ(4u, service_->extensions()->size()); |
| |
| ResetAndWait(ProfileResetter::EXTENSIONS); |
| EXPECT_EQ(2u, service_->extensions()->size()); |
| EXPECT_FALSE(service_->extensions()->Contains(theme->id())); |
| EXPECT_FALSE(service_->extensions()->Contains(ext2->id())); |
| EXPECT_TRUE(service_->extensions()->Contains(ext3->id())); |
| EXPECT_TRUE(service_->extensions()->Contains(ext4->id())); |
| EXPECT_TRUE(theme_service->UsingDefaultTheme()); |
| } |
| |
| TEST_F(ProfileResetterTest, ResetExtensionsByDisablingNonOrganic) { |
| scoped_refptr<Extension> ext2 = CreateExtension( |
| "example2", |
| base::FilePath(FILE_PATH_LITERAL("//nonexistent")), |
| Manifest::INVALID_LOCATION, |
| extensions::Manifest::TYPE_EXTENSION, |
| false); |
| service_->AddExtension(ext2.get()); |
| // Components and external policy extensions shouldn't be deleted. |
| scoped_refptr<Extension> ext3 = CreateExtension( |
| "example3", |
| base::FilePath(FILE_PATH_LITERAL("//nonexistent2")), |
| Manifest::INVALID_LOCATION, |
| extensions::Manifest::TYPE_EXTENSION, |
| false); |
| service_->AddExtension(ext3.get()); |
| EXPECT_EQ(2u, service_->extensions()->size()); |
| |
| std::string master_prefs(kDistributionConfig); |
| ReplaceString(&master_prefs, "placeholder_for_id", ext3->id()); |
| |
| ResetAndWait(ProfileResetter::EXTENSIONS, master_prefs); |
| |
| EXPECT_EQ(1u, service_->extensions()->size()); |
| EXPECT_TRUE(service_->extensions()->Contains(ext3->id())); |
| } |
| |
| TEST_F(ProfileResetterTest, ResetExtensionsAndDefaultApps) { |
| service_->Init(); |
| |
| base::ScopedTempDir temp_dir; |
| ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); |
| |
| scoped_refptr<Extension> ext1 = |
| CreateExtension("example1", |
| temp_dir.path(), |
| Manifest::INVALID_LOCATION, |
| extensions::Manifest::TYPE_THEME, |
| false); |
| service_->FinishInstallationForTest(ext1.get()); |
| // Let ThemeService finish creating the theme pack. |
| base::MessageLoop::current()->RunUntilIdle(); |
| |
| ThemeService* theme_service = |
| ThemeServiceFactory::GetForProfile(profile()); |
| EXPECT_FALSE(theme_service->UsingDefaultTheme()); |
| |
| scoped_refptr<Extension> ext2 = |
| CreateExtension("example2", |
| base::FilePath(FILE_PATH_LITERAL("//nonexistent2")), |
| Manifest::INVALID_LOCATION, |
| extensions::Manifest::TYPE_EXTENSION, |
| false); |
| service_->AddExtension(ext2.get()); |
| |
| scoped_refptr<Extension> ext3 = |
| CreateExtension("example2", |
| base::FilePath(FILE_PATH_LITERAL("//nonexistent3")), |
| Manifest::INVALID_LOCATION, |
| extensions::Manifest::TYPE_HOSTED_APP, |
| true); |
| service_->AddExtension(ext3.get()); |
| EXPECT_EQ(3u, service_->extensions()->size()); |
| |
| ResetAndWait(ProfileResetter::EXTENSIONS); |
| |
| EXPECT_EQ(1u, service_->extensions()->size()); |
| EXPECT_FALSE(service_->extensions()->Contains(ext1->id())); |
| EXPECT_FALSE(service_->extensions()->Contains(ext2->id())); |
| EXPECT_TRUE(service_->extensions()->Contains(ext3->id())); |
| EXPECT_TRUE(theme_service->UsingDefaultTheme()); |
| } |
| |
| TEST_F(ProfileResetterTest, ResetStartPage) { |
| PrefService* prefs = profile()->GetPrefs(); |
| DCHECK(prefs); |
| |
| SessionStartupPref startup_pref(SessionStartupPref::URLS); |
| startup_pref.urls.push_back(GURL("http://foo")); |
| startup_pref.urls.push_back(GURL("http://bar")); |
| SessionStartupPref::SetStartupPref(prefs, startup_pref); |
| |
| ResetAndWait(ProfileResetter::STARTUP_PAGES); |
| |
| startup_pref = SessionStartupPref::GetStartupPref(prefs); |
| EXPECT_EQ(SessionStartupPref::GetDefaultStartupType(), startup_pref.type); |
| EXPECT_EQ(std::vector<GURL>(), startup_pref.urls); |
| } |
| |
| TEST_F(ProfileResetterTest, ResetStartPageNonOrganic) { |
| PrefService* prefs = profile()->GetPrefs(); |
| DCHECK(prefs); |
| |
| SessionStartupPref startup_pref(SessionStartupPref::LAST); |
| SessionStartupPref::SetStartupPref(prefs, startup_pref); |
| |
| ResetAndWait(ProfileResetter::STARTUP_PAGES, kDistributionConfig); |
| |
| startup_pref = SessionStartupPref::GetStartupPref(prefs); |
| EXPECT_EQ(SessionStartupPref::URLS, startup_pref.type); |
| const GURL urls[] = {GURL("http://goo.gl"), GURL("http://foo.de")}; |
| EXPECT_EQ(std::vector<GURL>(urls, urls + arraysize(urls)), startup_pref.urls); |
| } |
| |
| TEST_F(PinnedTabsResetTest, ResetPinnedTabs) { |
| scoped_refptr<Extension> extension_app = CreateExtension( |
| "hello!", |
| base::FilePath(FILE_PATH_LITERAL("//nonexistent")), |
| Manifest::INVALID_LOCATION, |
| extensions::Manifest::TYPE_HOSTED_APP, |
| false); |
| scoped_ptr<content::WebContents> contents1(CreateWebContents()); |
| extensions::TabHelper::CreateForWebContents(contents1.get()); |
| extensions::TabHelper::FromWebContents(contents1.get())-> |
| SetExtensionApp(extension_app.get()); |
| scoped_ptr<content::WebContents> contents2(CreateWebContents()); |
| scoped_ptr<content::WebContents> contents3(CreateWebContents()); |
| scoped_ptr<content::WebContents> contents4(CreateWebContents()); |
| TabStripModel* tab_strip_model = browser()->tab_strip_model(); |
| |
| tab_strip_model->AppendWebContents(contents4.get(), true); |
| tab_strip_model->AppendWebContents(contents3.get(), true); |
| tab_strip_model->AppendWebContents(contents2.get(), true); |
| tab_strip_model->SetTabPinned(2, true); |
| tab_strip_model->AppendWebContents(contents1.get(), true); |
| tab_strip_model->SetTabPinned(3, true); |
| |
| EXPECT_EQ(contents2, tab_strip_model->GetWebContentsAt(0)); |
| EXPECT_EQ(contents1, tab_strip_model->GetWebContentsAt(1)); |
| EXPECT_EQ(contents3, tab_strip_model->GetWebContentsAt(2)); |
| EXPECT_EQ(contents4, tab_strip_model->GetWebContentsAt(3)); |
| EXPECT_EQ(3, tab_strip_model->IndexOfFirstNonMiniTab()); |
| |
| ResetAndWait(ProfileResetter::PINNED_TABS); |
| |
| EXPECT_EQ(contents1, tab_strip_model->GetWebContentsAt(0)); |
| EXPECT_EQ(contents2, tab_strip_model->GetWebContentsAt(1)); |
| EXPECT_EQ(contents3, tab_strip_model->GetWebContentsAt(2)); |
| EXPECT_EQ(contents4, tab_strip_model->GetWebContentsAt(3)); |
| EXPECT_EQ(1, tab_strip_model->IndexOfFirstNonMiniTab()); |
| } |
| |
| TEST_F(ProfileResetterTest, ResetFewFlags) { |
| // mock_object_ is a StrictMock, so we verify that it is called only once. |
| ResetAndWait(ProfileResetter::DEFAULT_SEARCH_ENGINE | |
| ProfileResetter::HOMEPAGE | |
| ProfileResetter::CONTENT_SETTINGS); |
| } |
| |
| // Tries to load unavailable config file. |
| TEST_F(ConfigParserTest, NoConnectivity) { |
| const std::string url("http://test"); |
| factory().SetFakeResponse(url, "", false); |
| |
| scoped_ptr<BrandcodeConfigFetcher> fetcher = WaitForRequest(GURL(url)); |
| EXPECT_FALSE(fetcher->GetSettings()); |
| } |
| |
| // Tries to load available config file. |
| TEST_F(ConfigParserTest, ParseConfig) { |
| const std::string url("http://test"); |
| std::string xml_config(kXmlConfig); |
| ReplaceString(&xml_config, "placeholder_for_data", kDistributionConfig); |
| ReplaceString(&xml_config, |
| "placeholder_for_id", |
| "abbaabbaabbaabbaabbaabbaabbaabba"); |
| factory().SetFakeResponse(url, xml_config, true); |
| |
| scoped_ptr<BrandcodeConfigFetcher> fetcher = WaitForRequest(GURL(url)); |
| scoped_ptr<BrandcodedDefaultSettings> settings = fetcher->GetSettings(); |
| ASSERT_TRUE(settings); |
| |
| std::vector<std::string> extension_ids; |
| EXPECT_TRUE(settings->GetExtensions(&extension_ids)); |
| EXPECT_EQ(1u, extension_ids.size()); |
| EXPECT_EQ("abbaabbaabbaabbaabbaabbaabbaabba", extension_ids[0]); |
| |
| std::string homepage; |
| EXPECT_TRUE(settings->GetHomepage(&homepage)); |
| EXPECT_EQ("http://www.foo.com", homepage); |
| |
| scoped_ptr<base::ListValue> startup_list( |
| settings->GetUrlsToRestoreOnStartup()); |
| EXPECT_TRUE(startup_list); |
| std::vector<std::string> startup_pages; |
| for (base::ListValue::iterator i = startup_list->begin(); |
| i != startup_list->end(); ++i) { |
| std::string url; |
| EXPECT_TRUE((*i)->GetAsString(&url)); |
| startup_pages.push_back(url); |
| } |
| ASSERT_EQ(2u, startup_pages.size()); |
| EXPECT_EQ("http://goo.gl", startup_pages[0]); |
| EXPECT_EQ("http://foo.de", startup_pages[1]); |
| } |
| |
| TEST_F(ProfileResetterTest, CheckSnapshots) { |
| ResettableSettingsSnapshot empty_snap(profile()); |
| EXPECT_EQ(0, empty_snap.FindDifferentFields(empty_snap)); |
| |
| scoped_refptr<Extension> ext = CreateExtension( |
| "example", |
| base::FilePath(FILE_PATH_LITERAL("//nonexistent")), |
| Manifest::INVALID_LOCATION, |
| extensions::Manifest::TYPE_EXTENSION, |
| false); |
| ASSERT_TRUE(ext); |
| service_->AddExtension(ext.get()); |
| |
| std::string master_prefs(kDistributionConfig); |
| std::string ext_id = ext->id(); |
| ReplaceString(&master_prefs, "placeholder_for_id", ext_id); |
| |
| // Reset to non organic defaults. |
| ResetAndWait(ProfileResetter::DEFAULT_SEARCH_ENGINE | |
| ProfileResetter::HOMEPAGE | |
| ProfileResetter::STARTUP_PAGES, master_prefs); |
| |
| ResettableSettingsSnapshot nonorganic_snap(profile()); |
| EXPECT_EQ(ResettableSettingsSnapshot::ALL_FIELDS, |
| empty_snap.FindDifferentFields(nonorganic_snap)); |
| empty_snap.Subtract(nonorganic_snap); |
| EXPECT_TRUE(empty_snap.startup_urls().empty()); |
| EXPECT_EQ(SessionStartupPref::GetDefaultStartupType(), |
| empty_snap.startup_type()); |
| EXPECT_TRUE(empty_snap.homepage().empty()); |
| EXPECT_TRUE(empty_snap.homepage_is_ntp()); |
| EXPECT_NE(std::string::npos, empty_snap.dse_url().find("{google:baseURL}")); |
| EXPECT_EQ(ResettableSettingsSnapshot::ExtensionList(), |
| empty_snap.enabled_extensions()); |
| |
| // Reset to organic defaults. |
| ResetAndWait(ProfileResetter::DEFAULT_SEARCH_ENGINE | |
| ProfileResetter::HOMEPAGE | |
| ProfileResetter::STARTUP_PAGES | |
| ProfileResetter::EXTENSIONS); |
| |
| ResettableSettingsSnapshot organic_snap(profile()); |
| EXPECT_EQ(ResettableSettingsSnapshot::ALL_FIELDS, |
| nonorganic_snap.FindDifferentFields(organic_snap)); |
| nonorganic_snap.Subtract(organic_snap); |
| const GURL urls[] = {GURL("http://foo.de"), GURL("http://goo.gl")}; |
| EXPECT_EQ(std::vector<GURL>(urls, urls + arraysize(urls)), |
| nonorganic_snap.startup_urls()); |
| EXPECT_EQ(SessionStartupPref::URLS, nonorganic_snap.startup_type()); |
| EXPECT_EQ("http://www.foo.com", nonorganic_snap.homepage()); |
| EXPECT_FALSE(nonorganic_snap.homepage_is_ntp()); |
| EXPECT_EQ("http://www.foo.com/s?q={searchTerms}", nonorganic_snap.dse_url()); |
| EXPECT_EQ(ResettableSettingsSnapshot::ExtensionList( |
| 1, std::make_pair(ext_id, "example")), |
| nonorganic_snap.enabled_extensions()); |
| } |
| |
| TEST_F(ProfileResetterTest, FeedbackSerializtionTest) { |
| // Reset to non organic defaults. |
| ResetAndWait(ProfileResetter::DEFAULT_SEARCH_ENGINE | |
| ProfileResetter::HOMEPAGE | |
| ProfileResetter::STARTUP_PAGES, kDistributionConfig); |
| |
| scoped_refptr<Extension> ext = CreateExtension( |
| "example", |
| base::FilePath(FILE_PATH_LITERAL("//nonexistent")), |
| Manifest::INVALID_LOCATION, |
| extensions::Manifest::TYPE_EXTENSION, |
| false); |
| ASSERT_TRUE(ext); |
| service_->AddExtension(ext.get()); |
| |
| const ResettableSettingsSnapshot nonorganic_snap(profile()); |
| |
| COMPILE_ASSERT(ResettableSettingsSnapshot::ALL_FIELDS == 63, |
| expand_this_test); |
| for (int field_mask = 0; field_mask <= ResettableSettingsSnapshot::ALL_FIELDS; |
| ++field_mask) { |
| std::string report = SerializeSettingsReport(nonorganic_snap, field_mask); |
| JSONStringValueSerializer json(report); |
| std::string error; |
| scoped_ptr<base::Value> root(json.Deserialize(NULL, &error)); |
| ASSERT_TRUE(root) << error; |
| ASSERT_TRUE(root->IsType(base::Value::TYPE_DICTIONARY)) << error; |
| |
| base::DictionaryValue* dict = |
| static_cast<base::DictionaryValue*>(root.get()); |
| |
| ListValue* startup_urls = NULL; |
| int startup_type = 0; |
| std::string homepage; |
| bool homepage_is_ntp = true; |
| std::string default_search_engine; |
| ListValue* extensions; |
| |
| EXPECT_EQ(!!(field_mask & ResettableSettingsSnapshot::STARTUP_URLS), |
| dict->GetList("startup_urls", &startup_urls)); |
| EXPECT_EQ(!!(field_mask & ResettableSettingsSnapshot::STARTUP_TYPE), |
| dict->GetInteger("startup_type", &startup_type)); |
| EXPECT_EQ(!!(field_mask & ResettableSettingsSnapshot::HOMEPAGE), |
| dict->GetString("homepage", &homepage)); |
| EXPECT_EQ(!!(field_mask & ResettableSettingsSnapshot::HOMEPAGE_IS_NTP), |
| dict->GetBoolean("homepage_is_ntp", &homepage_is_ntp)); |
| EXPECT_EQ(!!(field_mask & ResettableSettingsSnapshot::DSE_URL), |
| dict->GetString("default_search_engine", &default_search_engine)); |
| EXPECT_EQ(!!(field_mask & ResettableSettingsSnapshot::EXTENSIONS), |
| dict->GetList("enabled_extensions", &extensions)); |
| } |
| } |
| |
| } // namespace |