1 /*
2 * Copyright (c) 2023 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
16 #include "cloud_syncer_test.h"
17 #include "distributeddb_tools_unit_test.h"
18 #include "mock_iclouddb.h"
19 #include "mock_icloud_sync_storage_interface.h"
20 #include "time_helper.h"
21 #include "types_export.h"
22
23 using namespace testing::ext;
24 using namespace testing;
25 using namespace DistributedDB;
26 using namespace DistributedDBUnitTest;
27
28 namespace {
29 static int64_t g_photoCount = 10;
30 static double g_dataHeight = 166.0;
31 class DistributedDBCloudSyncerDownloadTest : public testing::Test {
32 public:
33 static void SetUpTestCase(void);
34 static void TearDownTestCase(void);
35 void SetUp();
36 void TearDown();
37 };
38
39 MockICloudSyncStorageInterface *g_iCloud = nullptr;
40 std::shared_ptr<TestStorageProxy> g_storageProxy = nullptr;
41 MockICloudDB *g_idb = nullptr;
42 std::unique_ptr<TestCloudSyncer> g_cloudSyncer = nullptr;
43
SetUpTestCase(void)44 void DistributedDBCloudSyncerDownloadTest::SetUpTestCase(void)
45 {
46 g_iCloud = new MockICloudSyncStorageInterface();
47 g_storageProxy = std::make_shared<TestStorageProxy>(g_iCloud);
48 g_cloudSyncer = std::make_unique<TestCloudSyncer>(g_storageProxy);
49 g_idb = new MockICloudDB();
50 g_cloudSyncer->SetMockICloudDB(g_idb);
51 }
52
TearDownTestCase(void)53 void DistributedDBCloudSyncerDownloadTest::TearDownTestCase(void)
54 {
55 g_cloudSyncer = nullptr;
56 g_storageProxy = nullptr;
57 delete g_iCloud;
58 }
59
SetUp(void)60 void DistributedDBCloudSyncerDownloadTest::SetUp(void)
61 {
62 DistributedDBToolsUnitTest::PrintTestCaseInfo();
63 }
64
TearDown(void)65 void DistributedDBCloudSyncerDownloadTest::TearDown(void)
66 {
67 }
68
GetRetCloudData(uint64_t cnt)69 std::vector<VBucket> GetRetCloudData(uint64_t cnt)
70 {
71 std::vector<uint8_t> photo(g_photoCount, 'v');
72 std::vector<VBucket> cloudData;
73 static uint64_t totalCnt = 0;
74 for (uint64_t i = totalCnt; i < totalCnt + cnt; ++i) {
75 VBucket data;
76 data.insert_or_assign("name", "Cloud" + std::to_string(i));
77 data.insert_or_assign("height", g_dataHeight);
78 data.insert_or_assign("married", (bool)0);
79 data.insert_or_assign("photo", photo);
80 data.insert_or_assign("age", 13L);
81 data.insert_or_assign(CloudDbConstant::GID_FIELD, std::to_string(i));
82 data.insert_or_assign(CloudDbConstant::CREATE_FIELD, (int64_t)i);
83 data.insert_or_assign(CloudDbConstant::MODIFY_FIELD, (int64_t)i);
84 data.insert_or_assign(CloudDbConstant::DELETE_FIELD, false);
85 data.insert_or_assign(CloudDbConstant::CURSOR_FIELD, std::to_string(i));
86 cloudData.push_back(data);
87 }
88 totalCnt += cnt;
89 return cloudData;
90 }
91
92 struct InvalidCloudDataOpt {
93 bool invalidGID = true;
94 bool invalidCreateField = true;
95 bool invalidModifyField = true;
96 bool invalidDeleteField = true;
97 bool invalidCursor = true;
98 };
99
GenerateTableSchema(TableSchema & tableSchema)100 void GenerateTableSchema(TableSchema &tableSchema)
101 {
102 tableSchema = {
103 "TestTable1",
104 {{"name", TYPE_INDEX<std::string>, true}}
105 };
106 }
107
GetInvalidTypeCloudData(uint64_t cnt,InvalidCloudDataOpt fieldOpt)108 std::vector<VBucket> GetInvalidTypeCloudData(uint64_t cnt, InvalidCloudDataOpt fieldOpt)
109 {
110 std::vector<uint8_t> photo(g_photoCount, 'v');
111 std::vector<VBucket> cloudData;
112 static uint64_t totalCnt = 0;
113 for (uint64_t i = totalCnt; i < totalCnt + cnt; ++i) {
114 VBucket data;
115 data.insert_or_assign("name", "Cloud" + std::to_string(i));
116 data.insert_or_assign("height", g_dataHeight);
117 data.insert_or_assign("married", (bool)0);
118 data.insert_or_assign("photo", photo);
119 data.insert_or_assign("age", 13L);
120
121 if (fieldOpt.invalidGID) {
122 data.insert_or_assign(CloudDbConstant::GID_FIELD, (int64_t)i);
123 }
124 if (fieldOpt.invalidCreateField) {
125 data.insert_or_assign(CloudDbConstant::CREATE_FIELD, (Bytes)i);
126 }
127 if (fieldOpt.invalidModifyField) {
128 data.insert_or_assign(CloudDbConstant::MODIFY_FIELD, std::to_string(i));
129 }
130 if (fieldOpt.invalidDeleteField) {
131 data.insert_or_assign(CloudDbConstant::DELETE_FIELD, (int64_t)false);
132 }
133 if (fieldOpt.invalidCursor) {
134 data.insert_or_assign(CloudDbConstant::CURSOR_FIELD, (int64_t)i);
135 }
136 cloudData.push_back(data);
137 }
138 totalCnt += cnt;
139 return cloudData;
140 }
141
GetInvalidFieldCloudData(uint64_t cnt,InvalidCloudDataOpt fieldOpt)142 std::vector<VBucket> GetInvalidFieldCloudData(uint64_t cnt, InvalidCloudDataOpt fieldOpt)
143 {
144 std::vector<uint8_t> photo(g_photoCount, 'v');
145 std::vector<VBucket> cloudData;
146 static uint64_t totalCnt = 0;
147 for (uint64_t i = totalCnt; i < totalCnt + cnt; ++i) {
148 VBucket data;
149 data.insert_or_assign("name", "Cloud" + std::to_string(i));
150 data.insert_or_assign("height", g_dataHeight);
151 data.insert_or_assign("married", (bool)0);
152 data.insert_or_assign("photo", photo);
153 data.insert_or_assign("age", 13L);
154 // Invalid means don't have here
155 if (!fieldOpt.invalidGID) {
156 data.insert_or_assign(CloudDbConstant::GID_FIELD, std::to_string(i));
157 }
158 if (!fieldOpt.invalidCreateField) {
159 data.insert_or_assign(CloudDbConstant::CREATE_FIELD, (int64_t)i);
160 }
161 if (!fieldOpt.invalidModifyField) {
162 data.insert_or_assign(CloudDbConstant::MODIFY_FIELD, (int64_t)i);
163 }
164 if (!fieldOpt.invalidDeleteField) {
165 data.insert_or_assign(CloudDbConstant::DELETE_FIELD, false);
166 }
167 if (!fieldOpt.invalidCursor) {
168 data.insert_or_assign(CloudDbConstant::CURSOR_FIELD, std::to_string(i));
169 }
170 cloudData.push_back(data);
171 }
172 totalCnt += cnt;
173 return cloudData;
174 }
175
GetLogInfo(uint64_t timestamp,bool isDeleted)176 DataInfoWithLog GetLogInfo(uint64_t timestamp, bool isDeleted)
177 {
178 LogInfo logInfo;
179 logInfo.timestamp = timestamp;
180 logInfo.cloudGid = std::to_string(timestamp);
181 if (isDeleted) {
182 logInfo.flag = 1u;
183 }
184 DataInfoWithLog dataInfoWithLog;
185 dataInfoWithLog.logInfo = logInfo;
186 return dataInfoWithLog;
187 }
188
Expect2GetInfoByPrimaryKeyOrGidCall()189 static void Expect2GetInfoByPrimaryKeyOrGidCall()
190 {
191 EXPECT_CALL(*g_iCloud, GetInfoByPrimaryKeyOrGid(_, _, _, _))
192 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
193 info = GetLogInfo(0, false); // Gen data with timestamp 0
194 return E_OK;
195 })
196 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
197 info = GetLogInfo(1, false); // Gen data with timestamp 1
198 return E_OK;
199 })
200 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
201 info = GetLogInfo(2, false); // Gen data with timestamp 2
202 return E_OK;
203 })
204 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
205 info = GetLogInfo(3, false); // Gen data with timestamp 3
206 return E_OK;
207 })
208 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
209 info = GetLogInfo(4, false); // Gen data with timestamp 4
210 return E_OK;
211 });
212 }
213
214 /**
215 * @tc.name: DownloadMockTest001
216 * @tc.desc: Test situation with all possible output for GetCloudWaterMark
217 * @tc.type: FUNC
218 * @tc.require:
219 * @tc.author: WanYi
220 */
221 HWTEST_F(DistributedDBCloudSyncerDownloadTest, DownloadMockTest001, TestSize.Level1)
222 {
223 TaskId taskId = 1u;
224 EXPECT_CALL(*g_iCloud, StartTransaction(_)).WillRepeatedly(Return(E_OK));
225 EXPECT_CALL(*g_iCloud, GetUploadCount(_, _, _, _)).WillRepeatedly(Return(E_OK));
226 EXPECT_CALL(*g_iCloud, Commit()).WillRepeatedly(Return(E_OK));
227 EXPECT_CALL(*g_iCloud, PutCloudSyncData(_, _)).WillRepeatedly(Return(E_OK));
228 EXPECT_CALL(*g_iCloud, PutMetaData(_, _)).WillRepeatedly(Return(E_OK));
229 EXPECT_CALL(*g_iCloud, GetCloudTableSchema(_, _)).WillRepeatedly(Return(E_OK));
230 EXPECT_CALL(*g_iCloud, TriggerObserverAction(_, _, _)).WillRepeatedly(Return());
231 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff750702(const std::string &, VBucket &, std::vector<VBucket> &data) 232 .WillRepeatedly([](const std::string &, VBucket &, std::vector<VBucket> &data) {
233 data = GetRetCloudData(5); // Gen 5 data
234 return QUERY_END;
235 });
236 EXPECT_CALL(*g_iCloud, ChkSchema(_)).WillRepeatedly(Return(E_OK));
237
238 // 1. Read meta data success
239 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
240 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillOnce(Return(E_OK));
241 Expect2GetInfoByPrimaryKeyOrGidCall();
242
243 int errCode = g_cloudSyncer->CallDoDownload(taskId);
244 EXPECT_EQ(errCode, E_OK);
245
246 // // 2. Failed to read water level
247 taskId = 3u;
248 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_FORCE_PUSH);
249 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillOnce(Return(-E_INVALID_DB));
250 errCode = g_cloudSyncer->CallDoDownload(taskId);
251 EXPECT_EQ(errCode, -E_INVALID_DB);
252
253 taskId = 4u;
254 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_FORCE_PUSH);
255 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillOnce(Return(-E_SECUREC_ERROR));
256 errCode = g_cloudSyncer->CallDoDownload(taskId);
257 EXPECT_EQ(errCode, -E_SECUREC_ERROR);
258
259 taskId = 5u;
260 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_FORCE_PUSH);
261 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillOnce(Return(-E_INVALID_ARGS));
262 errCode = g_cloudSyncer->CallDoDownload(taskId);
263 EXPECT_EQ(errCode, -E_INVALID_ARGS);
264 }
265
266 /**
267 * @tc.name: DownloadMockTest002
268 * @tc.desc: Test situation with all possible output for GetCloudWaterMark
269 * @tc.type: FUNC
270 * @tc.require:
271 * @tc.author: WanYi
272 */
273 HWTEST_F(DistributedDBCloudSyncerDownloadTest, DownloadMockTest002, TestSize.Level1)
274 {
275 TaskId taskId = 6u;
276 EXPECT_CALL(*g_iCloud, StartTransaction(_)).WillRepeatedly(Return(E_OK));
277 EXPECT_CALL(*g_iCloud, GetUploadCount(_, _, _, _)).WillRepeatedly(Return(E_OK));
278 EXPECT_CALL(*g_iCloud, Commit()).WillRepeatedly(Return(E_OK));
279 EXPECT_CALL(*g_iCloud, Rollback()).WillRepeatedly(Return(E_OK));
280 EXPECT_CALL(*g_iCloud, PutCloudSyncData(_, _)).WillRepeatedly(Return(E_OK));
281 EXPECT_CALL(*g_iCloud, PutMetaData(_, _)).WillRepeatedly(Return(E_OK));
282 EXPECT_CALL(*g_iCloud, GetCloudTableSchema(_, _)).WillRepeatedly(Return(E_OK));
283 EXPECT_CALL(*g_iCloud, TriggerObserverAction(_, _, _)).WillRepeatedly(Return());
284 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff750802(const std::string &, VBucket &, std::vector<VBucket> &data) 285 .WillRepeatedly([](const std::string &, VBucket &, std::vector<VBucket> &data) {
286 data = GetRetCloudData(5); // Gen 5 data
287 return QUERY_END;
288 });
289 EXPECT_CALL(*g_iCloud, ChkSchema(_)).WillRepeatedly(Return(E_OK));
290
291 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_FORCE_PUSH);
292 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillOnce(Return(-E_BUSY));
293 int errCode = g_cloudSyncer->CallDoDownload(taskId);
294 EXPECT_EQ(errCode, -E_BUSY);
295
296 taskId = 7u;
297 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_FORCE_PUSH);
298 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillOnce(Return(-E_NOT_FOUND));
299 Expect2GetInfoByPrimaryKeyOrGidCall();
300 errCode = g_cloudSyncer->CallDoDownload(taskId);
301 // when we coudln't find key in get meta data, read local water mark will return default value and E_OK
302 EXPECT_EQ(errCode, E_OK);
303
304 // Other sqlite error, like SQLITE_ERROR
305 taskId = 8u;
306 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_FORCE_PUSH);
307 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillOnce(Return(SQLITE_ERROR));
308 errCode = g_cloudSyncer->CallDoDownload(taskId);
309 EXPECT_EQ(errCode, SQLITE_ERROR);
310 }
311
312 /**
313 * @tc.name: DownloadMockQueryTest002
314 * @tc.desc: Test situation with all possible output for Query
315 * @tc.type: FUNC
316 * @tc.require:
317 * @tc.author: WanYi
318 */
319 HWTEST_F(DistributedDBCloudSyncerDownloadTest, DownloadMockQueryTest002, TestSize.Level1)
320 {
321 TaskId taskId = 1u;
322 EXPECT_CALL(*g_iCloud, StartTransaction(_)).WillRepeatedly(Return(E_OK));
323 EXPECT_CALL(*g_iCloud, GetUploadCount(_, _, _, _)).WillRepeatedly(Return(E_OK));
324 EXPECT_CALL(*g_iCloud, Commit()).WillRepeatedly(Return(E_OK));
325 EXPECT_CALL(*g_iCloud, Rollback()).WillRepeatedly(Return(E_OK));
326 EXPECT_CALL(*g_iCloud, PutCloudSyncData(_, _)).WillRepeatedly(Return(E_OK));
327 EXPECT_CALL(*g_iCloud, PutMetaData(_, _)).WillRepeatedly(Return(E_OK));
328 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillRepeatedly(Return(E_OK));
329 EXPECT_CALL(*g_iCloud, TriggerObserverAction(_, _, _)).WillRepeatedly(Return());
330 EXPECT_CALL(*g_iCloud, GetCloudTableSchema(_, _)).WillRepeatedly(Return(E_OK));
331
332 // 1. Query data success for the first time, but will not reach end
333 // 2. While quring second time, no more data comes back and return QUERY END
334 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
335 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff750902(const std::string &, VBucket &, std::vector<VBucket> &data) 336 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
337 data = GetRetCloudData(5); // Gen 5 data
338 return QUERY_END;});
339 EXPECT_CALL(*g_iCloud, ChkSchema(_)).WillRepeatedly(Return(E_OK));
340 Expect2GetInfoByPrimaryKeyOrGidCall();
341 int errCode = g_cloudSyncer->CallDoDownload(taskId);
342 EXPECT_EQ(errCode, E_OK);
343 }
344
345 /**
346 * @tc.name: DownloadMockQueryTest003
347 * @tc.desc: Query data success but return invalid data (type mismatch)
348 * @tc.type: FUNC
349 * @tc.require:
350 * @tc.author: WanYi
351 */
352 HWTEST_F(DistributedDBCloudSyncerDownloadTest, DownloadMockQueryTest003, TestSize.Level1)
353 {
354 TaskId taskId = 1u;
355 EXPECT_CALL(*g_iCloud, StartTransaction(_)).WillRepeatedly(Return(E_OK));
356 EXPECT_CALL(*g_iCloud, GetUploadCount(_, _, _, _)).WillRepeatedly(Return(E_OK));
357 EXPECT_CALL(*g_iCloud, Commit()).WillRepeatedly(Return(E_OK));
358 EXPECT_CALL(*g_iCloud, Rollback()).WillRepeatedly(Return(E_OK));
359 EXPECT_CALL(*g_iCloud, PutCloudSyncData(_, _)).WillRepeatedly(Return(E_OK));
360 EXPECT_CALL(*g_iCloud, PutMetaData(_, _)).WillRepeatedly(Return(E_OK));
361 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillRepeatedly(Return(E_OK));
362 EXPECT_CALL(*g_iCloud, ChkSchema(_)).WillRepeatedly(Return(E_OK));
363 EXPECT_CALL(*g_iCloud, TriggerObserverAction(_, _, _)).WillRepeatedly(Return());
364 EXPECT_CALL(*g_iCloud, GetCloudTableSchema(_, _)).WillRepeatedly(Return(E_OK));
365
366 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
367 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff750a02(const std::string &, VBucket &, std::vector<VBucket> &data) 368 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
369 data = GetInvalidTypeCloudData(5, {.invalidCursor = false});
370 return QUERY_END;
371 });
372 int errCode = g_cloudSyncer->CallDoDownload(taskId);
373 EXPECT_EQ(errCode, -E_CLOUD_ERROR);
374
375 taskId = 2u;
376 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
377 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff750b02(const std::string &, VBucket &, std::vector<VBucket> &data) 378 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
379 data = GetInvalidTypeCloudData(5, {.invalidCursor = false});
380 return QUERY_END;
381 });
382 errCode = g_cloudSyncer->CallDoDownload(taskId);
383 EXPECT_EQ(errCode, -E_CLOUD_ERROR);
384
385
386 taskId = 3u;
387 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
388 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff750c02(const std::string &, VBucket &, std::vector<VBucket> &data) 389 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
390 data = GetInvalidTypeCloudData(5, {.invalidDeleteField = false});
391 return QUERY_END;
392 });
393 errCode = g_cloudSyncer->CallDoDownload(taskId);
394 EXPECT_EQ(errCode, -E_CLOUD_ERROR);
395 }
396
397 /**
398 * @tc.name: DownloadMockQueryTest00302
399 * @tc.desc: Query data success but return invalid data (type mismatch)
400 * @tc.type: FUNC
401 * @tc.require:
402 * @tc.author: WanYi
403 */
404 HWTEST_F(DistributedDBCloudSyncerDownloadTest, DownloadMockQueryTest00302, TestSize.Level1)
405 {
406 TaskId taskId = 4u;
407 EXPECT_CALL(*g_iCloud, StartTransaction(_)).WillRepeatedly(Return(E_OK));
408 EXPECT_CALL(*g_iCloud, GetUploadCount(_, _, _, _)).WillRepeatedly(Return(E_OK));
409 EXPECT_CALL(*g_iCloud, Commit()).WillRepeatedly(Return(E_OK));
410 EXPECT_CALL(*g_iCloud, Rollback()).WillRepeatedly(Return(E_OK));
411 EXPECT_CALL(*g_iCloud, PutCloudSyncData(_, _)).WillRepeatedly(Return(E_OK));
412 EXPECT_CALL(*g_iCloud, PutMetaData(_, _)).WillRepeatedly(Return(E_OK));
413 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillRepeatedly(Return(E_OK));
414 EXPECT_CALL(*g_iCloud, ChkSchema(_)).WillRepeatedly(Return(E_OK));
415 EXPECT_CALL(*g_iCloud, TriggerObserverAction(_, _, _)).WillRepeatedly(Return());
416 EXPECT_CALL(*g_iCloud, GetCloudTableSchema(_, _)).WillRepeatedly(Return(E_OK));
417 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
418 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff750d02(const std::string &, VBucket &, std::vector<VBucket> &data) 419 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
420 data = GetInvalidTypeCloudData(5, {.invalidGID = false});
421 return QUERY_END;
422 });
423 int errCode = g_cloudSyncer->CallDoDownload(taskId);
424 EXPECT_EQ(errCode, -E_CLOUD_ERROR);
425
426 taskId = 5u;
427 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
428 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff750e02(const std::string &, VBucket &, std::vector<VBucket> &data) 429 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
430 data = GetInvalidTypeCloudData(5, {.invalidModifyField = false});
431 return QUERY_END;
432 });
433 errCode = g_cloudSyncer->CallDoDownload(taskId);
434 EXPECT_EQ(errCode, -E_CLOUD_ERROR);
435 }
436
437 /**
438 * @tc.name: DownloadMockQueryTest004
439 * @tc.desc: Query data success but return invalid data (field mismatch)
440 * @tc.type: FUNC
441 * @tc.require:
442 * @tc.author: WanYi
443 */
444 HWTEST_F(DistributedDBCloudSyncerDownloadTest, DownloadMockQueryTest004, TestSize.Level1)
445 {
446 TaskId taskId = 1u;
447 EXPECT_CALL(*g_iCloud, StartTransaction(_)).WillRepeatedly(Return(E_OK));
448 EXPECT_CALL(*g_iCloud, GetUploadCount(_, _, _, _)).WillRepeatedly(Return(E_OK));
449 EXPECT_CALL(*g_iCloud, Commit()).WillRepeatedly(Return(E_OK));
450 EXPECT_CALL(*g_iCloud, Rollback()).WillRepeatedly(Return(E_OK));
451 EXPECT_CALL(*g_iCloud, PutCloudSyncData(_, _)).WillRepeatedly(Return(E_OK));
452 EXPECT_CALL(*g_iCloud, PutMetaData(_, _)).WillRepeatedly(Return(E_OK));
453 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillRepeatedly(Return(E_OK));
454 EXPECT_CALL(*g_iCloud, ChkSchema(_)).WillRepeatedly(Return(E_OK));
455 EXPECT_CALL(*g_iCloud, TriggerObserverAction(_, _, _)).WillRepeatedly(Return());
456 EXPECT_CALL(*g_iCloud, GetCloudTableSchema(_, _)).WillRepeatedly(Return(E_OK));
457
458 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
459 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff750f02(const std::string &, VBucket &, std::vector<VBucket> &data) 460 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
461 data = GetInvalidFieldCloudData(5, {.invalidCreateField = false});
462 return QUERY_END;
463 });
464 int errCode = g_cloudSyncer->CallDoDownload(taskId);
465 EXPECT_EQ(errCode, -E_CLOUD_ERROR);
466
467 taskId = 2u;
468 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
469 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff751002(const std::string &, VBucket &, std::vector<VBucket> &data) 470 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
471 data = GetInvalidFieldCloudData(5, {.invalidCursor = false});
472 return QUERY_END;
473 });
474 errCode = g_cloudSyncer->CallDoDownload(taskId);
475 EXPECT_EQ(errCode, -E_CLOUD_ERROR);
476 }
477
478 /**
479 * @tc.name: DownloadMockQueryTest00402
480 * @tc.desc: Query data success but return invalid data (field mismatch)
481 * @tc.type: FUNC
482 * @tc.require:
483 * @tc.author: WanYi
484 */
485 HWTEST_F(DistributedDBCloudSyncerDownloadTest, DownloadMockQueryTest00402, TestSize.Level1)
486 {
487 TaskId taskId = 3u;
488 EXPECT_CALL(*g_iCloud, StartTransaction(_)).WillRepeatedly(Return(E_OK));
489 EXPECT_CALL(*g_iCloud, GetUploadCount(_, _, _, _)).WillRepeatedly(Return(E_OK));
490 EXPECT_CALL(*g_iCloud, Commit()).WillRepeatedly(Return(E_OK));
491 EXPECT_CALL(*g_iCloud, Rollback()).WillRepeatedly(Return(E_OK));
492 EXPECT_CALL(*g_iCloud, PutCloudSyncData(_, _)).WillRepeatedly(Return(E_OK));
493 EXPECT_CALL(*g_iCloud, PutMetaData(_, _)).WillRepeatedly(Return(E_OK));
494 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillRepeatedly(Return(E_OK));
495 EXPECT_CALL(*g_iCloud, ChkSchema(_)).WillRepeatedly(Return(E_OK));
496 EXPECT_CALL(*g_iCloud, TriggerObserverAction(_, _, _)).WillRepeatedly(Return());
497 EXPECT_CALL(*g_iCloud, GetCloudTableSchema(_, _)).WillRepeatedly(Return(E_OK));
498 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
499 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff751102(const std::string &, VBucket &, std::vector<VBucket> &data) 500 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
501 data = GetInvalidFieldCloudData(5, {.invalidDeleteField = false}); // Generate 5 data
502 return QUERY_END;
503 });
504 int errCode = g_cloudSyncer->CallDoDownload(taskId);
505 EXPECT_EQ(errCode, -E_CLOUD_ERROR);
506
507 taskId = 4u;
508 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
509 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff751202(const std::string &, VBucket &, std::vector<VBucket> &data) 510 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
511 data = GetInvalidFieldCloudData(5, {.invalidGID = false}); // Generate 5 data
512 return QUERY_END;
513 });
514 errCode = g_cloudSyncer->CallDoDownload(taskId);
515 EXPECT_EQ(errCode, -E_CLOUD_ERROR);
516
517 taskId = 5u;
518 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
519 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff751302(const std::string &, VBucket &, std::vector<VBucket> &data) 520 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
521 data = GetInvalidFieldCloudData(5, {.invalidModifyField = false}); // Generate 5 data
522 return QUERY_END;
523 });
524 errCode = g_cloudSyncer->CallDoDownload(taskId);
525 EXPECT_EQ(errCode, -E_CLOUD_ERROR);
526 }
527
528 /**
529 * @tc.name: DownloadMockQueryTest005
530 * @tc.desc: First time, query return OK but empty data set
531 * @tc.type: FUNC
532 * @tc.require:
533 * @tc.author: WanYi
534 */
535 HWTEST_F(DistributedDBCloudSyncerDownloadTest, DownloadMockQueryTest005, TestSize.Level1)
536 {
537 TaskId taskId = 1u;
538 EXPECT_CALL(*g_iCloud, StartTransaction(_)).WillRepeatedly(Return(E_OK));
539 EXPECT_CALL(*g_iCloud, GetUploadCount(_, _, _, _)).WillRepeatedly(Return(E_OK));
540 EXPECT_CALL(*g_iCloud, Commit()).WillRepeatedly(Return(E_OK));
541 EXPECT_CALL(*g_iCloud, Rollback()).WillRepeatedly(Return(E_OK));
542 EXPECT_CALL(*g_iCloud, PutCloudSyncData(_, _)).WillRepeatedly(Return(E_OK));
543 EXPECT_CALL(*g_iCloud, PutMetaData(_, _)).WillRepeatedly(Return(E_OK));
544 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillRepeatedly(Return(E_OK));
545 EXPECT_CALL(*g_iCloud, ChkSchema(_)).WillRepeatedly(Return(E_OK));
546 EXPECT_CALL(*g_iCloud, TriggerObserverAction(_, _, _)).WillRepeatedly(Return());
547 EXPECT_CALL(*g_iCloud, GetCloudTableSchema(_, _)).WillRepeatedly(Return(E_OK));
548 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
549
550 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff751402(const std::string &, VBucket &, std::vector<VBucket> &data) 551 .WillRepeatedly([](const std::string &, VBucket &, std::vector<VBucket> &data) {
552 data = GetRetCloudData(0); // Gen 0 data
553 return QUERY_END;
554 });
555 int errCode = g_cloudSyncer->CallDoDownload(taskId);
556 EXPECT_EQ(errCode, E_OK);
557 }
558
559 /**
560 * @tc.name: DownloadMockTest006
561 * @tc.desc: Data from cloud do not exist in local database.
562 * therefore, GetInfoByPrimaryKeyOrGid will indicate that the datum is -E_NOT_FOUND
563 * @tc.type: FUNC
564 * @tc.require:
565 * @tc.author: WanYi
566 */
567 HWTEST_F(DistributedDBCloudSyncerDownloadTest, DownloadMockTest006, TestSize.Level1)
568 {
569 TaskId taskId = 1u;
570 EXPECT_CALL(*g_iCloud, StartTransaction(_)).WillRepeatedly(Return(E_OK));
571 EXPECT_CALL(*g_iCloud, GetUploadCount(_, _, _, _)).WillRepeatedly(Return(E_OK));
572 EXPECT_CALL(*g_iCloud, Commit()).WillRepeatedly(Return(E_OK));
573 EXPECT_CALL(*g_iCloud, Rollback()).WillRepeatedly(Return(E_OK));
574 EXPECT_CALL(*g_iCloud, PutCloudSyncData(_, _)).WillRepeatedly(Return(E_OK));
575 EXPECT_CALL(*g_iCloud, PutMetaData(_, _)).WillRepeatedly(Return(E_OK));
576 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillRepeatedly(Return(E_OK));
577 EXPECT_CALL(*g_iCloud, ChkSchema(_)).WillRepeatedly(Return(E_OK));
578 EXPECT_CALL(*g_iCloud, TriggerObserverAction(_, _, _)).WillRepeatedly(Return());
579 EXPECT_CALL(*g_iCloud, GetCloudTableSchema(_, _))
__anon8096ff751502(const TableName &, TableSchema &tableSchema) 580 .WillRepeatedly([](const TableName &, TableSchema &tableSchema) {
581 GenerateTableSchema(tableSchema);
582 return E_OK;
583 });
584 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
585
586 EXPECT_CALL(*g_idb, Query(_, _, _))
__anon8096ff751602(const std::string &, VBucket &, std::vector<VBucket> &data) 587 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
588 data = GetRetCloudData(5); // Gen 5 data
589 return QUERY_END;
590 });
591 EXPECT_CALL(*g_iCloud, GetInfoByPrimaryKeyOrGid(_, _, _, _))
__anon8096ff751702(const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) 592 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
593 info = GetLogInfo(0, false); // Gen log info with timestamp 0
594 return E_OK;
595 })
__anon8096ff751802(const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) 596 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
597 info = GetLogInfo(1, false); // Gen log info with timestamp 1
598 return -E_NOT_FOUND;
599 })
__anon8096ff751902(const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) 600 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
601 info = GetLogInfo(2, false); // Gen log info with timestamp 2
602 return E_OK;
603 })
__anon8096ff751a02(const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) 604 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
605 info = GetLogInfo(3, false); // Gen log info with timestamp 3
606 return E_OK;
607 })
__anon8096ff751b02(const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) 608 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
609 info = GetLogInfo(4, false); // Gen log info with timestamp 4
610 return E_OK;
611 });
612 int errCode = g_cloudSyncer->CallDoDownload(taskId);
613 EXPECT_EQ(errCode, E_OK);
614 }
615
ExpectQueryCall()616 static void ExpectQueryCall()
617 {
618 EXPECT_CALL(*g_idb, Query(_, _, _))
619 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
620 data = GetRetCloudData(3); // Gen 3 data
621 return OK;
622 })
623 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
624 data = GetRetCloudData(3); // Gen 3 data
625 return OK;
626 })
627 .WillOnce([](const std::string &, VBucket &, std::vector<VBucket> &data) {
628 data = GetRetCloudData(4); // Gen 4 data
629 return QUERY_END;
630 });
631 }
632
ExpectGetInfoByPrimaryKeyOrGidCall()633 static void ExpectGetInfoByPrimaryKeyOrGidCall()
634 {
635 EXPECT_CALL(*g_iCloud, GetInfoByPrimaryKeyOrGid(_, _, _, _))
636 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
637 info = GetLogInfo(0, false); // Gen log info with timestamp 0
638 return -E_NOT_FOUND;
639 })
640 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
641 info = GetLogInfo(1, false); // Gen log info with timestamp 1
642 return -E_NOT_FOUND;
643 })
644 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
645 info = GetLogInfo(2, false); // Gen log info with timestamp 2
646 return E_OK;
647 })
648 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
649 info = GetLogInfo(3, false); // Gen log info with timestamp 3
650 return E_OK;
651 })
652 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
653 info = GetLogInfo(4, false); // Gen log info with timestamp 4
654 return E_OK;
655 })
656 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
657 info = GetLogInfo(5, false); // Gen log info with timestamp 5
658 return E_OK;
659 })
660 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
661 info = GetLogInfo(6, false); // Gen log info with timestamp 6
662 return -E_NOT_FOUND;
663 })
664 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
665 info = GetLogInfo(7, false); // Gen log info with timestamp 7
666 return -E_NOT_FOUND;
667 })
668 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
669 info = GetLogInfo(8, false); // Gen log info with timestamp 8
670 return E_OK;
671 })
672 .WillOnce([](const std::string &, const VBucket &, DataInfoWithLog &info, VBucket &) {
673 info = GetLogInfo(9, false); // Gen log info with timestamp 9
674 return E_OK;
675 });
676 }
677
678 /**
679 * @tc.name: DownloadMockTest007
680 * @tc.desc: Query return OK multiple times and return E_OK finally
681 * @tc.type: FUNC
682 * @tc.require:
683 * @tc.author: WanYi
684 */
685 HWTEST_F(DistributedDBCloudSyncerDownloadTest, DownloadMockTest007, TestSize.Level1)
686 {
687 TaskId taskId = 1u;
688 EXPECT_CALL(*g_iCloud, StartTransaction(_)).WillRepeatedly(Return(E_OK));
689 EXPECT_CALL(*g_iCloud, GetUploadCount(_, _, _, _)).WillRepeatedly(Return(E_OK));
690 EXPECT_CALL(*g_iCloud, Commit()).WillRepeatedly(Return(E_OK));
691 EXPECT_CALL(*g_iCloud, Rollback()).WillRepeatedly(Return(E_OK));
692 EXPECT_CALL(*g_iCloud, PutCloudSyncData(_, _)).WillRepeatedly(Return(E_OK));
693 EXPECT_CALL(*g_iCloud, PutMetaData(_, _)).WillRepeatedly(Return(E_OK));
694 EXPECT_CALL(*g_iCloud, GetMetaData(_, _)).WillRepeatedly(Return(E_OK));
695 EXPECT_CALL(*g_iCloud, ChkSchema(_)).WillRepeatedly(Return(E_OK));
696 EXPECT_CALL(*g_iCloud, TriggerObserverAction(_, _, _)).WillRepeatedly(Return());
697 EXPECT_CALL(*g_iCloud, GetCloudTableSchema(_, _))
__anon8096ff752902(const TableName &, TableSchema &tableSchema) 698 .WillRepeatedly([](const TableName &, TableSchema &tableSchema) {
699 GenerateTableSchema(tableSchema);
700 return E_OK;
701 });
702 g_cloudSyncer->InitCloudSyncer(taskId, SYNC_MODE_CLOUD_MERGE);
703 ExpectQueryCall();
704 ExpectGetInfoByPrimaryKeyOrGidCall();
705 int errCode = g_cloudSyncer->CallDoDownload(taskId);
706 EXPECT_EQ(errCode, E_OK);
707 }
708
709 }