1 | /** |
2 | * Copyright 2021 Alibaba, Inc. and its affiliates. All Rights Reserved. |
3 | * |
4 | * Licensed under the Apache License, Version 2.0 (the "License"); |
5 | * you may not use this file except in compliance with the License. |
6 | * You may obtain a copy of the License at |
7 | * |
8 | * http://www.apache.org/licenses/LICENSE-2.0 |
9 | * |
10 | * Unless required by applicable law or agreed to in writing, software |
11 | * distributed under the License is distributed on an "AS IS" BASIS, |
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
13 | * See the License for the specific language governing permissions and |
14 | * limitations under the License. |
15 | */ |
16 | |
17 | #include "index/version_manager.h" |
18 | #include <gtest/gtest.h> |
19 | |
20 | using namespace proxima::be; |
21 | using namespace proxima::be::index; |
22 | |
23 | |
24 | class VersionManagerTest : public testing::Test { |
25 | protected: |
26 | void SetUp() { |
27 | char cmd_buf[100]; |
28 | snprintf(cmd_buf, 100, "rm -rf ./data.manifest" ); |
29 | system(cmd_buf); |
30 | } |
31 | |
32 | void TearDown() {} |
33 | }; |
34 | |
35 | TEST_F(VersionManagerTest, TestGeneral) { |
36 | auto version_manager = VersionManager::Create("collection_test" , "./" ); |
37 | ASSERT_NE(version_manager, nullptr); |
38 | |
39 | ReadOptions read_options; |
40 | read_options.use_mmap = true; |
41 | read_options.create_new = true; |
42 | int ret = version_manager->open(read_options); |
43 | ASSERT_EQ(ret, 0); |
44 | |
45 | ASSERT_EQ(version_manager->total_segment_count(), 1); |
46 | |
47 | for (size_t i = 1; i < 100; i++) { |
48 | SegmentMeta segment_meta; |
49 | int ret = version_manager->alloc_segment_meta(&segment_meta); |
50 | ASSERT_EQ(ret, 0); |
51 | segment_meta.state = SegmentState::WRITING; |
52 | ret = version_manager->update_segment_meta(segment_meta); |
53 | ASSERT_EQ(ret, 0); |
54 | ASSERT_EQ(segment_meta.segment_id, i); |
55 | ASSERT_EQ(version_manager->total_segment_count(), i + 1); |
56 | } |
57 | |
58 | for (size_t i = 0; i < 100; i++) { |
59 | VersionEdit edit; |
60 | edit.add_segments.emplace_back(i); |
61 | ret = version_manager->apply(edit); |
62 | ASSERT_EQ(ret, 0); |
63 | ASSERT_EQ(version_manager->current_version().size(), i + 1); |
64 | } |
65 | |
66 | for (size_t i = 0; i < 100; i++) { |
67 | SegmentMeta segment_meta; |
68 | segment_meta.segment_id = i; |
69 | segment_meta.state = SegmentState::WRITING; |
70 | segment_meta.doc_count = i; |
71 | segment_meta.min_primary_key = i; |
72 | segment_meta.max_primary_key = i; |
73 | segment_meta.min_doc_id = i; |
74 | segment_meta.max_doc_id = i; |
75 | segment_meta.min_timestamp = i; |
76 | segment_meta.max_timestamp = i; |
77 | |
78 | ret = version_manager->update_segment_meta(segment_meta); |
79 | ASSERT_EQ(ret, 0); |
80 | } |
81 | |
82 | for (size_t i = 0; i < 100; i++) { |
83 | SegmentMeta segment_meta; |
84 | int ret = version_manager->get_segment_meta(i, &segment_meta); |
85 | ASSERT_EQ(ret, 0); |
86 | ASSERT_EQ(segment_meta.segment_id, i); |
87 | ASSERT_EQ(segment_meta.state, SegmentState::WRITING); |
88 | ASSERT_EQ(segment_meta.doc_count, i); |
89 | ASSERT_EQ(segment_meta.min_primary_key, i); |
90 | ASSERT_EQ(segment_meta.max_primary_key, i); |
91 | ASSERT_EQ(segment_meta.min_doc_id, i); |
92 | ASSERT_EQ(segment_meta.max_doc_id, i); |
93 | ASSERT_EQ(segment_meta.min_timestamp, i); |
94 | ASSERT_EQ(segment_meta.max_timestamp, i); |
95 | } |
96 | version_manager->close(); |
97 | |
98 | read_options.create_new = false; |
99 | ret = version_manager->open(read_options); |
100 | ASSERT_EQ(ret, 0); |
101 | for (size_t i = 0; i < 100; i++) { |
102 | SegmentMeta segment_meta; |
103 | int ret = version_manager->get_segment_meta(i, &segment_meta); |
104 | ASSERT_EQ(ret, 0); |
105 | ASSERT_EQ(segment_meta.segment_id, i); |
106 | ASSERT_EQ(segment_meta.state, SegmentState::WRITING); |
107 | ASSERT_EQ(segment_meta.doc_count, i); |
108 | ASSERT_EQ(segment_meta.min_doc_id, i); |
109 | ASSERT_EQ(segment_meta.max_doc_id, i); |
110 | ASSERT_EQ(segment_meta.min_primary_key, i); |
111 | ASSERT_EQ(segment_meta.max_primary_key, i); |
112 | ASSERT_EQ(segment_meta.min_timestamp, i); |
113 | ASSERT_EQ(segment_meta.max_timestamp, i); |
114 | } |
115 | |
116 | ASSERT_EQ(version_manager->current_version().size(), 100); |
117 | for (size_t i = 0; i < 100; i++) { |
118 | const SegmentMeta &segment_meta = version_manager->current_version()[i]; |
119 | ASSERT_EQ(segment_meta.segment_id, i); |
120 | ASSERT_EQ(segment_meta.doc_count, i); |
121 | ASSERT_EQ(segment_meta.min_primary_key, i); |
122 | ASSERT_EQ(segment_meta.max_primary_key, i); |
123 | ASSERT_EQ(segment_meta.min_doc_id, i); |
124 | ASSERT_EQ(segment_meta.max_doc_id, i); |
125 | ASSERT_EQ(segment_meta.min_timestamp, i); |
126 | ASSERT_EQ(segment_meta.max_timestamp, i); |
127 | } |
128 | |
129 | // test alloc unused segment meta |
130 | // check if it will be reused |
131 | for (size_t i = 0; i < 100; i++) { |
132 | SegmentMeta segment_meta; |
133 | int ret = version_manager->alloc_segment_meta(&segment_meta); |
134 | ASSERT_EQ(ret, 0); |
135 | ASSERT_EQ(segment_meta.segment_id, 100); |
136 | } |
137 | } |
138 | |
139 | TEST_F(VersionManagerTest, TestVersionEdit) { |
140 | auto version_manager = VersionManager::Create("collection_test" , "./" ); |
141 | ASSERT_NE(version_manager, nullptr); |
142 | |
143 | ReadOptions read_options; |
144 | read_options.use_mmap = true; |
145 | read_options.create_new = true; |
146 | int ret = version_manager->open(read_options); |
147 | ASSERT_EQ(ret, 0); |
148 | |
149 | for (size_t i = 0; i < 100; i++) { |
150 | SegmentMeta segment_meta; |
151 | ret = version_manager->alloc_segment_meta(&segment_meta); |
152 | ASSERT_EQ(ret, 0); |
153 | segment_meta.state = SegmentState::WRITING; |
154 | ret = version_manager->update_segment_meta(segment_meta); |
155 | ASSERT_EQ(ret, 0); |
156 | ASSERT_EQ(segment_meta.segment_id, i + 1); |
157 | } |
158 | |
159 | VersionEdit edit1; |
160 | edit1.add_segments.emplace_back(10); |
161 | edit1.add_segments.emplace_back(11); |
162 | |
163 | ret = version_manager->apply(edit1); |
164 | ASSERT_EQ(ret, 0); |
165 | ASSERT_EQ(version_manager->current_version().size(), 2); |
166 | ASSERT_EQ(version_manager->current_version()[0].segment_id, 10); |
167 | ASSERT_EQ(version_manager->current_version()[1].segment_id, 11); |
168 | |
169 | VersionEdit edit2; |
170 | edit2.add_segments.emplace_back(12); |
171 | edit2.add_segments.emplace_back(13); |
172 | edit2.delete_segments.emplace_back(10); |
173 | ret = version_manager->apply(edit2); |
174 | ASSERT_EQ(ret, 0); |
175 | ASSERT_EQ(version_manager->current_version().size(), 3); |
176 | ASSERT_EQ(version_manager->current_version()[0].segment_id, 11); |
177 | ASSERT_EQ(version_manager->current_version()[1].segment_id, 12); |
178 | ASSERT_EQ(version_manager->current_version()[2].segment_id, 13); |
179 | } |
180 | |