Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(904)

Side by Side Diff: chrome/browser/extensions/extension_service_unittest.cc

Issue 9817018: Cleaning Up Extensions When Local Content Removed (Closed) Base URL: http://git.chromium.org/chromium/src.git@master
Patch Set: Modified for thread safety Created 8 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "chrome/browser/extensions/extension_service_unittest.h" 5 #include "chrome/browser/extensions/extension_service_unittest.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <set> 8 #include <set>
9 #include <vector> 9 #include <vector>
10 10
(...skipping 231 matching lines...) Expand 10 before | Expand all | Expand 10 after
242 mutable int visit_count_; 242 mutable int visit_count_;
243 243
244 int creation_flags_; 244 int creation_flags_;
245 245
246 DISALLOW_COPY_AND_ASSIGN(MockExtensionProvider); 246 DISALLOW_COPY_AND_ASSIGN(MockExtensionProvider);
247 }; 247 };
248 248
249 class MockProviderVisitor 249 class MockProviderVisitor
250 : public ExternalExtensionProviderInterface::VisitorInterface { 250 : public ExternalExtensionProviderInterface::VisitorInterface {
251 public: 251 public:
252
253 // The provider will return |fake_base_path| from 252 // The provider will return |fake_base_path| from
254 // GetBaseCrxFilePath(). User can test the behavior with 253 // GetBaseCrxFilePath(). User can test the behavior with
255 // and without an empty path using this parameter. 254 // and without an empty path using this parameter.
256 explicit MockProviderVisitor(FilePath fake_base_path) 255 explicit MockProviderVisitor(FilePath fake_base_path)
257 : ids_found_(0), 256 : ids_found_(0),
258 fake_base_path_(fake_base_path) { 257 fake_base_path_(fake_base_path) {
259 } 258 }
260 259
261 int Visit(const std::string& json_data) { 260 int Visit(const std::string& json_data) {
262 // Give the test json file to the provider for parsing. 261 // Give the test json file to the provider for parsing.
(...skipping 735 matching lines...) Expand 10 before | Expand all | Expand 10 after
998 ASSERT_TRUE(file_util::PathExists(private_key_path)); 997 ASSERT_TRUE(file_util::PathExists(private_key_path));
999 } 998 }
1000 999
1001 // The tests are designed so that we never expect to see a packing error. 1000 // The tests are designed so that we never expect to see a packing error.
1002 void PackExtensionTestClient::OnPackFailure(const std::string& error_message, 1001 void PackExtensionTestClient::OnPackFailure(const std::string& error_message,
1003 ExtensionCreator::ErrorType type) { 1002 ExtensionCreator::ErrorType type) {
1004 if (type == ExtensionCreator::kCRXExists) 1003 if (type == ExtensionCreator::kCRXExists)
1005 FAIL() << "Packing should not fail."; 1004 FAIL() << "Packing should not fail.";
1006 else 1005 else
1007 FAIL() << "Existing CRX should have been overwritten."; 1006 FAIL() << "Existing CRX should have been overwritten.";
1008
1009 } 1007 }
1010 1008
1011 // Test loading good extensions from the profile directory. 1009 // Test loading good extensions from the profile directory.
1012 TEST_F(ExtensionServiceTest, LoadAllExtensionsFromDirectorySuccess) { 1010 TEST_F(ExtensionServiceTest, LoadAllExtensionsFromDirectorySuccess) {
1013 PluginService::GetInstance()->Init(); 1011 PluginService::GetInstance()->Init();
1014 1012
1015 // Initialize the test dir with a good Preferences/extensions. 1013 // Initialize the test dir with a good Preferences/extensions.
1016 FilePath source_install_dir = data_dir_ 1014 FilePath source_install_dir = data_dir_
1017 .AppendASCII("good") 1015 .AppendASCII("good")
1018 .AppendASCII("Extensions"); 1016 .AppendASCII("Extensions");
(...skipping 123 matching lines...) Expand 10 before | Expand all | Expand 10 after
1142 std::string("Could not load extension from '*'. ") + 1140 std::string("Could not load extension from '*'. ") +
1143 extension_manifest_errors::kMissingFile)) << 1141 extension_manifest_errors::kMissingFile)) <<
1144 UTF16ToUTF8(GetErrors()[2]); 1142 UTF16ToUTF8(GetErrors()[2]);
1145 1143
1146 EXPECT_TRUE(MatchPattern(UTF16ToUTF8(GetErrors()[3]), 1144 EXPECT_TRUE(MatchPattern(UTF16ToUTF8(GetErrors()[3]),
1147 std::string("Could not load extension from '*'. ") + 1145 std::string("Could not load extension from '*'. ") +
1148 extension_manifest_errors::kManifestUnreadable)) << 1146 extension_manifest_errors::kManifestUnreadable)) <<
1149 UTF16ToUTF8(GetErrors()[3]); 1147 UTF16ToUTF8(GetErrors()[3]);
1150 }; 1148 };
1151 1149
1152 // Test that partially deleted extensions are cleaned up during startup 1150 // Test that old versions of extensions are deleted during garbage collection.
1153 // Test loading bad extensions from the profile directory. 1151 TEST_F(ExtensionServiceTest, GarbageCollectOldVersions) {
1154 TEST_F(ExtensionServiceTest, CleanupOnStartup) {
1155 PluginService::GetInstance()->Init(); 1152 PluginService::GetInstance()->Init();
1156 1153
1157 FilePath source_install_dir = data_dir_ 1154 FilePath source_install_dir = data_dir_
1155 .AppendASCII("garbage_collection")
1156 .AppendASCII("Extensions");
1157
1158 FilePath pref_path = source_install_dir
1159 .DirName()
1160 .AppendASCII("Preferences");
1161
1162 InitializeInstalledExtensionService(pref_path, source_install_dir);
1163
1164 // Verify that there are two versions present initially.
1165 ASSERT_TRUE(file_util::PathExists(
1166 extensions_install_dir_.AppendASCII("fdoajpacpdeapbmhbblepcnilfkpmkff")
1167 .AppendASCII("1.0_0")));
1168 ASSERT_TRUE(file_util::PathExists(
1169 extensions_install_dir_.AppendASCII("fdoajpacpdeapbmhbblepcnilfkpmkff")
1170 .AppendASCII("1.1_0")));
1171 service_->Init();
1172 loop_.RunAllPending();
1173
1174 // Garbage collection should have deleted the old version.
1175 ASSERT_FALSE(file_util::PathExists(
1176 extensions_install_dir_.AppendASCII("fdoajpacpdeapbmhbblepcnilfkpmkff")
1177 .AppendASCII("1.0_0")));
1178 ASSERT_TRUE(file_util::PathExists(
1179 extensions_install_dir_.AppendASCII("fdoajpacpdeapbmhbblepcnilfkpmkff")
1180 .AppendASCII("1.1_0")));
1181 }
1182
1183 // Test that extensions which were deleted from the preferences are cleaned up
1184 // during startup.
1185 // Test loading bad extensions from the profile directory.
1186 TEST_F(ExtensionServiceTest, GarbageCollectOnStartup) {
1187 PluginService::GetInstance()->Init();
1188
1189 FilePath source_install_dir = data_dir_
1158 .AppendASCII("good") 1190 .AppendASCII("good")
1159 .AppendASCII("Extensions"); 1191 .AppendASCII("Extensions");
1160 FilePath pref_path = source_install_dir 1192 FilePath pref_path = source_install_dir
1161 .DirName() 1193 .DirName()
1162 .AppendASCII("Preferences"); 1194 .AppendASCII("Preferences");
1163 1195
1164 InitializeInstalledExtensionService(pref_path, source_install_dir); 1196 InitializeInstalledExtensionService(pref_path, source_install_dir);
1165 1197
1166 // Simulate that one of them got partially deleted by clearing its pref. 1198 // Simulate that one of them got partially deleted by clearing its pref.
1167 { 1199 {
1168 DictionaryPrefUpdate update(profile_->GetPrefs(), "extensions.settings"); 1200 DictionaryPrefUpdate update(profile_->GetPrefs(), "extensions.settings");
1169 DictionaryValue* dict = update.Get(); 1201 DictionaryValue* dict = update.Get();
1170 ASSERT_TRUE(dict != NULL); 1202 ASSERT_TRUE(dict);
1171 dict->Remove("behllobkkfkfnphdnhnkndlbkcpglgmj", NULL); 1203 dict->Remove("behllobkkfkfnphdnhnkndlbkcpglgmj", NULL);
1172 } 1204 }
1173 1205
1174 service_->Init(); 1206 service_->Init();
1175 // Wait for GarbageCollectExtensions task to complete. 1207 // Wait for GarbageCollectExtensions task to complete.
1176 loop_.RunAllPending(); 1208 loop_.RunAllPending();
1177 1209
1178 file_util::FileEnumerator dirs(extensions_install_dir_, false, 1210 file_util::FileEnumerator dirs(extensions_install_dir_, false,
1179 file_util::FileEnumerator::DIRECTORIES); 1211 file_util::FileEnumerator::DIRECTORIES);
1180 size_t count = 0; 1212 size_t count = 0;
1181 while (!dirs.Next().empty()) 1213 while (!dirs.Next().empty())
1182 count++; 1214 count++;
1183 1215
1184 // We should have only gotten two extensions now. 1216 // We should have only gotten two extensions now.
1185 EXPECT_EQ(2u, count); 1217 EXPECT_EQ(2u, count);
1186 1218
1187 // And extension1 dir should now be toast. 1219 // And extension1 dir should now be toast.
1188 FilePath extension_dir = extensions_install_dir_ 1220 FilePath extension_dir = extensions_install_dir_
1189 .AppendASCII("behllobkkfkfnphdnhnkndlbkcpglgmj"); 1221 .AppendASCII("behllobkkfkfnphdnhnkndlbkcpglgmj");
1190 ASSERT_FALSE(file_util::PathExists(extension_dir)); 1222 ASSERT_FALSE(file_util::PathExists(extension_dir));
1191 } 1223 }
1192 1224
1225 // Test that internal extensions which are referenced in the preferences but
1226 // had their content deleted are cleaned up during startup.
1227 TEST_F(ExtensionServiceTest, GarbageCollectInternalExtensionsMissingContent) {
1228 PluginService::GetInstance()->Init();
Aaron Boodman 2012/04/07 18:01:03 I don't think this is needed unless you're using p
Devlin 2012/04/14 18:13:21 Tried removing; it broke.
1229
1230 FilePath source_dir = data_dir_.AppendASCII("good").AppendASCII("Extensions");
1231 FilePath pref_path = source_dir.DirName().AppendASCII("Preferences");
1232
1233 InitializeInstalledExtensionService(pref_path, source_dir);
Aaron Boodman 2012/04/07 18:01:03 ASSERT the number of extensions in the prefs you'r
Devlin 2012/04/14 18:13:21 Done.
1234
1235 // Delete the extension's directory.
1236 FilePath extension_dir = extensions_install_dir_
1237 .AppendASCII("behllobkkfkfnphdnhnkndlbkcpglgmj");
1238 ASSERT_TRUE(file_util::Delete(extension_dir, true));
1239
1240 // Run GarbageCollectExtensions.
1241 service_->Init();
1242 loop_.RunAllPending();
1243
1244 file_util::FileEnumerator dirs(extensions_install_dir_, false,
1245 file_util::FileEnumerator::DIRECTORIES);
1246 size_t count = 0;
1247 while (!dirs.Next().empty())
1248 count++;
1249
1250 // We should have only gotten two extensions now.
1251 EXPECT_EQ(2u, count);
1252
1253 DictionaryPrefUpdate update(profile_->GetPrefs(), "extensions.settings");
Aaron Boodman 2012/04/07 18:01:03 Nit: If you're not actually doing any updating, yo
Devlin 2012/04/14 18:13:21 Done.
1254 DictionaryValue* dictionary = update.Get();
1255 ASSERT_TRUE(dictionary);
1256 ASSERT_FALSE(dictionary->HasKey("behllobkkfkfnphdnhnkndlbkcpglgmj"));
1257 }
1258
1259 // Test that unpacked extensions which are referenced in the preferences but
1260 // had their content deleted are cleaned up during startup.
1261 TEST_F(ExtensionServiceTest, GarbageCollectUnpackedExtensionsMissingContent) {
Aaron Boodman 2012/04/07 18:01:03 Can you look into moving all the garbage collectio
Devlin 2012/04/14 18:13:21 Unfortunately, these tests use a few things unique
1262 InitializeEmptyExtensionService();
1263
1264 ScopedTempDir temp;
1265 ASSERT_TRUE(temp.CreateUniqueTempDir());
1266
1267 // Write the manifest dynamically, since we have to delete the file anyway.
1268 FilePath extension_path = temp.path();
1269 FilePath manifest_path = extension_path.Append(Extension::kManifestFilename);
1270 ASSERT_FALSE(file_util::PathExists(manifest_path));
1271
1272 // Construct a simple manifest and install it.
1273 DictionaryValue manifest;
1274 manifest.SetString("version", "1.0");
1275 manifest.SetString("name", "Cleanup Unpacked Extensions Missing Content");
1276 manifest.SetInteger("manifest_version", 2);
1277
1278 JSONFileValueSerializer serializer(manifest_path);
1279 ASSERT_TRUE(serializer.Serialize(manifest));
1280
1281 extensions::UnpackedInstaller::Create(service_)->Load(extension_path);
1282 loop_.RunAllPending();
1283
1284 // Make sure it installed correctly.
1285 EXPECT_EQ(0u, GetErrors().size());
1286 ASSERT_EQ(1u, loaded_.size());
1287 EXPECT_EQ(Extension::LOAD, loaded_[0]->location());
1288 EXPECT_EQ(1u, service_->extensions()->size());
1289
1290 std::string extension_id = loaded_[0]->id();
1291
1292 // Make sure it is in the preferences at this point.
1293 DictionaryPrefUpdate initial_update(
1294 profile_->GetPrefs(), "extensions.settings");
1295 DictionaryValue* initial_dictionary = initial_update.Get();
1296 ASSERT_TRUE(initial_dictionary);
1297 ASSERT_TRUE(initial_dictionary->HasKey(extension_id));
1298
1299 // Delete local content, GarbageCollectExtensions, and test whether the key
1300 // is still in the preferences.
1301 ASSERT_TRUE(file_util::Delete(extension_path, true));
1302 service_->GarbageCollectExtensions();
1303 loop_.RunAllPending();
1304
1305 DictionaryPrefUpdate final_update(
1306 profile_->GetPrefs(), "extensions.settings");
1307 DictionaryValue* final_dictionary = final_update.Get();
1308 ASSERT_TRUE(final_dictionary);
1309 ASSERT_FALSE(final_dictionary->HasKey(extension_id));
1310 }
1311
1193 // Test installing extensions. This test tries to install few extensions using 1312 // Test installing extensions. This test tries to install few extensions using
1194 // crx files. If you need to change those crx files, feel free to repackage 1313 // crx files. If you need to change those crx files, feel free to repackage
1195 // them, throw away the key used and change the id's above. 1314 // them, throw away the key used and change the id's above.
1196 TEST_F(ExtensionServiceTest, InstallExtension) { 1315 TEST_F(ExtensionServiceTest, InstallExtension) {
1197 InitializeEmptyExtensionService(); 1316 InitializeEmptyExtensionService();
1198 1317
1199 // Extensions not enabled. 1318 // Extensions not enabled.
1200 set_extensions_enabled(false); 1319 set_extensions_enabled(false);
1201 FilePath path = data_dir_.AppendASCII("good.crx"); 1320 FilePath path = data_dir_.AppendASCII("good.crx");
1202 InstallCRX(path, INSTALL_FAILED); 1321 InstallCRX(path, INSTALL_FAILED);
(...skipping 3657 matching lines...) Expand 10 before | Expand all | Expand 10 after
4860 provider->UpdateOrAddExtension(hosted_app, "1.0.0.0", 4979 provider->UpdateOrAddExtension(hosted_app, "1.0.0.0",
4861 data_dir_.AppendASCII("hosted_app.crx")); 4980 data_dir_.AppendASCII("hosted_app.crx"));
4862 4981
4863 service_->CheckForExternalUpdates(); 4982 service_->CheckForExternalUpdates();
4864 loop_.RunAllPending(); 4983 loop_.RunAllPending();
4865 4984
4866 ASSERT_TRUE(service_->PopulateExtensionGlobalError( 4985 ASSERT_TRUE(service_->PopulateExtensionGlobalError(
4867 extension_global_error.get())); 4986 extension_global_error.get()));
4868 ASSERT_EQ(1u, extension_global_error->get_external_extension_ids()->size()); 4987 ASSERT_EQ(1u, extension_global_error->get_external_extension_ids()->size());
4869 } 4988 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698