OLD | NEW |
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 "components/drive/file_cache.h" | 5 #include "components/drive/file_cache.h" |
6 | 6 |
7 #include <stddef.h> | 7 #include <stddef.h> |
8 #include <stdint.h> | 8 #include <stdint.h> |
9 #include <sys/stat.h> | |
10 #include <sys/types.h> | |
11 #include <unistd.h> | |
12 | 9 |
13 #include <string> | 10 #include <string> |
14 #include <vector> | 11 #include <vector> |
15 | 12 |
16 #include "base/callback_helpers.h" | 13 #include "base/callback_helpers.h" |
17 #include "base/files/file_enumerator.h" | 14 #include "base/files/file_enumerator.h" |
18 #include "base/files/file_util.h" | 15 #include "base/files/file_util.h" |
19 #include "base/files/scoped_temp_dir.h" | 16 #include "base/files/scoped_temp_dir.h" |
20 #include "base/md5.h" | 17 #include "base/md5.h" |
21 #include "base/path_service.h" | 18 #include "base/path_service.h" |
(...skipping 11 matching lines...) Expand all Loading... |
33 #include "testing/gtest/include/gtest/gtest.h" | 30 #include "testing/gtest/include/gtest/gtest.h" |
34 | 31 |
35 namespace drive { | 32 namespace drive { |
36 namespace internal { | 33 namespace internal { |
37 namespace { | 34 namespace { |
38 | 35 |
39 const base::FilePath::CharType kCacheFileDirectory[] = | 36 const base::FilePath::CharType kCacheFileDirectory[] = |
40 FILE_PATH_LITERAL("files"); | 37 FILE_PATH_LITERAL("files"); |
41 const base::FilePath::CharType kNewCacheFileDirectory[] = | 38 const base::FilePath::CharType kNewCacheFileDirectory[] = |
42 FILE_PATH_LITERAL("blobs"); | 39 FILE_PATH_LITERAL("blobs"); |
43 const base::FilePath::CharType kLinkDirectory[] = FILE_PATH_LITERAL("links"); | |
44 | 40 |
45 const int kTemporaryFileSizeInBytes = 10; | 41 const int kTemporaryFileSizeInBytes = 10; |
46 | 42 |
47 int GetNumberOfLinks(const base::FilePath& file_path) { | |
48 struct stat result; | |
49 if (stat(file_path.AsUTF8Unsafe().c_str(), &result) != 0) { | |
50 return -1; | |
51 } | |
52 return result.st_nlink; | |
53 } | |
54 | |
55 } // namespace | 43 } // namespace |
56 | 44 |
57 // Tests FileCache methods working with the blocking task runner. | 45 // Tests FileCache methods working with the blocking task runner. |
58 class FileCacheTest : public testing::Test { | 46 class FileCacheTest : public testing::Test { |
59 protected: | 47 protected: |
60 void SetUp() override { | 48 void SetUp() override { |
61 ASSERT_TRUE(temp_dir_.CreateUniqueTempDir()); | 49 ASSERT_TRUE(temp_dir_.CreateUniqueTempDir()); |
62 const base::FilePath metadata_dir = temp_dir_.path().AppendASCII("meta"); | 50 const base::FilePath metadata_dir = temp_dir_.path().AppendASCII("meta"); |
63 cache_files_dir_ = temp_dir_.path().Append(kCacheFileDirectory); | 51 cache_files_dir_ = temp_dir_.path().Append(kCacheFileDirectory); |
64 | 52 |
(...skipping 649 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
714 // Test for migrating cache files from files to blobs. | 702 // Test for migrating cache files from files to blobs. |
715 TEST_F(FileCacheTest, MigrateCacheFiles) { | 703 TEST_F(FileCacheTest, MigrateCacheFiles) { |
716 // Create test files and metadata. | 704 // Create test files and metadata. |
717 base::FilePath temp_file; | 705 base::FilePath temp_file; |
718 ASSERT_TRUE(base::CreateTemporaryFileInDir(temp_dir_.path(), &temp_file)); | 706 ASSERT_TRUE(base::CreateTemporaryFileInDir(temp_dir_.path(), &temp_file)); |
719 | 707 |
720 const base::FilePath old_cache_dir = | 708 const base::FilePath old_cache_dir = |
721 temp_dir_.path().Append(kCacheFileDirectory); | 709 temp_dir_.path().Append(kCacheFileDirectory); |
722 const base::FilePath new_cache_dir = | 710 const base::FilePath new_cache_dir = |
723 temp_dir_.path().Append(kNewCacheFileDirectory); | 711 temp_dir_.path().Append(kNewCacheFileDirectory); |
724 const base::FilePath link_dir = temp_dir_.path().Append(kLinkDirectory); | |
725 ASSERT_TRUE(base::CreateDirectory(old_cache_dir)); | 712 ASSERT_TRUE(base::CreateDirectory(old_cache_dir)); |
726 ASSERT_TRUE(base::CreateDirectory(new_cache_dir)); | 713 ASSERT_TRUE(base::CreateDirectory(new_cache_dir)); |
727 ASSERT_TRUE(base::CreateDirectory(link_dir)); | |
728 | 714 |
729 // Entry A: cache file in old cache directory with metadata. | 715 // Entry A: cache file in old cache directory with metadata. |
730 const std::string id_a = "id_a"; | 716 const std::string id_a = "id_a"; |
731 ResourceEntry entry_a; | 717 ResourceEntry entry_a; |
732 entry_a.set_local_id(id_a); | 718 entry_a.set_local_id(id_a); |
733 entry_a.mutable_file_specific_info()->mutable_cache_state()->set_is_present( | 719 entry_a.mutable_file_specific_info()->mutable_cache_state()->set_is_present( |
734 true); | 720 true); |
735 ASSERT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry_a)); | 721 ASSERT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry_a)); |
736 const base::FilePath old_file_path_a = old_cache_dir.AppendASCII(id_a); | 722 const base::FilePath old_file_path_a = old_cache_dir.AppendASCII(id_a); |
737 const base::FilePath new_file_path_a = new_cache_dir.AppendASCII(id_a); | 723 const base::FilePath new_file_path_a = new_cache_dir.AppendASCII(id_a); |
(...skipping 15 matching lines...) Expand all Loading... |
753 ASSERT_TRUE(base::CopyFile(temp_file, new_file_path_c)); | 739 ASSERT_TRUE(base::CopyFile(temp_file, new_file_path_c)); |
754 | 740 |
755 // Entry D: metadata entry without cache file. | 741 // Entry D: metadata entry without cache file. |
756 const std::string id_d = "id_d"; | 742 const std::string id_d = "id_d"; |
757 ResourceEntry entry_d; | 743 ResourceEntry entry_d; |
758 entry_d.set_local_id(id_d); | 744 entry_d.set_local_id(id_d); |
759 entry_d.mutable_file_specific_info()->mutable_cache_state()->set_is_present( | 745 entry_d.mutable_file_specific_info()->mutable_cache_state()->set_is_present( |
760 true); | 746 true); |
761 ASSERT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry_d)); | 747 ASSERT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry_d)); |
762 | 748 |
763 // Entry E: pinned cache file. | |
764 const std::string id_e = "id_e"; | |
765 ResourceEntry entry_e; | |
766 entry_e.set_local_id(id_e); | |
767 FileCacheEntry* file_cache_entry_e = | |
768 entry_e.mutable_file_specific_info()->mutable_cache_state(); | |
769 file_cache_entry_e->set_is_present(true); | |
770 file_cache_entry_e->set_is_pinned(true); | |
771 file_cache_entry_e->set_is_dirty(false); | |
772 ASSERT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry_e)); | |
773 const base::FilePath old_file_path_e = old_cache_dir.AppendASCII(id_e); | |
774 const base::FilePath new_file_path_e = new_cache_dir.AppendASCII(id_e); | |
775 const base::FilePath link_path_e = link_dir.AppendASCII(id_e); | |
776 ASSERT_TRUE(base::CopyFile(temp_file, old_file_path_e)); | |
777 | |
778 // Entry F: dirty cache file. | |
779 const std::string id_f = "id_f"; | |
780 ResourceEntry entry_f; | |
781 entry_f.set_local_id(id_f); | |
782 FileCacheEntry* file_cache_entry_f = | |
783 entry_f.mutable_file_specific_info()->mutable_cache_state(); | |
784 file_cache_entry_f->set_is_present(true); | |
785 file_cache_entry_f->set_is_pinned(false); | |
786 file_cache_entry_f->set_is_dirty(true); | |
787 ASSERT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry_f)); | |
788 const base::FilePath old_file_path_f = old_cache_dir.AppendASCII(id_f); | |
789 const base::FilePath new_file_path_f = new_cache_dir.AppendASCII(id_f); | |
790 const base::FilePath link_path_f = link_dir.AppendASCII(id_f); | |
791 ASSERT_TRUE(base::CopyFile(temp_file, old_file_path_f)); | |
792 | |
793 // Entry G: partially migrated pinned cache file. | |
794 const std::string id_g = "id_g"; | |
795 ResourceEntry entry_g; | |
796 entry_g.set_local_id(id_g); | |
797 FileCacheEntry* file_cache_entry_g = | |
798 entry_g.mutable_file_specific_info()->mutable_cache_state(); | |
799 file_cache_entry_g->set_is_present(true); | |
800 file_cache_entry_g->set_is_pinned(true); | |
801 file_cache_entry_g->set_is_dirty(false); | |
802 ASSERT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry_g)); | |
803 const base::FilePath old_file_path_g = old_cache_dir.AppendASCII(id_g); | |
804 const base::FilePath new_file_path_g = new_cache_dir.AppendASCII(id_g); | |
805 const base::FilePath link_path_g = link_dir.AppendASCII(id_g); | |
806 ASSERT_TRUE(base::CopyFile(temp_file, old_file_path_g)); | |
807 ASSERT_EQ(0, link(old_file_path_g.AsUTF8Unsafe().c_str(), | |
808 link_path_g.AsUTF8Unsafe().c_str())); | |
809 | |
810 // Entry H: pinned entry without cache file. | |
811 const std::string id_h = "id_h"; | |
812 ResourceEntry entry_h; | |
813 entry_h.set_local_id(id_h); | |
814 FileCacheEntry* file_cache_entry_h = | |
815 entry_h.mutable_file_specific_info()->mutable_cache_state(); | |
816 file_cache_entry_h->set_is_present(true); | |
817 file_cache_entry_h->set_is_pinned(true); | |
818 file_cache_entry_h->set_is_dirty(false); | |
819 ASSERT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry_h)); | |
820 | |
821 // Entry I: already migrated pinned cache file. | |
822 const std::string id_i = "id_i"; | |
823 ResourceEntry entry_i; | |
824 entry_i.set_local_id(id_i); | |
825 FileCacheEntry* file_cache_entry_i = | |
826 entry_i.mutable_file_specific_info()->mutable_cache_state(); | |
827 file_cache_entry_i->set_is_present(true); | |
828 file_cache_entry_i->set_is_pinned(true); | |
829 file_cache_entry_i->set_is_dirty(false); | |
830 ASSERT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry_i)); | |
831 const base::FilePath new_file_path_i = new_cache_dir.AppendASCII(id_i); | |
832 const base::FilePath link_path_i = link_dir.AppendASCII(id_i); | |
833 ASSERT_TRUE(base::CopyFile(temp_file, new_file_path_i)); | |
834 ASSERT_EQ(0, link(new_file_path_i.AsUTF8Unsafe().c_str(), | |
835 link_path_i.AsUTF8Unsafe().c_str())); | |
836 | |
837 // Run migration. | 749 // Run migration. |
838 ASSERT_TRUE(FileCache::MigrateCacheFiles(old_cache_dir, new_cache_dir, | 750 ASSERT_TRUE(FileCache::MigrateCacheFiles(old_cache_dir, new_cache_dir, |
839 link_dir, metadata_storage_.get())); | 751 metadata_storage_.get())); |
840 | 752 |
841 // Check result. | 753 // Check result. |
842 EXPECT_FALSE(base::PathExists(old_file_path_a)); | 754 EXPECT_FALSE(base::PathExists(old_file_path_a)); |
843 EXPECT_TRUE(base::PathExists(new_file_path_a)); | 755 EXPECT_TRUE(base::PathExists(new_file_path_a)); |
844 EXPECT_EQ(1, GetNumberOfLinks(new_file_path_a)); | |
845 // MigrateCacheFiles doesn't delete invalid cache file. | 756 // MigrateCacheFiles doesn't delete invalid cache file. |
846 EXPECT_TRUE(base::PathExists(old_file_path_b)); | 757 EXPECT_TRUE(base::PathExists(old_file_path_b)); |
847 EXPECT_TRUE(base::PathExists(new_file_path_c)); | 758 EXPECT_TRUE(base::PathExists(new_file_path_c)); |
848 EXPECT_EQ(1, GetNumberOfLinks(new_file_path_c)); | |
849 EXPECT_FALSE(base::PathExists(old_file_path_e)); | |
850 EXPECT_TRUE(base::PathExists(new_file_path_e)); | |
851 EXPECT_TRUE(base::PathExists(link_path_e)); | |
852 EXPECT_EQ(2, GetNumberOfLinks(new_file_path_e)); | |
853 EXPECT_FALSE(base::PathExists(old_file_path_f)); | |
854 EXPECT_TRUE(base::PathExists(new_file_path_f)); | |
855 EXPECT_TRUE(base::PathExists(link_path_f)); | |
856 EXPECT_EQ(2, GetNumberOfLinks(new_file_path_f)); | |
857 EXPECT_FALSE(base::PathExists(old_file_path_g)); | |
858 EXPECT_TRUE(base::PathExists(new_file_path_g)); | |
859 EXPECT_TRUE(base::PathExists(link_path_g)); | |
860 EXPECT_EQ(2, GetNumberOfLinks(new_file_path_g)); | |
861 EXPECT_TRUE(base::PathExists(new_file_path_i)); | |
862 EXPECT_TRUE(base::PathExists(link_path_i)); | |
863 EXPECT_EQ(2, GetNumberOfLinks(new_file_path_i)); | |
864 } | 759 } |
865 | 760 |
866 TEST_F(FileCacheTest, ClearAll) { | 761 TEST_F(FileCacheTest, ClearAll) { |
867 const std::string id("1a2b"); | 762 const std::string id("1a2b"); |
868 const std::string md5("abcdef0123456789"); | 763 const std::string md5("abcdef0123456789"); |
869 | 764 |
870 // Store an existing file. | 765 // Store an existing file. |
871 ResourceEntry entry; | 766 ResourceEntry entry; |
872 entry.set_local_id(id); | 767 entry.set_local_id(id); |
873 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); | 768 EXPECT_EQ(FILE_ERROR_OK, metadata_storage_->PutEntry(entry)); |
874 base::FilePath src_file; | 769 base::FilePath src_file; |
875 ASSERT_TRUE(base::CreateTemporaryFileInDir(temp_dir_.path(), &src_file)); | 770 ASSERT_TRUE(base::CreateTemporaryFileInDir(temp_dir_.path(), &src_file)); |
876 ASSERT_EQ(FILE_ERROR_OK, | 771 ASSERT_EQ(FILE_ERROR_OK, |
877 cache_->Store(id, md5, src_file, FileCache::FILE_OPERATION_COPY)); | 772 cache_->Store(id, md5, src_file, FileCache::FILE_OPERATION_COPY)); |
878 | 773 |
879 // Clear cache. | 774 // Clear cache. |
880 EXPECT_TRUE(cache_->ClearAll()); | 775 EXPECT_TRUE(cache_->ClearAll()); |
881 | 776 |
882 // Verify that the cache is removed. | 777 // Verify that the cache is removed. |
883 EXPECT_TRUE(base::IsDirectoryEmpty(cache_files_dir_)); | 778 EXPECT_TRUE(base::IsDirectoryEmpty(cache_files_dir_)); |
884 } | 779 } |
885 | 780 |
886 } // namespace internal | 781 } // namespace internal |
887 } // namespace drive | 782 } // namespace drive |
OLD | NEW |