diff options
author | treib <treib@chromium.org> | 2015-05-20 05:56:07 -0700 |
---|---|---|
committer | Commit bot <commit-bot@chromium.org> | 2015-05-20 12:56:03 +0000 |
commit | c11923254ee7e930b2cd3431d94a6937982906f9 (patch) | |
tree | 8f36f6fc40434cbdb109cf78a53a41d3638eeacb | |
parent | ef99191240af78a81c19f34cf39c5097208246b7 (diff) | |
download | chromium_src-c11923254ee7e930b2cd3431d94a6937982906f9.zip chromium_src-c11923254ee7e930b2cd3431d94a6937982906f9.tar.gz chromium_src-c11923254ee7e930b2cd3431d94a6937982906f9.tar.bz2 |
Extensions: Store disable reasons in Sync
This will allow us (in a follow-up CL) to *not* grant permissions to extensions that come in via Sync disabled due to a permission increase.
BUG=484214
Review URL: https://codereview.chromium.org/1136543003
Cr-Commit-Position: refs/heads/master@{#330727}
17 files changed, 241 insertions, 89 deletions
diff --git a/chrome/browser/apps/ephemeral_app_browsertest.cc b/chrome/browser/apps/ephemeral_app_browsertest.cc index 2804632..07e01b5 100644 --- a/chrome/browser/apps/ephemeral_app_browsertest.cc +++ b/chrome/browser/apps/ephemeral_app_browsertest.cc @@ -483,10 +483,12 @@ class EphemeralAppBrowserTest : public EphemeralAppTestBase { ASSERT_TRUE(app); // Simulate an install from sync. + int disable_reasons = enable_from_sync ? 0 : Extension::DISABLE_USER_ACTION; const syncer::StringOrdinal kAppLaunchOrdinal("x"); const syncer::StringOrdinal kPageOrdinal("y"); AppSyncData app_sync_data(*app, enable_from_sync, + disable_reasons, false /* incognito enabled */, false /* remote install */, extensions::ExtensionSyncData::BOOLEAN_UNSET, diff --git a/chrome/browser/extensions/app_sync_data.cc b/chrome/browser/extensions/app_sync_data.cc index d49eb4e..6f231ba 100644 --- a/chrome/browser/extensions/app_sync_data.cc +++ b/chrome/browser/extensions/app_sync_data.cc @@ -24,6 +24,7 @@ AppSyncData::AppSyncData() {} AppSyncData::AppSyncData(const Extension& extension, bool enabled, + int disable_reasons, bool incognito_enabled, bool remote_install, ExtensionSyncData::OptionalBoolean all_urls_enabled, @@ -32,6 +33,7 @@ AppSyncData::AppSyncData(const Extension& extension, extensions::LaunchType launch_type) : extension_sync_data_(extension, enabled, + disable_reasons, incognito_enabled, remote_install, all_urls_enabled), diff --git a/chrome/browser/extensions/app_sync_data.h b/chrome/browser/extensions/app_sync_data.h index bbb8123..4d19060 100644 --- a/chrome/browser/extensions/app_sync_data.h +++ b/chrome/browser/extensions/app_sync_data.h @@ -39,6 +39,7 @@ class AppSyncData { AppSyncData(); AppSyncData(const Extension& extension, bool enabled, + int disable_reasons, bool incognito_enabled, bool remote_install, ExtensionSyncData::OptionalBoolean all_urls_enabled, diff --git a/chrome/browser/extensions/app_sync_data_unittest.cc b/chrome/browser/extensions/app_sync_data_unittest.cc index 5b90621..ca4e7ef 100644 --- a/chrome/browser/extensions/app_sync_data_unittest.cc +++ b/chrome/browser/extensions/app_sync_data_unittest.cc @@ -27,6 +27,7 @@ class AppSyncDataTest : public testing::Test { extension_specifics->set_update_url(kValidUpdateUrl); extension_specifics->set_version(kValidVersion); extension_specifics->set_enabled(false); + extension_specifics->set_disable_reasons(0); extension_specifics->set_incognito_enabled(true); extension_specifics->set_remote_install(false); extension_specifics->set_all_urls_enabled(true); diff --git a/chrome/browser/extensions/extension_service.cc b/chrome/browser/extensions/extension_service.cc index c18d612..c066fd0 100644 --- a/chrome/browser/extensions/extension_service.cc +++ b/chrome/browser/extensions/extension_service.cc @@ -867,14 +867,13 @@ void ExtensionService::EnableExtension(const std::string& extension_id) { extension_sync_service_->SyncEnableExtension(*extension); } -void ExtensionService::DisableExtension( - const std::string& extension_id, - Extension::DisableReason disable_reason) { +void ExtensionService::DisableExtension(const std::string& extension_id, + int disable_reasons) { CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); // The extension may have been disabled already. Just add a disable reason. if (!IsExtensionEnabled(extension_id)) { - extension_prefs_->AddDisableReason(extension_id, disable_reason); + extension_prefs_->AddDisableReasons(extension_id, disable_reasons); return; } @@ -885,15 +884,15 @@ void ExtensionService::DisableExtension( // can be uninstalled by the browser if the user sets extension-specific // preferences. if (extension && - disable_reason != Extension::DISABLE_RELOAD && - disable_reason != Extension::DISABLE_UPDATE_REQUIRED_BY_POLICY && + !(disable_reasons & Extension::DISABLE_RELOAD) && + !(disable_reasons & Extension::DISABLE_UPDATE_REQUIRED_BY_POLICY) && !system_->management_policy()->UserMayModifySettings(extension, NULL) && extension->location() != Manifest::EXTERNAL_COMPONENT) { return; } extension_prefs_->SetExtensionState(extension_id, Extension::DISABLED); - extension_prefs_->AddDisableReason(extension_id, disable_reason); + extension_prefs_->AddDisableReasons(extension_id, disable_reasons); int include_mask = ExtensionRegistry::EVERYTHING & ~ExtensionRegistry::DISABLED; diff --git a/chrome/browser/extensions/extension_service.h b/chrome/browser/extensions/extension_service.h index 04d0f4e..0b97b1a 100644 --- a/chrome/browser/extensions/extension_service.h +++ b/chrome/browser/extensions/extension_service.h @@ -279,11 +279,12 @@ class ExtensionService // nothing. virtual void EnableExtension(const std::string& extension_id); - // Disables the extension. If the extension is already disabled, or - // cannot be disabled, does nothing. - virtual void DisableExtension( - const std::string& extension_id, - extensions::Extension::DisableReason disable_reason); + // Disables the extension. If the extension is already disabled, just adds + // the |disable_reasons| (a bitmask of Extension::DisableReason - there can + // be multiple DisableReasons e.g. when an extension comes in disabled from + // Sync). If the extension cannot be disabled (due to policy), does nothing. + virtual void DisableExtension(const std::string& extension_id, + int disable_reasons); // Disable non-default and non-managed extensions with ids not in // |except_ids|. Default extensions are those from the Web Store with diff --git a/chrome/browser/extensions/extension_service_unittest.cc b/chrome/browser/extensions/extension_service_unittest.cc index 308af80..7d8042d 100644 --- a/chrome/browser/extensions/extension_service_unittest.cc +++ b/chrome/browser/extensions/extension_service_unittest.cc @@ -924,12 +924,17 @@ class ExtensionServiceTest : public extensions::ExtensionServiceTestBase, } void UninstallExtension(const std::string& id, bool use_helper) { + UninstallExtension(id, use_helper, Extension::ENABLED); + } + + void UninstallExtension(const std::string& id, bool use_helper, + Extension::State expected_state) { // Verify that the extension is installed. base::FilePath extension_path = extensions_install_dir().AppendASCII(id); EXPECT_TRUE(base::PathExists(extension_path)); size_t pref_key_count = GetPrefKeyCount(); EXPECT_GT(pref_key_count, 0u); - ValidateIntegerPref(id, "state", Extension::ENABLED); + ValidateIntegerPref(id, "state", expected_state); // Uninstall it. if (use_helper) { @@ -5909,10 +5914,11 @@ TEST_F(ExtensionServiceTest, DisableExtensionFromSync) { const Extension* extension = service()->GetExtensionById(good0, true); ASSERT_TRUE(extension); ASSERT_TRUE(service()->IsExtensionEnabled(good0)); - ExtensionSyncData disable_good_crx(*extension, false, false, false, - ExtensionSyncData::BOOLEAN_UNSET); // Then sync data arrives telling us to disable |good0|. + ExtensionSyncData disable_good_crx(*extension, false, + Extension::DISABLE_USER_ACTION, false, + false, ExtensionSyncData::BOOLEAN_UNSET); syncer::SyncDataList sync_data; sync_data.push_back(disable_good_crx.GetSyncData()); extension_sync_service()->MergeDataAndStartSyncing( @@ -5956,8 +5962,9 @@ TEST_F(ExtensionServiceTest, DontDisableExtensionWithPendingEnableFromSync) { // Now sync data comes in that says to disable good0. This should be // ignored. - ExtensionSyncData disable_good_crx(*extension, false, false, false, - ExtensionSyncData::BOOLEAN_FALSE); + ExtensionSyncData disable_good_crx(*extension, false, + Extension::DISABLE_USER_ACTION, false, + false, ExtensionSyncData::BOOLEAN_UNSET); syncer::SyncDataList sync_data; sync_data.push_back(disable_good_crx.GetSyncData()); extension_sync_service()->MergeDataAndStartSyncing( @@ -6514,6 +6521,101 @@ TEST_F(ExtensionServiceTest, ProcessSyncDataSettings) { EXPECT_FALSE(service()->pending_extension_manager()->IsIdPending(good_crx)); } +TEST_F(ExtensionServiceTest, ProcessSyncDataNewExtension) { + InitializeEmptyExtensionService(); + InitializeExtensionSyncService(); + syncer::FakeSyncChangeProcessor processor; + extension_sync_service()->MergeDataAndStartSyncing( + syncer::EXTENSIONS, + syncer::SyncDataList(), + scoped_ptr<syncer::SyncChangeProcessor>( + new syncer::FakeSyncChangeProcessor), + scoped_ptr<syncer::SyncErrorFactory>(new syncer::SyncErrorFactoryMock())); + + sync_pb::EntitySpecifics specifics; + sync_pb::ExtensionSpecifics* ext_specifics = specifics.mutable_extension(); + ext_specifics->set_id(good_crx); + ext_specifics->set_version(base::Version("1").GetString()); + + const base::FilePath path = data_dir().AppendASCII("good.crx"); + const ExtensionPrefs* prefs = ExtensionPrefs::Get(profile()); + + { + ext_specifics->set_enabled(true); + ext_specifics->set_disable_reasons(0); + + syncer::SyncData sync_data = + syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); + syncer::SyncChange sync_change(FROM_HERE, + syncer::SyncChange::ACTION_UPDATE, + sync_data); + syncer::SyncChangeList list(1); + list[0] = sync_change; + extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); + + ASSERT_TRUE(service()->pending_extension_manager()->IsIdPending(good_crx)); + UpdateExtension(good_crx, path, ENABLED); + EXPECT_EQ(0, prefs->GetDisableReasons(good_crx)); + // Permissions should have been granted during installation. + scoped_refptr<PermissionSet> permissions( + prefs->GetGrantedPermissions(good_crx)); + EXPECT_FALSE(permissions->IsEmpty()); + ASSERT_FALSE(service()->pending_extension_manager()->IsIdPending(good_crx)); + } + UninstallExtension(good_crx, false); + { + ext_specifics->set_enabled(false); + ext_specifics->set_disable_reasons(Extension::DISABLE_USER_ACTION); + + syncer::SyncData sync_data = + syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); + syncer::SyncChange sync_change(FROM_HERE, + syncer::SyncChange::ACTION_UPDATE, + sync_data); + syncer::SyncChangeList list(1); + list[0] = sync_change; + extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); + + ASSERT_TRUE(service()->pending_extension_manager()->IsIdPending(good_crx)); + UpdateExtension(good_crx, path, DISABLED); + EXPECT_EQ(Extension::DISABLE_USER_ACTION, + prefs->GetDisableReasons(good_crx)); + // Even if the extension came in disabled, its permissions should have been + // granted (the user already approved them on another machine). + scoped_refptr<PermissionSet> permissions( + prefs->GetGrantedPermissions(good_crx)); + EXPECT_FALSE(permissions->IsEmpty()); + ASSERT_FALSE(service()->pending_extension_manager()->IsIdPending(good_crx)); + } + UninstallExtension(good_crx, false, Extension::DISABLED); + { + ext_specifics->set_enabled(false); + // Legacy case (<M45): No disable reasons come in from Sync (see + // crbug.com/484214). After installation, the reason should be set to + // DISABLE_UNKNOWN_FROM_SYNC. + ext_specifics->set_disable_reasons(0); + + syncer::SyncData sync_data = + syncer::SyncData::CreateLocalData(good_crx, "Name", specifics); + syncer::SyncChange sync_change(FROM_HERE, + syncer::SyncChange::ACTION_UPDATE, + sync_data); + syncer::SyncChangeList list(1); + list[0] = sync_change; + extension_sync_service()->ProcessSyncChanges(FROM_HERE, list); + + ASSERT_TRUE(service()->pending_extension_manager()->IsIdPending(good_crx)); + UpdateExtension(good_crx, path, DISABLED); + EXPECT_EQ(Extension::DISABLE_UNKNOWN_FROM_SYNC, + prefs->GetDisableReasons(good_crx)); + scoped_refptr<PermissionSet> permissions( + prefs->GetGrantedPermissions(good_crx)); + EXPECT_FALSE(permissions->IsEmpty()); + ASSERT_FALSE(service()->pending_extension_manager()->IsIdPending(good_crx)); + } + UninstallExtension(good_crx, false, Extension::DISABLED); +} + TEST_F(ExtensionServiceTest, ProcessSyncDataTerminatedExtension) { InitializeExtensionServiceWithUpdater(); InitializeExtensionSyncService(); diff --git a/chrome/browser/extensions/extension_sync_data.cc b/chrome/browser/extensions/extension_sync_data.cc index aa56051..6914bc1 100644 --- a/chrome/browser/extensions/extension_sync_data.cc +++ b/chrome/browser/extensions/extension_sync_data.cc @@ -55,6 +55,7 @@ void RecordBadSyncData(BadSyncDataReason reason) { ExtensionSyncData::ExtensionSyncData() : uninstalled_(false), enabled_(false), + disable_reasons_(Extension::DISABLE_NONE), incognito_enabled_(false), remote_install_(false), all_urls_enabled_(BOOLEAN_UNSET), @@ -63,12 +64,14 @@ ExtensionSyncData::ExtensionSyncData() ExtensionSyncData::ExtensionSyncData(const Extension& extension, bool enabled, + int disable_reasons, bool incognito_enabled, bool remote_install, OptionalBoolean all_urls_enabled) : id_(extension.id()), uninstalled_(false), enabled_(enabled), + disable_reasons_(disable_reasons), incognito_enabled_(incognito_enabled), remote_install_(remote_install), all_urls_enabled_(all_urls_enabled), @@ -122,6 +125,7 @@ void ExtensionSyncData::PopulateExtensionSpecifics( specifics->set_update_url(update_url_.spec()); specifics->set_version(version_.GetString()); specifics->set_enabled(enabled_); + specifics->set_disable_reasons(disable_reasons_); specifics->set_incognito_enabled(incognito_enabled_); specifics->set_remote_install(remote_install_); if (all_urls_enabled_ != BOOLEAN_UNSET) @@ -160,6 +164,7 @@ bool ExtensionSyncData::PopulateFromExtensionSpecifics( update_url_ = specifics_update_url; version_ = specifics_version; enabled_ = specifics.enabled(); + disable_reasons_ = specifics.disable_reasons(); incognito_enabled_ = specifics.incognito_enabled(); if (specifics.has_all_urls_enabled()) { all_urls_enabled_ = diff --git a/chrome/browser/extensions/extension_sync_data.h b/chrome/browser/extensions/extension_sync_data.h index 5808b6b..5a94eab 100644 --- a/chrome/browser/extensions/extension_sync_data.h +++ b/chrome/browser/extensions/extension_sync_data.h @@ -36,6 +36,7 @@ class ExtensionSyncData { ExtensionSyncData(); ExtensionSyncData(const Extension& extension, bool enabled, + int disable_reasons, bool incognito_enabled, bool remote_install, OptionalBoolean all_urls_enabled); @@ -69,13 +70,14 @@ class ExtensionSyncData { // |version|). bool uninstalled() const { return uninstalled_; } bool enabled() const { return enabled_; } + int disable_reasons() const { return disable_reasons_; } bool incognito_enabled() const { return incognito_enabled_; } bool remote_install() const { return remote_install_; } OptionalBoolean all_urls_enabled() const { return all_urls_enabled_; } bool installed_by_custodian() const { return installed_by_custodian_; } // Version-dependent properties (i.e., should be used only when the - // version of the currenty-installed extension matches |version|). + // version of the currently-installed extension matches |version|). const Version& version() const { return version_; } const GURL& update_url() const { return update_url_; } // Used only for debugging. @@ -88,6 +90,7 @@ class ExtensionSyncData { std::string id_; bool uninstalled_; bool enabled_; + int disable_reasons_; bool incognito_enabled_; bool remote_install_; OptionalBoolean all_urls_enabled_; diff --git a/chrome/browser/extensions/extension_sync_service.cc b/chrome/browser/extensions/extension_sync_service.cc index 9a8fddb..12769c6 100644 --- a/chrome/browser/extensions/extension_sync_service.cc +++ b/chrome/browser/extensions/extension_sync_service.cc @@ -283,6 +283,7 @@ ExtensionSyncData ExtensionSyncService::GetExtensionSyncData( return ExtensionSyncData( extension, extension_service_->IsExtensionEnabled(extension.id()), + extension_prefs_->GetDisableReasons(extension.id()), extensions::util::IsIncognitoEnabled(extension.id(), profile_), extension_prefs_->HasDisableReason(extension.id(), Extension::DISABLE_REMOTE_INSTALL), @@ -293,6 +294,7 @@ AppSyncData ExtensionSyncService::GetAppSyncData( const Extension& extension) const { return AppSyncData( extension, extension_service_->IsExtensionEnabled(extension.id()), + extension_prefs_->GetDisableReasons(extension.id()), extensions::util::IsIncognitoEnabled(extension.id(), profile_), extension_prefs_->HasDisableReason(extension.id(), Extension::DISABLE_REMOTE_INSTALL), @@ -516,13 +518,22 @@ bool ExtensionSyncService::ProcessExtensionSyncDataHelper( if (extension_sync_data.enabled()) { extension_service_->EnableExtension(id); } else if (!IsPendingEnable(id)) { + int disable_reasons = extension_sync_data.disable_reasons(); if (extension_sync_data.remote_install()) { - extension_service_->DisableExtension(id, - Extension::DISABLE_REMOTE_INSTALL); - } else { - extension_service_->DisableExtension( - id, Extension::DISABLE_UNKNOWN_FROM_SYNC); + // In the non-legacy case (>=M45) where disable reasons are synced at all, + // DISABLE_REMOTE_INSTALL should be among them already. + DCHECK(!disable_reasons || + (disable_reasons & Extension::DISABLE_REMOTE_INSTALL)); + disable_reasons |= Extension::DISABLE_REMOTE_INSTALL; } + if (!disable_reasons) { + // Legacy case (<M45), from before we synced disable reasons (see + // crbug.com/484214). + disable_reasons = Extension::DISABLE_UNKNOWN_FROM_SYNC; + } + + extension_service_->DisableExtension( + id, Extension::DisableReason(disable_reasons)); } // We need to cache some version information here because setting the diff --git a/chrome/browser/sync/test/integration/sync_extension_helper.cc b/chrome/browser/sync/test/integration/sync_extension_helper.cc index a041671..d51c5a9 100644 --- a/chrome/browser/sync/test/integration/sync_extension_helper.cc +++ b/chrome/browser/sync/test/integration/sync_extension_helper.cc @@ -16,6 +16,7 @@ #include "chrome/browser/sync/test/integration/sync_datatype_helper.h" #include "chrome/browser/sync/test/integration/sync_test.h" #include "components/crx_file/id_util.h" +#include "extensions/browser/extension_prefs.h" #include "extensions/browser/extension_registry.h" #include "extensions/browser/extension_system.h" #include "extensions/browser/install_flag.h" @@ -27,17 +28,19 @@ #include "testing/gtest/include/gtest/gtest.h" using extensions::Extension; +using extensions::ExtensionPrefs; using extensions::ExtensionRegistry; using extensions::Manifest; SyncExtensionHelper::ExtensionState::ExtensionState() - : enabled_state(ENABLED), incognito_enabled(false) {} + : enabled_state(ENABLED), disable_reasons(0), incognito_enabled(false) {} SyncExtensionHelper::ExtensionState::~ExtensionState() {} bool SyncExtensionHelper::ExtensionState::Equals( const SyncExtensionHelper::ExtensionState &other) const { return ((enabled_state == other.enabled_state) && + (disable_reasons == other.disable_reasons) && (incognito_enabled == other.incognito_enabled)); } @@ -205,20 +208,21 @@ SyncExtensionHelper::ExtensionStateMap ExtensionService* extension_service = extensions::ExtensionSystem::Get(profile)->extension_service(); - for (extensions::ExtensionSet::const_iterator it = extensions->begin(); - it != extensions->end(); ++it) { - const std::string& id = (*it)->id(); - extension_state_map[id].enabled_state = + for (const scoped_refptr<const Extension>& extension : *extensions) { + const std::string& id = extension->id(); + ExtensionState& extension_state = extension_state_map[id]; + extension_state.enabled_state = extension_service->IsExtensionEnabled(id) ? ExtensionState::ENABLED : ExtensionState::DISABLED; - extension_state_map[id].incognito_enabled = + extension_state.disable_reasons = + ExtensionPrefs::Get(profile)->GetDisableReasons(id); + extension_state.incognito_enabled = extensions::util::IsIncognitoEnabled(id, profile); - DVLOG(2) << "Extension " << (*it)->id() << " in profile " - << profile_debug_name << " is " - << (extension_service->IsExtensionEnabled(id) ? - "enabled" : "disabled"); + DVLOG(2) << "Extension " << id << " in profile " << profile_debug_name + << " is " << (extension_service->IsExtensionEnabled(id) ? + "enabled" : "disabled"); } const extensions::PendingExtensionManager* pending_extension_manager = @@ -227,12 +231,14 @@ SyncExtensionHelper::ExtensionStateMap std::list<std::string> pending_crx_ids; pending_extension_manager->GetPendingIdsForUpdateCheck(&pending_crx_ids); - std::list<std::string>::const_iterator id; - for (id = pending_crx_ids.begin(); id != pending_crx_ids.end(); ++id) { - extension_state_map[*id].enabled_state = ExtensionState::PENDING; - extension_state_map[*id].incognito_enabled = - extensions::util::IsIncognitoEnabled(*id, profile); - DVLOG(2) << "Extension " << *id << " in profile " + for (const std::string& id : pending_crx_ids) { + ExtensionState& extension_state = extension_state_map[id]; + extension_state.enabled_state = ExtensionState::PENDING; + extension_state.disable_reasons = + ExtensionPrefs::Get(profile)->GetDisableReasons(id); + extension_state.incognito_enabled = + extensions::util::IsIncognitoEnabled(id, profile); + DVLOG(2) << "Extension " << id << " in profile " << profile_debug_name << " is pending"; } diff --git a/chrome/browser/sync/test/integration/sync_extension_helper.h b/chrome/browser/sync/test/integration/sync_extension_helper.h index 06bf60a..c81977d 100644 --- a/chrome/browser/sync/test/integration/sync_extension_helper.h +++ b/chrome/browser/sync/test/integration/sync_extension_helper.h @@ -83,6 +83,7 @@ class SyncExtensionHelper { bool Equals(const ExtensionState &other) const; EnabledState enabled_state; + int disable_reasons; bool incognito_enabled; }; diff --git a/chrome/browser/sync/test/integration/two_client_apps_sync_test.cc b/chrome/browser/sync/test/integration/two_client_apps_sync_test.cc index 19f360d..4989ae2 100644 --- a/chrome/browser/sync/test/integration/two_client_apps_sync_test.cc +++ b/chrome/browser/sync/test/integration/two_client_apps_sync_test.cc @@ -409,6 +409,7 @@ IN_PROC_BROWSER_TEST_F(TwoClientAppsSyncTest, UnexpectedLaunchType) { extensions::AppSyncData invalid_launch_type_data( *extension, original_data.extension_sync_data().enabled(), + original_data.extension_sync_data().disable_reasons(), original_data.extension_sync_data().incognito_enabled(), original_data.extension_sync_data().remote_install(), original_data.extension_sync_data().all_urls_enabled(), diff --git a/extensions/browser/extension_prefs.cc b/extensions/browser/extension_prefs.cc index 99955f4..460e0de 100644 --- a/extensions/browser/extension_prefs.cc +++ b/extensions/browser/extension_prefs.cc @@ -539,7 +539,7 @@ bool ExtensionPrefs::HasPrefForExtension( bool ExtensionPrefs::ReadPrefAsURLPatternSet(const std::string& extension_id, const std::string& pref_key, URLPatternSet* result, - int valid_schemes) { + int valid_schemes) const { const base::ListValue* value = NULL; if (!ReadPrefAsList(extension_id, pref_key, &value)) return false; @@ -572,7 +572,7 @@ bool ExtensionPrefs::ReadPrefAsBooleanAndReturn( PermissionSet* ExtensionPrefs::ReadPrefAsPermissionSet( const std::string& extension_id, - const std::string& pref_key) { + const std::string& pref_key) const { if (!GetExtensionPref(extension_id)) return NULL; @@ -682,7 +682,7 @@ int ExtensionPrefs::IncrementAcknowledgePromptCount( } bool ExtensionPrefs::IsExternalExtensionAcknowledged( - const std::string& extension_id) { + const std::string& extension_id) const { return ReadPrefAsBooleanAndReturn(extension_id, kPrefExternalAcknowledged); } @@ -695,7 +695,7 @@ void ExtensionPrefs::AcknowledgeExternalExtension( } bool ExtensionPrefs::IsBlacklistedExtensionAcknowledged( - const std::string& extension_id) { + const std::string& extension_id) const { return ReadPrefAsBooleanAndReturn(extension_id, kPrefBlacklistAcknowledged); } @@ -708,7 +708,7 @@ void ExtensionPrefs::AcknowledgeBlacklistedExtension( } bool ExtensionPrefs::IsExternalInstallFirstRun( - const std::string& extension_id) { + const std::string& extension_id) const { return ReadPrefAsBooleanAndReturn(extension_id, kPrefExternalInstallFirstRun); } @@ -728,7 +728,7 @@ bool ExtensionPrefs::SetAlertSystemFirstRun() { } bool ExtensionPrefs::DidExtensionEscalatePermissions( - const std::string& extension_id) { + const std::string& extension_id) const { return ReadPrefAsBooleanAndReturn(extension_id, kExtensionDidEscalatePermissions); } @@ -759,6 +759,11 @@ void ExtensionPrefs::AddDisableReason(const std::string& extension_id, ModifyDisableReasons(extension_id, disable_reason, DISABLE_REASON_ADD); } +void ExtensionPrefs::AddDisableReasons(const std::string& extension_id, + int disable_reasons) { + ModifyDisableReasons(extension_id, disable_reasons, DISABLE_REASON_ADD); +} + void ExtensionPrefs::RemoveDisableReason( const std::string& extension_id, Extension::DisableReason disable_reason) { @@ -803,7 +808,7 @@ void ExtensionPrefs::ModifyDisableReasons(const std::string& extension_id, OnExtensionDisableReasonsChanged(extension_id, new_value)); } -std::set<std::string> ExtensionPrefs::GetBlacklistedExtensions() { +std::set<std::string> ExtensionPrefs::GetBlacklistedExtensions() const { std::set<std::string> ids; const base::DictionaryValue* extensions = @@ -921,7 +926,8 @@ void ExtensionPrefs::SetBlacklistLastPingDay(const base::Time& time) { SaveTime(update.Get(), kLastPingDay, time); } -base::Time ExtensionPrefs::LastActivePingDay(const std::string& extension_id) { +base::Time ExtensionPrefs::LastActivePingDay( + const std::string& extension_id) const { DCHECK(crx_file::id_util::IdIsValid(extension_id)); return ReadTime(GetExtensionPref(extension_id), kLastActivePingDay); } @@ -933,7 +939,7 @@ void ExtensionPrefs::SetLastActivePingDay(const std::string& extension_id, SaveTime(update.Get(), kLastActivePingDay, time); } -bool ExtensionPrefs::GetActiveBit(const std::string& extension_id) { +bool ExtensionPrefs::GetActiveBit(const std::string& extension_id) const { const base::DictionaryValue* dictionary = GetExtensionPref(extension_id); bool result = false; if (dictionary && dictionary->GetBoolean(kActiveBit, &result)) @@ -1026,7 +1032,7 @@ void ExtensionPrefs::MigrateDisableReasons( } PermissionSet* ExtensionPrefs::GetGrantedPermissions( - const std::string& extension_id) { + const std::string& extension_id) const { CHECK(crx_file::id_util::IdIsValid(extension_id)); return ReadPrefAsPermissionSet(extension_id, kPrefGrantedPermissions); } @@ -1068,7 +1074,7 @@ void ExtensionPrefs::RemoveGrantedPermissions( } PermissionSet* ExtensionPrefs::GetActivePermissions( - const std::string& extension_id) { + const std::string& extension_id) const { CHECK(crx_file::id_util::IdIsValid(extension_id)); return ReadPrefAsPermissionSet(extension_id, kPrefActivePermissions); } @@ -1086,7 +1092,7 @@ void ExtensionPrefs::SetExtensionRunning(const std::string& extension_id, UpdateExtensionPref(extension_id, kPrefRunning, value); } -bool ExtensionPrefs::IsExtensionRunning(const std::string& extension_id) { +bool ExtensionPrefs::IsExtensionRunning(const std::string& extension_id) const { const base::DictionaryValue* extension = GetExtensionPref(extension_id); if (!extension) return false; @@ -1101,7 +1107,7 @@ void ExtensionPrefs::SetIsActive(const std::string& extension_id, UpdateExtensionPref(extension_id, kIsActive, value); } -bool ExtensionPrefs::IsActive(const std::string& extension_id) { +bool ExtensionPrefs::IsActive(const std::string& extension_id) const { const base::DictionaryValue* extension = GetExtensionPref(extension_id); if (!extension) return false; @@ -1162,7 +1168,7 @@ bool ExtensionPrefs::IsExtensionDisabled( return DoesExtensionHaveState(id, Extension::DISABLED); } -ExtensionIdList ExtensionPrefs::GetToolbarOrder() { +ExtensionIdList ExtensionPrefs::GetToolbarOrder() const { ExtensionIdList id_list_out; GetUserExtensionPrefIntoContainer(pref_names::kToolbar, &id_list_out); return id_list_out; @@ -1238,7 +1244,7 @@ void ExtensionPrefs::SetExtensionBlacklistState(const std::string& extension_id, } BlacklistState ExtensionPrefs::GetExtensionBlacklistState( - const std::string& extension_id) { + const std::string& extension_id) const { if (IsExtensionBlacklisted(extension_id)) return BLACKLISTED_MALWARE; const base::DictionaryValue* ext_prefs = GetExtensionPref(extension_id); @@ -1249,7 +1255,8 @@ BlacklistState ExtensionPrefs::GetExtensionBlacklistState( return NOT_BLACKLISTED; } -std::string ExtensionPrefs::GetVersionString(const std::string& extension_id) { +std::string ExtensionPrefs::GetVersionString( + const std::string& extension_id) const { const base::DictionaryValue* extension = GetExtensionPref(extension_id); if (!extension) return std::string(); @@ -1546,7 +1553,8 @@ void ExtensionPrefs::OnEphemeralAppPromoted(const std::string& extension_id) { } } -bool ExtensionPrefs::WasAppDraggedByUser(const std::string& extension_id) { +bool ExtensionPrefs::WasAppDraggedByUser( + const std::string& extension_id) const { return ReadPrefAsBooleanAndReturn(extension_id, kPrefUserDraggedApp); } @@ -1684,7 +1692,7 @@ void ExtensionPrefs::ClearLastLaunchTimes() { } } -void ExtensionPrefs::GetExtensions(ExtensionIdList* out) { +void ExtensionPrefs::GetExtensions(ExtensionIdList* out) const { CHECK(out); scoped_ptr<ExtensionsInfo> extensions_info(GetInstalledExtensionsInfo()); @@ -1783,7 +1791,7 @@ void ExtensionPrefs::InitPrefStore() { extension_pref_value_map_->NotifyInitializationCompleted(); } -bool ExtensionPrefs::HasIncognitoPrefValue(const std::string& pref_key) { +bool ExtensionPrefs::HasIncognitoPrefValue(const std::string& pref_key) const { bool has_incognito_pref_value = false; extension_pref_value_map_->GetEffectivePrefValue(pref_key, true, @@ -1810,7 +1818,7 @@ void ExtensionPrefs::SetGeometryCache( UpdateExtensionPref(extension_id, kPrefGeometryCache, cache.release()); } -const base::DictionaryValue* ExtensionPrefs::GetInstallSignature() { +const base::DictionaryValue* ExtensionPrefs::GetInstallSignature() const { return prefs_->GetDictionary(kInstallSignature); } @@ -1843,7 +1851,7 @@ void ExtensionPrefs::SetInstallParam(const std::string& extension_id, new base::StringValue(install_parameter)); } -int ExtensionPrefs::GetCorruptedDisableCount() { +int ExtensionPrefs::GetCorruptedDisableCount() const { return prefs_->GetInteger(kCorruptedDisableCount); } @@ -1888,7 +1896,7 @@ void ExtensionPrefs::SetNeedsStorageGarbageCollection(bool value) { prefs_->SetBoolean(pref_names::kStorageGarbageCollect, value); } -bool ExtensionPrefs::NeedsStorageGarbageCollection() { +bool ExtensionPrefs::NeedsStorageGarbageCollection() const { return prefs_->GetBoolean(pref_names::kStorageGarbageCollect); } @@ -1925,7 +1933,7 @@ void ExtensionPrefs::RegisterProfilePrefs( template <class ExtensionIdContainer> bool ExtensionPrefs::GetUserExtensionPrefIntoContainer( const char* pref, - ExtensionIdContainer* id_container_out) { + ExtensionIdContainer* id_container_out) const { DCHECK(id_container_out->empty()); const base::Value* user_pref_value = prefs_->GetUserPrefValue(pref); @@ -1966,7 +1974,7 @@ void ExtensionPrefs::PopulateExtensionInfoPrefs( Extension::State initial_state, int install_flags, const std::string& install_parameter, - base::DictionaryValue* extension_dict) { + base::DictionaryValue* extension_dict) const { extension_dict->Set(kPrefState, new base::FundamentalValue(initial_state)); extension_dict->Set(kPrefLocation, new base::FundamentalValue(extension->location())); diff --git a/extensions/browser/extension_prefs.h b/extensions/browser/extension_prefs.h index e946901..88ff025 100644 --- a/extensions/browser/extension_prefs.h +++ b/extensions/browser/extension_prefs.h @@ -173,7 +173,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { bool IsExtensionDisabled(const std::string& id) const; // Get/Set the order that the browser actions appear in the toolbar. - ExtensionIdList GetToolbarOrder(); + ExtensionIdList GetToolbarOrder() const; void SetToolbarOrder(const ExtensionIdList& extension_ids); // Called when an extension is installed, so that prefs get created. @@ -212,10 +212,11 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { // Checks whether |extension_id| is marked as greylisted. // TODO(oleg): Replace IsExtensionBlacklisted by this method. - BlacklistState GetExtensionBlacklistState(const std::string& extension_id); + BlacklistState GetExtensionBlacklistState( + const std::string& extension_id) const; // Populates |out| with the ids of all installed extensions. - void GetExtensions(ExtensionIdList* out); + void GetExtensions(ExtensionIdList* out) const; // ExtensionScopedPrefs methods: void UpdateExtensionPref(const std::string& id, @@ -248,7 +249,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { bool HasPrefForExtension(const std::string& extension_id) const override; // Did the extension ask to escalate its permission during an upgrade? - bool DidExtensionEscalatePermissions(const std::string& id); + bool DidExtensionEscalatePermissions(const std::string& id) const; // If |did_escalate| is true, the preferences for |extension| will be set to // require the install warning when the user tries to enable. @@ -262,6 +263,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { Extension::DisableReason disable_reason) const; void AddDisableReason(const std::string& extension_id, Extension::DisableReason disable_reason); + void AddDisableReasons(const std::string& extension_id, int disable_reasons); void RemoveDisableReason(const std::string& extension_id, Extension::DisableReason disable_reason); void ClearDisableReasons(const std::string& extension_id); @@ -270,7 +272,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { // return only the blocked extensions, not the "greylist" extensions. // TODO(oleg): Make method names consistent here, in extension service and in // blacklist. - std::set<std::string> GetBlacklistedExtensions(); + std::set<std::string> GetBlacklistedExtensions() const; // Sets whether the extension with |id| is blacklisted. void SetExtensionBlacklisted(const std::string& extension_id, @@ -278,7 +280,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { // Returns the version string for the currently installed extension, or // the empty string if not found. - std::string GetVersionString(const std::string& extension_id); + std::string GetVersionString(const std::string& extension_id) const; // Re-writes the extension manifest into the prefs. // Called to change the extension's manifest when it's re-localized. @@ -300,16 +302,17 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { int IncrementAcknowledgePromptCount(const std::string& extension_id); // Whether the user has acknowledged an external extension. - bool IsExternalExtensionAcknowledged(const std::string& extension_id); + bool IsExternalExtensionAcknowledged(const std::string& extension_id) const; void AcknowledgeExternalExtension(const std::string& extension_id); // Whether the user has acknowledged a blacklisted extension. - bool IsBlacklistedExtensionAcknowledged(const std::string& extension_id); + bool IsBlacklistedExtensionAcknowledged( + const std::string& extension_id) const; void AcknowledgeBlacklistedExtension(const std::string& extension_id); // Whether the external extension was installed during the first run // of this profile. - bool IsExternalInstallFirstRun(const std::string& extension_id); + bool IsExternalInstallFirstRun(const std::string& extension_id) const; void SetExternalInstallFirstRun(const std::string& extension_id); // Returns true if the extension notification code has already run for the @@ -334,20 +337,20 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { // Similar to LastPingDay/SetLastPingDay, but for sending "days since active" // ping. - base::Time LastActivePingDay(const std::string& extension_id); + base::Time LastActivePingDay(const std::string& extension_id) const; void SetLastActivePingDay(const std::string& extension_id, const base::Time& time); // A bit we use for determining if we should send the "days since active" // ping. A value of true means the item has been active (launched) since the // last update check. - bool GetActiveBit(const std::string& extension_id); + bool GetActiveBit(const std::string& extension_id) const; void SetActiveBit(const std::string& extension_id, bool active); // Returns the granted permission set for the extension with |extension_id|, // and NULL if no preferences were found for |extension_id|. // This passes ownership of the returned set to the caller. - PermissionSet* GetGrantedPermissions(const std::string& extension_id); + PermissionSet* GetGrantedPermissions(const std::string& extension_id) const; // Adds |permissions| to the granted permissions set for the extension with // |extension_id|. The new granted permissions set will be the union of @@ -362,7 +365,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { // Gets the active permission set for the specified extension. This may // differ from the permissions in the manifest due to the optional // permissions API. This passes ownership of the set to the caller. - PermissionSet* GetActivePermissions(const std::string& extension_id); + PermissionSet* GetActivePermissions(const std::string& extension_id) const; // Sets the active |permissions| for the extension with |extension_id|. void SetActivePermissions(const std::string& extension_id, @@ -373,13 +376,13 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { // Returns whether or not this extension is marked as running. This is used to // restart apps across browser restarts. - bool IsExtensionRunning(const std::string& extension_id); + bool IsExtensionRunning(const std::string& extension_id) const; // Set/Get whether or not the app is active. Used to force a launch of apps // that don't handle onRestarted() on a restart. We can only safely do that if // the app was active when it was last running. void SetIsActive(const std::string& extension_id, bool is_active); - bool IsActive(const std::string& extension_id); + bool IsActive(const std::string& extension_id) const; // Returns true if the user enabled this extension to be loaded in incognito // mode. @@ -450,7 +453,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { // Returns true if the user repositioned the app on the app launcher via drag // and drop. - bool WasAppDraggedByUser(const std::string& extension_id); + bool WasAppDraggedByUser(const std::string& extension_id) const; // Sets a flag indicating that the user repositioned the app on the app // launcher by drag and dropping it. @@ -458,7 +461,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { // Returns true if there is an extension which controls the preference value // for |pref_key| *and* it is specific to incognito mode. - bool HasIncognitoPrefValue(const std::string& pref_key); + bool HasIncognitoPrefValue(const std::string& pref_key) const; // Returns the creation flags mask for the extension. int GetCreationFlags(const std::string& extension_id) const; @@ -510,7 +513,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { // start of this ExtensionService. Applies only to extensions with isolated // storage. void SetNeedsStorageGarbageCollection(bool value); - bool NeedsStorageGarbageCollection(); + bool NeedsStorageGarbageCollection() const; // Used by AppWindowGeometryCache to persist its cache. These methods // should not be called directly. @@ -521,7 +524,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { // Used for verification of installed extension ids. For the Set method, pass // null to remove the preference. - const base::DictionaryValue* GetInstallSignature(); + const base::DictionaryValue* GetInstallSignature() const; void SetInstallSignature(const base::DictionaryValue* signature); // The installation parameter associated with the extension. @@ -531,7 +534,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { // The total number of times we've disabled an extension due to corrupted // contents. - int GetCorruptedDisableCount(); + int GetCorruptedDisableCount() const; void IncrementCorruptedDisableCount(); private: @@ -574,7 +577,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { bool ReadPrefAsURLPatternSet(const std::string& extension_id, const std::string& pref_key, URLPatternSet* result, - int valid_schemes); + int valid_schemes) const; // Converts |new_value| to a list of strings and sets the |pref_key| pref // belonging to |extension_id|. @@ -590,7 +593,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { // Interprets |pref_key| in |extension_id|'s preferences as an // PermissionSet, and passes ownership of the set to the caller. PermissionSet* ReadPrefAsPermissionSet(const std::string& extension_id, - const std::string& pref_key); + const std::string& pref_key) const; // Converts the |new_value| to its value and sets the |pref_key| pref // belonging to |extension_id|. @@ -635,7 +638,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { template <class ExtensionIdContainer> bool GetUserExtensionPrefIntoContainer( const char* pref, - ExtensionIdContainer* id_container_out); + ExtensionIdContainer* id_container_out) const; // Writes the list of strings contained in |strings| to |pref| in prefs. template <class ExtensionIdContainer> @@ -644,7 +647,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { // Helper function to populate |extension_dict| with the values needed // by a newly installed extension. Work is broken up between this - // function and FinishExtensionInfoPrefs() to accomodate delayed + // function and FinishExtensionInfoPrefs() to accommodate delayed // installations. // // |install_flags| are a bitmask of extension::InstallFlags. @@ -653,7 +656,7 @@ class ExtensionPrefs : public ExtensionScopedPrefs, public KeyedService { Extension::State initial_state, int install_flags, const std::string& install_parameter, - base::DictionaryValue* extension_dict); + base::DictionaryValue* extension_dict) const; void InitExtensionControlledPrefs(ExtensionPrefValueMap* value_map); diff --git a/sync/protocol/extension_specifics.proto b/sync/protocol/extension_specifics.proto index 8e724a3..a854e01 100644 --- a/sync/protocol/extension_specifics.proto +++ b/sync/protocol/extension_specifics.proto @@ -48,5 +48,10 @@ message ExtensionSpecifics { // optional and may be absent. We need this for the time being because we need // to know if a user has not set an explicit preference. optional bool all_urls_enabled = 9; + + // Bitmask of the set of reasons why the extension is disabled (see + // Extension::DisableReason). Only relevant when enabled == false. Note that + // old clients (<M45) won't set this, even when enabled is false. + optional int32 disable_reasons = 10; } diff --git a/sync/protocol/proto_value_conversions.cc b/sync/protocol/proto_value_conversions.cc index 3ce9528..758729b 100644 --- a/sync/protocol/proto_value_conversions.cc +++ b/sync/protocol/proto_value_conversions.cc @@ -456,10 +456,11 @@ scoped_ptr<base::DictionaryValue> ExtensionSpecificsToValue( SET_STR(update_url); SET_BOOL(enabled); SET_BOOL(incognito_enabled); + SET_STR(name); SET_BOOL(remote_install); SET_BOOL(installed_by_custodian); SET_BOOL(all_urls_enabled); - SET_STR(name); + SET_INT32(disable_reasons); return value; } |