1 /*
2 * Copyright (c) 2021 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15 #ifndef OMIT_MULTI_VER
16 #include <gtest/gtest.h>
17 #include <ctime>
18 #include <string>
19
20 #include "delegate_callback.h"
21 #include "distributeddb_data_generator.h"
22 #include "distributed_test_tools.h"
23 #include "kv_store_delegate.h"
24 #include "kv_store_delegate_manager.h"
25 #include "kv_store_snapshot_callback.h"
26
27 using namespace std;
28 using namespace testing;
29 #if defined TESTCASES_USING_GTEST_EXT
30 using namespace testing::ext;
31 #endif
32 using namespace DistributedDB;
33 using namespace std::placeholders;
34 using namespace DistributedDBDataGenerator;
35
36 namespace DistributeddbKvBatchCrud {
37 class DistributeddbKvBatchCrudTest : public testing::Test {
38 public:
39 static void SetUpTestCase(void);
40 static void TearDownTestCase(void);
41 void SetUp();
42 void TearDown();
43 private:
44 };
45
46 const bool IS_LOCAL = false;
47 KvStoreDelegate *g_kvStoreBatchDelegate = nullptr; // the delegate used in this suit.
48 KvStoreDelegateManager *g_batchManager = nullptr;
SetUpTestCase(void)49 void DistributeddbKvBatchCrudTest::SetUpTestCase(void)
50 {
51 MST_LOG("SetUpTestCase before all cases local[%d].", IS_LOCAL);
52 RemoveDir(DIRECTOR);
53 KvOption option = g_kvOption;
54 option.localOnly = IS_LOCAL;
55 g_kvStoreBatchDelegate = DistributedTestTools::GetDelegateSuccess(g_batchManager,
56 g_kvdbParameter1, option);
57 ASSERT_TRUE(g_batchManager != nullptr && g_kvStoreBatchDelegate != nullptr);
58 }
59
TearDownTestCase(void)60 void DistributeddbKvBatchCrudTest::TearDownTestCase(void)
61 {
62 MST_LOG("TearDownTestCase after all cases.");
63 EXPECT_EQ(g_batchManager->CloseKvStore(g_kvStoreBatchDelegate), OK);
64 g_kvStoreBatchDelegate = nullptr;
65 DBStatus status = g_batchManager->DeleteKvStore(STORE_ID_1);
66 EXPECT_EQ(status, OK) << "fail to delete exist kvdb";
67 delete g_batchManager;
68 g_batchManager = nullptr;
69 RemoveDir(DIRECTOR);
70 }
71
SetUp(void)72 void DistributeddbKvBatchCrudTest::SetUp(void)
73 {
74 ASSERT_TRUE(g_kvStoreBatchDelegate != nullptr);
75 UnitTest *test = UnitTest::GetInstance();
76 ASSERT_NE(test, nullptr);
77 const TestInfo *testinfo = test->current_test_info();
78 ASSERT_NE(testinfo, nullptr);
79 string testCaseName = string(testinfo->name());
80 MST_LOG("[SetUp] test case %s is start to run", testCaseName.c_str());
81 }
82
TearDown(void)83 void DistributeddbKvBatchCrudTest::TearDown(void)
84 {
85 }
86
87 class KvStoreObserverSnapImpl final : public KvStoreObserver {
88 public:
OnChange(const KvStoreChangedData & data)89 void OnChange(const KvStoreChangedData &data)
90 {
91 changed_++;
92 onChangeTime_ = std::chrono::time_point_cast<std::chrono::microseconds>(std::chrono::steady_clock::now());
93 MST_LOG("comes a change,changed[%ld]!!!", changed_);
94 MST_LOG("GetEntriesInserted().size() = %zu, GetEntriesUpdated() = %zu, GetEntriesDeleted() = %zu",
95 data.GetEntriesInserted().size(), data.GetEntriesUpdated().size(), data.GetEntriesDeleted().size());
96 insertCrudList_.assign(data.GetEntriesInserted().begin(), data.GetEntriesInserted().end());
97 updateCrudList_.assign(data.GetEntriesUpdated().begin(), data.GetEntriesUpdated().end());
98 deleteCrudList_.assign(data.GetEntriesDeleted().begin(), data.GetEntriesDeleted().end());
99 }
100
KvStoreObserverSnapImpl()101 KvStoreObserverSnapImpl()
102 {
103 insertCrudList_.clear();
104 updateCrudList_.clear();
105 deleteCrudList_.clear();
106 changed_ = 0;
107 onChangeTime_ = std::chrono::time_point_cast<std::chrono::microseconds>(std::chrono::steady_clock::now());
108 }
109
~KvStoreObserverSnapImpl()110 ~KvStoreObserverSnapImpl()
111 {
112 changed_ = 0;
113 }
114
GetChanged()115 long GetChanged()
116 {
117 return changed_;
118 }
119
GetInsertList()120 const list<Entry> GetInsertList()
121 {
122 return insertCrudList_;
123 }
124
GetDeleteList()125 const list<Entry> GetDeleteList()
126 {
127 return deleteCrudList_;
128 }
129
GetUpdateList()130 const list<Entry> GetUpdateList()
131 {
132 return updateCrudList_;
133 }
134
GetOnChangeTime()135 microClock_type GetOnChangeTime()
136 {
137 return onChangeTime_;
138 }
139
Clear()140 void Clear()
141 {
142 insertCrudList_.clear();
143 deleteCrudList_.clear();
144 updateCrudList_.clear();
145 changed_ = 0;
146 }
147
148 private:
149 list<Entry> insertCrudList_ = {};
150 list<Entry> deleteCrudList_ = {};
151 list<Entry> updateCrudList_ = {};
152 long changed_ = 0;
153 microClock_type onChangeTime_
154 = std::chrono::time_point_cast<std::chrono::microseconds>(std::chrono::steady_clock::now());
155 };
156
157 /*
158 * @tc.name: SimpleData 001
159 * @tc.desc: Verify that can PutBatch(keys,values) and get.
160 * @tc.type: FUN
161 * @tc.require: SR000BUH3J
162 * @tc.author: luqianfu
163 */
164 HWTEST_F(DistributeddbKvBatchCrudTest, SimpleData001, TestSize.Level1)
165 {
166 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
167
168 vector<Entry> entries1;
169 entries1.push_back(ENTRY_1);
170 entries1.push_back(ENTRY_2);
171 vector<Entry> entries2;
172 entries2.push_back(ENTRY_3);
173
174 /**
175 * @tc.steps: step1. create kv db and PutBatch (k1,v1)(k2,v2) then get.
176 * @tc.expected: step1. PutBatch successfully and get the value of k1 is v1,get the value of k2 is v2.
177 */
178 DBStatus status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries1);
179 EXPECT_EQ(status, OK);
180 Value valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
181 EXPECT_NE(valueResult.size(), size_t(0));
182 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_1));
183 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_2);
184 EXPECT_NE(valueResult.size(), size_t(0));
185 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_2));
186
187 /**
188 * @tc.steps: step2. create kv db and PutBatch (k3,v3) then get.
189 * @tc.expected: step2. PutBatch successfully and get the value of k3 is v3.
190 */
191 DBStatus status2 = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries2);
192 EXPECT_EQ(status2, OK);
193 Value valueResult2 = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_3);
194 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult2, VALUE_3));
195
196 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
197 }
198
199 /*
200 * @tc.name: SimpleData 002
201 * @tc.desc: Verify that can PutBatch(keys,values) and update them.
202 * @tc.type: FUN
203 * @tc.require: SR000BUH3J
204 * @tc.author: luqianfu
205 */
206 HWTEST_F(DistributeddbKvBatchCrudTest, SimpleData002, TestSize.Level1)
207 {
208 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
209
210 vector<Entry> entries1;
211 entries1.push_back(ENTRY_1);
212 entries1.push_back(ENTRY_2);
213 vector<Entry> entries1Up;
214 entries1Up.push_back(ENTRY_1_2);
215 entries1Up.push_back(ENTRY_2_3);
216
217 /**
218 * @tc.steps: step1. create kv db and PutBatch (k1,v1)(k2,v2) then get.
219 * @tc.expected: step1. PutBatch successfully and get the value of k1 is v1,get the value of k2 is v2.
220 */
221 DBStatus status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries1);
222 EXPECT_EQ(status, OK);
223
224 Value valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
225 EXPECT_NE(valueResult.size(), size_t(0));
226 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_1));
227
228 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_2);
229 EXPECT_NE(valueResult.size(), size_t(0));
230 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_2));
231
232 /**
233 * @tc.steps: step2. update (k1,v1)(k2,v2) to (k1,v2)(k2,v3).
234 * @tc.expected: step2. update successfully and get the value of k1 is v2,get the value of k2 is v3.
235 */
236 status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries1Up);
237 EXPECT_EQ(status, DBStatus::OK);
238
239 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
240 EXPECT_NE(valueResult.size(), size_t(0));
241 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_2));
242
243 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_2);
244 EXPECT_NE(valueResult.size(), size_t(0));
245 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_3));
246
247 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
248 }
249
250 /*
251 * @tc.name: SimpleData 003
252 * @tc.desc: Verify that can deletebatch list.
253 * @tc.type: FUN
254 * @tc.require: SR000BUH3J
255 * @tc.author: luqianfu
256 */
257 HWTEST_F(DistributeddbKvBatchCrudTest, SimpleData003, TestSize.Level1)
258 {
259 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
260 vector<Entry> entries1;
261 entries1.push_back(ENTRY_1);
262 entries1.push_back(ENTRY_2);
263 /**
264 * @tc.steps: step1. create kv db and PutBatch (k1,v1)(k2,v2) then get.
265 * @tc.expected: step1. PutBatch successfully and get the value of k1 is v1,get the value of k2 is v2.
266 */
267 DBStatus status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries1);
268 ASSERT_EQ(status, DBStatus::OK);
269 Value valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
270 EXPECT_NE(valueResult.size(), size_t(0));
271 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_1));
272 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_2);
273 EXPECT_NE(valueResult.size(), size_t(0));
274 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_2));
275
276 /**
277 * @tc.steps: step2. deleteBatch (k1)(k2) then get.
278 * @tc.expected: step2. deleteBatch successfully and get the value of k1 is null,get the value of k2 is null.
279 */
280 vector<Key> keys1;
281 keys1.push_back(ENTRY_1.key);
282 keys1.push_back(ENTRY_2.key);
283
284 DBStatus status2 = DistributedTestTools::DeleteBatch(*g_kvStoreBatchDelegate, keys1);
285
286 ASSERT_EQ(status2, DBStatus::OK);
287 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
288 EXPECT_EQ(valueResult.size(), size_t(0));
289 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_2);
290 EXPECT_EQ(valueResult.size(), size_t(0));
291 }
292
293 /*
294 * @tc.name: SimpleData 004
295 * @tc.desc: Verify that can put batch with some null value.
296 * @tc.type: FUN
297 * @tc.require: SR000BUH3J
298 * @tc.author: luqianfu
299 */
300 HWTEST_F(DistributeddbKvBatchCrudTest, SimpleData004, TestSize.Level1)
301 {
302 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
303
304 vector<Entry> entries1;
305 entries1.push_back(ENTRY_1_NULL); // KEY_1 with null value.
306 entries1.push_back(ENTRY_2);
307
308 /**
309 * @tc.steps: step1. create kv db and PutBatch (k1,v1)(k2,v2) that v1=null.
310 * @tc.expected: step1. PutBatch successfully.
311 */
312 DBStatus status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries1);
313 ASSERT_TRUE(status == DBStatus::OK);
314
315 /**
316 * @tc.steps: step2. get k1,k2 from db.
317 * @tc.expected: step2. get the value of k1 is null,get the value of k2 is not null.
318 */
319 Value valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
320 EXPECT_EQ(valueResult.size(), size_t(0));
321 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_2);
322 EXPECT_NE(valueResult.size(), size_t(0));
323 }
324
325 /*
326 * @tc.name: SimpleData 005
327 * @tc.desc: Verify that can not put batch with some null key.
328 * @tc.type: FUN
329 * @tc.require: SR000BUH3J
330 * @tc.author: luqianfu
331 */
332 HWTEST_F(DistributeddbKvBatchCrudTest, SimpleData005, TestSize.Level1)
333 {
334 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
335
336 vector<Entry> entries1;
337 entries1.push_back(ENTRY_NULL_1); // null key with VALUE_1.
338 entries1.push_back(ENTRY_2);
339
340 /**
341 * @tc.steps: step1. create kv db and PutBatch (k1,v1)(k2,v2) that k1=null.
342 * @tc.expected: step1. PutBatch failed.
343 */
344 DBStatus status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries1);
345 ASSERT_TRUE(status != DBStatus::OK);
346
347 /**
348 * @tc.steps: step2. get k1,k2 from db.
349 * @tc.expected: step2. get the value of k1 is null,get the value of k2 is null.
350 */
351 Value valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
352 EXPECT_EQ(valueResult.size(), size_t(0));
353 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_2);
354 EXPECT_EQ(valueResult.size(), size_t(0));
355 }
356
357 /*
358 * @tc.name: SimpleData 006
359 * @tc.desc: Verify that get batch none exist data will get null.
360 * @tc.type: FUN
361 * @tc.require: SR000BUH3J
362 * @tc.author: luqianfu
363 */
364 HWTEST_F(DistributeddbKvBatchCrudTest, SimpleData006, TestSize.Level1)
365 {
366 /**
367 * @tc.steps: step1. clear kv db.
368 * @tc.expected: step1. Construct that none exist data.
369 */
370 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
371
372 /**
373 * @tc.steps: step2. get batch(k1)(k2).
374 * @tc.expected: step2. get null.
375 */
376 vector<Entry> valueResult = DistributedTestTools::GetEntries(*g_kvStoreBatchDelegate, KEY_SEARCH);
377 ASSERT_TRUE(valueResult.size() == 0);
378 }
379
380 /*
381 * @tc.name: SimpleData 007
382 * @tc.desc: Verify that delete batch none exist data will return OK.
383 * @tc.type: FUN
384 * @tc.require: SR000BUH3J
385 * @tc.author: luqianfu
386 */
387 HWTEST_F(DistributeddbKvBatchCrudTest, SimpleData007, TestSize.Level1)
388 {
389 /**
390 * @tc.steps: step1. clear kv db.
391 * @tc.expected: step1. Construct that none exist data.
392 */
393 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
394
395 vector<Key> keys1;
396 keys1.push_back(ENTRY_1.key);
397 keys1.push_back(ENTRY_2.key);
398
399 /**
400 * @tc.steps: step2. delete batch none exist data.
401 * @tc.expected: step2. delete failed but return OK.
402 */
403 DBStatus status = DistributedTestTools::DeleteBatch(*g_kvStoreBatchDelegate, keys1);
404 ASSERT_TRUE(status == DBStatus::OK);
405 }
406
407 /*
408 * @tc.name: SimpleData 008
409 * @tc.desc: Verify that can get entries with prefix-key.
410 * @tc.type: FUN
411 * @tc.require: SR000BUH3J
412 * @tc.author: luqianfu
413 */
414 HWTEST_F(DistributeddbKvBatchCrudTest, SimpleData008, TestSize.Level1)
415 {
416 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
417 vector<Entry> entries1;
418 entries1.push_back(ENTRY_A_1);
419 entries1.push_back(ENTRY_A_2);
420 entries1.push_back(ENTRY_A_3);
421 DBStatus status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries1);
422 ASSERT_TRUE(status == DBStatus::OK);
423
424 /**
425 * @tc.steps: step1. get entries that prefix-key="ab".
426 * @tc.expected: step1. get 3 records which are key="abc","abcdasd","abcds".
427 */
428 vector<Entry> valueResult = DistributedTestTools::GetEntries(*g_kvStoreBatchDelegate, KEY_SEARCH);
429 MST_LOG("value size %zu", valueResult.size());
430 EXPECT_EQ(valueResult.size(), THREE_RECORDS);
431 /**
432 * @tc.steps: step2. get entries that prefix-key="abcde".
433 * @tc.expected: step2. get 0 record.
434 */
435 valueResult = DistributedTestTools::GetEntries(*g_kvStoreBatchDelegate, KEY_SEARCH_2);
436 EXPECT_EQ(valueResult.size(), size_t(0));
437 }
438
439 /*
440 * @tc.name: SimpleData 009
441 * @tc.desc: Verify that get entries with null key will return all records.
442 * @tc.type: FUN
443 * @tc.require: SR000BUH3J
444 * @tc.author: luqianfu
445 */
446 HWTEST_F(DistributeddbKvBatchCrudTest, SimpleData009, TestSize.Level1)
447 {
448 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
449 vector<Entry> entries1;
450 entries1.push_back(ENTRY_A_1);
451 entries1.push_back(ENTRY_A_2);
452 entries1.push_back(ENTRY_A_3);
453 /**
454 * @tc.steps: step1. PutBatch (k1=abc,v1=a1)(k2=abcdasd,v2=a2)(k3=abcds,v3=a3).
455 * @tc.expected: step1. PutBatch successfully to construct exist data.
456 */
457 DBStatus status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries1);
458 ASSERT_TRUE(status == DBStatus::OK);
459
460 /**
461 * @tc.steps: step2. GetEntries with key=null.
462 * @tc.expected: step2. GetEntries successfully and return all records in db.
463 */
464 vector<Entry> valueResult = DistributedTestTools::GetEntries(*g_kvStoreBatchDelegate, KEY_EMPTY);
465 ASSERT_TRUE(valueResult.size() == entries1.size());
466 }
467
468 /*
469 * @tc.name: SimpleData 010
470 * @tc.desc: Verify that can release snapshot.
471 * @tc.type: FUN
472 * @tc.require: SR000CQDTF
473 * @tc.author: luqianfu
474 */
475 HWTEST_F(DistributeddbKvBatchCrudTest, SimpleData010, TestSize.Level1)
476 {
477 DelegateCallback delegateCallback;
478 function<void(DBStatus, KvStoreSnapshotDelegate *)> function
479 = bind(&DelegateCallback::Callback, &delegateCallback, _1, _2);
480
481 g_kvStoreBatchDelegate->GetKvStoreSnapshot(nullptr, function);
482 DBStatus status = delegateCallback.GetStatus();
483 EXPECT_EQ(status, DBStatus::OK);
484 KvStoreSnapshotDelegate *snapshot
485 = const_cast<KvStoreSnapshotDelegate *>(delegateCallback.GetKvStoreSnapshot());
486 EXPECT_NE(snapshot, nullptr);
487 /**
488 * @tc.steps: step1. release snapshot.
489 * @tc.expected: step1. release snapshot successfully.
490 */
491 EXPECT_EQ(g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snapshot), OK);
492 }
493
PutBatchTwoRecords(vector<Entry> & entries)494 bool PutBatchTwoRecords(vector<Entry> &entries)
495 {
496 bool result = true;
497 DBStatus status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries);
498 result = result && (status == DBStatus::OK);
499 Value valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, entries[0].key);
500 result = result && (valueResult.size() != 0);
501 if (!result) {
502 MST_LOG("value.size() of entries[0].key is 0, and failed");
503 }
504 result = result && (DistributedTestTools::IsValueEquals(valueResult, entries[0].value));
505 if (!result) {
506 MST_LOG("value.size() Got of entries[0].key is not equal to the value entries[0].key Expected");
507 }
508 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, entries[1].key);
509 result = result && (valueResult.size() != 0);
510 if (!result) {
511 MST_LOG("value.size() of entries[1].key is 0, and failed");
512 }
513 result = result && (DistributedTestTools::IsValueEquals(valueResult, entries[1].value));
514 if (!result) {
515 MST_LOG("value.size() Got of entries[1].key is not equal to the value entries[1].key Expected");
516 }
517 return result;
518 }
519
520 /*
521 * @tc.name: ComplexData 001
522 * @tc.desc: Verify that can batch crud for same keys repeatedly.
523 * @tc.type: FUN
524 * @tc.require: SR000CQDTF
525 * @tc.author: luqianfu
526 */
527 HWTEST_F(DistributeddbKvBatchCrudTest, ComplexData001, TestSize.Level1)
528 {
529 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
530
531 vector<Entry> entries1;
532 entries1.push_back(ENTRY_1);
533 entries1.push_back(ENTRY_2);
534 vector<Entry> entries12;
535 entries12.push_back(ENTRY_1_2);
536 entries12.push_back(ENTRY_2_3);
537
538 /**
539 * @tc.steps: step1. PutBatch (k1,v1)(k2,v2) and then get.
540 * @tc.expected: step1. PutBatch successfully get v1 of k1,v2 of k2.
541 */
542 EXPECT_TRUE(PutBatchTwoRecords(entries1));
543
544 /**
545 * @tc.steps: step2. DeleteBatch (k1)(k2) and then get.
546 * @tc.expected: step2. DeleteBatch successfully get null of k1,k2.
547 */
548 DBStatus status2 = DistributedTestTools::DeleteBatch(*g_kvStoreBatchDelegate, KEYS_1);
549 ASSERT_EQ(status2, DBStatus::OK);
550 Value valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
551 EXPECT_EQ(valueResult.size(), size_t(0));
552 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_2);
553 EXPECT_EQ(valueResult.size(), size_t(0));
554
555 /**
556 * @tc.steps: step3. PutBatch (k1,v1)(k2,v2) and then get.
557 * @tc.expected: step3. PutBatch successfully get v1,v2 of k1,k2.
558 */
559 EXPECT_TRUE(PutBatchTwoRecords(entries1));
560
561 /**
562 * @tc.steps: step4. PutBatch (k1,v2)(k2,v3) and then get.
563 * @tc.expected: step4. PutBatch successfully get v2 of k1,v3 of k2.
564 */
565 EXPECT_TRUE(PutBatchTwoRecords(entries12));
566
567 /**
568 * @tc.steps: step5. DeleteBatch (k1)(k2) and then get.
569 * @tc.expected: step5. DeleteBatch successfully get null of k1,k2.
570 */
571 status2 = DistributedTestTools::DeleteBatch(*g_kvStoreBatchDelegate, KEYS_1);
572 EXPECT_EQ(status2, DBStatus::OK);
573 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
574 EXPECT_EQ(valueResult.size(), size_t(0));
575 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_2);
576 EXPECT_EQ(valueResult.size(), size_t(0));
577 }
578
CheckBatchCrud(vector<Key> keys23)579 void CheckBatchCrud(vector<Key> keys23)
580 {
581 /**
582 * @tc.steps: step3. Put(k1,v3) Put(k2,v4) Put(k3,v3) and then get.
583 * @tc.expected: step3. Put successfully get v3 of k1,v4 of k2,v3 of k3.
584 */
585 DBStatus status = DistributedTestTools::Put(*g_kvStoreBatchDelegate, ENTRY_1_3.key, ENTRY_1_3.value);
586 ASSERT_EQ(status, DBStatus::OK);
587 status = DistributedTestTools::Put(*g_kvStoreBatchDelegate, ENTRY_2_4.key, ENTRY_2_4.value);
588 ASSERT_EQ(status, DBStatus::OK);
589 status = DistributedTestTools::Put(*g_kvStoreBatchDelegate, ENTRY_3.key, ENTRY_3.value);
590 ASSERT_EQ(status, DBStatus::OK);
591 Value valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
592 EXPECT_NE(valueResult.size(), size_t(0));
593 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_3));
594 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_2);
595 EXPECT_NE(valueResult.size(), size_t(0));
596 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_4));
597 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_3);
598 EXPECT_NE(valueResult.size(), size_t(0));
599 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_3));
600 /**
601 * @tc.steps: step4. DeleteBatch (k2)(k3) and then get.
602 * @tc.expected: step4. DeleteBatch successfully get not null of k1,null of k2,k3.
603 */
604 DBStatus status2 = DistributedTestTools::DeleteBatch(*g_kvStoreBatchDelegate, keys23);
605 ASSERT_TRUE(status2 == DBStatus::OK);
606 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
607 EXPECT_NE(valueResult.size(), size_t(0));
608 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_3));
609 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_2);
610 EXPECT_TRUE(valueResult.size() == size_t(0));
611 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_3);
612 EXPECT_TRUE(valueResult.size() == size_t(0));
613 /**
614 * @tc.steps: step5. clear all and then Put(k1,v1) then get.
615 * @tc.expected: step5. clear and Put successfully, get v1 of k1.
616 */
617 status2 = DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
618 ASSERT_TRUE(status2 == DBStatus::OK);
619 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
620 EXPECT_TRUE(valueResult.size() == size_t(0));
621 status = DistributedTestTools::Put(*g_kvStoreBatchDelegate, ENTRY_1.key, ENTRY_1.value);
622 ASSERT_TRUE(status == DBStatus::OK);
623 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
624 EXPECT_TRUE(valueResult.size() != size_t(0));
625 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_1));
626 }
627
628 /*
629 * @tc.name: ComplexData 002
630 * @tc.desc: Verify that can batch and single crud continuously.
631 * @tc.type: FUN
632 * @tc.require: SR000BUH3J
633 * @tc.author: luqianfu
634 */
635 HWTEST_F(DistributeddbKvBatchCrudTest, ComplexData002, TestSize.Level1)
636 {
637 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
638
639 vector<Entry> entries1;
640 entries1.push_back(ENTRY_1);
641 entries1.push_back(ENTRY_2);
642 vector<Entry> entries12;
643 entries12.push_back(ENTRY_1_2);
644 entries12.push_back(ENTRY_2_3);
645 vector<Entry> entries23;
646 entries23.push_back(ENTRY_2);
647 entries23.push_back(ENTRY_3);
648 vector<Key> keys23;
649 keys23.push_back(ENTRY_2.key);
650 keys23.push_back(ENTRY_3.key);
651
652 /**
653 * @tc.steps: step1. PutBatch (k1,v1)(k2,v2) and then get.
654 * @tc.expected: step1. PutBatch successfully get v1 of k1,v2 of k2.
655 */
656 EXPECT_TRUE(PutBatchTwoRecords(entries1));
657
658 /**
659 * @tc.steps: step2. delete k1 and then get.
660 * @tc.expected: step2. delete successfully get null of k1,v2 of k2.
661 */
662 DBStatus status2 = DistributedTestTools::Delete(*g_kvStoreBatchDelegate, KEY_1);
663 ASSERT_TRUE(status2 == DBStatus::OK);
664 Value valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_1);
665 EXPECT_TRUE(valueResult.size() == 0);
666 valueResult = DistributedTestTools::Get(*g_kvStoreBatchDelegate, KEY_2);
667 EXPECT_TRUE(valueResult.size() != 0);
668 EXPECT_TRUE(DistributedTestTools::IsValueEquals(valueResult, VALUE_2));
669
670 CheckBatchCrud(keys23);
671 }
672
MultiSnapCheck1(vector<Entry> & entries1,vector<Entry> & entries2,DistributedDB::Key & keyPrefix,KvStoreObserverSnapImpl & observer3,KvStoreObserverSnapImpl & observer4)673 vector<Entry> MultiSnapCheck1(vector<Entry> &entries1, vector<Entry> &entries2, DistributedDB::Key &keyPrefix,
674 KvStoreObserverSnapImpl &observer3, KvStoreObserverSnapImpl &observer4)
675 {
676 /**
677 * @tc.steps: step3. Register snap2 then getEntries with keyPrefix="k".
678 * @tc.expected: step3. operate successfully and getEntries are null.
679 */
680 KvStoreObserverSnapImpl observer2;
681 KvStoreSnapshotCallback kvStoreSnapshotCallback2;
682 function<void(DBStatus, const std::vector<Entry>&)> function2
683 = bind(&KvStoreSnapshotCallback::Callback, &kvStoreSnapshotCallback2, _1, _2);
684 KvStoreSnapshotDelegate *snap2 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer2);
685 EXPECT_NE(snap2, nullptr);
686 snap2->GetEntries(keyPrefix, function2);
687 vector<Entry> resultEntries2 = kvStoreSnapshotCallback2.GetEntries();
688 vector<Entry> resultEmptyEntry;
689 EXPECT_TRUE(CompareEntriesVector(resultEntries2, resultEmptyEntry));
690 /**
691 * @tc.steps: step4. putBatch (k1,v1)(k2,v2) again and Register snap3 then getEntries with keyPrefix="k".
692 * @tc.expected: step4. operate successfully and getEntries are (k1,v1)(k2,v2).
693 */
694 vector<Entry> entriesInDB;
695 DBStatus status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries1);
696 EXPECT_TRUE(status == DBStatus::OK);
697 for (auto eachEntry : entries1) {
698 entriesInDB.push_back(eachEntry);
699 }
700 KvStoreSnapshotCallback kvStoreSnapshotCallback3;
701 function<void(DBStatus, const std::vector<Entry>&)> function3
702 = bind(&KvStoreSnapshotCallback::Callback, &kvStoreSnapshotCallback3, _1, _2);
703 KvStoreSnapshotDelegate *snap3 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer3);
704 EXPECT_NE(snap3, nullptr);
705 snap3->GetEntries(keyPrefix, function3);
706 vector<Entry> resultEntries3 = kvStoreSnapshotCallback3.GetEntries();
707 EXPECT_TRUE(CompareEntriesVector(resultEntries3, entries1));
708 /**
709 * @tc.steps: step5. putBatch (k1,v2)(k2,v3) again, Register snap4 then getEntries with keyPrefix="k".
710 * @tc.expected: step5. operate successfully and getEntries are (k1,v2)(k2,v3).
711 */
712 status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries2);
713 for (auto eachEntry : entries2) {
714 PutUniqueKey(entriesInDB, eachEntry.key, eachEntry.value);
715 }
716 KvStoreSnapshotCallback kvStoreSnapshotCallback4;
717 function<void(DBStatus, const std::vector<Entry>&)> function4
718 = bind(&KvStoreSnapshotCallback::Callback, &kvStoreSnapshotCallback4, _1, _2);
719 KvStoreSnapshotDelegate *snap4 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer4);
720 EXPECT_NE(snap4, nullptr);
721 snap4->GetEntries(keyPrefix, function4);
722 vector<Entry> resultEntries4 = kvStoreSnapshotCallback4.GetEntries();
723 EXPECT_TRUE(CompareEntriesVector(resultEntries4, entries2));
724 status = g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap2);
725 EXPECT_TRUE(status == DBStatus::OK);
726 status = g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap3);
727 EXPECT_TRUE(status == DBStatus::OK);
728 status = g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap4);
729 EXPECT_TRUE(status == DBStatus::OK);
730 return entriesInDB;
731 }
732
SnapWithTransactionCheck(vector<Key> keys1,DistributedDB::Key keyPrefix,KvStoreObserverSnapImpl observer5,vector<Entry> entriesInDB)733 void SnapWithTransactionCheck(vector<Key> keys1, DistributedDB::Key keyPrefix,
734 KvStoreObserverSnapImpl observer5, vector<Entry> entriesInDB)
735 {
736 /**
737 * @tc.steps: step6. StartTransaction then deleteBatch (k1,v2)(k2,v3).
738 * @tc.expected: step6. operate successfully to construct there is no data in db.
739 */
740 KvStoreSnapshotCallback kvStoreSnapshotCallback5;
741 function<void(DBStatus, const std::vector<Entry>&)> function5
742 = bind(&KvStoreSnapshotCallback::Callback, &kvStoreSnapshotCallback5, _1, _2);
743
744 DBStatus statusStart = g_kvStoreBatchDelegate->StartTransaction();
745 EXPECT_TRUE(statusStart == DBStatus::OK);
746 DBStatus status = DistributedTestTools::DeleteBatch(*g_kvStoreBatchDelegate, keys1);
747 ASSERT_TRUE(status == DBStatus::OK);
748 for (unsigned long idxKey = 0; idxKey < keys1.size(); ++idxKey) {
749 for (unsigned long idxEntry = 0; idxEntry < entriesInDB.size(); ++idxEntry) {
750 if (CompareVector(keys1[idxKey], entriesInDB[idxEntry].key)) {
751 entriesInDB.erase(entriesInDB.begin() + idxEntry);
752 }
753 }
754 }
755 /**
756 * @tc.steps: step7. put(k1,v1)(k2,v3) alone and commit, Register snap5 to getEntries with prefix-key='k'.
757 * @tc.expected: step7. operate successfully and getEntries are (k1,v1)(k2,v3).
758 */
759 status = DistributedTestTools::Put(*g_kvStoreBatchDelegate, KEY_1, VALUE_1);
760 ASSERT_TRUE(status == DBStatus::OK);
761 PutUniqueKey(entriesInDB, KEY_1, VALUE_1);
762 status = DistributedTestTools::Put(*g_kvStoreBatchDelegate, KEY_2, VALUE_2);
763 ASSERT_TRUE(status == DBStatus::OK);
764 PutUniqueKey(entriesInDB, KEY_2, VALUE_2);
765 status = DistributedTestTools::Put(*g_kvStoreBatchDelegate, KEY_3, VALUE_3);
766 ASSERT_TRUE(status == DBStatus::OK);
767 PutUniqueKey(entriesInDB, KEY_3, VALUE_3);
768 status = DistributedTestTools::Put(*g_kvStoreBatchDelegate, KEY_2, VALUE_3);
769 ASSERT_TRUE(status == DBStatus::OK);
770 PutUniqueKey(entriesInDB, KEY_2, VALUE_3);
771 status = DistributedTestTools::Delete(*g_kvStoreBatchDelegate, KEY_3);
772 ASSERT_TRUE(status == DBStatus::OK);
773 for (unsigned long idx = 0; idx < entriesInDB.size(); ++idx) {
774 if (CompareVector(entriesInDB[idx].key, KEY_3)) {
775 entriesInDB.erase(entriesInDB.begin() + idx);
776 }
777 }
778 DBStatus statusCommit = g_kvStoreBatchDelegate->Commit();
779 EXPECT_TRUE(statusCommit == DBStatus::OK);
780 KvStoreSnapshotDelegate *snap5 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer5);
781 EXPECT_NE(snap5, nullptr);
782 snap5->GetEntries(keyPrefix, function5);
783 vector<Entry> resultEntries5 = kvStoreSnapshotCallback5.GetEntries();
784 EXPECT_TRUE(CompareEntriesVector(resultEntries5, entriesInDB));
785 status = g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap5);
786 ASSERT_TRUE(status == DBStatus::OK);
787 }
788
789 /*
790 * @tc.name: ComplexSnap 001
791 * @tc.desc: Verify that can read multiple snapshots correctly after crud repeatedly.
792 * @tc.type: FUN
793 * @tc.require: SR000BUH3J
794 * @tc.author: luqianfu
795 */
796 HWTEST_F(DistributeddbKvBatchCrudTest, ComplexSnap001, TestSize.Level1)
797 {
798 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
799 vector<Entry> entries1;
800 entries1.push_back(ENTRY_1);
801 entries1.push_back(ENTRY_2);
802 vector<Entry> entries2;
803 entries2.push_back(ENTRY_1_2);
804 entries2.push_back(ENTRY_2_3);
805 KvStoreObserverSnapImpl observer1;
806 KvStoreObserverSnapImpl observer3;
807 KvStoreObserverSnapImpl observer4;
808 KvStoreObserverSnapImpl observer5;
809 /**
810 * @tc.steps: step1. putBatch (k1,v1)(k2,v2) to db.
811 * @tc.expected: step1. putBatch successfully to construct data in db.
812 */
813 DBStatus status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries1);
814 ASSERT_TRUE(status == DBStatus::OK);
815 KvStoreSnapshotCallback kvStoreSnapshotCallback;
816 function<void(DBStatus, const std::vector<Entry>&)> function1
817 = bind(&KvStoreSnapshotCallback::Callback, &kvStoreSnapshotCallback, _1, _2);
818 /**
819 * @tc.steps: step2. Register snap1 then getEntries with keyPrefix="k" and then delete.
820 * @tc.expected: step2. operate successfully and getEntries are (k1,v1)(k2,v2).
821 */
822 KvStoreSnapshotDelegate *snap1 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer1);
823 EXPECT_NE(snap1, nullptr);
824 vector<Key> keys1;
825 for (unsigned long time = 0; time < entries1.size(); ++time) {
826 keys1.push_back(entries1.at(time).key);
827 }
828 DistributedDB::Key keyPrefix = { 'k' };
829 snap1->GetEntries(keyPrefix, function1);
830 vector<Entry> resultEntries = kvStoreSnapshotCallback.GetEntries();
831 EXPECT_TRUE(CompareEntriesVector(resultEntries, entries1));
832 status = DistributedTestTools::DeleteBatch(*g_kvStoreBatchDelegate, keys1);
833 ASSERT_TRUE(status == DBStatus::OK);
834 vector<Entry> entriesInDB = MultiSnapCheck1(entries1, entries2, keyPrefix, observer3, observer4);
835 SnapWithTransactionCheck(keys1, keyPrefix, observer5, entriesInDB);
836
837 status = g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap1);
838 ASSERT_TRUE(status == DBStatus::OK);
839 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
840 }
841
RegisterSnapAgainAndCheck1(KvStoreObserverSnapImpl & observer1,KvStoreSnapshotDelegate * & snap1,vector<Entry> & entries,DistributedDB::Key & keyPrefix)842 void RegisterSnapAgainAndCheck1(KvStoreObserverSnapImpl &observer1, KvStoreSnapshotDelegate *&snap1,
843 vector<Entry> &entries, DistributedDB::Key &keyPrefix)
844 {
845 DBStatus status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries);
846 ASSERT_TRUE(status == DBStatus::OK);
847 /**
848 * @tc.steps: step2. ReleaseKvStoreSnapshot then RegisterSnapObserver snap1 and getEntries with keyPrefix="k".
849 * @tc.expected: step2. operate successfully and getEntries are (k1,v1)(k2,v2).
850 */
851 status = g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap1);
852 ASSERT_TRUE(status == DBStatus::OK);
853 snap1 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer1);
854 EXPECT_NE(snap1, nullptr);
855 KvStoreSnapshotCallback kvStoreSnapshotCallback1;
856 function<void(DBStatus, const std::vector<Entry>&)> function1
857 = bind(&KvStoreSnapshotCallback::Callback, &kvStoreSnapshotCallback1, _1, _2);
858
859 snap1->GetEntries(keyPrefix, function1);
860 vector<Entry> resultEntries = kvStoreSnapshotCallback1.GetEntries();
861 EXPECT_TRUE(CompareEntriesVector(resultEntries, entries));
862 }
863
RegisterSnapAgainAndCheck2(KvStoreObserverSnapImpl & observer2,KvStoreSnapshotDelegate * & snap2,vector<Entry> & entries,DistributedDB::Key & keyPrefix)864 vector<Key> RegisterSnapAgainAndCheck2(KvStoreObserverSnapImpl &observer2, KvStoreSnapshotDelegate *&snap2,
865 vector<Entry> &entries, DistributedDB::Key &keyPrefix)
866 {
867 /**
868 * @tc.steps: step3. deleteBatch and RegisterSnapObserver snap2 then getEntries with keyPrefix="k".
869 * @tc.expected: step3. operate successfully and getEntries are null.
870 */
871 vector<Key> keys1;
872 for (unsigned long time = 0; time < entries.size(); ++time) {
873 keys1.push_back(entries.at(time).key);
874 }
875 DBStatus status = DistributedTestTools::DeleteBatch(*g_kvStoreBatchDelegate, keys1);
876 EXPECT_TRUE(status == DBStatus::OK);
877 status = g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap2);
878 EXPECT_TRUE(status == DBStatus::OK);
879 snap2 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer2);
880 EXPECT_NE(snap2, nullptr);
881 KvStoreSnapshotCallback kvStoreSnapshotCallback2;
882 function<void(DBStatus, const std::vector<Entry>&)> function2
883 = bind(&KvStoreSnapshotCallback::Callback, &kvStoreSnapshotCallback2, _1, _2);
884 snap2->GetEntries(keyPrefix, function2);
885 vector<Entry> resultEntries2 = kvStoreSnapshotCallback2.GetEntries();
886 vector<Entry> resultEmptyEntry;
887 EXPECT_TRUE(CompareEntriesVector(resultEntries2, resultEmptyEntry));
888 return keys1;
889 }
890
RegisterSnapAgainAndCheck3(KvStoreObserverSnapImpl & observer3,KvStoreSnapshotDelegate * & snap3,vector<Entry> & entries,DistributedDB::Key & keyPrefix)891 vector<Entry> RegisterSnapAgainAndCheck3(KvStoreObserverSnapImpl &observer3, KvStoreSnapshotDelegate *&snap3,
892 vector<Entry> &entries, DistributedDB::Key &keyPrefix)
893 {
894 /**
895 * @tc.steps: step4. putBatch (k1,v1)(k2,v2) again and RegisterSnapObserver snap3 then getEntries with keyPrefix="k"
896 * @tc.expected: step4. operate successfully and getEntries are (k1,v1)(k2,v2).
897 */
898 DBStatus status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries);
899 EXPECT_TRUE(status == DBStatus::OK);
900 vector<Entry> entriesInDB;
901 for (auto eachEntry : entries) {
902 entriesInDB.push_back(eachEntry);
903 }
904 status = g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap3);
905 EXPECT_TRUE(status == DBStatus::OK);
906 snap3 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer3);
907 EXPECT_NE(snap3, nullptr);
908 KvStoreSnapshotCallback kvStoreSnapshotCallback3;
909 function<void(DBStatus, const std::vector<Entry>&)> function3
910 = bind(&KvStoreSnapshotCallback::Callback, &kvStoreSnapshotCallback3, _1, _2);
911 snap3->GetEntries(keyPrefix, function3);
912 vector<Entry> resultEntries3 = kvStoreSnapshotCallback3.GetEntries();
913 EXPECT_TRUE(CompareEntriesVector(resultEntries3, entries));
914 return entriesInDB;
915 }
916
RegisterSnapAgainAndCheck4(KvStoreObserverSnapImpl & observer4,KvStoreSnapshotDelegate * & snap4,vector<Entry> & entries,DistributedDB::Key & keyPrefix,vector<Entry> & entriesInDB)917 void RegisterSnapAgainAndCheck4(KvStoreObserverSnapImpl &observer4, KvStoreSnapshotDelegate *&snap4,
918 vector<Entry> &entries, DistributedDB::Key &keyPrefix, vector<Entry> &entriesInDB)
919 {
920 /**
921 * @tc.steps: step5. putBatch (k1,v2)(k2,v3) again and RegisterSnapObserver snap4 then getEntries with keyPrefix="k"
922 * @tc.expected: step5. operate successfully and getEntries are (k1,v2)(k2,v3).
923 */
924 DBStatus status = DistributedTestTools::PutBatch(*g_kvStoreBatchDelegate, entries);
925 ASSERT_TRUE(status == DBStatus::OK);
926 for (auto eachEntry : entries) {
927 PutUniqueKey(entriesInDB, eachEntry.key, eachEntry.value);
928 }
929 status = g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap4);
930 ASSERT_TRUE(status == DBStatus::OK);
931 snap4 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer4);
932 EXPECT_NE(snap4, nullptr);
933 KvStoreSnapshotCallback kvStoreSnapshotCallback4;
934 function<void(DBStatus, const std::vector<Entry>&)> function4
935 = bind(&KvStoreSnapshotCallback::Callback, &kvStoreSnapshotCallback4, _1, _2);
936 snap4->GetEntries(keyPrefix, function4);
937 vector<Entry> resultEntries4 = kvStoreSnapshotCallback4.GetEntries();
938 EXPECT_TRUE(CompareEntriesVector(resultEntries4, entries));
939 }
940
PutAndCheck(DistributedDB::Key KEY_1,DistributedDB::Value VALUE_1,vector<Entry> & entriesInDB)941 void PutAndCheck(DistributedDB::Key KEY_1, DistributedDB::Value VALUE_1, vector<Entry> &entriesInDB)
942 {
943 DBStatus status = DistributedTestTools::Put(*g_kvStoreBatchDelegate, KEY_1, VALUE_1);
944 ASSERT_TRUE(status == DBStatus::OK);
945 PutUniqueKey(entriesInDB, KEY_1, VALUE_1);
946 }
947
RegisterSnapAgainAndCheck5(KvStoreObserverSnapImpl & observer5,KvStoreSnapshotDelegate * & snap5,vector<Entry> & entries1,DistributedDB::Key & keyPrefix,vector<Entry> & entriesInDB)948 void RegisterSnapAgainAndCheck5(KvStoreObserverSnapImpl &observer5, KvStoreSnapshotDelegate *&snap5,
949 vector<Entry> &entries1, DistributedDB::Key &keyPrefix, vector<Entry> &entriesInDB)
950 {
951 vector<Key> keys1;
952 for (unsigned long time = 0; time < entries1.size(); ++time) {
953 keys1.push_back(entries1.at(time).key);
954 }
955 /**
956 * @tc.steps: step6. StartTransaction then deleteBatch (k1,v2)(k2,v3).
957 * @tc.expected: step6. operate successfully to construct there is no data in db.
958 */
959 ASSERT_TRUE((g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap5)) == OK);
960 snap5 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer5);
961 EXPECT_NE(snap5, nullptr);
962 KvStoreSnapshotCallback kvStoreSnapshotCallback5;
963 function<void(DBStatus, const std::vector<Entry>&)> function5
964 = bind(&KvStoreSnapshotCallback::Callback, &kvStoreSnapshotCallback5, _1, _2);
965 EXPECT_TRUE((g_kvStoreBatchDelegate->StartTransaction()) == OK);
966 ASSERT_TRUE((DistributedTestTools::DeleteBatch(*g_kvStoreBatchDelegate, keys1)) == OK);
967 for (unsigned long idxKey = 0; idxKey < keys1.size(); ++idxKey) {
968 for (unsigned long idxEntry = 0; idxEntry < entriesInDB.size(); ++idxEntry) {
969 if (CompareVector(keys1[idxKey], entriesInDB[idxEntry].key)) {
970 entriesInDB.erase(entriesInDB.begin() + idxEntry);
971 }
972 }
973 }
974 /**
975 * @tc.steps: step7. put(k1,v1)(k2,v3) alone and commit, Register snap5 to getEntries with prefix-key='k'.
976 * @tc.expected: step7. operate successfully and getEntries are (k1,v1)(k2,v3).
977 */
978 PutAndCheck(KEY_1, VALUE_1, entriesInDB);
979 PutAndCheck(KEY_2, VALUE_2, entriesInDB);
980 PutAndCheck(KEY_3, VALUE_3, entriesInDB);
981 PutAndCheck(KEY_2, VALUE_3, entriesInDB);
982 ASSERT_TRUE((DistributedTestTools::Delete(*g_kvStoreBatchDelegate, KEY_3)) == OK);
983 for (unsigned long idx = 0; idx < entriesInDB.size(); ++idx) {
984 if (CompareVector(entriesInDB[idx].key, KEY_3)) {
985 entriesInDB.erase(entriesInDB.begin() + idx);
986 }
987 }
988 EXPECT_TRUE((g_kvStoreBatchDelegate->Commit()) == OK);
989 ASSERT_TRUE((g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap5)) == OK);
990 snap5 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer5);
991 EXPECT_NE(snap5, nullptr);
992 snap5->GetEntries(keyPrefix, function5);
993 vector<Entry> resultEntries5 = kvStoreSnapshotCallback5.GetEntries();
994 EXPECT_TRUE(CompareEntriesVector(resultEntries5, entriesInDB));
995 }
996
RegisterSnapAgainAndCheck6(KvStoreSnapshotDelegate * snap6,KvStoreSnapshotDelegate * snap7,KvStoreSnapshotDelegate * snap8,DistributedDB::Key & keyPrefix)997 void RegisterSnapAgainAndCheck6(KvStoreSnapshotDelegate *snap6, KvStoreSnapshotDelegate *snap7,
998 KvStoreSnapshotDelegate *snap8, DistributedDB::Key &keyPrefix)
999 {
1000 /**
1001 * @tc.steps: step8. RegisterSnapObserver snap6,snap7,snap8 to getEntries with prefix-key='k'.
1002 * @tc.expected: step8. getEntries are empty.
1003 */
1004 KvStoreSnapshotCallback kvStoreSnapshotCallback6;
1005 function<void(DBStatus, const std::vector<Entry>&)> function6
1006 = bind(&KvStoreSnapshotCallback::Callback, &kvStoreSnapshotCallback6, _1, _2);
1007 snap6->GetEntries(keyPrefix, function6);
1008 vector<Entry> resultEntries6 = kvStoreSnapshotCallback6.GetEntries();
1009 vector<Entry> resultEmptyEntry;
1010 EXPECT_TRUE(CompareEntriesVector(resultEntries6, resultEmptyEntry));
1011 KvStoreSnapshotCallback kvStoreSnapshotCallback7;
1012 function<void(DBStatus, const std::vector<Entry>&)> function7
1013 = bind(&KvStoreSnapshotCallback::Callback, &kvStoreSnapshotCallback7, _1, _2);
1014 snap7->GetEntries(keyPrefix, function7);
1015 vector<Entry> resultEntries7 = kvStoreSnapshotCallback7.GetEntries();
1016 EXPECT_TRUE(CompareEntriesVector(resultEntries7, resultEmptyEntry));
1017 KvStoreSnapshotCallback kvStoreSnapshotCallback8;
1018 function<void(DBStatus, const std::vector<Entry>&)> function8
1019 = bind(&KvStoreSnapshotCallback::Callback, &kvStoreSnapshotCallback8, _1, _2);
1020 snap8->GetEntries(keyPrefix, function8);
1021 vector<Entry> resultEntries8 = kvStoreSnapshotCallback8.GetEntries();
1022 EXPECT_TRUE(CompareEntriesVector(resultEntries8, resultEmptyEntry));
1023 }
1024
ReleaseSnap(KvStoreSnapshotDelegate * & snap1,KvStoreSnapshotDelegate * & snap2,KvStoreSnapshotDelegate * & snap3,KvStoreSnapshotDelegate * & snap4)1025 void ReleaseSnap(KvStoreSnapshotDelegate *&snap1, KvStoreSnapshotDelegate *&snap2,
1026 KvStoreSnapshotDelegate *&snap3, KvStoreSnapshotDelegate *&snap4)
1027 {
1028 DBStatus status = g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap1);
1029 ASSERT_TRUE(status == DBStatus::OK);
1030 status = g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap2);
1031 ASSERT_TRUE(status == DBStatus::OK);
1032 status = g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap3);
1033 ASSERT_TRUE(status == DBStatus::OK);
1034 status = g_kvStoreBatchDelegate->ReleaseKvStoreSnapshot(snap4);
1035 ASSERT_TRUE(status == DBStatus::OK);
1036 }
1037
1038 /*
1039 * @tc.name: ComplexSnap 002
1040 * @tc.desc: Verify that release the registered snapshot, register again successfully.
1041 * @tc.type: FUN
1042 * @tc.require: SR000BUH3J
1043 * @tc.author: luqianfu
1044 */
1045 HWTEST_F(DistributeddbKvBatchCrudTest, ComplexSnap002, TestSize.Level1)
1046 {
1047 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
1048 vector<Entry> entries1;
1049 entries1.push_back(ENTRY_1);
1050 entries1.push_back(ENTRY_2);
1051 vector<Entry> entries12;
1052 entries12.push_back(ENTRY_1_2);
1053 entries12.push_back(ENTRY_2_3);
1054 KvStoreObserverSnapImpl observer1, observer2, observer3, observer4, observer5, observer6, observer7, observer8;
1055 KvStoreSnapshotDelegate *snap1 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer1);
1056 EXPECT_NE(snap1, nullptr);
1057 KvStoreSnapshotDelegate *snap2 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer2);
1058 EXPECT_NE(snap2, nullptr);
1059 KvStoreSnapshotDelegate *snap3 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer3);
1060 EXPECT_NE(snap3, nullptr);
1061 KvStoreSnapshotDelegate *snap4 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer4);
1062 EXPECT_NE(snap4, nullptr);
1063 KvStoreSnapshotDelegate *snap5 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer5);
1064 EXPECT_NE(snap5, nullptr);
1065 KvStoreSnapshotDelegate *snap6 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer6);
1066 EXPECT_NE(snap6, nullptr);
1067 KvStoreSnapshotDelegate *snap7 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer7);
1068 EXPECT_NE(snap7, nullptr);
1069 KvStoreSnapshotDelegate *snap8 = DistributedTestTools::RegisterSnapObserver(g_kvStoreBatchDelegate, &observer8);
1070 EXPECT_NE(snap8, nullptr);
1071 /**
1072 * @tc.steps: step1. putBatch (k1,v1)(k2,v2) to db.
1073 * @tc.expected: step1. putBatch successfully to construct data in db.
1074 */
1075 DistributedDB::Key keyPrefix = { 'k' };
1076 RegisterSnapAgainAndCheck1(observer1, snap1, entries1, keyPrefix);
1077 vector<Key> keys1 = RegisterSnapAgainAndCheck2(observer2, snap2, entries1, keyPrefix);
1078 vector<Entry> entriesInDB = RegisterSnapAgainAndCheck3(observer3, snap3, entries1, keyPrefix);
1079 RegisterSnapAgainAndCheck4(observer4, snap4, entries1, keyPrefix, entriesInDB);
1080 RegisterSnapAgainAndCheck5(observer5, snap5, entries1, keyPrefix, entriesInDB);
1081 RegisterSnapAgainAndCheck6(snap6, snap7, snap8, keyPrefix);
1082 ReleaseSnap(snap1, snap2, snap3, snap4);
1083 ReleaseSnap(snap5, snap6, snap7, snap8);
1084 DistributedTestTools::Clear(*g_kvStoreBatchDelegate);
1085 }
1086 }
1087 #endif // OMIT_MULTI_VER
1088