• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-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 "app_account_info.h"
17 
18 #include "account_log_wrapper.h"
19 #include "nlohmann/json.hpp"
20 
21 namespace OHOS {
22 namespace AccountSA {
23 namespace {
24 const std::string OWNER = "owner";
25 const std::string NAME = "name";
26 const std::string EXTRA_INFO = "extraInfo";
27 const std::string SYNC_ENABLE = "syncEnable";
28 const std::string AUTHORIZED_APPS = "authorizedApps";
29 const std::string ASSOCIATED_DATA = "associatedData";
30 const std::string ACCOUNT_CREDENTIAL = "accountCredential";
31 const std::string OAUTH_TOKEN = "oauthToken";
32 const std::string OAUTH_TOKEN_INFOS = "tokenInfos";
33 const std::string OAUTH_TYPE = "authType";
34 const std::string OAUTH_AUTH_LIST = "authList";
35 const std::string OAUTH_TOKEN_TO_TYPE = "tokenToType";
36 const std::string HYPHEN = "#";
37 constexpr uint32_t APP_INDEX = 0;
38 constexpr uint32_t MAX_TOKEN_NUMBER = 128;
39 constexpr uint32_t MAX_OAUTH_LIST_SIZE = 512;
40 constexpr uint32_t MAX_ASSOCIATED_DATA_NUMBER = 1024;
41 constexpr int32_t MAX_MAP_SZIE = 1024;
42 }  // namespace
43 
AppAccountInfo()44 AppAccountInfo::AppAccountInfo()
45 {
46     owner_ = "";
47     name_ = "";
48     appIndex_ = APP_INDEX;
49     extraInfo_ = "";
50     authorizedApps_.clear();
51     syncEnable_ = false;
52     associatedData_ = "";
53     accountCredential_ = "";
54     oauthTokens_.clear();
55 }
56 
AppAccountInfo(const std::string & name,const std::string & owner)57 AppAccountInfo::AppAccountInfo(const std::string &name, const std::string &owner)
58 {
59     name_ = name;
60     owner_ = owner;
61     appIndex_ = APP_INDEX;
62     extraInfo_ = "";
63     authorizedApps_.clear();
64     syncEnable_ = false;
65     associatedData_ = "";
66     accountCredential_ = "";
67     oauthTokens_.clear();
68 }
69 
GetOwner()70 std::string AppAccountInfo::GetOwner()
71 {
72     return owner_;
73 }
74 
GetOwner(std::string & owner)75 void AppAccountInfo::GetOwner(std::string &owner)
76 {
77     owner = owner_;
78 }
79 
SetOwner(const std::string & owner)80 void AppAccountInfo::SetOwner(const std::string &owner)
81 {
82     owner_ = owner;
83 }
84 
GetName()85 std::string AppAccountInfo::GetName()
86 {
87     return name_;
88 }
89 
GetName(std::string & name) const90 void AppAccountInfo::GetName(std::string &name) const
91 {
92     name = name_;
93 }
94 
SetName(const std::string & name)95 void AppAccountInfo::SetName(const std::string &name)
96 {
97     name_ = name;
98 }
99 
GetAppIndex()100 uint32_t AppAccountInfo::GetAppIndex()
101 {
102     return appIndex_;
103 }
104 
SetAppIndex(const uint32_t & appIndex)105 void AppAccountInfo::SetAppIndex(const uint32_t &appIndex)
106 {
107     appIndex_ = appIndex;
108 }
109 
GetExtraInfo(std::string & extraInfo) const110 void AppAccountInfo::GetExtraInfo(std::string &extraInfo) const
111 {
112     extraInfo = extraInfo_;
113 }
114 
SetExtraInfo(const std::string & extraInfo)115 void AppAccountInfo::SetExtraInfo(const std::string &extraInfo)
116 {
117     extraInfo_ = extraInfo;
118 }
119 
EnableAppAccess(const std::string & authorizedApp,const uint32_t apiVersion)120 ErrCode AppAccountInfo::EnableAppAccess(const std::string &authorizedApp, const uint32_t apiVersion)
121 {
122     auto it = authorizedApps_.emplace(authorizedApp);
123     if (!it.second && apiVersion < Constants::API_VERSION9) {
124         return ERR_APPACCOUNT_SERVICE_ENABLE_APP_ACCESS_ALREADY_EXISTS;
125     }
126     return ERR_OK;
127 }
128 
DisableAppAccess(const std::string & authorizedApp,const uint32_t apiVersion)129 ErrCode AppAccountInfo::DisableAppAccess(const std::string &authorizedApp, const uint32_t apiVersion)
130 {
131     auto result = authorizedApps_.erase(authorizedApp);
132     if (result == 0 && apiVersion < Constants::API_VERSION9) {
133         return ERR_APPACCOUNT_SERVICE_DISABLE_APP_ACCESS_NOT_EXISTED;
134     }
135     return ERR_OK;
136 }
137 
CheckAppAccess(const std::string & authorizedApp,bool & isAccessible)138 ErrCode AppAccountInfo::CheckAppAccess(const std::string &authorizedApp, bool &isAccessible)
139 {
140     isAccessible = false;
141     auto it = authorizedApps_.find(authorizedApp);
142     if (it != authorizedApps_.end()) {
143         isAccessible = true;
144     }
145     return ERR_OK;
146 }
147 
GetAuthorizedApps(std::set<std::string> & apps) const148 void AppAccountInfo::GetAuthorizedApps(std::set<std::string> &apps) const
149 {
150     apps = authorizedApps_;
151 }
152 
SetAuthorizedApps(const std::set<std::string> & apps)153 void AppAccountInfo::SetAuthorizedApps(const std::set<std::string> &apps)
154 {
155     authorizedApps_ = apps;
156 }
157 
GetSyncEnable(bool & syncEnable) const158 void AppAccountInfo::GetSyncEnable(bool &syncEnable) const
159 {
160     syncEnable = syncEnable_;
161 }
162 
SetSyncEnable(const bool & syncEnable)163 void AppAccountInfo::SetSyncEnable(const bool &syncEnable)
164 {
165     syncEnable_ = syncEnable;
166 }
167 
InitCustomData(const std::map<std::string,std::string> & data)168 ErrCode AppAccountInfo::InitCustomData(const std::map<std::string, std::string> &data)
169 {
170     Json jsonObject = data;
171     try {
172         associatedData_ = jsonObject.dump();
173     } catch (Json::type_error& err) {
174         ACCOUNT_LOGE("failed to dump json object, reason: %{public}s", err.what());
175         return ERR_ACCOUNT_COMMON_DUMP_JSON_ERROR;
176     }
177     return ERR_OK;
178 }
179 
GetAllAssociatedData(std::map<std::string,std::string> & data) const180 ErrCode AppAccountInfo::GetAllAssociatedData(std::map<std::string, std::string> &data) const
181 {
182     auto jsonObject = Json::parse(associatedData_, nullptr, false);
183     if (!jsonObject.is_object()) {
184         ACCOUNT_LOGE("jsonObject is_discarded");
185         return ERR_APPACCOUNT_SERVICE_GET_ASSOCIATED_DATA;
186     }
187     try {
188         data = jsonObject.get<std::map<std::string, std::string>>();
189     }  catch (Json::type_error& err) {
190         ACCOUNT_LOGE("failed to convert json object to map, reason: %{public}s", err.what());
191         return ERR_APPACCOUNT_SERVICE_GET_ASSOCIATED_DATA;
192     }
193     return ERR_OK;
194 }
195 
GetAssociatedData(const std::string & key,std::string & value) const196 ErrCode AppAccountInfo::GetAssociatedData(const std::string &key, std::string &value) const
197 {
198     auto jsonObject = Json::parse(associatedData_, nullptr, false);
199     if (jsonObject.is_discarded()) {
200         ACCOUNT_LOGI("jsonObject is_discarded");
201         jsonObject = Json::object();
202     }
203 
204     if (jsonObject.find(key) == jsonObject.end()) {
205         ACCOUNT_LOGE("failed to find value, key = %{public}s", key.c_str());
206         return ERR_APPACCOUNT_SERVICE_ASSOCIATED_DATA_KEY_NOT_EXIST;
207     }
208 
209     value = jsonObject.at(key);
210     return ERR_OK;
211 }
212 
SetAssociatedData(const std::string & key,const std::string & value)213 ErrCode AppAccountInfo::SetAssociatedData(const std::string &key, const std::string &value)
214 {
215     auto jsonObject = Json::parse(associatedData_, nullptr, false);
216     if (jsonObject.is_discarded() || (!jsonObject.is_object())) {
217         ACCOUNT_LOGI("jsonObject is discarded");
218         jsonObject = Json::object();
219     }
220     auto it = jsonObject.find(key);
221     if (it == jsonObject.end()) {
222         if (jsonObject.size() >= MAX_ASSOCIATED_DATA_NUMBER) {
223             ACCOUNT_LOGW("associated data is over size, the max number is: %{public}d", MAX_ASSOCIATED_DATA_NUMBER);
224             return ERR_APPACCOUNT_SERVICE_ASSOCIATED_DATA_OVER_SIZE;
225         }
226         jsonObject.emplace(key, value);
227     } else {
228         jsonObject[key] = value;
229     }
230 
231     try {
232         associatedData_ = jsonObject.dump();
233     } catch (Json::type_error& err) {
234         ACCOUNT_LOGE("failed to dump json object, reason: %{public}s", err.what());
235         return ERR_ACCOUNT_COMMON_DUMP_JSON_ERROR;
236     }
237     return ERR_OK;
238 }
239 
GetAccountCredential(const std::string & credentialType,std::string & credential) const240 ErrCode AppAccountInfo::GetAccountCredential(const std::string &credentialType, std::string &credential) const
241 {
242     auto jsonObject = Json::parse(accountCredential_, nullptr, false);
243     if (jsonObject.is_discarded()) {
244         jsonObject = Json::object();
245     }
246 
247     if (jsonObject.find(credentialType) == jsonObject.end()) {
248         ACCOUNT_LOGE("failed to find value, credentialType = %{public}s", credentialType.c_str());
249         return ERR_APPACCOUNT_SERVICE_ACCOUNT_CREDENTIAL_NOT_EXIST;
250     }
251 
252     credential = jsonObject.at(credentialType);
253     return ERR_OK;
254 }
255 
SetAccountCredential(const std::string & credentialType,const std::string & credential,bool isDelete)256 ErrCode AppAccountInfo::SetAccountCredential(
257     const std::string &credentialType, const std::string &credential, bool isDelete)
258 {
259     auto jsonObject = Json::parse(accountCredential_, nullptr, false);
260     if (jsonObject.is_discarded() || (!jsonObject.is_object())) {
261         ACCOUNT_LOGI("jsonObject is discarded");
262         jsonObject = Json::object();
263     }
264 
265     if (isDelete) {
266         auto ret = jsonObject.erase(credentialType);
267         if (ret == 0) {
268             return ERR_APPACCOUNT_SERVICE_ACCOUNT_CREDENTIAL_NOT_EXIST;
269         }
270     } else {
271         jsonObject[credentialType] = credential;
272     }
273 
274     try {
275         accountCredential_ = jsonObject.dump();
276     } catch (Json::type_error& err) {
277         ACCOUNT_LOGE("failed to dump json object, reason: %{public}s", err.what());
278         return ERR_ACCOUNT_COMMON_DUMP_JSON_ERROR;
279     }
280     return ERR_OK;
281 }
282 
GetOAuthToken(const std::string & authType,std::string & token,const uint32_t apiVersion) const283 ErrCode AppAccountInfo::GetOAuthToken(const std::string &authType, std::string &token, const uint32_t apiVersion) const
284 {
285     token = "";
286     auto it = oauthTokens_.find(authType);
287     if (apiVersion >= Constants::API_VERSION9) {
288         if ((it == oauthTokens_.end()) || (!it->second.status)) {
289             ACCOUNT_LOGE("oauth token not exist");
290             return ERR_APPACCOUNT_SERVICE_OAUTH_TOKEN_NOT_EXIST;
291         }
292     } else {
293         if ((it == oauthTokens_.end()) || (it->second.token.empty())) {
294             ACCOUNT_LOGE("oauth token not exist");
295             return ERR_APPACCOUNT_SERVICE_OAUTH_TOKEN_NOT_EXIST;
296         }
297     }
298     token = it->second.token;
299     return ERR_OK;
300 }
301 
SetOAuthToken(const std::string & authType,const std::string & token)302 ErrCode AppAccountInfo::SetOAuthToken(const std::string &authType, const std::string &token)
303 {
304     auto it = oauthTokens_.find(authType);
305     if (it != oauthTokens_.end()) {
306         it->second.token = token;
307         return ERR_OK;
308     }
309     if (oauthTokens_.size() >= MAX_TOKEN_NUMBER) {
310         ACCOUNT_LOGE("too many types of oauth token, capacity for each account is %{public}d", MAX_TOKEN_NUMBER);
311         return ERR_APPACCOUNT_SERVICE_OAUTH_TOKEN_MAX_SIZE;
312     }
313     OAuthTokenInfo tokenInfo;
314     tokenInfo.token = token;
315     oauthTokens_.emplace(authType, tokenInfo);
316     return ERR_OK;
317 }
318 
DeleteOAuthToken(const std::string & authType,const std::string & token)319 ErrCode AppAccountInfo::DeleteOAuthToken(const std::string &authType, const std::string &token)
320 {
321     auto it = oauthTokens_.find(authType);
322     if ((it != oauthTokens_.end()) && (it->second.token == token)) {
323         it->second.token = "";
324         return ERR_OK;
325     }
326     return ERR_APPACCOUNT_SERVICE_OAUTH_TOKEN_NOT_EXIST;
327 }
328 
DeleteAuthToken(const std::string & authType,const std::string & token,bool isOwnerSelf)329 ErrCode AppAccountInfo::DeleteAuthToken(const std::string &authType, const std::string &token, bool isOwnerSelf)
330 {
331     auto it = oauthTokens_.find(authType);
332     if (it == oauthTokens_.end()) {
333         return ERR_APPACCOUNT_SERVICE_OAUTH_TOKEN_NOT_EXIST;
334     }
335     if (it->second.token == token && isOwnerSelf) {
336         oauthTokens_.erase(it);
337     } else {
338         it->second.status = false;
339     }
340     return ERR_OK;
341 }
342 
SetOAuthTokenVisibility(const std::string & authType,const std::string & bundleName,bool isVisible,const uint32_t apiVersion)343 ErrCode AppAccountInfo::SetOAuthTokenVisibility(
344     const std::string &authType, const std::string &bundleName, bool isVisible, const uint32_t apiVersion)
345 {
346     if (bundleName == owner_) {
347         return ERR_OK;
348     }
349     auto it = oauthTokens_.find(authType);
350     if (it == oauthTokens_.end()) {
351         if (apiVersion >= Constants::API_VERSION9) {
352             return ERR_APPACCOUNT_SERVICE_OAUTH_TYPE_NOT_EXIST;
353         }
354         if (!isVisible) {
355             return ERR_OK;
356         }
357         if (oauthTokens_.size() >= MAX_TOKEN_NUMBER) {
358             ACCOUNT_LOGE("too many types of oauth token, capacity for each account is %{public}d", MAX_TOKEN_NUMBER);
359             return ERR_APPACCOUNT_SERVICE_OAUTH_TOKEN_MAX_SIZE;
360         }
361         OAuthTokenInfo tokenInfo;
362         tokenInfo.authList.emplace(bundleName);
363         oauthTokens_.emplace(authType, tokenInfo);
364         return ERR_OK;
365     }
366     if (!isVisible) {
367         it->second.authList.erase(bundleName);
368         return ERR_OK;
369     }
370     it->second.authList.emplace(bundleName);
371     if (it->second.authList.size() > MAX_OAUTH_LIST_SIZE) {
372         ACCOUNT_LOGE("the authorization list is too large, whose capacity for each authType is %{public}d",
373             MAX_OAUTH_LIST_SIZE);
374         it->second.authList.erase(bundleName);
375         return ERR_APPACCOUNT_SERVICE_OAUTH_LIST_MAX_SIZE;
376     }
377     return ERR_OK;
378 }
379 
CheckOAuthTokenVisibility(const std::string & authType,const std::string & bundleName,bool & isVisible,const uint32_t apiVersion) const380 ErrCode AppAccountInfo::CheckOAuthTokenVisibility(
381     const std::string &authType, const std::string &bundleName, bool &isVisible, const uint32_t apiVersion) const
382 {
383     isVisible = false;
384     if (bundleName == owner_) {
385         isVisible = true;
386         return ERR_OK;
387     }
388     auto tokenInfoIt = oauthTokens_.find(authType);
389     if (tokenInfoIt == oauthTokens_.end()) {
390         if (apiVersion >= Constants::API_VERSION9) {
391             return ERR_APPACCOUNT_SERVICE_OAUTH_TYPE_NOT_EXIST;
392         } else {
393             return ERR_OK;
394         }
395     }
396     std::set<std::string> authList = tokenInfoIt->second.authList;
397     auto it = authList.find(bundleName);
398     if (it != authList.end()) {
399         isVisible = true;
400     }
401     return ERR_OK;
402 }
403 
GetAllOAuthTokens(std::vector<OAuthTokenInfo> & tokenInfos) const404 ErrCode AppAccountInfo::GetAllOAuthTokens(std::vector<OAuthTokenInfo> &tokenInfos) const
405 {
406     tokenInfos.clear();
407     for (auto it = oauthTokens_.begin(); it != oauthTokens_.end(); ++it) {
408         tokenInfos.push_back(it->second);
409     }
410     return ERR_OK;
411 }
412 
GetOAuthList(const std::string & authType,std::set<std::string> & oauthList,const uint32_t apiVersion) const413 ErrCode AppAccountInfo::GetOAuthList(
414     const std::string &authType, std::set<std::string> &oauthList, const uint32_t apiVersion) const
415 {
416     oauthList.clear();
417     auto it = oauthTokens_.find(authType);
418     if (it == oauthTokens_.end()) {
419         if (apiVersion >= Constants::API_VERSION9) {
420             return ERR_APPACCOUNT_SERVICE_OAUTH_TYPE_NOT_EXIST;
421         } else {
422             return ERR_OK;
423         }
424     }
425     oauthList = it->second.authList;
426     return ERR_OK;
427 }
428 
Marshalling(Parcel & parcel) const429 bool AppAccountInfo::Marshalling(Parcel &parcel) const
430 {
431     if (!parcel.WriteString(owner_)) {
432         ACCOUNT_LOGE("failed to write string for owner_");
433         return false;
434     }
435 
436     if (!parcel.WriteString(name_)) {
437         ACCOUNT_LOGE("failed to write string for name_");
438         return false;
439     }
440 
441     if (!parcel.WriteString(extraInfo_)) {
442         ACCOUNT_LOGE("failed to write string for extraInfo_");
443         return false;
444     }
445 
446     if (!WriteStringSet(authorizedApps_, parcel)) {
447         ACCOUNT_LOGE("failed to write string set for authorizedApps_");
448         return false;
449     }
450 
451     if (!parcel.WriteBool(syncEnable_)) {
452         ACCOUNT_LOGE("failed to write bool for syncEnable_");
453         return false;
454     }
455 
456     if (!parcel.WriteString(associatedData_)) {
457         ACCOUNT_LOGE("failed to write string for associatedData_");
458         return false;
459     }
460 
461     if (!parcel.WriteString(accountCredential_)) {
462         ACCOUNT_LOGE("failed to write string for accountCredential_");
463         return false;
464     }
465 
466     if (!WriteTokenInfos(oauthTokens_, parcel)) {
467         ACCOUNT_LOGE("failed to write string map for oauthTokens_");
468         return false;
469     }
470     return true;
471 }
472 
Unmarshalling(Parcel & parcel)473 AppAccountInfo *AppAccountInfo::Unmarshalling(Parcel &parcel)
474 {
475     AppAccountInfo *appAccountInfo = new (std::nothrow) AppAccountInfo();
476 
477     if ((appAccountInfo != nullptr) && (!appAccountInfo->ReadFromParcel(parcel))) {
478         ACCOUNT_LOGE("failed to read from parcel");
479         delete appAccountInfo;
480         appAccountInfo = nullptr;
481     }
482 
483     return appAccountInfo;
484 }
485 
ToJson() const486 Json AppAccountInfo::ToJson() const
487 {
488     auto tokenArray = Json::array();
489     for (auto it = oauthTokens_.begin(); it != oauthTokens_.end(); ++it) {
490         if ((it->second.token.empty()) && (it->second.authList.size() == 0)) {
491             continue;
492         }
493         auto tokenObject = Json {
494             {OAUTH_TYPE, it->first},
495             {OAUTH_TOKEN, it->second.token},
496             {OAUTH_AUTH_LIST, it->second.authList}
497         };
498         tokenArray.push_back(tokenObject);
499     }
500     auto jsonObject = Json {
501         {OWNER, owner_},
502         {NAME, name_},
503         {EXTRA_INFO, extraInfo_},
504         {AUTHORIZED_APPS, authorizedApps_},
505         {SYNC_ENABLE, syncEnable_},
506         {ASSOCIATED_DATA, associatedData_},
507         {ACCOUNT_CREDENTIAL, accountCredential_},
508         {OAUTH_TOKEN_INFOS, tokenArray},
509     };
510 
511     return jsonObject;
512 }
513 
ParseTokenInfosFromJson(const Json & jsonObject)514 void AppAccountInfo::ParseTokenInfosFromJson(const Json &jsonObject)
515 {
516     oauthTokens_.clear();
517     for (auto it = jsonObject.begin(); it != jsonObject.end(); ++it) {
518         OAuthTokenInfo tokenInfo;
519         if (it->find(OAUTH_TOKEN) != it->end()) {
520             it->at(OAUTH_TOKEN).get_to(tokenInfo.token);
521         }
522         if (it->find(OAUTH_TYPE) != it->end()) {
523             it->at(OAUTH_TYPE).get_to(tokenInfo.authType);
524         }
525         if (it->find(OAUTH_AUTH_LIST) != it->end()) {
526             it->at(OAUTH_AUTH_LIST).get_to(tokenInfo.authList);
527         }
528         oauthTokens_.emplace(tokenInfo.authType, tokenInfo);
529     }
530 }
531 
FromJson(const Json & jsonObject)532 void AppAccountInfo::FromJson(const Json &jsonObject)
533 {
534     const auto &jsonObjectEnd = jsonObject.end();
535 
536     OHOS::AccountSA::GetDataByType<std::string>(
537         jsonObject, jsonObjectEnd, OWNER, owner_, OHOS::AccountSA::JsonType::STRING);
538     OHOS::AccountSA::GetDataByType<std::string>(
539         jsonObject, jsonObjectEnd, NAME, name_, OHOS::AccountSA::JsonType::STRING);
540     OHOS::AccountSA::GetDataByType<std::string>(
541         jsonObject, jsonObjectEnd, EXTRA_INFO, extraInfo_, OHOS::AccountSA::JsonType::STRING);
542     OHOS::AccountSA::GetDataByType<bool>(
543         jsonObject, jsonObjectEnd, SYNC_ENABLE, syncEnable_, OHOS::AccountSA::JsonType::BOOLEAN);
544     OHOS::AccountSA::GetDataByType<std::set<std::string>>(
545         jsonObject, jsonObjectEnd, AUTHORIZED_APPS, authorizedApps_, OHOS::AccountSA::JsonType::ARRAY);
546     OHOS::AccountSA::GetDataByType<std::string>(
547         jsonObject, jsonObjectEnd, ASSOCIATED_DATA, associatedData_, OHOS::AccountSA::JsonType::STRING);
548     OHOS::AccountSA::GetDataByType<std::string>(
549         jsonObject, jsonObjectEnd, ACCOUNT_CREDENTIAL, accountCredential_, OHOS::AccountSA::JsonType::STRING);
550     if (jsonObject.find(OAUTH_TOKEN_INFOS) != jsonObjectEnd) {
551         ParseTokenInfosFromJson(jsonObject.at(OAUTH_TOKEN_INFOS));
552     }
553 }
554 
ToString() const555 std::string AppAccountInfo::ToString() const
556 {
557     auto jsonObject = ToJson();
558     try {
559         return jsonObject.dump();
560     } catch (Json::type_error& err) {
561         ACCOUNT_LOGE("failed to dump json object, reason: %{public}s", err.what());
562         return "";
563     }
564 }
565 
GetPrimeKey() const566 std::string AppAccountInfo::GetPrimeKey() const
567 {
568     return (owner_ + HYPHEN + std::to_string(appIndex_) + HYPHEN + name_ + HYPHEN);
569 }
570 
ReadFromParcel(Parcel & parcel)571 bool AppAccountInfo::ReadFromParcel(Parcel &parcel)
572 {
573     if (!parcel.ReadString(owner_)) {
574         ACCOUNT_LOGE("failed to read string for owner_");
575         return false;
576     }
577 
578     if (!parcel.ReadString(name_)) {
579         ACCOUNT_LOGE("failed to read string for name_");
580         return false;
581     }
582 
583     if (!parcel.ReadString(extraInfo_)) {
584         ACCOUNT_LOGE("failed to read string for extraInfo_");
585         return false;
586     }
587 
588     if (!ReadStringSet(authorizedApps_, parcel)) {
589         ACCOUNT_LOGE("failed to read string set for authorizedApps_");
590         return false;
591     }
592 
593     if (!parcel.ReadBool(syncEnable_)) {
594         ACCOUNT_LOGE("failed to read string for syncEnable_");
595         return false;
596     }
597 
598     if (!parcel.ReadString(associatedData_)) {
599         ACCOUNT_LOGE("failed to read string for associatedData_");
600         return false;
601     }
602 
603     if (!parcel.ReadString(accountCredential_)) {
604         ACCOUNT_LOGE("failed to read string for accountCredential_");
605         return false;
606     }
607 
608     if (!ReadTokenInfos(oauthTokens_, parcel)) {
609         ACCOUNT_LOGE("failed to read string map for oauthTokens_");
610         return false;
611     }
612     return true;
613 }
614 
WriteStringSet(const std::set<std::string> & stringSet,Parcel & data) const615 bool AppAccountInfo::WriteStringSet(const std::set<std::string> &stringSet, Parcel &data) const
616 {
617     if (!data.WriteUint32(stringSet.size())) {
618         ACCOUNT_LOGE("failed to WriteInt32 for stringSet.size()");
619         return false;
620     }
621 
622     for (auto it : stringSet) {
623         if (!data.WriteString(it)) {
624             ACCOUNT_LOGE("failed to WriteString for it");
625             return false;
626         }
627     }
628 
629     return true;
630 }
631 
ReadStringSet(std::set<std::string> & stringSet,Parcel & data)632 bool AppAccountInfo::ReadStringSet(std::set<std::string> &stringSet, Parcel &data)
633 {
634     uint32_t size = 0;
635     if (!data.ReadUint32(size)) {
636         ACCOUNT_LOGE("failed to ReadInt32 for size");
637         return false;
638     }
639 
640     if (size > Constants::MAX_CUSTOM_DATA_SIZE) {
641         ACCOUNT_LOGE("ReadStringSet oversize");
642         return false;
643     }
644     stringSet.clear();
645     for (uint32_t index = 0; index < size; index += 1) {
646         std::string it = data.ReadString();
647         if (it.size() == 0) {
648             ACCOUNT_LOGE("failed to ReadString for it");
649             return false;
650         }
651         stringSet.emplace(it);
652     }
653 
654     return true;
655 }
656 
WriteStringMap(const std::map<std::string,std::string> & stringMap,Parcel & data) const657 bool AppAccountInfo::WriteStringMap(const std::map<std::string, std::string> &stringMap, Parcel &data) const
658 {
659     if (!data.WriteInt32(stringMap.size())) {
660         ACCOUNT_LOGE("failed to WriteInt32 for stringSet.size()");
661         return false;
662     }
663 
664     for (auto& it : stringMap) {
665         if (!data.WriteString(it.first)) {
666             ACCOUNT_LOGE("failed to WriteString for authType");
667             return false;
668         }
669         if (!data.WriteString(it.second)) {
670             ACCOUNT_LOGE("failed to WriteString for token");
671             return false;
672         }
673     }
674 
675     return true;
676 }
677 
WriteTokenInfos(const std::map<std::string,OAuthTokenInfo> & tokenInfos,Parcel & data) const678 bool AppAccountInfo::WriteTokenInfos(const std::map<std::string, OAuthTokenInfo> &tokenInfos, Parcel &data) const
679 {
680     if (!data.WriteUint32(tokenInfos.size())) {
681         ACCOUNT_LOGE("failed to WriteInt32 for stringSet.size()");
682         return false;
683     }
684     for (auto& it : tokenInfos) {
685         if (!data.WriteString(it.first)) {
686             ACCOUNT_LOGE("failed to WriteString for authType");
687             return false;
688         }
689         if (!data.WriteString(it.second.token)) {
690             ACCOUNT_LOGE("failed to WriteString for token");
691             return false;
692         }
693         if (!WriteStringSet(it.second.authList, data)) {
694             ACCOUNT_LOGE("failed to WriteString for authList");
695             return false;
696         }
697     }
698     return true;
699 }
700 
ReadStringMap(std::map<std::string,std::string> & stringMap,Parcel & data)701 bool AppAccountInfo::ReadStringMap(std::map<std::string, std::string> &stringMap, Parcel &data)
702 {
703     int32_t size = 0;
704     if (!data.ReadInt32(size)) {
705         ACCOUNT_LOGE("failed to ReadInt32 for size");
706         return false;
707     }
708     if ((size < 0) || (size > MAX_MAP_SZIE)) {
709         ACCOUNT_LOGE("ReadStringMap oversize");
710         return false;
711     }
712     stringMap.clear();
713     for (int32_t index = 0; index < size; ++index) {
714         std::string key;
715         std::string value;
716         if (!data.ReadString(key)) {
717             ACCOUNT_LOGE("failed to ReadString for key");
718             return false;
719         }
720         if (!data.ReadString(value)) {
721             ACCOUNT_LOGE("failed to ReadString for value");
722             return false;
723         }
724         stringMap.emplace(key, value);
725     }
726 
727     return true;
728 }
729 
ReadTokenInfos(std::map<std::string,OAuthTokenInfo> & tokenInfos,Parcel & data)730 bool AppAccountInfo::ReadTokenInfos(std::map<std::string, OAuthTokenInfo> &tokenInfos, Parcel &data)
731 {
732     uint32_t size = 0;
733     if (!data.ReadUint32(size)) {
734         ACCOUNT_LOGE("failed to ReadInt32 for size");
735         return false;
736     }
737     if (size > MAX_TOKEN_NUMBER) {
738         ACCOUNT_LOGE("invalid token number");
739         return false;
740     }
741     tokenInfos.clear();
742     for (uint32_t index = 0; index < size; ++index) {
743         OAuthTokenInfo tokenInfo;
744         if (!data.ReadString(tokenInfo.authType)) {
745             ACCOUNT_LOGE("failed to ReadString for authType");
746             return false;
747         }
748         if (!data.ReadString(tokenInfo.token)) {
749             ACCOUNT_LOGE("failed to ReadString for token");
750             return false;
751         }
752         if (!ReadStringSet(tokenInfo.authList, data)) {
753             ACCOUNT_LOGE("failed to ReadString for authList");
754             return false;
755         }
756         tokenInfos.emplace(tokenInfo.authType, tokenInfo);
757     }
758     return true;
759 }
760 }  // namespace AccountSA
761 }  // namespace OHOS
762