1 /*
2 * Copyright (c) 2021-2022 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 "os_account_database_operator.h"
16 #include "account_log_wrapper.h"
17 #include "os_account_constants.h"
18 #include "os_account_data_storage.h"
19
20 namespace OHOS {
21 namespace AccountSA {
22 namespace {
23 const char OS_ACCOUNT_STORE_ID[] = "os_account_info";
24 const char APP_ID[] = "os_account_mgr_service";
25 }
26
OsAccountDatabaseOperator()27 OsAccountDatabaseOperator::OsAccountDatabaseOperator()
28 {}
29
~OsAccountDatabaseOperator()30 OsAccountDatabaseOperator::~OsAccountDatabaseOperator()
31 {}
32
InnerInit()33 bool OsAccountDatabaseOperator::InnerInit()
34 {
35 std::lock_guard<std::mutex> lock(initMutex_);
36 if (accountDataStorage_ == nullptr) {
37 ACCOUNT_LOGI("Database operator inner init, create accountDataStorage_!");
38 accountDataStorage_ = std::make_shared<OsAccountDataStorage>(
39 APP_ID, OS_ACCOUNT_STORE_ID, Constants::SYNC_OS_ACCOUNT_DATABASE);
40 }
41 if (!accountDataStorage_->IsKeyExists(Constants::ACCOUNT_LIST)) {
42 ACCOUNT_LOGI("Database operator inner init, create account list.");
43 std::vector<std::string> accountListVec;
44 auto accountList = CreateJson();
45 AddVectorStringToJson(accountList, Constants::ACCOUNT_LIST, accountListVec);
46 AddIntToJson(accountList, Constants::COUNT_ACCOUNT_NUM, 0);
47 AddIntToJson(accountList, Constants::MAX_ALLOW_CREATE_ACCOUNT_ID, Constants::MAX_USER_ID);
48 AddInt64ToJson(accountList, Constants::SERIAL_NUMBER_NUM, Constants::SERIAL_NUMBER_NUM_START);
49 std::string strValue = PackJsonToString(accountList);
50 ErrCode errCode = accountDataStorage_->PutValueToKvStore(
51 Constants::ACCOUNT_LIST, strValue);
52 if (errCode != ERR_OK) {
53 ACCOUNT_LOGE("Initialize account list failed! errCode %{public}d.", errCode);
54 return false;
55 }
56 }
57 return true;
58 }
59
GetOsAccountListFromDatabase(const std::string & storeID,std::vector<OsAccountInfo> & osAccountList)60 ErrCode OsAccountDatabaseOperator::GetOsAccountListFromDatabase(const std::string& storeID,
61 std::vector<OsAccountInfo> &osAccountList)
62 {
63 osAccountList.clear();
64 if (!InnerInit()) {
65 ACCOUNT_LOGE("InnerInit failed!");
66 return ERR_ACCOUNT_COMMON_NOT_INIT_ERROR;
67 }
68
69 std::map<std::string, std::shared_ptr<IAccountInfo>> osAccountMapInfos;
70 ErrCode errCode = ERR_OK;
71 if (storeID.empty()) {
72 errCode = accountDataStorage_->LoadAllData(osAccountMapInfos);
73 } else {
74 std::shared_ptr<AccountDataStorage> storagePtr = std::make_shared<OsAccountDataStorage>(
75 APP_ID, storeID, Constants::SYNC_OS_ACCOUNT_DATABASE);
76 if (storagePtr == nullptr) {
77 ACCOUNT_LOGE("StoragePtr is still nullptr, storeID %{public}s.", storeID.c_str());
78 return ERR_ACCOUNT_COMMON_INSUFFICIENT_MEMORY_ERROR;
79 }
80 errCode = storagePtr->LoadAllData(osAccountMapInfos);
81 }
82
83 if (errCode != ERR_OK) {
84 ACCOUNT_LOGE("LoadAllData failed! storeID %{public}s.", storeID.c_str());
85 return errCode;
86 }
87
88 for (auto it = osAccountMapInfos.begin(); it != osAccountMapInfos.end(); it++) {
89 OsAccountInfo curOsInfo = *(std::static_pointer_cast<OsAccountInfo>(it->second));
90 if (curOsInfo.GetLocalId() >= Constants::START_USER_ID) {
91 osAccountList.push_back(curOsInfo);
92 }
93 }
94 return ERR_OK;
95 }
96
InsertOsAccountIntoDataBase(const OsAccountInfo & osAccountInfo)97 void OsAccountDatabaseOperator::InsertOsAccountIntoDataBase(const OsAccountInfo &osAccountInfo)
98 {
99 if (!InnerInit()) {
100 ACCOUNT_LOGE("InnerInit failed! target localID %{public}d!", osAccountInfo.GetLocalId());
101 return;
102 }
103
104 if (osAccountInfo.GetLocalId() < Constants::START_USER_ID && osAccountInfo.GetLocalId() != Constants::U1_ID) {
105 ACCOUNT_LOGI("Target os account id %{public}d will not be saved in database!", osAccountInfo.GetLocalId());
106 return;
107 }
108
109 ErrCode errCode = accountDataStorage_->AddAccountInfo(osAccountInfo);
110 if (errCode != ERR_OK) {
111 ACCOUNT_LOGE("AddAccountInfo failed, error code %{public}d, target id %{public}d.",
112 errCode, osAccountInfo.GetLocalId());
113 return;
114 }
115 ACCOUNT_LOGI("Insert account %{public}d to database succeed.", osAccountInfo.GetLocalId());
116 }
117
DelOsAccountFromDatabase(const int id)118 void OsAccountDatabaseOperator::DelOsAccountFromDatabase(const int id)
119 {
120 if (!InnerInit()) {
121 ACCOUNT_LOGE("InnerInit failed! id %{public}d!", id);
122 return;
123 }
124
125 ErrCode errCode = accountDataStorage_->RemoveValueFromKvStore(std::to_string(id));
126 if (errCode != ERR_OK) {
127 ACCOUNT_LOGE("Delete os account %{public}d from database failed! error code %{public}d.", id, errCode);
128 } else {
129 ACCOUNT_LOGI("Delete os account %{public}d from database succeed!", id);
130 }
131 }
132
UpdateOsAccountInDatabase(const OsAccountInfo & osAccountInfo)133 void OsAccountDatabaseOperator::UpdateOsAccountInDatabase(const OsAccountInfo &osAccountInfo)
134 {
135 if (!InnerInit()) {
136 ACCOUNT_LOGE("InnerInit failed! local id %{public}d!", osAccountInfo.GetLocalId());
137 return;
138 }
139
140 ErrCode errCode = accountDataStorage_->SaveAccountInfo(osAccountInfo);
141 if (errCode != ERR_OK) {
142 ACCOUNT_LOGE("Update os account info in database failed, localId = %{public}d, errCode = %{public}d.",
143 osAccountInfo.GetLocalId(), errCode);
144 } else {
145 ACCOUNT_LOGI("Update os account info in database for account %{public}d succeed!", osAccountInfo.GetLocalId());
146 }
147 }
148
GetOsAccountFromDatabase(const std::string & storeID,const int id,OsAccountInfo & osAccountInfo)149 ErrCode OsAccountDatabaseOperator::GetOsAccountFromDatabase(const std::string& storeID,
150 const int id,
151 OsAccountInfo &osAccountInfo)
152 {
153 if (!InnerInit()) {
154 ACCOUNT_LOGE("InnerInit failed! storeID %{public}s id %{public}d!", storeID.c_str(), id);
155 return ERR_ACCOUNT_COMMON_NOT_INIT_ERROR;
156 }
157
158 if (storeID.empty()) {
159 return accountDataStorage_->GetAccountInfoById(std::to_string(id), osAccountInfo);
160 }
161
162 std::shared_ptr<AccountDataStorage> storagePtr = std::make_shared<OsAccountDataStorage>(
163 APP_ID, storeID, Constants::SYNC_OS_ACCOUNT_DATABASE);
164 if (storagePtr == nullptr) {
165 ACCOUNT_LOGE("StoragePtr is nullptr, for other storeID %{public}s, id %{public}d.", storeID.c_str(), id);
166 return ERR_ACCOUNT_COMMON_INSUFFICIENT_MEMORY_ERROR;
167 }
168 return storagePtr->GetAccountInfoById(std::to_string(id), osAccountInfo);
169 }
170
GetCreatedOsAccountNumFromDatabase(const std::string & storeID,int & createdOsAccountNum)171 ErrCode OsAccountDatabaseOperator::GetCreatedOsAccountNumFromDatabase(
172 const std::string& storeID, int &createdOsAccountNum)
173 {
174 CJsonUnique accountListJson = nullptr;
175 ErrCode ret = GetAccountListFromStoreID(storeID, accountListJson);
176 if (ret != ERR_OK) {
177 ACCOUNT_LOGE("Get account list from database failed, storeID %{public}s.", storeID.c_str());
178 return ret;
179 };
180 GetDataByType<int>(accountListJson, Constants::COUNT_ACCOUNT_NUM, createdOsAccountNum);
181 return ERR_OK;
182 }
183
UpdateOsAccountIDListInDatabase(const CJsonUnique & accountListJson)184 void OsAccountDatabaseOperator::UpdateOsAccountIDListInDatabase(const CJsonUnique &accountListJson)
185 {
186 if (!InnerInit()) {
187 ACCOUNT_LOGE("InnerInit failed!");
188 return;
189 }
190 std::string strValue = PackJsonToString(accountListJson);
191 ErrCode errCode = accountDataStorage_->PutValueToKvStore(Constants::ACCOUNT_LIST, strValue);
192 if (errCode != ERR_OK) {
193 ACCOUNT_LOGE("Update os account id list to database failed! errCode %{public}d.", errCode);
194 return;
195 }
196 ACCOUNT_LOGD("Update os account id list to database succeed.");
197 }
198
GetSerialNumberFromDatabase(const std::string & storeID,int64_t & serialNumber)199 ErrCode OsAccountDatabaseOperator::GetSerialNumberFromDatabase(
200 const std::string& storeID, int64_t &serialNumber)
201 {
202 CJsonUnique accountListJson = nullptr;
203 ErrCode ret = GetAccountListFromStoreID(storeID, accountListJson);
204 if (ret != ERR_OK) {
205 ACCOUNT_LOGE("Get serial number from database failed! err %{public}d, storeID %{public}s.",
206 ret, storeID.c_str());
207 return ret;
208 }
209 GetDataByType<int64_t>(accountListJson, Constants::SERIAL_NUMBER_NUM, serialNumber);
210 return ERR_OK;
211 }
212
GetMaxAllowCreateIdFromDatabase(const std::string & storeID,int & id)213 ErrCode OsAccountDatabaseOperator::GetMaxAllowCreateIdFromDatabase(const std::string& storeID, int &id)
214 {
215 CJsonUnique accountListJson = nullptr;
216 ErrCode ret = GetAccountListFromStoreID(storeID, accountListJson);
217 if (ret != ERR_OK) {
218 ACCOUNT_LOGE("Get max allow created id from database failed. err %{public}d, storeID %{public}s.",
219 ret, storeID.c_str());
220 return ret;
221 }
222 GetDataByType<int>(accountListJson, Constants::MAX_ALLOW_CREATE_ACCOUNT_ID, id);
223
224 return ERR_OK;
225 }
226
GetAccountListFromStoreID(const std::string & storeID,CJsonUnique & accountListJson)227 ErrCode OsAccountDatabaseOperator::GetAccountListFromStoreID(
228 const std::string& storeID, CJsonUnique &accountListJson)
229 {
230 if (!InnerInit()) {
231 ACCOUNT_LOGE("InnerInit failed! storeID %{public}s!", storeID.c_str());
232 return ERR_ACCOUNT_COMMON_NOT_INIT_ERROR;
233 }
234
235 std::string accountList;
236 ErrCode errCode = ERR_OK;
237 if (storeID.empty()) {
238 errCode = accountDataStorage_->GetValueFromKvStore(Constants::ACCOUNT_LIST, accountList);
239 } else {
240 std::shared_ptr<AccountDataStorage> storagePtr = std::make_shared<OsAccountDataStorage>(
241 APP_ID, storeID, Constants::SYNC_OS_ACCOUNT_DATABASE);
242 if (storagePtr == nullptr) {
243 ACCOUNT_LOGE("StoragePtr is nullptr, for other storeID %{public}s.", storeID.c_str());
244 return ERR_ACCOUNT_COMMON_INSUFFICIENT_MEMORY_ERROR;
245 }
246 errCode = storagePtr->GetValueFromKvStore(Constants::ACCOUNT_LIST, accountList);
247 }
248
249 if (errCode != ERR_OK) {
250 ACCOUNT_LOGE("Get account list info from database failed! storeID %{public}s.", storeID.c_str());
251 return errCode;
252 }
253 accountListJson = CreateJsonFromString(accountList);
254 if (accountListJson == nullptr) {
255 ACCOUNT_LOGE("AccountListFile does not comply with the json format.");
256 return ERR_ACCOUNT_COMMON_BAD_JSON_FORMAT_ERROR;
257 }
258 return ERR_OK;
259 }
260 } // namespace AccountSA
261 } // namespace OHOS