1 /*
2 * Copyright (c) 2021-2025 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 #include "account_data_storage.h"
16 #include <memory>
17 #include <unistd.h>
18 #include "account_log_wrapper.h"
19 #include "account_hisysevent_adapter.h"
20 #include "app_account_info_json_parser.h"
21 #include "os_account_info_json_parser.h"
22
23 namespace OHOS {
24 namespace AccountSA {
25 const int32_t MAX_TIMES = 10;
26 const int32_t SLEEP_INTERVAL = 100 * 1000;
27 constexpr char KV_STORE_EL1_BASE_DIR[] = "/data/service/el1/public/database/";
28
29 #ifndef SQLITE_DLCLOSE_ENABLE
AccountDataStorage(const std::string & appId,const std::string & storeId,const AccountDataStorageOptions & options)30 AccountDataStorage::AccountDataStorage(const std::string &appId, const std::string &storeId,
31 const AccountDataStorageOptions &options)
32 {
33 ACCOUNT_LOGI("Constructed");
34 appId_.appId = appId;
35 storeId_.storeId = storeId;
36 options_ = options;
37 if (options_.area == DistributedKv::EL1) {
38 baseDir_ = KV_STORE_EL1_BASE_DIR + appId;
39 } else {
40 baseDir_ = options.baseDir;
41 }
42 }
43 #else
AccountDataStorage(const std::string & appId,const std::string & storeId,const DbAdapterOptions & options)44 AccountDataStorage::AccountDataStorage(const std::string &appId, const std::string &storeId,
45 const DbAdapterOptions &options)
46 {
47 appId_ = appId;
48 storeId_ = storeId;
49 options_ = options;
50 dataManager_ = DatabaseAdapterLoader::GetInstance().GetDataManager();
51 if (options_.area == DbAdapterArea::EL1) {
52 baseDir_ = KV_STORE_EL1_BASE_DIR + appId;
53 } else {
54 baseDir_ = options.baseDir;
55 }
56 options_.baseDir = baseDir_;
57 }
58 #endif // SQLITE_DLCLOSE_ENABLE
59
~AccountDataStorage()60 AccountDataStorage::~AccountDataStorage()
61 {
62 ACCOUNT_LOGI("Destroyed");
63 if (kvStorePtr_ != nullptr) {
64 #ifndef SQLITE_DLCLOSE_ENABLE
65 dataManager_.CloseKvStore(appId_, kvStorePtr_);
66 #else
67 dataManager_->CloseKvStore(appId_, kvStorePtr_);
68 #endif // SQLITE_DLCLOSE_ENABLE
69 }
70 }
71
72 #ifndef SQLITE_DLCLOSE_ENABLE
TryTwice(const std::function<DistributedKv::Status ()> & func) const73 void AccountDataStorage::TryTwice(const std::function<DistributedKv::Status()> &func) const
74 {
75 OHOS::DistributedKv::Status status = func();
76 if (status == OHOS::DistributedKv::Status::IPC_ERROR) {
77 status = func();
78 ACCOUNT_LOGE("distribute database ipc error and try again, status = %{public}d", status);
79 }
80 }
81 #else
TryTwice(const std::function<DbAdapterStatus ()> & func) const82 void AccountDataStorage::TryTwice(const std::function<DbAdapterStatus()> &func) const
83 {
84 DbAdapterStatus status = func();
85 if (status == DbAdapterStatus::IPC_ERROR) {
86 status = func();
87 ACCOUNT_LOGE("distribute database ipc error and try again, status = %{public}d", status);
88 }
89 }
90 #endif // SQLITE_DLCLOSE_ENABLE
91
92 #ifndef SQLITE_DLCLOSE_ENABLE
GetKvStore()93 OHOS::DistributedKv::Status AccountDataStorage::GetKvStore()
94 {
95 OHOS::DistributedKv::Options options = {
96 .createIfMissing = true,
97 .encrypt = options_.encrypt,
98 .autoSync = options_.autoSync,
99 .syncable = options_.autoSync,
100 .securityLevel = options_.securityLevel,
101 .area = options_.area,
102 .kvStoreType = OHOS::DistributedKv::KvStoreType::SINGLE_VERSION,
103 .baseDir = baseDir_,
104 };
105
106 OHOS::DistributedKv::Status status = dataManager_.GetSingleKvStore(options, appId_, storeId_, kvStorePtr_);
107 if (status != OHOS::DistributedKv::Status::SUCCESS || kvStorePtr_ == nullptr) {
108 #else
109 DbAdapterStatus AccountDataStorage::GetKvStore()
110 {
111 DbAdapterStatus status = dataManager_->GetSingleKvStore(options_, appId_, storeId_, kvStorePtr_);
112 if (status != DbAdapterStatus::SUCCESS || kvStorePtr_ == nullptr) {
113 #endif // SQLITE_DLCLOSE_ENABLE
114 ACCOUNT_LOGE("GetSingleKvStore failed! status %{public}d, kvStorePtr_ is nullptr", status);
115 return status;
116 }
117 return status;
118 }
119
120 bool AccountDataStorage::CheckKvStore()
121 {
122 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
123
124 if (kvStorePtr_ != nullptr) {
125 return true;
126 }
127 int32_t tryTimes = MAX_TIMES;
128 #ifndef SQLITE_DLCLOSE_ENABLE
129 OHOS::DistributedKv::Status status = OHOS::DistributedKv::Status::SUCCESS;
130 #else
131 DbAdapterStatus status = DbAdapterStatus::SUCCESS;
132 #endif // SQLITE_DLCLOSE_ENABLE
133 while (tryTimes > 0) {
134 status = GetKvStore();
135 #ifndef SQLITE_DLCLOSE_ENABLE
136 if (status == OHOS::DistributedKv::Status::SUCCESS && kvStorePtr_ != nullptr) {
137 break;
138 }
139 #else
140 if (status == DbAdapterStatus::SUCCESS && kvStorePtr_ != nullptr) {
141 break;
142 }
143 #endif // SQLITE_DLCLOSE_ENABLE
144
145 usleep(SLEEP_INTERVAL);
146 tryTimes--;
147 }
148
149 if (kvStorePtr_ == nullptr) {
150 return false;
151 }
152
153 return true;
154 }
155
156 ErrCode AccountDataStorage::LoadAllData(std::map<std::string, std::shared_ptr<IAccountInfo>> &infos)
157 {
158 if (!CheckKvStore()) {
159 ACCOUNT_LOGE("kvStore is nullptr");
160 return OHOS::ERR_OSACCOUNT_SERVICE_MANAGER_QUERY_DISTRIBUTE_DATA_ERROR;
161 }
162 #ifndef SQLITE_DLCLOSE_ENABLE
163 OHOS::DistributedKv::Status status = DistributedKv::Status::SUCCESS;
164 std::vector<OHOS::DistributedKv::Entry> allEntries;
165 TryTwice([this, &status, &allEntries] {
166 status = GetEntries("", allEntries);
167 return status;
168 });
169
170 if (status != OHOS::DistributedKv::Status::SUCCESS) {
171 #else
172 DbAdapterStatus status = DbAdapterStatus::SUCCESS;
173 std::vector<DbAdapterEntry> allEntries;
174 TryTwice([this, &status, &allEntries] {
175 status = GetEntries("", allEntries);
176 return status;
177 });
178
179 if (status != DbAdapterStatus::SUCCESS) {
180 #endif // SQLITE_DLCLOSE_ENABLE
181 ACCOUNT_LOGE("get entries error: %{public}d", status);
182 return OHOS::ERR_OSACCOUNT_SERVICE_MANAGER_QUERY_DISTRIBUTE_DATA_ERROR;
183 }
184 infos.clear();
185 SaveEntries(allEntries, infos);
186 return ERR_OK;
187 }
188
189 ErrCode AccountDataStorage::AddAccountInfo(const IAccountInfo &iAccountInfo)
190 {
191 if (IsKeyExists(iAccountInfo.GetPrimeKey())) {
192 ACCOUNT_LOGE("the key already exists.");
193 return ERR_OSACCOUNT_SERVICE_DATA_STORAGE_KEY_EXISTED_ERROR;
194 }
195
196 std::string accountInfoStr = iAccountInfo.ToString();
197 if (accountInfoStr.empty()) {
198 ACCOUNT_LOGE("account info str is empty!");
199 return ERR_OSACCOUNT_SERVICE_ACCOUNT_INFO_EMPTY_ERROR;
200 }
201 return PutValueToKvStore(iAccountInfo.GetPrimeKey(), accountInfoStr);
202 }
203
204 ErrCode AccountDataStorage::SaveAccountInfo(const IAccountInfo &iAccountInfo)
205 {
206 if (!IsKeyExists(iAccountInfo.GetPrimeKey())) {
207 ACCOUNT_LOGE("the key does not exist");
208 return ERR_OSACCOUNT_SERVICE_DATA_STORAGE_KEY_NOT_EXISTS_ERROR;
209 }
210
211 std::string accountInfoStr = iAccountInfo.ToString();
212 if (accountInfoStr.empty()) {
213 ACCOUNT_LOGE("account info str is empty!");
214 return ERR_OSACCOUNT_SERVICE_ACCOUNT_INFO_EMPTY_ERROR;
215 }
216 return PutValueToKvStore(iAccountInfo.GetPrimeKey(), accountInfoStr);
217 }
218
219 #ifndef SQLITE_DLCLOSE_ENABLE
220 ErrCode AccountDataStorage::RemoveValueFromKvStore(const std::string &keyStr)
221 {
222 if (!CheckKvStore()) {
223 ACCOUNT_LOGE("kvStore is nullptr");
224 return ERR_ACCOUNT_COMMON_CHECK_KVSTORE_ERROR;
225 }
226
227 OHOS::DistributedKv::Key key(keyStr);
228 OHOS::DistributedKv::Status status;
229 OHOS::DistributedKv::Value value;
230 {
231 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
232 // check exist
233 TryTwice([this, &status, &key, &value] {
234 status = kvStorePtr_->Get(key, value);
235 return status;
236 });
237 if (status != OHOS::DistributedKv::Status::SUCCESS) {
238 ACCOUNT_LOGI("key does not exist in kvStore.");
239 return ERR_OK;
240 }
241
242 // delete
243 TryTwice([this, &status, &key] {
244 status = kvStorePtr_->Delete(key);
245 return status;
246 });
247 }
248
249 if (status != OHOS::DistributedKv::Status::SUCCESS) {
250 ACCOUNT_LOGE("delete key from kvstore failed, status %{public}d.", status);
251 return ERR_ACCOUNT_COMMON_DELETE_KEY_FROM_KVSTORE_ERROR;
252 }
253
254 ACCOUNT_LOGD("delete key from kvStore succeed!");
255 return ERR_OK;
256 }
257 #else
258 ErrCode AccountDataStorage::RemoveValueFromKvStore(const std::string &keyStr)
259 {
260 if (!CheckKvStore()) {
261 ACCOUNT_LOGE("kvStore is nullptr");
262 return ERR_ACCOUNT_COMMON_CHECK_KVSTORE_ERROR;
263 }
264
265 DbAdapterStatus status;
266 std::string value;
267 {
268 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
269 // check exist
270 TryTwice([this, &status, &keyStr, &value] {
271 status = kvStorePtr_->Get(keyStr, value);
272 return status;
273 });
274 if (status != DbAdapterStatus::SUCCESS) {
275 ACCOUNT_LOGI("key does not exist in kvStore.");
276 return ERR_OK;
277 }
278
279 // delete
280 TryTwice([this, &status, &keyStr] {
281 status = kvStorePtr_->Delete(keyStr);
282 return status;
283 });
284 }
285
286 if (status != DbAdapterStatus::SUCCESS) {
287 ACCOUNT_LOGE("delete key from kvstore failed, status %{public}d.", status);
288 return ERR_ACCOUNT_COMMON_DELETE_KEY_FROM_KVSTORE_ERROR;
289 }
290
291 ACCOUNT_LOGD("delete key from kvStore succeed!");
292 return ERR_OK;
293 }
294 #endif // SQLITE_DLCLOSE_ENABLE
295
296 #ifndef SQLITE_DLCLOSE_ENABLE
297 OHOS::DistributedKv::Status AccountDataStorage::GetEntries(
298 std::string subId, std::vector<OHOS::DistributedKv::Entry> &allEntries) const
299 {
300 OHOS::DistributedKv::Key allEntryKeyPrefix(subId);
301 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
302 OHOS::DistributedKv::Status status = kvStorePtr_->GetEntries(allEntryKeyPrefix, allEntries);
303
304 return status;
305 }
306 #else
307 DbAdapterStatus AccountDataStorage::GetEntries(
308 std::string subId, std::vector<DbAdapterEntry> &allEntries) const
309 {
310 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
311 DbAdapterStatus status = kvStorePtr_->GetEntries(subId, allEntries);
312
313 return status;
314 }
315 #endif // SQLITE_DLCLOSE_ENABLE
316
317 ErrCode AccountDataStorage::Close()
318 {
319 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
320 #ifndef SQLITE_DLCLOSE_ENABLE
321 ErrCode errCode = dataManager_.CloseKvStore(appId_, kvStorePtr_);
322 #else
323 ErrCode errCode = dataManager_->CloseKvStore(appId_, kvStorePtr_);
324 #endif // SQLITE_DLCLOSE_ENABLE
325 kvStorePtr_ = nullptr;
326 return errCode;
327 }
328
329 ErrCode AccountDataStorage::DeleteKvStore()
330 {
331 #ifndef SQLITE_DLCLOSE_ENABLE
332 if (!CheckKvStore()) {
333 ACCOUNT_LOGE("kvStore is nullptr");
334 return OHOS::ERR_OSACCOUNT_SERVICE_MANAGER_QUERY_DISTRIBUTE_DATA_ERROR;
335 }
336
337 OHOS::DistributedKv::Status status;
338 {
339 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
340 dataManager_.CloseKvStore(this->appId_, this->storeId_);
341 status = dataManager_.DeleteKvStore(this->appId_, this->storeId_, baseDir_);
342 }
343 if (status != OHOS::DistributedKv::Status::SUCCESS) {
344 ACCOUNT_LOGE("error, status = %{public}d", status);
345 return OHOS::ERR_OSACCOUNT_SERVICE_MANAGER_QUERY_DISTRIBUTE_DATA_ERROR;
346 }
347 #else
348 ACCOUNT_LOGI("DeleteKvStore not enabled.");
349 #endif // SQLITE_DLCLOSE_ENABLE
350 return ERR_OK;
351 }
352
353 ErrCode AccountDataStorage::GetAccountInfoById(const std::string id, OHOS::AccountSA::AppAccountInfo &accountInfo)
354 {
355 std::string valueStr;
356 ErrCode ret = GetValueFromKvStore(id, valueStr);
357 if (ret != ERR_OK) {
358 ACCOUNT_LOGE("get value from kvstore failed! id %{public}s.", id.c_str());
359 return ret;
360 }
361
362 auto jsonObject = CreateJsonFromString(valueStr);
363 if (jsonObject == nullptr || !IsStructured(jsonObject)) { // check format
364 ACCOUNT_LOGE("bad format of value from kvstore! id %{public}s.", id.c_str());
365 return ERR_ACCOUNT_COMMON_BAD_JSON_FORMAT_ERROR;
366 }
367 FromJson(jsonObject.get(), accountInfo);
368 return ERR_OK;
369 }
370
371 ErrCode AccountDataStorage::GetAccountInfoById(const std::string id, OHOS::AccountSA::OsAccountInfo &accountInfo)
372 {
373 std::string valueStr;
374 ErrCode ret = GetValueFromKvStore(id, valueStr);
375 if (ret != ERR_OK) {
376 ACCOUNT_LOGE("get value from kvstore failed! id %{public}s.", id.c_str());
377 return ret;
378 }
379
380 auto jsonObject = CreateJsonFromString(valueStr);
381 if (jsonObject == nullptr || !IsStructured(jsonObject)) { // check format
382 ACCOUNT_LOGE("bad format of value from kvstore! id %{public}s.", id.c_str());
383 return ERR_ACCOUNT_COMMON_BAD_JSON_FORMAT_ERROR;
384 }
385 FromJson(jsonObject.get(), accountInfo);
386 return ERR_OK;
387 }
388
389 ErrCode AccountDataStorage::LoadDataByLocalFuzzyQuery(
390 std::string subId, std::map<std::string, std::shared_ptr<IAccountInfo>> &infos)
391 {
392 if (!CheckKvStore()) {
393 ACCOUNT_LOGE("kvStore is nullptr");
394 return OHOS::ERR_OSACCOUNT_SERVICE_MANAGER_QUERY_DISTRIBUTE_DATA_ERROR;
395 }
396 #ifndef SQLITE_DLCLOSE_ENABLE
397 OHOS::DistributedKv::Status status = OHOS::DistributedKv::Status::SUCCESS;
398 std::vector<OHOS::DistributedKv::Entry> allEntries;
399 #else
400 DbAdapterStatus status = DbAdapterStatus::SUCCESS;
401 std::vector<DbAdapterEntry> allEntries;
402 #endif // SQLITE_DLCLOSE_ENABLE
403 TryTwice([this, &status, &allEntries, subId] {
404 status = GetEntries(subId, allEntries);
405 return status;
406 });
407 #ifndef SQLITE_DLCLOSE_ENABLE
408 if (status != OHOS::DistributedKv::Status::SUCCESS) {
409 #else
410 if (status != DbAdapterStatus::SUCCESS) {
411 #endif // SQLITE_DLCLOSE_ENABLE
412 ACCOUNT_LOGE("get entries error: %{public}d", status);
413 return OHOS::ERR_OSACCOUNT_SERVICE_MANAGER_QUERY_DISTRIBUTE_DATA_ERROR;
414 }
415 infos.clear();
416 SaveEntries(allEntries, infos);
417 return ERR_OK;
418 }
419
420 ErrCode AccountDataStorage::PutValueToKvStore(const std::string &keyStr, const std::string &valueStr)
421 {
422 if (!CheckKvStore()) {
423 ACCOUNT_LOGE("kvStore is nullptr");
424 return ERR_ACCOUNT_COMMON_CHECK_KVSTORE_ERROR;
425 }
426 #ifndef SQLITE_DLCLOSE_ENABLE
427 OHOS::DistributedKv::Key key(keyStr);
428 OHOS::DistributedKv::Value value(valueStr);
429 OHOS::DistributedKv::Status status;
430
431 {
432 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
433 status = kvStorePtr_->Put(key, value);
434 if (status == OHOS::DistributedKv::Status::IPC_ERROR) {
435 status = kvStorePtr_->Put(key, value);
436 }
437 }
438
439 if (status != OHOS::DistributedKv::Status::SUCCESS) {
440 #else
441 DbAdapterStatus status = DbAdapterStatus::SUCCESS;
442 {
443 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
444 status = kvStorePtr_->Put(keyStr, valueStr);
445 if (status == DbAdapterStatus::IPC_ERROR) {
446 status = kvStorePtr_->Put(keyStr, valueStr);
447 }
448 }
449
450 if (status != DbAdapterStatus::SUCCESS) {
451 #endif // SQLITE_DLCLOSE_ENABLE
452 ACCOUNT_LOGE("put value to kvStore error, status = %{public}d", status);
453 return OHOS::ERR_OSACCOUNT_SERVICE_MANAGER_QUERY_DISTRIBUTE_DATA_ERROR;
454 }
455
456 return ERR_OK;
457 }
458
459 ErrCode AccountDataStorage::GetValueFromKvStore(const std::string &keyStr, std::string &valueStr)
460 {
461 if (!CheckKvStore()) {
462 ACCOUNT_LOGE("kvStore is nullptr");
463 return ERR_ACCOUNT_COMMON_CHECK_KVSTORE_ERROR;
464 }
465 #ifndef SQLITE_DLCLOSE_ENABLE
466 OHOS::DistributedKv::Key key(keyStr);
467 OHOS::DistributedKv::Value value;
468 OHOS::DistributedKv::Status status;
469
470 {
471 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
472 status = kvStorePtr_->Get(key, value);
473 if (status == OHOS::DistributedKv::Status::IPC_ERROR) {
474 ACCOUNT_LOGE("kvstore ipc error and try again, status = %{public}d", status);
475 status = kvStorePtr_->Get(key, value);
476 }
477 }
478
479 if (status != OHOS::DistributedKv::Status::SUCCESS) {
480 #else
481 DbAdapterStatus status;
482
483 {
484 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
485 status = kvStorePtr_->Get(keyStr, valueStr);
486 if (status == DbAdapterStatus::IPC_ERROR) {
487 ACCOUNT_LOGE("kvstore ipc error and try again, status = %{public}d", status);
488 status = kvStorePtr_->Get(keyStr, valueStr);
489 }
490 }
491
492 if (status != DbAdapterStatus::SUCCESS) {
493 #endif // SQLITE_DLCLOSE_ENABLE
494 ACCOUNT_LOGE("get value from kvstore error, status %{public}d.", status);
495 return ERR_OSACCOUNT_SERVICE_MANAGER_QUERY_DISTRIBUTE_DATA_ERROR;
496 }
497 #ifndef SQLITE_DLCLOSE_ENABLE
498 valueStr = value.ToString();
499 #endif
500 return ERR_OK;
501 }
502
503 bool AccountDataStorage::IsKeyExists(const std::string keyStr)
504 {
505 std::string valueStr;
506 if (GetValueFromKvStore(keyStr, valueStr) != ERR_OK) {
507 return false;
508 }
509 return true;
510 }
511
512 ErrCode AccountDataStorage::MoveData(const std::shared_ptr<AccountDataStorage> &ptr)
513 {
514 #ifndef SQLITE_DLCLOSE_ENABLE
515 if (ptr == nullptr || !ptr->CheckKvStore() || !CheckKvStore()) {
516 ACCOUNT_LOGE("AccountDataStorage is nullptr");
517 return ERR_ACCOUNT_COMMON_CHECK_KVSTORE_ERROR;
518 }
519 std::vector<OHOS::DistributedKv::Entry> entries;
520 OHOS::DistributedKv::Status status = ptr->GetEntries("", entries);
521 if (status != OHOS::DistributedKv::Status::SUCCESS) {
522 ACCOUNT_LOGE("GetEntries failed, result=%{public}u", status);
523 return ERR_OSACCOUNT_SERVICE_MANAGER_QUERY_DISTRIBUTE_DATA_ERROR;
524 }
525 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
526 ErrCode errCode = StartTransaction();
527 if (errCode != ERR_OK) {
528 ACCOUNT_LOGE("StartTransaction failed, errCode=%{public}d", errCode);
529 return errCode;
530 }
531 status = kvStorePtr_->PutBatch(entries);
532 if (status != OHOS::DistributedKv::Status::SUCCESS) {
533 ACCOUNT_LOGE("PutBatch failed, result=%{public}u", status);
534 Rollback();
535 return ERR_OSACCOUNT_SERVICE_MANAGER_QUERY_DISTRIBUTE_DATA_ERROR;
536 }
537 errCode = Commit();
538 if (errCode != ERR_OK) {
539 ACCOUNT_LOGE("Commit failed, errCode=%{public}d", errCode);
540 Rollback();
541 return errCode;
542 }
543 #else
544 ACCOUNT_LOGI("MoveData not enabled.");
545 #endif
546 return ERR_OK;
547 }
548
549 ErrCode AccountDataStorage::StartTransaction()
550 {
551 #ifndef SQLITE_DLCLOSE_ENABLE
552 if (!CheckKvStore()) {
553 ACCOUNT_LOGE("KvStore is nullptr");
554 return ERR_ACCOUNT_COMMON_CHECK_KVSTORE_ERROR;
555 }
556 transactionMutex_.lock();
557 OHOS::DistributedKv::Status status;
558 {
559 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
560 TryTwice([this, &status] {
561 status = kvStorePtr_->StartTransaction();
562 return status;
563 });
564 }
565 if (status != OHOS::DistributedKv::Status::SUCCESS) {
566 ACCOUNT_LOGE("Distributed data start transaction failed, status = %{public}d", status);
567 transactionMutex_.unlock();
568 return OHOS::ERR_OSACCOUNT_SERVICE_MANAGER_QUERY_DISTRIBUTE_DATA_ERROR;
569 }
570 #endif // SQLITE_DLCLOSE_ENABLE
571 return ERR_OK;
572 }
573
574 ErrCode AccountDataStorage::Commit()
575 {
576 #ifndef SQLITE_DLCLOSE_ENABLE
577 if (!CheckKvStore()) {
578 ACCOUNT_LOGE("KvStore is nullptr");
579 return ERR_ACCOUNT_COMMON_CHECK_KVSTORE_ERROR;
580 }
581 OHOS::DistributedKv::Status status;
582 {
583 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
584 TryTwice([this, &status] {
585 status = kvStorePtr_->Commit();
586 return status;
587 });
588 }
589 if (status != OHOS::DistributedKv::Status::SUCCESS) {
590 ACCOUNT_LOGE("Distributed data commit failed, status = %{public}d", status);
591 return OHOS::ERR_OSACCOUNT_SERVICE_MANAGER_QUERY_DISTRIBUTE_DATA_ERROR;
592 }
593 transactionMutex_.unlock();
594 #endif // SQLITE_DLCLOSE_ENABLE
595 return ERR_OK;
596 }
597
598 ErrCode AccountDataStorage::Rollback()
599 {
600 #ifndef SQLITE_DLCLOSE_ENABLE
601 if (!CheckKvStore()) {
602 ACCOUNT_LOGE("KvStore is nullptr");
603 transactionMutex_.unlock();
604 return ERR_ACCOUNT_COMMON_CHECK_KVSTORE_ERROR;
605 }
606 OHOS::DistributedKv::Status status;
607 {
608 std::lock_guard<std::recursive_mutex> lock(kvStorePtrMutex_);
609 TryTwice([this, &status] {
610 status = kvStorePtr_->Rollback();
611 return status;
612 });
613 }
614 transactionMutex_.unlock();
615 if (status != OHOS::DistributedKv::Status::SUCCESS) {
616 ACCOUNT_LOGE("Distributed data rollback failed, status = %{public}d", status);
617 return OHOS::ERR_OSACCOUNT_SERVICE_MANAGER_QUERY_DISTRIBUTE_DATA_ERROR;
618 }
619 #endif // SQLITE_DLCLOSE_ENABLE
620 return ERR_OK;
621 }
622
623 ErrCode StartDbTransaction(
624 const std::shared_ptr<AccountDataStorage> &dataStoragePtr, DatabaseTransaction &dbTransaction)
625 {
626 ErrCode transactionRet = dataStoragePtr->StartTransaction();
627 if (transactionRet != ERR_OK) {
628 ACCOUNT_LOGE("StartTransaction failed, ret = %{public}d", transactionRet);
629 return transactionRet;
630 }
631 std::function<void(bool *)> callback = [dataStoragePtr](bool *pointer) {
632 if (pointer == nullptr) {
633 return;
634 }
635 dataStoragePtr->Rollback();
636 delete pointer;
637 };
638 dbTransaction = DatabaseTransaction(new bool(true), callback);
639 return ERR_OK;
640 }
641
642 ErrCode CommitDbTransaction(
643 const std::shared_ptr<AccountDataStorage> &dataStoragePtr, DatabaseTransaction &dbTransaction)
644 {
645 ErrCode transactionRet = dataStoragePtr->Commit();
646 if (transactionRet != ERR_OK) {
647 ACCOUNT_LOGE("Failed to commit database, result: %{public}d", transactionRet);
648 return transactionRet;
649 }
650 delete dbTransaction.release();
651 dbTransaction = nullptr;
652 return ERR_OK;
653 }
654 } // namespace AccountSA
655 } // namespace OHOS
656