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 3 // found in the LICENSE file. 4 5 #include "chrome/browser/chromeos/drive/file_cache.h" 6 7 #include <string> 8 #include <vector> 9 10 #include "base/callback_helpers.h" 11 #include "base/files/file_enumerator.h" 12 #include "base/files/file_util.h" 13 #include "base/files/scoped_temp_dir.h" 14 #include "base/md5.h" 15 #include "base/path_service.h" 16 #include "chrome/browser/chromeos/drive/drive.pb.h" 17 #include "chrome/browser/chromeos/drive/fake_free_disk_space_getter.h" 18 #include "chrome/browser/chromeos/drive/file_system_util.h" 19 #include "chrome/browser/chromeos/drive/resource_metadata_storage.h" 20 #include "chrome/browser/chromeos/drive/test_util.h" 21 #include "content/public/test/test_browser_thread_bundle.h" 22 #include "google_apis/drive/test_util.h" 23 #include "testing/gtest/include/gtest/gtest.h" 24 25 namespace drive { 26 namespace internal { 27 namespace { 28 29 const char kCacheFileDirectory[] = "files"; 30 31 } // namespace 32 33 // Tests FileCache methods working with the blocking task runner. 34 class FileCacheTest : public testing::Test { 35 protected: 36 virtual void SetUp() OVERRIDE { 37 ASSERT_TRUE(temp_dir_.CreateUniqueTempDir()); 38 const base::FilePath metadata_dir = temp_dir_.path().AppendASCII("meta"); 39 cache_files_dir_ = temp_dir_.path().AppendASCII(kCacheFileDirectory); 40 41 ASSERT_TRUE(base::CreateDirectory(metadata_dir)); 42 ASSERT_TRUE(base::CreateDirectory(cache_files_dir_)); 43 44 fake_free_disk_space_getter_.reset(new FakeFreeDiskSpaceGetter); 45 46 metadata_storage_.reset(new ResourceMetadataStorage( 47 metadata_dir, 48 base::MessageLoopProxy::current().get())); 49 ASSERT_TRUE(metadata_storage_->Initialize()); 50 51 cache_.reset(new FileCache( 52 metadata_storage_.get(), 53 cache_files_dir_, 54 base::MessageLoopProxy::current().get(), 55 fake_free_disk_space_getter_.get())); 56 ASSERT_TRUE(cache_->Initialize()); 57 } 58 59 static bool RenameCacheFilesToNewFormat(FileCache* cache) { 60 return cache->RenameCacheFilesToNewFormat(); 61 } 62 63 content::TestBrowserThreadBundle thread_bundle_; 64 base::ScopedTempDir temp_dir_; 65 base::FilePath cache_files_dir_; 66 67 scoped_ptr<ResourceMetadataStorage, test_util::DestroyHelperForTests> 68 metadata_storage_; 69 scoped_ptr<FileCache, test_util::DestroyHelperForTests> cache_; 70 scoped_ptr<FakeFreeDiskSpaceGetter> fake_free_disk_space_getter_; 71 }; 72 73 TEST_F(FileCacheTest, RecoverFilesFromCacheDirectory) { 74 base::FilePath dir_source_root; 75 EXPECT_TRUE(PathService::Get(base::DIR_SOURCE_ROOT, &dir_source_root)); 76 const base::FilePath src_path = 77 dir_source_root.AppendASCII("chrome/test/data/chromeos/drive/image.png"); 78 79 // Store files. This file should not be moved. 80 ResourceEntry entry; 81 entry.set_local_id("id_foo"); 82 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 83 EXPECT_EQ(FILE_ERROR_OK, cache_->Store("id_foo", "md5", src_path, 84 FileCache::FILE_OPERATION_COPY)); 85 86 // Set up files in the cache directory. These files should be moved. 87 const base::FilePath file_directory = 88 temp_dir_.path().AppendASCII(kCacheFileDirectory); 89 ASSERT_TRUE(base::CopyFile(src_path, file_directory.AppendASCII("id_bar"))); 90 ASSERT_TRUE(base::CopyFile(src_path, file_directory.AppendASCII("id_baz"))); 91 92 // Insert a dirty entry with "id_baz" to |recovered_cache_info|. 93 // This should not prevent the file from being recovered. 94 ResourceMetadataStorage::RecoveredCacheInfoMap recovered_cache_info; 95 recovered_cache_info["id_baz"].is_dirty = true; 96 recovered_cache_info["id_baz"].title = "baz.png"; 97 98 // Recover files. 99 const base::FilePath dest_directory = temp_dir_.path().AppendASCII("dest"); 100 EXPECT_TRUE(cache_->RecoverFilesFromCacheDirectory(dest_directory, 101 recovered_cache_info)); 102 103 // Only two files should be recovered. 104 EXPECT_TRUE(base::PathExists(dest_directory)); 105 // base::FileEnumerator does not guarantee the order. 106 if (base::PathExists(dest_directory.AppendASCII("baz00000001.png"))) { 107 EXPECT_TRUE(base::ContentsEqual( 108 src_path, 109 dest_directory.AppendASCII("baz00000001.png"))); 110 EXPECT_TRUE(base::ContentsEqual( 111 src_path, 112 dest_directory.AppendASCII("image00000002.png"))); 113 } else { 114 EXPECT_TRUE(base::ContentsEqual( 115 src_path, 116 dest_directory.AppendASCII("image00000001.png"))); 117 EXPECT_TRUE(base::ContentsEqual( 118 src_path, 119 dest_directory.AppendASCII("baz00000002.png"))); 120 } 121 EXPECT_FALSE(base::PathExists( 122 dest_directory.AppendASCII("image00000003.png"))); 123 } 124 125 TEST_F(FileCacheTest, FreeDiskSpaceIfNeededFor) { 126 base::FilePath src_file; 127 ASSERT_TRUE(base::CreateTemporaryFileInDir(temp_dir_.path(), &src_file)); 128 129 // Store a file as a 'temporary' file and remember the path. 130 const std::string id_tmp = "id_tmp", md5_tmp = "md5_tmp"; 131 132 ResourceEntry entry; 133 entry.set_local_id(id_tmp); 134 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 135 ASSERT_EQ(FILE_ERROR_OK, 136 cache_->Store(id_tmp, md5_tmp, src_file, 137 FileCache::FILE_OPERATION_COPY)); 138 base::FilePath tmp_path; 139 ASSERT_EQ(FILE_ERROR_OK, cache_->GetFile(id_tmp, &tmp_path)); 140 141 // Store a file as a pinned file and remember the path. 142 const std::string id_pinned = "id_pinned", md5_pinned = "md5_pinned"; 143 entry.Clear(); 144 entry.set_local_id(id_pinned); 145 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 146 ASSERT_EQ(FILE_ERROR_OK, 147 cache_->Store(id_pinned, md5_pinned, src_file, 148 FileCache::FILE_OPERATION_COPY)); 149 ASSERT_EQ(FILE_ERROR_OK, cache_->Pin(id_pinned)); 150 base::FilePath pinned_path; 151 ASSERT_EQ(FILE_ERROR_OK, cache_->GetFile(id_pinned, &pinned_path)); 152 153 // Call FreeDiskSpaceIfNeededFor(). 154 fake_free_disk_space_getter_->set_default_value(test_util::kLotsOfSpace); 155 fake_free_disk_space_getter_->PushFakeValue(0); 156 const int64 kNeededBytes = 1; 157 EXPECT_TRUE(cache_->FreeDiskSpaceIfNeededFor(kNeededBytes)); 158 159 // Only 'temporary' file gets removed. 160 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id_tmp, &entry)); 161 EXPECT_FALSE(entry.file_specific_info().cache_state().is_present()); 162 EXPECT_FALSE(base::PathExists(tmp_path)); 163 164 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id_pinned, &entry)); 165 EXPECT_TRUE(entry.file_specific_info().cache_state().is_present()); 166 EXPECT_TRUE(base::PathExists(pinned_path)); 167 168 // Returns false when disk space cannot be freed. 169 fake_free_disk_space_getter_->set_default_value(0); 170 EXPECT_FALSE(cache_->FreeDiskSpaceIfNeededFor(kNeededBytes)); 171 } 172 173 TEST_F(FileCacheTest, GetFile) { 174 const base::FilePath src_file_path = temp_dir_.path().Append("test.dat"); 175 const std::string src_contents = "test"; 176 EXPECT_TRUE(google_apis::test_util::WriteStringToFile(src_file_path, 177 src_contents)); 178 std::string id("id1"); 179 std::string md5(base::MD5String(src_contents)); 180 181 const base::FilePath cache_file_directory = 182 temp_dir_.path().AppendASCII(kCacheFileDirectory); 183 184 // Try to get an existing file from cache. 185 ResourceEntry entry; 186 entry.set_local_id(id); 187 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 188 EXPECT_EQ(FILE_ERROR_OK, cache_->Store(id, md5, src_file_path, 189 FileCache::FILE_OPERATION_COPY)); 190 base::FilePath cache_file_path; 191 EXPECT_EQ(FILE_ERROR_OK, cache_->GetFile(id, &cache_file_path)); 192 EXPECT_EQ( 193 cache_file_directory.AppendASCII(util::EscapeCacheFileName(id)).value(), 194 cache_file_path.value()); 195 196 std::string contents; 197 EXPECT_TRUE(base::ReadFileToString(cache_file_path, &contents)); 198 EXPECT_EQ(src_contents, contents); 199 200 // Get file from cache with different id. 201 id = "id2"; 202 entry.Clear(); 203 entry.set_local_id(id); 204 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 205 EXPECT_EQ(FILE_ERROR_NOT_FOUND, cache_->GetFile(id, &cache_file_path)); 206 207 // Pin a non-existent file. 208 EXPECT_EQ(FILE_ERROR_OK, cache_->Pin(id)); 209 210 // Get the non-existent pinned file from cache. 211 EXPECT_EQ(FILE_ERROR_NOT_FOUND, cache_->GetFile(id, &cache_file_path)); 212 213 // Get a previously pinned and stored file from cache. 214 EXPECT_EQ(FILE_ERROR_OK, cache_->Store(id, md5, src_file_path, 215 FileCache::FILE_OPERATION_COPY)); 216 217 EXPECT_EQ(FILE_ERROR_OK, cache_->GetFile(id, &cache_file_path)); 218 EXPECT_EQ( 219 cache_file_directory.AppendASCII(util::EscapeCacheFileName(id)).value(), 220 cache_file_path.value()); 221 222 contents.clear(); 223 EXPECT_TRUE(base::ReadFileToString(cache_file_path, &contents)); 224 EXPECT_EQ(src_contents, contents); 225 } 226 227 TEST_F(FileCacheTest, Store) { 228 const base::FilePath src_file_path = temp_dir_.path().Append("test.dat"); 229 const std::string src_contents = "test"; 230 EXPECT_TRUE(google_apis::test_util::WriteStringToFile(src_file_path, 231 src_contents)); 232 std::string id("id"); 233 std::string md5(base::MD5String(src_contents)); 234 235 // Store a file. 236 ResourceEntry entry; 237 entry.set_local_id(id); 238 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 239 EXPECT_EQ(FILE_ERROR_OK, cache_->Store( 240 id, md5, src_file_path, FileCache::FILE_OPERATION_COPY)); 241 242 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id, &entry)); 243 EXPECT_TRUE(entry.file_specific_info().cache_state().is_present()); 244 EXPECT_EQ(md5, entry.file_specific_info().cache_state().md5()); 245 246 base::FilePath cache_file_path; 247 EXPECT_EQ(FILE_ERROR_OK, cache_->GetFile(id, &cache_file_path)); 248 EXPECT_TRUE(base::ContentsEqual(src_file_path, cache_file_path)); 249 250 // Store a non-existent file. 251 EXPECT_EQ(FILE_ERROR_FAILED, cache_->Store( 252 id, md5, base::FilePath::FromUTF8Unsafe("non_existent_file"), 253 FileCache::FILE_OPERATION_COPY)); 254 255 // Passing empty MD5 marks the entry as dirty. 256 EXPECT_EQ(FILE_ERROR_OK, cache_->Store( 257 id, std::string(), src_file_path, FileCache::FILE_OPERATION_COPY)); 258 259 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id, &entry)); 260 EXPECT_TRUE(entry.file_specific_info().cache_state().is_present()); 261 EXPECT_TRUE(entry.file_specific_info().cache_state().md5().empty()); 262 EXPECT_TRUE(entry.file_specific_info().cache_state().is_dirty()); 263 264 // No free space available. 265 fake_free_disk_space_getter_->set_default_value(0); 266 267 EXPECT_EQ(FILE_ERROR_NO_LOCAL_SPACE, cache_->Store( 268 id, md5, src_file_path, FileCache::FILE_OPERATION_COPY)); 269 } 270 271 TEST_F(FileCacheTest, PinAndUnpin) { 272 const base::FilePath src_file_path = temp_dir_.path().Append("test.dat"); 273 const std::string src_contents = "test"; 274 EXPECT_TRUE(google_apis::test_util::WriteStringToFile(src_file_path, 275 src_contents)); 276 std::string id("id_present"); 277 std::string md5(base::MD5String(src_contents)); 278 279 // Store a file. 280 ResourceEntry entry; 281 entry.set_local_id(id); 282 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 283 EXPECT_EQ(FILE_ERROR_OK, cache_->Store( 284 id, md5, src_file_path, FileCache::FILE_OPERATION_COPY)); 285 286 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id, &entry)); 287 EXPECT_FALSE(entry.file_specific_info().cache_state().is_pinned()); 288 289 // Pin the existing file. 290 EXPECT_EQ(FILE_ERROR_OK, cache_->Pin(id)); 291 292 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id, &entry)); 293 EXPECT_TRUE(entry.file_specific_info().cache_state().is_pinned()); 294 295 // Unpin the file. 296 EXPECT_EQ(FILE_ERROR_OK, cache_->Unpin(id)); 297 298 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id, &entry)); 299 EXPECT_FALSE(entry.file_specific_info().cache_state().is_pinned()); 300 301 // Pin a non-present file. 302 std::string id_non_present = "id_non_present"; 303 entry.Clear(); 304 entry.set_local_id(id_non_present); 305 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 306 EXPECT_EQ(FILE_ERROR_OK, cache_->Pin(id_non_present)); 307 308 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id_non_present, &entry)); 309 EXPECT_TRUE(entry.file_specific_info().cache_state().is_pinned()); 310 311 // Unpin the previously pinned non-existent file. 312 EXPECT_EQ(FILE_ERROR_OK, cache_->Unpin(id_non_present)); 313 314 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id_non_present, &entry)); 315 EXPECT_FALSE(entry.file_specific_info().has_cache_state()); 316 317 // Unpin a file that doesn't exist in cache and is not pinned. 318 EXPECT_EQ(FILE_ERROR_NOT_FOUND, cache_->Unpin("id_non_existent")); 319 } 320 321 TEST_F(FileCacheTest, MountUnmount) { 322 const base::FilePath src_file_path = temp_dir_.path().Append("test.dat"); 323 const std::string src_contents = "test"; 324 EXPECT_TRUE(google_apis::test_util::WriteStringToFile(src_file_path, 325 src_contents)); 326 std::string id("id_present"); 327 std::string md5(base::MD5String(src_contents)); 328 329 // Store a file. 330 ResourceEntry entry; 331 entry.set_local_id(id); 332 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 333 EXPECT_EQ(FILE_ERROR_OK, cache_->Store( 334 id, md5, src_file_path, FileCache::FILE_OPERATION_COPY)); 335 336 // Mark the file mounted. 337 base::FilePath cache_file_path; 338 EXPECT_EQ(FILE_ERROR_OK, cache_->MarkAsMounted(id, &cache_file_path)); 339 340 // Try to remove it. 341 EXPECT_EQ(FILE_ERROR_IN_USE, cache_->Remove(id)); 342 343 // Clear mounted state of the file. 344 EXPECT_EQ(FILE_ERROR_OK, cache_->MarkAsUnmounted(cache_file_path)); 345 346 // Try to remove again. 347 EXPECT_EQ(FILE_ERROR_OK, cache_->Remove(id)); 348 } 349 350 TEST_F(FileCacheTest, OpenForWrite) { 351 // Prepare a file. 352 base::FilePath src_file; 353 ASSERT_TRUE(base::CreateTemporaryFileInDir(temp_dir_.path(), &src_file)); 354 355 const std::string id = "id"; 356 ResourceEntry entry; 357 entry.set_local_id(id); 358 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 359 ASSERT_EQ(FILE_ERROR_OK, cache_->Store(id, "md5", src_file, 360 FileCache::FILE_OPERATION_COPY)); 361 EXPECT_EQ(0, entry.file_info().last_modified()); 362 363 // Entry is not dirty nor opened. 364 EXPECT_FALSE(cache_->IsOpenedForWrite(id)); 365 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id, &entry)); 366 EXPECT_FALSE(entry.file_specific_info().cache_state().is_dirty()); 367 368 // Open (1). 369 scoped_ptr<base::ScopedClosureRunner> file_closer1; 370 EXPECT_EQ(FILE_ERROR_OK, cache_->OpenForWrite(id, &file_closer1)); 371 EXPECT_TRUE(cache_->IsOpenedForWrite(id)); 372 373 // Entry is dirty. 374 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id, &entry)); 375 EXPECT_TRUE(entry.file_specific_info().cache_state().is_dirty()); 376 377 // Open (2). 378 scoped_ptr<base::ScopedClosureRunner> file_closer2; 379 EXPECT_EQ(FILE_ERROR_OK, cache_->OpenForWrite(id, &file_closer2)); 380 EXPECT_TRUE(cache_->IsOpenedForWrite(id)); 381 382 // Close (1). 383 file_closer1.reset(); 384 base::RunLoop().RunUntilIdle(); 385 EXPECT_TRUE(cache_->IsOpenedForWrite(id)); 386 387 // last_modified is updated. 388 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id, &entry)); 389 EXPECT_NE(0, entry.file_info().last_modified()); 390 391 // Close (2). 392 file_closer2.reset(); 393 base::RunLoop().RunUntilIdle(); 394 EXPECT_FALSE(cache_->IsOpenedForWrite(id)); 395 396 // Try to open non-existent file. 397 EXPECT_EQ(FILE_ERROR_NOT_FOUND, 398 cache_->OpenForWrite("nonexistent_id", &file_closer1)); 399 } 400 401 TEST_F(FileCacheTest, UpdateMd5) { 402 // Store test data. 403 const base::FilePath src_file_path = temp_dir_.path().Append("test.dat"); 404 const std::string contents_before = "before"; 405 EXPECT_TRUE(google_apis::test_util::WriteStringToFile(src_file_path, 406 contents_before)); 407 std::string id("id1"); 408 ResourceEntry entry; 409 entry.set_local_id(id); 410 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 411 EXPECT_EQ(FILE_ERROR_OK, cache_->Store(id, base::MD5String(contents_before), 412 src_file_path, 413 FileCache::FILE_OPERATION_COPY)); 414 415 // Modify the cache file. 416 scoped_ptr<base::ScopedClosureRunner> file_closer; 417 EXPECT_EQ(FILE_ERROR_OK, cache_->OpenForWrite(id, &file_closer)); 418 base::FilePath cache_file_path; 419 EXPECT_EQ(FILE_ERROR_OK, cache_->GetFile(id, &cache_file_path)); 420 const std::string contents_after = "after"; 421 EXPECT_TRUE(google_apis::test_util::WriteStringToFile(cache_file_path, 422 contents_after)); 423 424 // Cannot update MD5 of an opend file. 425 EXPECT_EQ(FILE_ERROR_IN_USE, cache_->UpdateMd5(id)); 426 427 // Close file. 428 file_closer.reset(); 429 base::RunLoop().RunUntilIdle(); 430 431 // MD5 was cleared by OpenForWrite(). 432 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id, &entry)); 433 EXPECT_TRUE(entry.file_specific_info().cache_state().md5().empty()); 434 435 // Update MD5. 436 EXPECT_EQ(FILE_ERROR_OK, cache_->UpdateMd5(id)); 437 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id, &entry)); 438 EXPECT_EQ(base::MD5String(contents_after), 439 entry.file_specific_info().cache_state().md5()); 440 } 441 442 TEST_F(FileCacheTest, ClearDirty) { 443 // Prepare a file. 444 base::FilePath src_file; 445 ASSERT_TRUE(base::CreateTemporaryFileInDir(temp_dir_.path(), &src_file)); 446 447 const std::string id = "id"; 448 ResourceEntry entry; 449 entry.set_local_id(id); 450 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 451 ASSERT_EQ(FILE_ERROR_OK, cache_->Store(id, "md5", src_file, 452 FileCache::FILE_OPERATION_COPY)); 453 454 // Open the file. 455 scoped_ptr<base::ScopedClosureRunner> file_closer; 456 EXPECT_EQ(FILE_ERROR_OK, cache_->OpenForWrite(id, &file_closer)); 457 458 // Entry is dirty. 459 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id, &entry)); 460 EXPECT_TRUE(entry.file_specific_info().cache_state().is_dirty()); 461 462 // Cannot clear the dirty bit of an opened entry. 463 EXPECT_EQ(FILE_ERROR_IN_USE, cache_->ClearDirty(id)); 464 465 // Close the file and clear the dirty bit. 466 file_closer.reset(); 467 base::RunLoop().RunUntilIdle(); 468 EXPECT_EQ(FILE_ERROR_OK, cache_->ClearDirty(id)); 469 470 // Entry is not dirty. 471 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->GetEntry(id, &entry)); 472 EXPECT_FALSE(entry.file_specific_info().cache_state().is_dirty()); 473 } 474 475 TEST_F(FileCacheTest, Remove) { 476 const base::FilePath src_file_path = temp_dir_.path().Append("test.dat"); 477 const std::string src_contents = "test"; 478 EXPECT_TRUE(google_apis::test_util::WriteStringToFile(src_file_path, 479 src_contents)); 480 std::string id("id"); 481 std::string md5(base::MD5String(src_contents)); 482 483 // First store a file to cache. 484 ResourceEntry entry; 485 entry.set_local_id(id); 486 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 487 base::FilePath src_file; 488 ASSERT_TRUE(base::CreateTemporaryFileInDir(temp_dir_.path(), &src_file)); 489 EXPECT_EQ(FILE_ERROR_OK, cache_->Store( 490 id, md5, src_file_path, FileCache::FILE_OPERATION_COPY)); 491 492 base::FilePath cache_file_path; 493 EXPECT_EQ(FILE_ERROR_OK, cache_->GetFile(id, &cache_file_path)); 494 495 // Then try to remove existing file from cache. 496 EXPECT_EQ(FILE_ERROR_OK, cache_->Remove(id)); 497 EXPECT_FALSE(base::PathExists(cache_file_path)); 498 } 499 500 TEST_F(FileCacheTest, RenameCacheFilesToNewFormat) { 501 const base::FilePath file_directory = 502 temp_dir_.path().AppendASCII(kCacheFileDirectory); 503 504 // File with an old style "<prefix>:<ID>.<MD5>" name. 505 ASSERT_TRUE(google_apis::test_util::WriteStringToFile( 506 file_directory.AppendASCII("file:id_koo.md5"), "koo")); 507 508 // File with multiple extensions should be removed. 509 ASSERT_TRUE(google_apis::test_util::WriteStringToFile( 510 file_directory.AppendASCII("id_kyu.md5.mounted"), "kyu (mounted)")); 511 ASSERT_TRUE(google_apis::test_util::WriteStringToFile( 512 file_directory.AppendASCII("id_kyu.md5"), "kyu")); 513 514 // Rename and verify the result. 515 EXPECT_TRUE(RenameCacheFilesToNewFormat(cache_.get())); 516 std::string contents; 517 EXPECT_TRUE(base::ReadFileToString(file_directory.AppendASCII("id_koo"), 518 &contents)); 519 EXPECT_EQ("koo", contents); 520 contents.clear(); 521 EXPECT_TRUE(base::ReadFileToString(file_directory.AppendASCII("id_kyu"), 522 &contents)); 523 EXPECT_EQ("kyu", contents); 524 525 // Rename again. 526 EXPECT_TRUE(RenameCacheFilesToNewFormat(cache_.get())); 527 528 // Files with new style names are not affected. 529 contents.clear(); 530 EXPECT_TRUE(base::ReadFileToString(file_directory.AppendASCII("id_koo"), 531 &contents)); 532 EXPECT_EQ("koo", contents); 533 contents.clear(); 534 EXPECT_TRUE(base::ReadFileToString(file_directory.AppendASCII("id_kyu"), 535 &contents)); 536 EXPECT_EQ("kyu", contents); 537 } 538 539 TEST_F(FileCacheTest, ClearAll) { 540 const std::string id("1a2b"); 541 const std::string md5("abcdef0123456789"); 542 543 // Store an existing file. 544 ResourceEntry entry; 545 entry.set_local_id(id); 546 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); 547 base::FilePath src_file; 548 ASSERT_TRUE(base::CreateTemporaryFileInDir(temp_dir_.path(), &src_file)); 549 ASSERT_EQ(FILE_ERROR_OK, 550 cache_->Store(id, md5, src_file, FileCache::FILE_OPERATION_COPY)); 551 552 // Clear cache. 553 EXPECT_TRUE(cache_->ClearAll()); 554 555 // Verify that the cache is removed. 556 EXPECT_TRUE(base::IsDirectoryEmpty(cache_files_dir_)); 557 } 558 559 } // namespace internal 560 } // namespace drive 561