diff options
14 files changed, 306 insertions, 41 deletions
diff --git a/chrome/browser/extensions/extension_content_settings_apitest.cc b/chrome/browser/extensions/extension_content_settings_apitest.cc index f16fdff..1ec6923 100644 --- a/chrome/browser/extensions/extension_content_settings_apitest.cc +++ b/chrome/browser/extensions/extension_content_settings_apitest.cc @@ -27,14 +27,15 @@ IN_PROC_BROWSER_TEST_F(ExtensionApiTest, ContentSettings) { EXPECT_TRUE(pref_service->GetBoolean(prefs::kEnableReferrers)); } -IN_PROC_BROWSER_TEST_F(ExtensionApiTest, IncognitoContentSettings) { +IN_PROC_BROWSER_TEST_F(ExtensionApiTest, PersistentIncognitoContentSettings) { CommandLine::ForCurrentProcess()->AppendSwitch( switches::kEnableExperimentalExtensionApis); PrefService* prefs = browser()->profile()->GetPrefs(); prefs->SetBoolean(prefs::kBlockThirdPartyCookies, false); - EXPECT_TRUE(RunExtensionTestIncognito("content_settings/incognito")) << + EXPECT_TRUE( + RunExtensionTestIncognito("content_settings/persistent_incognito")) << message_; // Setting an incognito preference should not create an incognito profile. @@ -58,7 +59,34 @@ IN_PROC_BROWSER_TEST_F(ExtensionApiTest, IncognitoDisabledContentSettings) { CommandLine::ForCurrentProcess()->AppendSwitch( switches::kEnableExperimentalExtensionApis); - EXPECT_FALSE(RunExtensionTest("content_settings/incognito")); + EXPECT_FALSE(RunExtensionTest("content_settings/persistent_incognito")); +} + +IN_PROC_BROWSER_TEST_F(ExtensionApiTest, SessionOnlyIncognitoContentSettings) { + CommandLine::ForCurrentProcess()->AppendSwitch( + switches::kEnableExperimentalExtensionApis); + + PrefService* prefs = browser()->profile()->GetPrefs(); + prefs->SetBoolean(prefs::kBlockThirdPartyCookies, false); + + EXPECT_TRUE( + RunExtensionTestIncognito("content_settings/session_only_incognito")) << + message_; + + EXPECT_TRUE(browser()->profile()->HasOffTheRecordProfile()); + + PrefService* otr_prefs = + browser()->profile()->GetOffTheRecordProfile()->GetPrefs(); + const PrefService::Preference* pref = + otr_prefs->FindPreference(prefs::kBlockThirdPartyCookies); + ASSERT_TRUE(pref); + EXPECT_TRUE(pref->IsExtensionControlled()); + EXPECT_FALSE(otr_prefs->GetBoolean(prefs::kBlockThirdPartyCookies)); + + pref = prefs->FindPreference(prefs::kBlockThirdPartyCookies); + ASSERT_TRUE(pref); + EXPECT_FALSE(pref->IsExtensionControlled()); + EXPECT_FALSE(prefs->GetBoolean(prefs::kBlockThirdPartyCookies)); } IN_PROC_BROWSER_TEST_F(ExtensionApiTest, ContentSettingsClear) { diff --git a/chrome/browser/extensions/extension_pref_value_map.cc b/chrome/browser/extensions/extension_pref_value_map.cc index 5b0b5ee..99bceb1 100644 --- a/chrome/browser/extensions/extension_pref_value_map.cc +++ b/chrome/browser/extensions/extension_pref_value_map.cc @@ -18,6 +18,9 @@ struct ExtensionPrefValueMap::ExtensionEntry { // Persistent extension controlled preferences for the incognito profile, // empty for regular profile ExtensionPrefStore. PrefValueMap incognito_profile_preferences_persistent; + // Session only extension controlled preferences for the incognito profile. + // These preferences are deleted when the incognito profile is destroyed. + PrefValueMap incognito_profile_preferences_session_only; }; ExtensionPrefValueMap::ExtensionPrefValueMap() { @@ -66,6 +69,25 @@ bool ExtensionPrefValueMap::CanExtensionControlPref( return winner->second->install_time <= ext->second->install_time; } +void ExtensionPrefValueMap::ClearAllIncognitoSessionOnlyPreferences() { + typedef std::set<std::string> KeySet; + KeySet deleted_keys; + + ExtensionEntryMap::iterator i; + for (i = entries_.begin(); i != entries_.end(); ++i) { + PrefValueMap& inc_prefs = + i->second->incognito_profile_preferences_session_only; + PrefValueMap::iterator j; + for (j = inc_prefs.begin(); j != inc_prefs.end(); ++j) + deleted_keys.insert(j->first); + inc_prefs.Clear(); + } + + KeySet::iterator k; + for (k = deleted_keys.begin(); k != deleted_keys.end(); ++k) + NotifyPrefValueChanged(*k); +} + bool ExtensionPrefValueMap::DoesExtensionControlPref( const std::string& extension_id, const std::string& pref_key, @@ -125,6 +147,8 @@ PrefValueMap* ExtensionPrefValueMap::GetExtensionPrefValueMap( return &(i->second->regular_profile_preferences); case extension_prefs_scope::kIncognitoPersistent: return &(i->second->incognito_profile_preferences_persistent); + case extension_prefs_scope::kIncognitoSessionOnly: + return &(i->second->incognito_profile_preferences_session_only); } NOTREACHED(); return NULL; @@ -140,6 +164,8 @@ const PrefValueMap* ExtensionPrefValueMap::GetExtensionPrefValueMap( return &(i->second->regular_profile_preferences); case extension_prefs_scope::kIncognitoPersistent: return &(i->second->incognito_profile_preferences_persistent); + case extension_prefs_scope::kIncognitoSessionOnly: + return &(i->second->incognito_profile_preferences_session_only); } NOTREACHED(); return NULL; @@ -158,6 +184,11 @@ void ExtensionPrefValueMap::GetExtensionControlledKeys( entry.incognito_profile_preferences_persistent; for (i = inc_prefs_pers.begin(); i != inc_prefs_pers.end(); ++i) out->insert(i->first); + + const PrefValueMap& inc_prefs_session = + entry.incognito_profile_preferences_session_only; + for (i = inc_prefs_session.begin(); i != inc_prefs_session.end(); ++i) + out->insert(i->first); } const Value* ExtensionPrefValueMap::GetEffectivePrefValue( @@ -171,11 +202,23 @@ const Value* ExtensionPrefValueMap::GetEffectivePrefValue( const Value* value = NULL; const std::string& ext_id = winner->first; + + // First search for incognito session only preferences. if (incognito) { const PrefValueMap* prefs = GetExtensionPrefValueMap( + ext_id, extension_prefs_scope::kIncognitoSessionOnly); + prefs->GetValue(key, &value); + } + + // If no incognito session only preference exists, fall back to persistent + // incognito preference. + if (incognito && !value) { + const PrefValueMap* prefs = GetExtensionPrefValueMap( ext_id, extension_prefs_scope::kIncognitoPersistent); prefs->GetValue(key, &value); } + + // Finally consider a regular preference. if (!value) { const PrefValueMap* prefs = GetExtensionPrefValueMap( ext_id, extension_prefs_scope::kRegular); @@ -224,6 +267,15 @@ ExtensionPrefValueMap::GetEffectivePrefValueController( if (from_incognito) *from_incognito = true; } + + prefs = GetExtensionPrefValueMap( + ext_id, extension_prefs_scope::kIncognitoSessionOnly); + if (prefs->GetValue(key, &value)) { + winner = i; + winners_install_time = install_time; + if (from_incognito) + *from_incognito = true; + } } return winner; } diff --git a/chrome/browser/extensions/extension_pref_value_map.h b/chrome/browser/extensions/extension_pref_value_map.h index 8b4db03..1328753 100644 --- a/chrome/browser/extensions/extension_pref_value_map.h +++ b/chrome/browser/extensions/extension_pref_value_map.h @@ -89,6 +89,9 @@ class ExtensionPrefValueMap { const std::string& pref_key, bool incognito) const; + // Removes all "incognito session only" preference values. + void ClearAllIncognitoSessionOnlyPreferences(); + // Returns true if an extension identified by |extension_id| controls the // preference. This means this extension has set a preference value and no // other extension with higher precedence overrides it. diff --git a/chrome/browser/extensions/extension_pref_value_map_unittest.cc b/chrome/browser/extensions/extension_pref_value_map_unittest.cc index d4ac026..40bb9e8 100644 --- a/chrome/browser/extensions/extension_pref_value_map_unittest.cc +++ b/chrome/browser/extensions/extension_pref_value_map_unittest.cc @@ -281,22 +281,30 @@ TEST_F(ExtensionPrefValueMapTest, ReenableExt) { struct OverrideIncognitoTestCase { OverrideIncognitoTestCase(int val_ext1_regular, - int val_ext1_incognito, + int val_ext1_incognito_pers, + int val_ext1_incognito_sess, int val_ext2_regular, - int val_ext2_incognito, + int val_ext2_incognito_pers, + int val_ext2_incognito_sess, int effective_value_regular, int effective_value_incognito) : val_ext1_regular_(val_ext1_regular), - val_ext1_incognito_(val_ext1_incognito), + val_ext1_incognito_pers_(val_ext1_incognito_pers), + val_ext1_incognito_sess_(val_ext1_incognito_sess), val_ext2_regular_(val_ext2_regular), - val_ext2_incognito_(val_ext2_incognito), + val_ext2_incognito_pers_(val_ext2_incognito_pers), + val_ext2_incognito_sess_(val_ext2_incognito_sess), effective_value_regular_(effective_value_regular), effective_value_incognito_(effective_value_incognito) {} + // pers. = persistent + // sess. = session only int val_ext1_regular_; // pref value of extension 1 - int val_ext1_incognito_; // pref value of extension 1 incognito + int val_ext1_incognito_pers_; // pref value of extension 1 incognito pers. + int val_ext1_incognito_sess_; // pref value of extension 1 incognito sess. int val_ext2_regular_; // pref value of extension 2 - int val_ext2_incognito_; // pref value of extension 2 incognito + int val_ext2_incognito_pers_; // pref value of extension 2 incognito pers. + int val_ext2_incognito_sess_; // pref value of extension 2 incognito sess. int effective_value_regular_; // desired winner regular int effective_value_incognito_; // desired winner incognito }; @@ -314,7 +322,9 @@ TEST_P(ExtensionPrefValueMapTestIncognitoTests, OverrideIncognito) { "val1", "val2", "val3", - "val4" + "val4", + "val5", + "val6" }; epvm_.RegisterExtension(kExt1, CreateTime(10), true); @@ -323,17 +333,25 @@ TEST_P(ExtensionPrefValueMapTestIncognitoTests, OverrideIncognito) { epvm_.SetExtensionPref(kExt1, kPref1, kRegular, CreateVal(strings[test.val_ext1_regular_])); } - if (test.val_ext1_incognito_) { + if (test.val_ext1_incognito_pers_) { epvm_.SetExtensionPref(kExt1, kPref1, kIncognitoPersistent, - CreateVal(strings[test.val_ext1_incognito_])); + CreateVal(strings[test.val_ext1_incognito_pers_])); + } + if (test.val_ext1_incognito_sess_) { + epvm_.SetExtensionPref(kExt1, kPref1, kIncognitoSessionOnly, + CreateVal(strings[test.val_ext1_incognito_sess_])); } if (test.val_ext2_regular_) { epvm_.SetExtensionPref(kExt2, kPref1, kRegular, CreateVal(strings[test.val_ext2_regular_])); } - if (test.val_ext2_incognito_) { + if (test.val_ext2_incognito_pers_) { epvm_.SetExtensionPref(kExt2, kPref1, kIncognitoPersistent, - CreateVal(strings[test.val_ext2_incognito_])); + CreateVal(strings[test.val_ext2_incognito_pers_])); + } + if (test.val_ext2_incognito_sess_) { + epvm_.SetExtensionPref(kExt2, kPref1, kIncognitoSessionOnly, + CreateVal(strings[test.val_ext2_incognito_sess_])); } std::string actual; EXPECT_EQ(strings[test.effective_value_regular_], GetValue(kPref1, false)); @@ -346,15 +364,20 @@ INSTANTIATE_TEST_CASE_P( ExtensionPrefValueMapTestIncognitoTestsInstance, ExtensionPrefValueMapTestIncognitoTests, testing::Values( - // e.g. (1, 0, 0, 4, 1, 4), means: - // ext1 regular is set to "val1", ext2 incognito is set to "val4" + // e.g. (1, 0, 0, 0, 4, 0, 1, 4), means: + // ext1 regular is set to "val1", ext2 incognito persistent is set to + // "val4" // --> the winning regular value is "val1", the winning incognito // value is "val4". - OverrideIncognitoTestCase(1, 0, 0, 0, 1, 1), - OverrideIncognitoTestCase(1, 2, 0, 0, 1, 2), - OverrideIncognitoTestCase(1, 0, 3, 0, 3, 3), - OverrideIncognitoTestCase(1, 0, 0, 4, 1, 4), - // The last 3 in the following line is intentional! - OverrideIncognitoTestCase(1, 2, 3, 0, 3, 3), - OverrideIncognitoTestCase(1, 2, 0, 4, 1, 4), - OverrideIncognitoTestCase(1, 2, 3, 4, 3, 4))); + OverrideIncognitoTestCase(1, 0, 0, 0, 0, 0, 1, 1), + OverrideIncognitoTestCase(1, 2, 0, 0, 0, 0, 1, 2), + OverrideIncognitoTestCase(1, 0, 3, 0, 0, 0, 1, 3), + OverrideIncognitoTestCase(1, 0, 0, 4, 0, 0, 4, 4), + OverrideIncognitoTestCase(1, 0, 0, 0, 5, 0, 1, 5), + OverrideIncognitoTestCase(1, 0, 0, 0, 0, 6, 1, 6), + // The last 4 in the following line is intentional! + OverrideIncognitoTestCase(1, 2, 0, 4, 0, 0, 4, 4), + OverrideIncognitoTestCase(1, 2, 0, 0, 5, 0, 1, 5), + OverrideIncognitoTestCase(1, 2, 3, 0, 5, 0, 1, 5), + OverrideIncognitoTestCase(1, 2, 0, 3, 5, 0, 3, 5), + OverrideIncognitoTestCase(1, 2, 0, 3, 5, 6, 3, 6))); diff --git a/chrome/browser/extensions/extension_preference_api.cc b/chrome/browser/extensions/extension_preference_api.cc index 3dcde37..2759c89 100644 --- a/chrome/browser/extensions/extension_preference_api.cc +++ b/chrome/browser/extensions/extension_preference_api.cc @@ -40,6 +40,7 @@ const char kScope[] = "scope"; const char kLevelOfControl[] = "levelOfControl"; const char kRegular[] = "regular"; const char kIncognitoPersistent[] = "incognito_persistent"; +const char kIncognitoSessionOnly[] = "incognito_session_only"; const char kValue[] = "value"; const char kOnPrefChangeFormat[] = @@ -48,6 +49,10 @@ const char kOnPrefChangeFormat[] = const char kIncognitoErrorMessage[] = "You do not have permission to access incognito preferences."; +const char kIncognitoSessionOnlyErrorMessage[] = + "You cannot set a preference with scope 'incognito_session_only' when no " + "incognito window is open."; + const char kPermissionErrorMessage[] = "You do not have permission to access the preference '%s'. " "Be sure to declare in your manifest what permissions you need."; @@ -118,6 +123,8 @@ bool StringToScope(const std::string& s, extension_prefs_scope::Scope* scope) { *scope = extension_prefs_scope::kRegular; else if (s == kIncognitoPersistent) *scope = extension_prefs_scope::kIncognitoPersistent; + else if (s == kIncognitoSessionOnly) + *scope = extension_prefs_scope::kIncognitoSessionOnly; else return false; return true; @@ -367,8 +374,8 @@ bool SetPreferenceFunction::RunImpl() { extension_prefs_scope::Scope scope; EXTENSION_FUNCTION_VALIDATE(StringToScope(scope_str, &scope)); - // TODO(battre): add kIncognitoSessionOnly - bool incognito = (scope == extension_prefs_scope::kIncognitoPersistent); + bool incognito = (scope == extension_prefs_scope::kIncognitoPersistent || + scope == extension_prefs_scope::kIncognitoSessionOnly); if (incognito) { // Regular profiles can't access incognito unless include_incognito is true. if (!profile()->IsOffTheRecord() && !include_incognito()) { @@ -384,6 +391,12 @@ bool SetPreferenceFunction::RunImpl() { } } + if (scope == extension_prefs_scope::kIncognitoSessionOnly && + !profile_->HasOffTheRecordProfile()) { + error_ = kIncognitoSessionOnlyErrorMessage; + return false; + } + std::string browser_pref; std::string permission; EXTENSION_FUNCTION_VALIDATE( @@ -431,8 +444,8 @@ bool ClearPreferenceFunction::RunImpl() { extension_prefs_scope::Scope scope; EXTENSION_FUNCTION_VALIDATE(StringToScope(scope_str, &scope)); - // TODO(battre): add kIncognitoSessionOnly - bool incognito = (scope == extension_prefs_scope::kIncognitoPersistent); + bool incognito = (scope == extension_prefs_scope::kIncognitoPersistent || + scope == extension_prefs_scope::kIncognitoSessionOnly); if (incognito) { // We don't check incognito permissions here, as an extension should be // always allowed to clear its own settings. diff --git a/chrome/browser/extensions/extension_prefs_scope.h b/chrome/browser/extensions/extension_prefs_scope.h index 6447234..f137f1b 100644 --- a/chrome/browser/extensions/extension_prefs_scope.h +++ b/chrome/browser/extensions/extension_prefs_scope.h @@ -17,7 +17,9 @@ enum Scope { // Incognito profile; preference is persisted to disk and remains active // after a browser restart. kIncognitoPersistent, - // TODO(battre): add kIncognitoSession + // Incognito profile; preference is kept in memory and deleted when the + // incognito session is terminated. + kIncognitoSessionOnly }; } // extension_prefs_scope diff --git a/chrome/browser/extensions/extension_prefs_unittest.cc b/chrome/browser/extensions/extension_prefs_unittest.cc index f386957..d2686fa 100644 --- a/chrome/browser/extensions/extension_prefs_unittest.cc +++ b/chrome/browser/extensions/extension_prefs_unittest.cc @@ -709,6 +709,16 @@ class ExtensionPrefsPreferencesBase : public ExtensionPrefsTest { kIncognitoPersistent, val); } + void InstallExtControlledPrefIncognitoSessionOnly( + Extension *ext, + const std::string& key, + Value* val) { + using namespace extension_prefs_scope; + EnsureExtensionInstalled(ext); + prefs()->SetExtensionControlledPref(ext->id(), key, + kIncognitoSessionOnly, val); + } + void InstallExtension(Extension *ext) { EnsureExtensionInstalled(ext); } @@ -767,7 +777,7 @@ class ExtensionPrefsInstallOneExtension TEST_F(ExtensionPrefsInstallOneExtension, ExtensionPrefsInstallOneExtension) {} // Check that we do not forget persistent incognito values after a reload. -class ExtensionPrefsInstallIncognito +class ExtensionPrefsInstallIncognitoPersistent : public ExtensionPrefsPreferencesBase { public: virtual void Initialize() { @@ -788,7 +798,43 @@ class ExtensionPrefsInstallIncognito EXPECT_EQ("val2", actual); } }; -TEST_F(ExtensionPrefsInstallIncognito, ExtensionPrefsInstallOneExtension) {} +TEST_F(ExtensionPrefsInstallIncognitoPersistent, + ExtensionPrefsInstallOneExtension) {} + +// Check that we forget 'session only' incognito values after a reload. +class ExtensionPrefsInstallIncognitoSessionOnly + : public ExtensionPrefsPreferencesBase { + public: + ExtensionPrefsInstallIncognitoSessionOnly() : iteration_(0) {} + + virtual void Initialize() { + InstallExtControlledPref(ext1_, kPref1, Value::CreateStringValue("val1")); + InstallExtControlledPrefIncognitoSessionOnly( + ext1_, kPref1, Value::CreateStringValue("val2")); + scoped_ptr<PrefService> incog_prefs(prefs_.CreateIncognitoPrefService()); + std::string actual = incog_prefs->GetString(kPref1); + EXPECT_EQ("val2", actual); + } + virtual void Verify() { + // Main pref service shall see only non-incognito settings. + std::string actual = prefs()->pref_service()->GetString(kPref1); + EXPECT_EQ("val1", actual); + // Incognito pref service shall see session-only incognito values only + // during first run. Once the pref service was reloaded, all values shall be + // discarded. + scoped_ptr<PrefService> incog_prefs(prefs_.CreateIncognitoPrefService()); + actual = incog_prefs->GetString(kPref1); + if (iteration_ == 0) { + EXPECT_EQ("val2", actual); + } else { + EXPECT_EQ("val1", actual); + } + ++iteration_; + } + int iteration_; +}; +TEST_F(ExtensionPrefsInstallIncognitoSessionOnly, + ExtensionPrefsInstallOneExtension) {} class ExtensionPrefsUninstallExtension : public ExtensionPrefsPreferencesBase { @@ -852,7 +898,7 @@ class ExtensionPrefsNotifyWhenNeeded Mock::VerifyAndClearExpectations(&observer); Mock::VerifyAndClearExpectations(&incognito_observer); - // Change only incognito value. + // Change only incognito persistent value. EXPECT_CALL(observer, Observe(_, _, _)).Times(0); EXPECT_CALL(incognito_observer, Observe(_, _, _)); InstallExtControlledPrefIncognito(ext1_, kPref1, @@ -860,6 +906,14 @@ class ExtensionPrefsNotifyWhenNeeded Mock::VerifyAndClearExpectations(&observer); Mock::VerifyAndClearExpectations(&incognito_observer); + // Change only incognito session-only value. + EXPECT_CALL(observer, Observe(_, _, _)).Times(0); + EXPECT_CALL(incognito_observer, Observe(_, _, _)); + InstallExtControlledPrefIncognito(ext1_, kPref1, + Value::CreateStringValue("chrome://newtab3")); + Mock::VerifyAndClearExpectations(&observer); + Mock::VerifyAndClearExpectations(&incognito_observer); + // Uninstall. EXPECT_CALL(observer, Observe(_, _, _)); EXPECT_CALL(incognito_observer, Observe(_, _, _)); diff --git a/chrome/browser/profiles/profile_impl.cc b/chrome/browser/profiles/profile_impl.cc index 650901c..5d8b6ad 100644 --- a/chrome/browser/profiles/profile_impl.cc +++ b/chrome/browser/profiles/profile_impl.cc @@ -712,6 +712,7 @@ Profile* ProfileImpl::GetOffTheRecordProfile() { void ProfileImpl::DestroyOffTheRecordProfile() { off_the_record_profile_.reset(); + extension_pref_value_map_->ClearAllIncognitoSessionOnlyPreferences(); } bool ProfileImpl::HasOffTheRecordProfile() { diff --git a/chrome/common/extensions/api/extension_api.json b/chrome/common/extensions/api/extension_api.json index 82645ba..b7cbc7b 100644 --- a/chrome/common/extensions/api/extension_api.json +++ b/chrome/common/extensions/api/extension_api.json @@ -5384,9 +5384,9 @@ }, "scope": { "type": "string", - "enum": ["regular", "incognito_persistent"], + "enum": ["regular", "incognito_persistent", "incognito_session_only"], "optional": true, - "description": "Where to set the preference (default: regular). 'regular' = preference for regular profile (which is inherited by the incognito profile if not overridden elsewhere), 'incognito_persistent' = preference for incognito profile that sustains browser restarts (overrides regular preferences)." + "description": "Where to set the preference (default: regular). One of<br><var>regular</var>: preference for regular profile (which is inherited by the incognito profile if not overridden elsewhere),<br><var>incognito_persistent</var>: preference for incognito profile that survives browser restarts (overrides regular preferences),<br><var>incognito_session_only</var>: preference for incognito profile that can only be set during an incognito session and is deleted when the incognito session ends (overrides regular and incognito_persistent preferences)." } } }, @@ -5411,9 +5411,9 @@ "properties": { "scope": { "type": "string", - "enum": ["regular", "incognito_persistent"], + "enum": ["regular", "incognito_persistent", "incognito_session_only"], "optional": true, - "description": "Where to set the preference (default: regular). 'regular' = preference for regular profile (which is inherited by the incognito profile if not overridden elsewhere), 'incognito_persistent' = preference for incognito profile that sustains browser restarts (overrides regular preferences)." + "description": "Where to set the preference (default: regular). One of<br><var>regular</var>: preference for regular profile (which is inherited by the incognito profile if not overridden elsewhere),<br><var>incognito_persistent</var>: preference for incognito profile that survives browser restarts (overrides regular preferences),<br><var>incognito_session_only</var>: preference for incognito profile that can only be set during an incognito session and is deleted when the incognito session ends (overrides regular and incognito_persistent preferences)." } } }, diff --git a/chrome/common/extensions/docs/preferences.html b/chrome/common/extensions/docs/preferences.html index bfd2ec6..b4be9f9 100644 --- a/chrome/common/extensions/docs/preferences.html +++ b/chrome/common/extensions/docs/preferences.html @@ -715,7 +715,7 @@ considering the preference rules. It is used by Chrome. array of <span><span></span></span> </span> <span>string</span> - <span>["regular", "incognito_persistent"]</span> + <span>["regular", "incognito_persistent", "incognito_session_only"]</span> </span> </span> ) @@ -726,7 +726,7 @@ considering the preference rules. It is used by Chrome. <dd class="todo" style="display: none; "> Undocumented. </dd> - <dd>Where to set the preference (default: regular). 'regular' = preference for regular profile (which is inherited by the incognito profile if not overridden elsewhere), 'incognito_persistent' = preference for incognito profile that sustains browser restarts (overrides regular preferences).</dd> + <dd>Where to set the preference (default: regular). One of<br><var>regular</var>: preference for regular profile (which is inherited by the incognito profile if not overridden elsewhere),<br><var>incognito_persistent</var>: preference for incognito profile that survives browser restarts (overrides regular preferences),<br><var>incognito_session_only</var>: preference for incognito profile that can only be set during an incognito session and is deleted when the incognito session ends (overrides regular and incognito_persistent preferences).</dd> <dd style="display: none; "> This parameter was added in version <b><span></span></b>. @@ -1577,7 +1577,7 @@ considering the preference rules. It is used by Chrome. array of <span><span></span></span> </span> <span>string</span> - <span>["regular", "incognito_persistent"]</span> + <span>["regular", "incognito_persistent", "incognito_session_only"]</span> </span> </span> ) @@ -1588,7 +1588,7 @@ considering the preference rules. It is used by Chrome. <dd class="todo" style="display: none; "> Undocumented. </dd> - <dd>Where to set the preference (default: regular). 'regular' = preference for regular profile (which is inherited by the incognito profile if not overridden elsewhere), 'incognito_persistent' = preference for incognito profile that sustains browser restarts (overrides regular preferences).</dd> + <dd>Where to set the preference (default: regular). One of<br><var>regular</var>: preference for regular profile (which is inherited by the incognito profile if not overridden elsewhere),<br><var>incognito_persistent</var>: preference for incognito profile that survives browser restarts (overrides regular preferences),<br><var>incognito_session_only</var>: preference for incognito profile that can only be set during an incognito session and is deleted when the incognito session ends (overrides regular and incognito_persistent preferences).</dd> <dd style="display: none; "> This parameter was added in version <b><span></span></b>. diff --git a/chrome/test/data/extensions/api_test/content_settings/incognito/manifest.json b/chrome/test/data/extensions/api_test/content_settings/persistent_incognito/manifest.json index 79541c3..79541c3 100644 --- a/chrome/test/data/extensions/api_test/content_settings/incognito/manifest.json +++ b/chrome/test/data/extensions/api_test/content_settings/persistent_incognito/manifest.json diff --git a/chrome/test/data/extensions/api_test/content_settings/incognito/test.html b/chrome/test/data/extensions/api_test/content_settings/persistent_incognito/test.html index b16f8c0..098ed2a 100644 --- a/chrome/test/data/extensions/api_test/content_settings/incognito/test.html +++ b/chrome/test/data/extensions/api_test/content_settings/persistent_incognito/test.html @@ -1,6 +1,6 @@ <script> // Content settings API test -// Run with browser_tests --gtest_filter=ExtensionApiTest.IncognitoContentSettings +// Run with browser_tests --gtest_filter=ExtensionApiTest.PersistentIncognitoContentSettings var cs = chrome.experimental.contentSettings; function expect(expected, message) { diff --git a/chrome/test/data/extensions/api_test/content_settings/session_only_incognito/manifest.json b/chrome/test/data/extensions/api_test/content_settings/session_only_incognito/manifest.json new file mode 100644 index 0000000..6c421de --- /dev/null +++ b/chrome/test/data/extensions/api_test/content_settings/session_only_incognito/manifest.json @@ -0,0 +1,7 @@ +{ + "name" : "Content Settings API Test Extension (Incognito)", + "version" : "0.1", + "description" : "Content Settings API Test Extension (Incognito)", + "permissions": [ "experimental", "contentSettings", "tabs" ], + "background_page": "test.html" +} diff --git a/chrome/test/data/extensions/api_test/content_settings/session_only_incognito/test.html b/chrome/test/data/extensions/api_test/content_settings/session_only_incognito/test.html new file mode 100644 index 0000000..3fac32a --- /dev/null +++ b/chrome/test/data/extensions/api_test/content_settings/session_only_incognito/test.html @@ -0,0 +1,82 @@ +<script> +// Content settings API test +// Run with browser_tests --gtest_filter=ExtensionApiTest.SessionOnlyIncognitoContentSettings + +var cs = chrome.experimental.contentSettings; +function expect(expected, message) { + return chrome.test.callbackPass(function(value) { + chrome.test.assertNoLastError(); + chrome.test.assertEq(expected, value, message); + }); +} +chrome.test.runTests([ + function getRegular() { + cs.misc.blockThirdPartyCookies.get( + {}, + expect({ 'value': false, + 'levelOfControl': "ControllableByThisExtension" }, + "third-party cookies should not be blocked")); + }, + function getIncognito() { + cs.misc.blockThirdPartyCookies.get( + { 'incognito': true }, + expect({ 'value': false, + 'incognitoSpecific': false, + 'levelOfControl': "ControllableByThisExtension" }, + "third-party cookies should not be blocked in incognito mode")); + }, + function set() { + cs.misc.blockThirdPartyCookies.set( + { 'scope': 'incognito_persistent', 'value': true }, + chrome.test.callbackPass()); + }, + function getRegular2() { + cs.misc.blockThirdPartyCookies.get( + {}, + expect({ 'value': false, + 'levelOfControl': "ControllableByThisExtension" }, + "third-party cookies should not be blocked")); + }, + function getIncognito2() { + cs.misc.blockThirdPartyCookies.get( + { 'incognito': true }, + expect({ 'value': true, + 'incognitoSpecific': true, + 'levelOfControl': "ControlledByThisExtension" }, + "third-party cookies should be blocked in incognito mode")); + }, + // We cannot set session_only_persistent preferences if there is no incognito + // session. + function set2() { + cs.misc.blockThirdPartyCookies.set( + { 'scope': 'incognito_session_only', 'value': false }, + chrome.test.callbackFail("You cannot set a preference with scope " + + "'incognito_session_only' when no incognito " + + "window is open.")); + }, + function openIncognito() { + chrome.windows.create({incognito: true}, chrome.test.callbackPass()); + }, + // session_only_persistent overrides incognito_persistent. + function set3() { + cs.misc.blockThirdPartyCookies.set( + { 'scope': 'incognito_session_only', 'value': false }, + chrome.test.callbackPass()); + }, + function getRegular3() { + cs.misc.blockThirdPartyCookies.get( + {}, + expect({ 'value': false, + 'levelOfControl': "ControllableByThisExtension" }, + "third-party cookies should not be blocked")); + }, + function getIncognito3() { + cs.misc.blockThirdPartyCookies.get( + { 'incognito': true }, + expect({ 'value': false, + 'incognitoSpecific': true, + 'levelOfControl': "ControlledByThisExtension" }, + "third-party cookies should be blocked in incognito mode")); + }, +]); +</script> |