• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 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 
16 #include "napi_settings.h"
17 #include "napi_settings_observer.h"
18 
19 #include <pthread.h>
20 #include <unistd.h>
21 
22 #include "abs_shared_result_set.h"
23 #include "napi_settings_log.h"
24 #include "values_bucket.h"
25 #include "datashare_business_error.h"
26 
27 #include "napi_base_context.h"
28 #include "os_account_manager.h"
29 
30 
31 using namespace OHOS::AppExecFwk;
32 using namespace OHOS::DataShare;
33 using namespace OHOS::AccountSA;
34 
35 namespace OHOS {
36 namespace Settings {
37 const std::string SETTINGS_DATA_BASE_URI = "dataability:///com.ohos.settingsdata.DataAbility";
38 const std::string SETTINGS_DATA_FIELD_KEYWORD = "KEYWORD";
39 const std::string SETTINGS_DATA_FIELD_VALUE = "VALUE";
40 const std::string PERMISSION_EXCEPTION = "201 - Permission denied";
41 const int PERMISSION_DENIED_CODE = -2;
42 const int DB_HELPER_TRIAL_NUMBER = 2;
43 const int USERID_HELPER_NUMBER = 100;
44 
ThrowExistingError(napi_env env,std::string errorMessage)45 void ThrowExistingError(napi_env env, std::string errorMessage)
46 {
47     napi_value message;
48     napi_value error;
49     napi_create_string_utf8(env, errorMessage.c_str(), NAPI_AUTO_LENGTH, &message);
50     napi_create_error(env, NULL, message, &error);
51     napi_throw(env, error);
52 }
53 
ThrowError(napi_env env,int status)54 bool ThrowError(napi_env env, int status)
55 {
56     if (status >= 0) {
57         return true;
58     }
59     if (status == PERMISSION_DENIED_CODE) {
60         ThrowExistingError(env, PERMISSION_EXCEPTION);
61     }
62     return false;
63 }
64 
65 /**
66  * @brief Wrap void to js value.
67  * ability_context
68  * @param env the environment that the Node-API call is invoked under
69  * @return napi_value napi_value after wrapped
70  */
wrap_void_to_js(napi_env env)71 napi_value wrap_void_to_js(napi_env env)
72 {
73     napi_value result = nullptr;
74     NAPI_CALL(env, napi_get_null(env, &result));
75     return result;
76 }
77 
78 /**
79  * @brief Unwrap string from js value.
80  *
81  * @param env the environment that the Node-API call is invoked under
82  * @param param js value to unwrap
83  * @return std::string string value after unwrapped
84  */
unwrap_string_from_js(napi_env env,napi_value param)85 std::string unwrap_string_from_js(napi_env env, napi_value param)
86 {
87     std::string defaultValue("");
88 
89     size_t size = 0;
90     if (napi_get_value_string_utf8(env, param, nullptr, 0, &size) != napi_ok) {
91         return defaultValue;
92     }
93 
94     if (size == 0) {
95         return defaultValue;
96     }
97 
98     std::string value("");
99 
100     char *buf = new (std::nothrow) char[size + 1];
101     if (buf == nullptr) {
102         SETTING_LOG_INFO("unwarp");
103         return value;
104     }
105     memset_s(buf, size + 1, 0, size + 1);
106 
107     bool rev = napi_get_value_string_utf8(env, param, buf, size + 1, &size) == napi_ok;
108     if (rev) {
109         value = buf;
110     } else {
111         value = defaultValue;
112     }
113 
114     delete[] buf;
115     buf = nullptr;
116     SETTING_LOG_INFO("unwarp str is : %{public}s", value.c_str());
117     return value;
118 }
119 
120 /**
121  * @brief Wrap string to js value.
122  *
123  * @param env the environment that the Node-API call is invoked under
124  * @param value string value to be wrap
125  * @return napi_value js value after wrapped
126  */
wrap_string_to_js(napi_env env,const std::string & value)127 napi_value wrap_string_to_js(napi_env env, const std::string &value)
128 {
129     napi_value result = nullptr;
130     NAPI_CALL(env, napi_create_string_utf8(env, value.c_str(), NAPI_AUTO_LENGTH, &result));
131     return result;
132 }
133 
134 /**
135  * @brief Wrap bool to js value.
136  *
137  * @param env the environment that the Node-API call is invoked under
138  * @param value bool value to be wrap
139  * @return napi_value js value after wrapped
140  */
wrap_bool_to_js(napi_env env,bool value)141 napi_value wrap_bool_to_js(napi_env env, bool value)
142 {
143     napi_value result = nullptr;
144     NAPI_CALL(env, napi_get_boolean(env, value, &result));
145     return result;
146 }
147 
148 /**
149  * @brief getUri NAPI implementation.
150  *
151  * @param env the environment that the Node-API call is invoked under
152  * @param info the callback info passed into the callback function
153  * @return napi_value the return value from NAPI C++ to JS for the module.
154  */
napi_get_uri_sync(napi_env env,napi_callback_info info)155 napi_value napi_get_uri_sync(napi_env env, napi_callback_info info)
156 {
157     SETTING_LOG_INFO("called");
158 
159     napi_value retUri = nullptr;
160 
161     // Check the number of the arguments
162     size_t argc = ARGS_TWO;
163     napi_value args[ARGS_TWO] = {nullptr};
164     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, args, nullptr, nullptr));
165     if (argc != ARGS_ONE && argc != ARGS_TWO) {
166         SETTING_LOG_ERROR("%{public}s, wrong number of arguments.", __func__);
167         return wrap_void_to_js(env);
168     }
169 
170     // Check the value type of the arguments
171     napi_valuetype valueType;
172     NAPI_CALL(env, napi_typeof(env, args[PARAM0], &valueType));
173     NAPI_ASSERT(env, valueType == napi_string, "Wrong argument type. String expected.");
174 
175     if (argc == ARGS_TWO) {
176         SETTING_LOG_INFO("ARGS_TWO");
177         std::string keyStr = unwrap_string_from_js(env, args[PARAM0]);
178         // get userId string
179         std::vector<int> tmpId;
180         OHOS::AccountSA::OsAccountManager::QueryActiveOsAccountIds(tmpId);
181         std::string tmpIdStr = "100";
182         if (tmpId.size() > 0) {
183             tmpIdStr = std::to_string(tmpId[0]);
184         } else {
185             SETTING_LOG_ERROR("userid is invalid, use id 100 instead");
186         }
187         std::string tableName = unwrap_string_from_js(env, args[PARAM1]);
188         std::string retStr = GetStageUriStr(tableName, tmpIdStr, keyStr);
189         retUri = wrap_string_to_js(env, retStr);
190         return retUri;
191     } else {
192         SETTING_LOG_INFO("ARGS_OTHER (should one)");
193         NAPI_CALL(env, napi_get_cb_info(env, info, &argc, args, nullptr, nullptr));
194         if (argc != ARGS_ONE) {
195             SETTING_LOG_ERROR("%{public}s, wrong number of arguments.", __func__);
196             return wrap_void_to_js(env);
197         }
198 
199         std::string uriArgStr = unwrap_string_from_js(env, args[PARAM0]);
200         uriArgStr = "datashare:///com.ohos.settingsdata/entry/settingsdata/SETTINGSDATA?Proxy=true&key=" + uriArgStr;
201         retUri = wrap_string_to_js(env, uriArgStr);
202         return retUri;
203     }
204 }
205 
napi_get_uri(napi_env env,napi_callback_info info)206 napi_value napi_get_uri(napi_env env, napi_callback_info info)
207 {
208     SETTING_LOG_INFO("uri called");
209     // Check the number of the arguments
210     size_t argc = ARGS_THREE;
211     napi_value args[ARGS_THREE] = {nullptr};
212     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, args, nullptr, nullptr));
213     if (argc != ARGS_ONE && argc != ARGS_TWO && argc != ARGS_THREE) {
214         SETTING_LOG_ERROR(
215             "uri %{public}s, wrong number of arguments, expect 1 or 2 or 3 but get %{public}zd",
216             __func__,
217             argc);
218         return wrap_void_to_js(env);
219     }
220 
221     // Check the value type of the arguments
222     napi_valuetype valueType;
223     NAPI_CALL(env, napi_typeof(env, args[PARAM0], &valueType));
224     NAPI_ASSERT(env, valueType == napi_string, "uri Wrong argument type. String expected.");
225 
226     // check call type for stage model
227     CallType callType = INVALID_CALL;
228     if (argc == ARGS_ONE) {
229         callType = STAGE_PROMISE;
230     } else if (argc == ARGS_TWO) {
231         napi_valuetype valueType;
232         NAPI_CALL(env, napi_typeof(env, args[PARAM1], &valueType));
233         if (valueType == napi_string) {
234             callType = STAGE_PROMISE_SPECIFIC;
235         } else {
236             callType = STAGE_CALLBACK;
237         }
238     } else if (argc == ARGS_THREE) {
239         callType = STAGE_CALLBACK_SPECIFIC;
240     }
241 
242     SETTING_LOG_INFO("uri arg count is %{public}zd", argc);
243     AsyncCallbackInfo* asyncCallbackInfo = new AsyncCallbackInfo {
244         .env = env,
245         .asyncWork = nullptr,
246         .deferred = nullptr,
247         .callbackRef = nullptr,
248         .dataAbilityHelper = nullptr,
249         .key = "",
250         .value = "",
251         .uri = "",
252         .status = false,
253     };
254 
255     std::string keyStr = unwrap_string_from_js(env, args[PARAM0]);
256     // get userId string
257     std::vector<int> tmpId;
258     OHOS::AccountSA::OsAccountManager::QueryActiveOsAccountIds(tmpId);
259     std::string tmpIdStr = "100";
260     if (tmpId.size() > 0) {
261         tmpIdStr = std::to_string(tmpId[0]);
262     } else {
263         SETTING_LOG_ERROR("userid is invalid, use id 100 instead");
264     }
265     std::string tableName = "";
266     if (callType == STAGE_CALLBACK_SPECIFIC) {
267         tableName = unwrap_string_from_js(env, args[PARAM2]);
268     } else if (callType == STAGE_PROMISE_SPECIFIC) {
269         tableName = unwrap_string_from_js(env, args[PARAM1]);
270     } else {
271         tableName = "global";
272     }
273     std::string retStr = GetStageUriStr(tableName, tmpIdStr, keyStr);
274     asyncCallbackInfo->uri = retStr;
275     SETTING_LOG_INFO("uri aft is %{public}s", asyncCallbackInfo->uri.c_str());
276 
277     napi_value resource = nullptr;
278     NAPI_CALL(env, napi_create_string_utf8(env, "getUri", NAPI_AUTO_LENGTH, &resource));
279 
280     if (callType == STAGE_CALLBACK || callType == STAGE_CALLBACK_SPECIFIC) {
281         SETTING_LOG_INFO("uri do c_b");
282         napi_create_reference(env, args[PARAM1], 1, &asyncCallbackInfo->callbackRef);
283 
284         napi_create_async_work(
285             env,
286             nullptr,
287             resource,
288             [](napi_env env, void* data) {
289                 SETTING_LOG_INFO("uri c_b asy execute c_b");
290             },
291             [](napi_env env, napi_status status, void* data) {
292                 if (data == nullptr) {
293                     SETTING_LOG_INFO("uri c_b asy end data is null");
294                     return;
295                 }
296                 SETTING_LOG_INFO("uri c_b asy end");
297                 AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
298                 napi_value undefine;
299                 napi_get_undefined(env, &undefine);
300                 napi_value callback = nullptr;
301                 napi_value result = wrap_string_to_js(env, asyncCallbackInfo->uri);
302                 napi_get_reference_value(env, asyncCallbackInfo->callbackRef, &callback);
303                 napi_call_function(env, nullptr, callback, 1, &result, &undefine);
304                 napi_delete_reference(env, asyncCallbackInfo->callbackRef);
305                 napi_delete_async_work(env, asyncCallbackInfo->asyncWork);
306                 delete asyncCallbackInfo;
307                 SETTING_LOG_INFO("uri c_b change complete");
308             },
309             (void*)asyncCallbackInfo,
310             &asyncCallbackInfo->asyncWork
311         );
312 
313         SETTING_LOG_INFO("uri c_b start asy work");
314         NAPI_CALL(env, napi_queue_async_work(env, asyncCallbackInfo->asyncWork));
315         SETTING_LOG_INFO("uri c_b end asy work");
316         return wrap_void_to_js(env);
317     } else {
318         SETTING_LOG_INFO("uri do p_m");
319         napi_value promise;
320         napi_deferred deferred;
321         NAPI_CALL(env, napi_create_promise(env, &deferred, &promise));
322         asyncCallbackInfo->deferred = deferred;
323 
324         napi_create_async_work(
325             env,
326             nullptr,
327             resource,
328             // aysnc executed task
329             [](napi_env env, void* data) {
330                 SETTING_LOG_INFO("uri p_m asy execute c_b");
331             },
332             // async end called callback+
333             [](napi_env env, napi_status status, void* data) {
334                 SETTING_LOG_INFO("uri p_m asy end");
335                 AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
336                 SETTING_LOG_INFO("uri p_m end get c_b value is %{public}s",
337                     asyncCallbackInfo->uri.c_str());
338                 napi_value result = wrap_string_to_js(env, asyncCallbackInfo->uri);
339                 napi_resolve_deferred(asyncCallbackInfo->env, asyncCallbackInfo->deferred, result);
340                 napi_delete_async_work(env, asyncCallbackInfo->asyncWork);
341                 delete asyncCallbackInfo;
342             },
343             (void*)asyncCallbackInfo,
344             &asyncCallbackInfo->asyncWork);
345         napi_queue_async_work(env, asyncCallbackInfo->asyncWork);
346         SETTING_LOG_INFO("uri p_m end asy work");
347         return promise;
348     }
349 }
350 
CheckDataShareHelper(napi_env env,const napi_value context,std::shared_ptr<OHOS::DataShare::DataShareHelper> dataShareHelper,OHOS::Uri proxyUri)351 void CheckDataShareHelper(napi_env env, const napi_value context,
352     std::shared_ptr<OHOS::DataShare::DataShareHelper> dataShareHelper, OHOS::Uri proxyUri)
353 {
354     std::shared_ptr<OHOS::DataShare::DataShareResultSet> resultset = nullptr;
355     std::string strUri = "datashare:///com.ohos.settingsdata.DataAbility";
356     DataSharePredicates predicates;
357     predicates.Limit(1, 0);
358     auto contextS = OHOS::AbilityRuntime::GetStageModeContext(env, context);
359     std::vector<std::string> columns;
360     DatashareBusinessError businessError;
361     resultset = dataShareHelper->Query(proxyUri, predicates, columns, &businessError);
362     int numRows = 0;
363     if (resultset != nullptr) {
364         resultset->GetRowCount(numRows);
365     }
366     SETTING_LOG_INFO("numRows %{public}d, error code %{public}d", numRows, businessError.GetCode());
367     if (businessError.GetCode() == PERMISSION_DENIED_CODE) {
368         if (resultset != nullptr) {
369             resultset->Close();
370         }
371         return;
372     } else if (resultset == nullptr || numRows <= 0) {
373         int trial = 0;
374         do {
375             SETTING_LOG_INFO("settingsnapi : getDataShareHelper resultset == nullptr, strUri %{public}s %{public}d",
376                 strUri.c_str(),
377                 trial);
378             dataShareHelper = OHOS::DataShare::DataShareHelper::Creator(contextS->GetToken(), strUri);
379         } while (trial++ < DB_HELPER_TRIAL_NUMBER && dataShareHelper == nullptr);
380         if (resultset != nullptr) {
381             resultset->Close();
382         }
383         return;
384     }
385     resultset->Close();
386 }
387 
getDataShareHelper(napi_env env,const napi_value context,const bool stageMode,std::string tableName,AsyncCallbackInfo * asyncCallbackInfo)388 std::shared_ptr<DataShareHelper> getDataShareHelper(
389     napi_env env, const napi_value context, const bool stageMode, std::string tableName,
390     AsyncCallbackInfo *asyncCallbackInfo)
391 {
392     std::shared_ptr<OHOS::DataShare::DataShareHelper> dataShareHelper = nullptr;
393     std::vector<int> tmpId;
394     OHOS::AccountSA::OsAccountManager::QueryActiveOsAccountIds(tmpId);
395     std::string tmpIdStr = "100";
396     if (tmpId.size() > 0) {
397         tmpIdStr = std::to_string(tmpId[0]);
398     } else {
399         SETTING_LOG_ERROR("userid is invalid, use id 100 instead");
400     }
401     std::string strUri = "datashare:///com.ohos.settingsdata.DataAbility";
402     std::string strProxyUri = GetProxyUriStr(tableName, tmpIdStr);
403     OHOS::Uri proxyUri(strProxyUri);
404     SETTING_LOG_INFO("<Ver-11-14> strProxyUri: %{public}s", strProxyUri.c_str());
405     auto contextS = OHOS::AbilityRuntime::GetStageModeContext(env, context);
406 
407     dataShareHelper = OHOS::DataShare::DataShareHelper::Creator(contextS->GetToken(), strProxyUri);
408     if (!dataShareHelper) {
409         SETTING_LOG_ERROR("dataShareHelper from strProxyUri is null");
410         dataShareHelper = OHOS::DataShare::DataShareHelper::Creator(contextS->GetToken(), strUri);
411         if (asyncCallbackInfo) {
412             asyncCallbackInfo->useSilent = true;
413         }
414     }
415     SETTING_LOG_INFO("g_D_S_H Creator called, valid %{public}d", dataShareHelper != nullptr);
416     return dataShareHelper;
417 }
418 
QueryValue(napi_env env,AsyncCallbackInfo * asyncCallbackInfo,OHOS::Uri uri)419 void QueryValue(napi_env env, AsyncCallbackInfo* asyncCallbackInfo, OHOS::Uri uri)
420 {
421     SETTING_LOG_INFO("a_C_B_I->d_S_H != nullptr");
422     if (asyncCallbackInfo->dataShareHelper == nullptr) {
423         SETTING_LOG_ERROR("helper is null");
424         asyncCallbackInfo->status = -1;
425         return;
426     }
427 
428     std::vector<std::string> columns;
429     columns.push_back(SETTINGS_DATA_FIELD_VALUE);
430 
431     OHOS::DataShare::DataSharePredicates predicates;
432     predicates.EqualTo(SETTINGS_DATA_FIELD_KEYWORD, asyncCallbackInfo->key);
433 
434     DatashareBusinessError businessError;
435     std::shared_ptr<OHOS::DataShare::DataShareResultSet> resultset = nullptr;
436     resultset = asyncCallbackInfo->dataShareHelper->Query(uri, predicates, columns, &businessError);
437     int numRows = 0;
438     if (resultset != nullptr) {
439         SETTING_LOG_INFO("G_V_E_E resultset is NOT empty");
440         resultset->GetRowCount(numRows);
441     }
442     SETTING_LOG_INFO("numRows %{public}d, error code %{public}d", numRows, businessError.GetCode());
443     if (businessError.GetCode() != 0) {
444         asyncCallbackInfo->status = businessError.GetCode();
445     } else if (resultset == nullptr || numRows <= 0) {
446         SETTING_LOG_INFO("G_V_E_E value is empty");
447         asyncCallbackInfo->status = -1;
448     } else {
449         std::string val;
450         int32_t columnIndex = 0;
451         resultset->GoToFirstRow();
452         resultset->GetString(columnIndex, val);
453 
454         SETTING_LOG_INFO("n_g_v_e %{public}s", val.c_str());
455         asyncCallbackInfo->value = val;
456         asyncCallbackInfo->status = napi_ok;
457     }
458 
459     if (resultset != nullptr) {
460         resultset->Close();
461     }
462 }
463 
GetValueExecuteExt(napi_env env,void * data)464 void GetValueExecuteExt(napi_env env, void *data)
465 {
466     if (data == nullptr) {
467         SETTING_LOG_INFO("execute data is null");
468         return;
469     }
470 
471     SETTING_LOG_INFO("G_V_E_E start");
472     AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
473 
474     if (asyncCallbackInfo->dataShareHelper == nullptr) {
475         SETTING_LOG_ERROR("dataShareHelper is empty");
476         asyncCallbackInfo->status = -1;
477         return;
478     }
479 
480     std::vector<int> tmpId;
481     OHOS::AccountSA::OsAccountManager::QueryActiveOsAccountIds(tmpId);
482     std::string tmpIdStr = "100";
483     if (tmpId.size() > 0) {
484         tmpIdStr = std::to_string(tmpId[0]);
485     } else {
486         SETTING_LOG_ERROR("userid is invalid, use id 100 instead");
487     }
488     std::string strUri = GetStageUriStr(asyncCallbackInfo->tableName, tmpIdStr, asyncCallbackInfo->key);
489     SETTING_LOG_INFO(
490         "Get uri : %{public}s, key: %{public}s", strUri.c_str(), (asyncCallbackInfo->key).c_str());
491     OHOS::Uri uri(strUri);
492 
493     QueryValue(env, asyncCallbackInfo, uri);
494 }
495 
DeleteCallbackInfo(napi_env env,AsyncCallbackInfo * asyncCallbackInfo)496 void DeleteCallbackInfo(napi_env env, AsyncCallbackInfo *asyncCallbackInfo)
497 {
498     if (env != nullptr) {
499         napi_delete_reference(env, asyncCallbackInfo->callbackRef);
500         napi_delete_async_work(env, asyncCallbackInfo->asyncWork);
501     }
502     asyncCallbackInfo->dataShareHelper = nullptr;
503     delete asyncCallbackInfo;
504 }
505 
CompleteCall(napi_env env,napi_status status,void * data,const napi_value retVaule)506 void CompleteCall(napi_env env, napi_status status, void *data, const napi_value retVaule)
507 {
508     AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
509     napi_value result[PARAM2] = {0};
510     if (status == napi_ok && asyncCallbackInfo->status == napi_ok) {
511         napi_get_undefined(env, &result[PARAM0]);
512         result[PARAM1] = retVaule;
513     } else {
514         napi_value message = nullptr;
515         napi_create_string_utf8(env, "async call failed", NAPI_AUTO_LENGTH, &message);
516         napi_create_error(env, nullptr, message, &result[PARAM0]);
517         napi_get_undefined(env, &result[PARAM1]);
518     }
519     napi_value callback = nullptr;
520     napi_get_reference_value(env, asyncCallbackInfo->callbackRef, &callback);
521     napi_value returnValue;
522     napi_call_function(env, nullptr, callback, PARAM2, result, &returnValue);
523     DeleteCallbackInfo(env, asyncCallbackInfo);
524     SETTING_LOG_INFO("c_b complete");
525 }
526 
CompletePromise(napi_env env,napi_status status,void * data,const napi_value retVaule)527 void CompletePromise(napi_env env, napi_status status, void *data, const napi_value retVaule)
528 {
529     SETTING_LOG_INFO("p_m asy end  c_b");
530     AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
531     napi_value result = nullptr;
532     if (status == napi_ok && asyncCallbackInfo->status == napi_ok) {
533         napi_resolve_deferred(env, asyncCallbackInfo->deferred, retVaule);
534     } else {
535         napi_get_undefined(env, &result);
536         napi_reject_deferred(env, asyncCallbackInfo->deferred, result);
537     }
538     DeleteCallbackInfo(env, asyncCallbackInfo);
539 }
540 
SetValueExecuteExt(napi_env env,void * data,const std::string setValue)541 void SetValueExecuteExt(napi_env env, void *data, const std::string setValue)
542 {
543     if (data == nullptr) {
544         SETTING_LOG_INFO("s_V_E_E data is null");
545         return;
546     }
547     SETTING_LOG_INFO("execute start");
548     AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
549 
550     if (asyncCallbackInfo->dataShareHelper == nullptr) {
551         SETTING_LOG_INFO("helper is null");
552         asyncCallbackInfo->status = -1;
553         return;
554     }
555 
556     OHOS::DataShare::DataShareValuesBucket val;
557     val.Put(SETTINGS_DATA_FIELD_KEYWORD, asyncCallbackInfo->key);
558     val.Put(SETTINGS_DATA_FIELD_VALUE, setValue);
559 
560     std::vector<int> tmpId;
561     OHOS::AccountSA::OsAccountManager::QueryActiveOsAccountIds(tmpId);
562     std::string tmpIdStr = "100";
563     if (tmpId.size() > 0) {
564         tmpIdStr = std::to_string(tmpId[0]);
565     } else {
566         SETTING_LOG_ERROR("userid is invalid, use id 100 instead");
567     }
568     std::string strUri = GetStageUriStr(asyncCallbackInfo->tableName, tmpIdStr, asyncCallbackInfo->key);
569     SETTING_LOG_INFO(
570         "Set uri : %{public}s, key: %{public}s", strUri.c_str(), (asyncCallbackInfo->key).c_str());
571     OHOS::Uri uri(strUri);
572 
573     OHOS::DataShare::DataSharePredicates predicates;
574     predicates.EqualTo(SETTINGS_DATA_FIELD_KEYWORD, asyncCallbackInfo->key);
575 
576     // update first.
577     int retInt = asyncCallbackInfo->dataShareHelper->Update(uri, predicates, val);
578     SETTING_LOG_ERROR("update ret: %{public}d", retInt);
579     if (retInt <= 0) {
580         // retry to insert.
581         retInt = asyncCallbackInfo->dataShareHelper->Insert(uri, val);
582         SETTING_LOG_ERROR("insert ret: %{public}d", retInt);
583     }
584     if (retInt > 0 && asyncCallbackInfo->useSilent) {
585         SETTING_LOG_INFO("use silent and notifyChange!");
586         asyncCallbackInfo->dataShareHelper->NotifyChange(uri);
587     }
588     asyncCallbackInfo->status = retInt;
589 }
590 
591 /**
592  * @brief getValue NAPI implementation.
593  *
594  * @param env the environment that the Node-API call is invoked under
595  * @param info the callback info passed into the callback function
596  * @return napi_value the return value from NAPI C++ to JS for the module.
597  */
napi_get_value_sync(napi_env env,napi_callback_info info)598 napi_value napi_get_value_sync(napi_env env, napi_callback_info info)
599 {
600     SETTING_LOG_INFO("n_g_v");
601 
602     // Check the number of the arguments
603     size_t argc = ARGS_FOUR;
604     napi_value args[ARGS_FOUR] = {nullptr};
605     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, args, nullptr, nullptr));
606     if (argc != ARGS_THREE && argc != ARGS_FOUR) {
607         SETTING_LOG_ERROR("%{public}s, wrong number of arguments.", __func__);
608         return wrap_void_to_js(env);
609     }
610 
611     // Check the value type of the arguments
612     napi_valuetype valueType;
613     NAPI_CALL(env, napi_typeof(env, args[PARAM0], &valueType));
614     NAPI_ASSERT(env, valueType == napi_object, "Wrong argument[0] type. Object expected.");
615     NAPI_CALL(env, napi_typeof(env, args[PARAM1], &valueType));
616     NAPI_ASSERT(env, valueType == napi_string, "Wrong argument[1] type. String expected.");
617     NAPI_CALL(env, napi_typeof(env, args[PARAM2], &valueType));
618     NAPI_ASSERT(env, valueType == napi_string, "Wrong argument[2] type. String expected.");
619 
620     bool stageMode = false;
621     napi_status status = OHOS::AbilityRuntime::IsStageContext(env, args[PARAM0], stageMode);
622     if (status == napi_ok) {
623         return napi_get_value_sync_ext(stageMode, argc, env, args);
624     }
625 
626     std::shared_ptr<Uri> uri = std::make_shared<Uri>(SETTINGS_DATA_BASE_URI);
627     std::shared_ptr<DataAbilityHelper> dataAbilityHelper = nullptr;
628     NAPIDataAbilityHelperWrapper* wrapper = nullptr;
629     NAPI_CALL(env, napi_unwrap(env, args[PARAM0], reinterpret_cast<void **>(&wrapper)));
630     if (wrapper != nullptr) {
631         dataAbilityHelper = wrapper->GetDataAbilityHelper();
632     }
633 
634     std::vector<std::string> columns;
635     columns.push_back(SETTINGS_DATA_FIELD_VALUE);
636     OHOS::NativeRdb::DataAbilityPredicates predicates;
637     predicates.EqualTo(SETTINGS_DATA_FIELD_KEYWORD, unwrap_string_from_js(env, args[PARAM1]));
638 
639     SETTING_LOG_INFO("n_g_v bef d_A_H->Query");
640     std::shared_ptr<OHOS::NativeRdb::AbsSharedResultSet> resultset = nullptr;
641     if (dataAbilityHelper != nullptr) {
642         resultset = dataAbilityHelper->Query(*uri, columns, predicates);
643     };
644 
645     napi_value retVal = nullptr;
646     int numRows = 0;
647 
648     if (resultset != nullptr) {
649         SETTING_LOG_INFO("n_g_v resultset is NOT empty");
650         resultset->GetRowCount(numRows);
651     }
652 
653     if (resultset == nullptr || numRows == 0) {
654         SETTING_LOG_INFO("n_g_v return def value");
655         retVal = args[PARAM2];
656     } else {
657         SETTING_LOG_INFO("n_g_v return value from resultset");
658         std::string val;
659         int32_t columnIndex = 0;
660         resultset->GoToFirstRow();
661         resultset->GetString(columnIndex, val);
662         retVal = wrap_string_to_js(env, val);
663     }
664 
665     if (resultset != nullptr) {
666         resultset->Close();
667     }
668     dataAbilityHelper = nullptr;
669     SETTING_LOG_INFO("n_g_v END!");
670     return retVal;
671 }
672 
get_val_CB_exe_CB(napi_env env,AsyncCallbackInfo * asyncCallbackInfo)673 void get_val_CB_exe_CB(napi_env env, AsyncCallbackInfo *asyncCallbackInfo)
674 {
675     std::vector<std::string> columns;
676     columns.push_back(SETTINGS_DATA_FIELD_VALUE);
677     OHOS::NativeRdb::DataAbilityPredicates predicates;
678     predicates.EqualTo(SETTINGS_DATA_FIELD_KEYWORD, asyncCallbackInfo->key);
679 
680     std::shared_ptr<Uri> uri = std::make_shared<Uri>(SETTINGS_DATA_BASE_URI);
681     std::shared_ptr<OHOS::NativeRdb::AbsSharedResultSet> resultset = nullptr;
682     if (asyncCallbackInfo->dataAbilityHelper != nullptr) {
683         resultset = asyncCallbackInfo->dataAbilityHelper->Query(*uri, columns, predicates);
684     };
685     SETTING_LOG_INFO("c_b n_g_v aft d_A_H->Query");
686 
687     int numRows = 0;
688     if (resultset != nullptr) {
689         SETTING_LOG_INFO("c_b n_g_v resultset is NOT empty");
690         resultset->GetRowCount(numRows);
691     }
692     if (resultset == nullptr || numRows == 0) {
693         SETTING_LOG_INFO("c_b n_g_v return def value");
694     } else {
695         std::string val;
696         int32_t columnIndex = 0;
697         resultset->GoToFirstRow();
698         resultset->GetString(columnIndex, val);
699         SETTING_LOG_INFO("c_b retVal is %{public}s", val.c_str());
700         asyncCallbackInfo->value = val;
701     }
702     if (resultset != nullptr) {
703         resultset->Close();
704     }
705 }
706 
napi_get_value(napi_env env,napi_callback_info info)707 napi_value napi_get_value(napi_env env, napi_callback_info info)
708 {
709     // getValue api need 3 parameters when Promise mode and need 4 parameters when callback mode
710     const size_t paramOfCallback = ARGS_THREE;
711 
712     size_t argc = ARGS_FOUR;
713     napi_value args[ARGS_FOUR] = {nullptr};
714     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, args, nullptr, nullptr));
715     if (argc != ARGS_TWO && argc != ARGS_THREE && argc != ARGS_FOUR) {
716         SETTING_LOG_ERROR(
717             "%{public}s, wrong number of arguments, expect 2 or 3 or 4 but get %{public}zd",
718             __func__,
719             argc);
720         return wrap_void_to_js(env);
721     }
722 
723     SETTING_LOG_INFO("n_g_v arg count is %{public}zd", argc);
724     AsyncCallbackInfo* asyncCallbackInfo = new AsyncCallbackInfo {
725         .env = env,
726         .asyncWork = nullptr,
727         .deferred = nullptr,
728         .callbackRef = nullptr,
729         .dataAbilityHelper = nullptr,
730         .key = "",
731         .value = "",
732         .uri = "",
733         .status = false,
734     };
735     // Check the value type of the arguments
736     napi_valuetype valueType;
737     NAPI_CALL(env, napi_typeof(env, args[PARAM0], &valueType));
738     NAPI_ASSERT(env, valueType == napi_object, "Wrong argument[0] type. Object expected.");
739     NAPI_CALL(env, napi_typeof(env, args[PARAM1], &valueType));
740     NAPI_ASSERT(env, valueType == napi_string, "Wrong argument[1], type. String expected");
741 
742     bool stageMode = false;
743     napi_status status = OHOS::AbilityRuntime::IsStageContext(env, args[PARAM0], stageMode);
744     if (status == napi_ok) {
745         SETTING_LOG_INFO("argv[0] is a context, Stage Model: %{public}d", stageMode);
746         return napi_get_value_ext(env, info, stageMode);
747     }
748 
749     NAPIDataAbilityHelperWrapper* wrapper = nullptr;
750     NAPI_CALL(env, napi_unwrap(env, args[PARAM0], reinterpret_cast<void **>(&wrapper)));
751     if (wrapper != nullptr) {
752         asyncCallbackInfo->dataAbilityHelper = wrapper->GetDataAbilityHelper();
753     }
754 
755     asyncCallbackInfo->key = unwrap_string_from_js(env, args[PARAM1]);
756     SETTING_LOG_INFO("input param is : (key %{public}s", asyncCallbackInfo->key.c_str());
757 
758     napi_value resource = nullptr;
759     NAPI_CALL(env, napi_create_string_utf8(env, "getValue", NAPI_AUTO_LENGTH, &resource));
760 
761     if (argc == paramOfCallback) {
762         SETTING_LOG_INFO("do c_b");
763 
764         napi_create_reference(env, args[PARAM2], 1, &asyncCallbackInfo->callbackRef);
765 
766         napi_create_async_work(
767             env,
768             nullptr,
769             resource,
770             // aysnc executed task
771             [](napi_env env, void *data) {
772                 if (data == nullptr) {
773                     SETTING_LOG_INFO("c_b async execute data is null");
774                     return;
775                 }
776                 SETTING_LOG_INFO("c_b async execute c_b");
777                 AsyncCallbackInfo *asyncCallbackInfo = (AsyncCallbackInfo *)data;
778                 get_val_CB_exe_CB(env, asyncCallbackInfo);
779             },
780             // async end called callback
781             [](napi_env env, napi_status status, void *data) {
782                 if (data == nullptr) {
783                     SETTING_LOG_INFO("c_b end data is null");
784                     return;
785                 }
786                 AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
787                 napi_value undefine;
788                 napi_get_undefined(env, &undefine);
789                 napi_value callback = nullptr;
790                 napi_value result = wrap_string_to_js(env, asyncCallbackInfo->value);
791                 napi_get_reference_value(env, asyncCallbackInfo->callbackRef, &callback);
792                 napi_call_function(env, nullptr, callback, 1, &result, &undefine);
793                 napi_delete_reference(env, asyncCallbackInfo->callbackRef);
794                 napi_delete_async_work(env, asyncCallbackInfo->asyncWork);
795                 asyncCallbackInfo->dataAbilityHelper = nullptr;
796                 delete asyncCallbackInfo;
797                 SETTING_LOG_INFO("c_b change complete");
798             },
799             (void *)asyncCallbackInfo,
800             &asyncCallbackInfo->asyncWork);
801 
802         NAPI_CALL(env, napi_queue_async_work(env, asyncCallbackInfo->asyncWork));
803         SETTING_LOG_INFO("c_b end async work");
804         return wrap_void_to_js(env);
805     } else {
806         SETTING_LOG_INFO("do p_m");
807         napi_value promise;
808         napi_deferred deferred;
809         NAPI_CALL(env, napi_create_promise(env, &deferred, &promise));
810         asyncCallbackInfo->deferred = deferred;
811 
812         napi_create_async_work(
813         env,
814         nullptr,
815         resource,
816         // aysnc executed task
817         [](napi_env env, void* data) {
818             AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
819             SETTING_LOG_INFO("p_m get c_b key is %{public}s, value is: %{public}s",
820 			    asyncCallbackInfo->key.c_str(), asyncCallbackInfo->value.c_str());
821 
822             std::vector<std::string> columns;
823             columns.push_back(SETTINGS_DATA_FIELD_VALUE);
824             OHOS::NativeRdb::DataAbilityPredicates predicates;
825             predicates.EqualTo(SETTINGS_DATA_FIELD_KEYWORD, asyncCallbackInfo->key);
826 
827             std::shared_ptr<Uri> uri = std::make_shared<Uri>(SETTINGS_DATA_BASE_URI);
828             std::shared_ptr<OHOS::NativeRdb::AbsSharedResultSet> resultset = nullptr;
829             if (asyncCallbackInfo->dataAbilityHelper != nullptr) {
830                 resultset = asyncCallbackInfo->dataAbilityHelper->Query(*uri, columns, predicates);
831             }
832             SETTING_LOG_INFO("p_m n_g_v aft d_A_H->Query");
833 
834             int numRows = 0;
835             if (resultset != nullptr) {
836                 SETTING_LOG_INFO("p_m n_g_v resultset is NOT empty");
837                 resultset->GetRowCount(numRows);
838             }
839             if (resultset == nullptr || numRows == 0) {
840                 SETTING_LOG_INFO("p_m n_g_v return def value");
841             } else {
842                 SETTING_LOG_INFO("p_m n_g_v return value from resultset");
843                 std::string val;
844                 int32_t columnIndex = 0;
845                 resultset->GoToFirstRow();
846                 resultset->GetString(columnIndex, val);
847                 asyncCallbackInfo->value = val;
848             }
849             if (resultset != nullptr) {
850                 resultset->Close();
851             }
852         },
853         // async end called callback
854         [](napi_env env, napi_status status, void* data) {
855             AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
856             SETTING_LOG_INFO("p_m end get c_b value is %{public}s",
857                 asyncCallbackInfo->value.c_str());
858             napi_value result = wrap_string_to_js(env, asyncCallbackInfo->value);
859             napi_resolve_deferred(asyncCallbackInfo->env, asyncCallbackInfo->deferred, result);
860             napi_delete_async_work(env, asyncCallbackInfo->asyncWork);
861             asyncCallbackInfo->dataAbilityHelper = nullptr;
862             delete asyncCallbackInfo;
863         },
864         (void*)asyncCallbackInfo,
865         &asyncCallbackInfo->asyncWork);
866         napi_queue_async_work(env, asyncCallbackInfo->asyncWork);
867         return promise;
868     }
869 }
870 
871 // api9
napi_get_value_ext(napi_env env,napi_callback_info info,const bool stageMode)872 napi_value napi_get_value_ext(napi_env env, napi_callback_info info, const bool stageMode)
873 {
874     AsyncCallbackInfo* asyncCallbackInfo = new AsyncCallbackInfo {
875         .env = env,
876         .asyncWork = nullptr,
877         .deferred = nullptr,
878         .callbackRef = nullptr,
879         .dataAbilityHelper = nullptr,
880         .key = "",
881         .value = "",
882         .uri = "",
883         .status = false,
884     };
885 
886     SETTING_LOG_INFO("n_g_v_e called");
887     size_t argc = ARGS_FOUR;
888     napi_value args[ARGS_FOUR] = {nullptr};
889     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, args, nullptr, nullptr));
890 
891     asyncCallbackInfo->dataShareHelper = getDataShareHelper(env, args[PARAM0], stageMode);
892 
893     asyncCallbackInfo->key = unwrap_string_from_js(env, args[PARAM1]);
894 
895     napi_value resource = nullptr;
896     NAPI_CALL(env, napi_create_string_utf8(env, "getValue", NAPI_AUTO_LENGTH, &resource));
897 
898     // set call type and table name, and check whether the parameter is valid
899     napi_valuetype valueType;
900     if (argc == ARGS_TWO) {
901         asyncCallbackInfo->callType = STAGE_PROMISE;
902         asyncCallbackInfo->tableName = "global";
903     } else if (argc == ARGS_THREE) {
904         NAPI_CALL(env, napi_typeof(env, args[PARAM2], &valueType));
905         if (valueType == napi_string) {
906             asyncCallbackInfo->tableName = unwrap_string_from_js(env, args[PARAM2]);
907             if (IsTableNameInvalid(asyncCallbackInfo->tableName)) {
908                 SETTING_LOG_ERROR("INVALID tableName [ARGS_THREE]");
909                 return wrap_void_to_js(env);
910             } else {
911                 asyncCallbackInfo->callType = STAGE_PROMISE_SPECIFIC;
912             }
913         } else {
914             asyncCallbackInfo->callType = STAGE_CALLBACK;
915             asyncCallbackInfo->tableName = "global";
916         }
917     } else if (argc == ARGS_FOUR) {
918         asyncCallbackInfo->callType = STAGE_CALLBACK_SPECIFIC;
919         asyncCallbackInfo->tableName = unwrap_string_from_js(env, args[PARAM3]);
920     } else {
921         asyncCallbackInfo->callType = INVALID_CALL;
922     }
923 
924     // check whether invalid call
925     if (asyncCallbackInfo->callType == INVALID_CALL) {
926         SETTING_LOG_ERROR("INVALID CALL");
927         return wrap_void_to_js(env);
928     }
929 
930     if (asyncCallbackInfo->callType == STAGE_CALLBACK || asyncCallbackInfo->callType == STAGE_CALLBACK_SPECIFIC) {
931         napi_create_reference(env, args[PARAM2], 1, &asyncCallbackInfo->callbackRef);
932         napi_create_async_work(
933             env,
934             nullptr,
935             resource,
936             GetValueExecuteExt,
937             [](napi_env env, napi_status status, void* data) {
938                 AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
939                 napi_value result = wrap_string_to_js(env, asyncCallbackInfo->value);
940                 CompleteCall(env, status, data, result);
941             },
942             (void*)asyncCallbackInfo,
943             &asyncCallbackInfo->asyncWork
944         );
945         NAPI_CALL(env, napi_queue_async_work(env, asyncCallbackInfo->asyncWork));
946         SETTING_LOG_INFO("c_b end async work");
947         return wrap_void_to_js(env);
948     } else if (asyncCallbackInfo->callType != INVALID_CALL) {
949         napi_value promise;
950         napi_deferred deferred;
951         NAPI_CALL(env, napi_create_promise(env, &deferred, &promise));
952         asyncCallbackInfo->deferred = deferred;
953         napi_create_async_work(
954             env,
955             nullptr,
956             resource,
957             GetValueExecuteExt,
958             [](napi_env env, napi_status status, void* data) {
959                 AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
960                 napi_value result = nullptr;
961                 result = wrap_string_to_js(env, asyncCallbackInfo->value);
962                 CompletePromise(env, status, data, result);
963             },
964             (void*)asyncCallbackInfo,
965             &asyncCallbackInfo->asyncWork
966         );
967         NAPI_CALL(env, napi_queue_async_work(env, asyncCallbackInfo->asyncWork));
968         return promise;
969     } else {
970         SETTING_LOG_ERROR("INVALID CALL");
971         return wrap_void_to_js(env);
972     }
973 }
974 
975 /**
976  * @brief setValue NAPI implementation.
977  *
978  * @param env the environment that the Node-API call is invoked under
979  * @param info the callback info passed into the callback function
980  * @return napi_value the return value from NAPI C++ to JS for the module.
981  */
napi_set_value_sync(napi_env env,napi_callback_info info)982 napi_value napi_set_value_sync(napi_env env, napi_callback_info info)
983 {
984     SETTING_LOG_INFO("n_s_v");
985 
986     // Check the number of the arguments
987     size_t argc = ARGS_FOUR;
988     napi_value args[ARGS_FOUR] = {nullptr};
989     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, args, nullptr, nullptr));
990     if (argc != ARGS_THREE && argc != ARGS_FOUR) {
991         SETTING_LOG_ERROR("%{public}s, wrong number of arguments.", __func__);
992         return wrap_void_to_js(env);
993     }
994 
995     // Check the value type of the arguments
996     napi_valuetype valueType;
997     NAPI_CALL(env, napi_typeof(env, args[PARAM0], &valueType));
998     NAPI_ASSERT(env, valueType == napi_object, "Wrong argument[0] type. Object expected.");
999     NAPI_CALL(env, napi_typeof(env, args[PARAM1], &valueType));
1000     NAPI_ASSERT(env, valueType == napi_string, "Wrong argument[1] type. String expected.");
1001     NAPI_CALL(env, napi_typeof(env, args[PARAM2], &valueType));
1002     NAPI_ASSERT(env, valueType == napi_string, "Wrong argument[2] type. String expected.");
1003 
1004     bool stageMode = false;
1005     napi_status status = OHOS::AbilityRuntime::IsStageContext(env, args[PARAM0], stageMode);
1006     if (status == napi_ok) {
1007         return napi_set_value_sync_ext(stageMode, argc, env, args);
1008     }
1009 
1010     std::shared_ptr<DataAbilityHelper> dataAbilityHelper = nullptr;
1011     NAPIDataAbilityHelperWrapper* wrapper = nullptr;
1012     NAPI_CALL(env, napi_unwrap(env, args[PARAM0], reinterpret_cast<void **>(&wrapper)));
1013     if (wrapper != nullptr) {
1014         dataAbilityHelper = wrapper->GetDataAbilityHelper();
1015     }
1016 
1017     std::string argsName = unwrap_string_from_js(env, args[PARAM1]);
1018     std::string argsDefaultValue = unwrap_string_from_js(env, args[PARAM2]);
1019 
1020     OHOS::NativeRdb::ValuesBucket val;
1021     val.PutString(SETTINGS_DATA_FIELD_KEYWORD, argsName);
1022     val.PutString(SETTINGS_DATA_FIELD_VALUE, argsDefaultValue);
1023 
1024     std::vector<std::string> columns;
1025     columns.push_back(SETTINGS_DATA_FIELD_VALUE);
1026     OHOS::NativeRdb::DataAbilityPredicates predicates;
1027     predicates.EqualTo(SETTINGS_DATA_FIELD_KEYWORD, argsName);
1028 
1029     std::shared_ptr<Uri> uri = std::make_shared<Uri>(SETTINGS_DATA_BASE_URI);
1030     std::shared_ptr<OHOS::NativeRdb::AbsSharedResultSet> resultset = nullptr;
1031     if (dataAbilityHelper != nullptr) {
1032         resultset = dataAbilityHelper->Query(*uri, columns, predicates);
1033     }
1034     SETTING_LOG_INFO("n_s_v aft d_A_H->Query");
1035 
1036     int retInt = 0;
1037     int numRows = 0;
1038 
1039     if (resultset != nullptr) {
1040         SETTING_LOG_INFO("n_s_v resultset is NOT empty");
1041         resultset->GetRowCount(numRows);
1042     }
1043 
1044     if (dataAbilityHelper != nullptr) {
1045         // insert
1046         if (resultset == nullptr || numRows == 0) {
1047             retInt = dataAbilityHelper->Insert(*uri, val);
1048             SETTING_LOG_INFO("n_s_v aft In");
1049         // update
1050         } else {
1051             retInt = dataAbilityHelper->Update(*uri, val, predicates);
1052             SETTING_LOG_INFO("n_s_v aft Up");
1053         }
1054         // notify change
1055         if (retInt != 0) {
1056             std::string uriWithNameStr =
1057                 argsName.empty() ? SETTINGS_DATA_BASE_URI : (SETTINGS_DATA_BASE_URI + "/" + argsName);
1058             std::shared_ptr<Uri> uriWithName = std::make_shared<Uri>(uriWithNameStr);
1059             dataAbilityHelper->NotifyChange(*uriWithName);
1060             SETTING_LOG_INFO("n_s_v aft NotifyChange with uri: %{public}s", uriWithNameStr.c_str());
1061         }
1062     }
1063     if (resultset != nullptr) {
1064         resultset->Close();
1065     }
1066 
1067     return wrap_bool_to_js(env, ThrowError(env, retInt));
1068 }
1069 
SetValueExecuteCB(napi_env env,void * data)1070 void SetValueExecuteCB(napi_env env, void *data)
1071 {
1072     if (data == nullptr) {
1073         SETTING_LOG_INFO("execute data is null");
1074         return;
1075     }
1076     AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
1077 
1078     if (asyncCallbackInfo->dataAbilityHelper == nullptr) {
1079         SETTING_LOG_ERROR("helper is null");
1080         asyncCallbackInfo->status = -1;
1081         return;
1082     }
1083 
1084     std::string argsName = asyncCallbackInfo->key;
1085     std::string argsDefaultValue = asyncCallbackInfo->value;
1086 
1087     OHOS::NativeRdb::ValuesBucket val;
1088     val.PutString(SETTINGS_DATA_FIELD_KEYWORD, argsName);
1089     val.PutString(SETTINGS_DATA_FIELD_VALUE, argsDefaultValue);
1090 
1091     OHOS::NativeRdb::DataAbilityPredicates predicates;
1092     predicates.EqualTo(SETTINGS_DATA_FIELD_KEYWORD, argsName);
1093 
1094     std::shared_ptr<Uri> uri = std::make_shared<Uri>(SETTINGS_DATA_BASE_URI);
1095     SETTING_LOG_INFO("execute bef d_A_H->Update");
1096     // update first
1097     int retInt = asyncCallbackInfo->dataAbilityHelper->Update(*uri, val, predicates);
1098     SETTING_LOG_ERROR("update ret: %{public}d", retInt);
1099     if (retInt <= 0) {
1100         // retry to insert
1101         retInt = asyncCallbackInfo->dataAbilityHelper->Insert(*uri, val);
1102         SETTING_LOG_ERROR("insert ret: %{public}d", retInt);
1103     }
1104     // notify change
1105     if (retInt > 0) {
1106         std::string uriWithNameStr =
1107             argsName.empty() ? SETTINGS_DATA_BASE_URI : (SETTINGS_DATA_BASE_URI + "/" + argsName);
1108         std::shared_ptr<Uri> uriWithName = std::make_shared<Uri>(uriWithNameStr);
1109         asyncCallbackInfo->dataAbilityHelper->NotifyChange(*uriWithName);
1110         SETTING_LOG_INFO("execute aft NotifyC with uri: %{public}s", uriWithNameStr.c_str());
1111     }
1112     SETTING_LOG_INFO("execute... END!");
1113     asyncCallbackInfo->status = retInt;
1114 }
1115 
SetValueAsync(napi_env env,AsyncCallbackInfo * asyncCallbackInfo)1116 napi_value SetValueAsync(napi_env env, AsyncCallbackInfo* asyncCallbackInfo)
1117 {
1118     SETTING_LOG_INFO("set do c_b");
1119     napi_value resource = nullptr;
1120     NAPI_CALL(env, napi_create_string_utf8(env, __func__, NAPI_AUTO_LENGTH, &resource));
1121 
1122     napi_create_async_work(
1123         env,
1124         nullptr,
1125         resource,
1126         SetValueExecuteCB,
1127         [](napi_env env, napi_status status, void* data) {
1128             if (data == nullptr) {
1129                 SETTING_LOG_INFO("c_b set asy end data is null");
1130                 return;
1131             }
1132             AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
1133             napi_value undefine;
1134             napi_get_undefined(env, &undefine);
1135             napi_value callback = nullptr;
1136             napi_value result = wrap_bool_to_js(env, ThrowError(env, asyncCallbackInfo->status));
1137             napi_get_reference_value(env, asyncCallbackInfo->callbackRef, &callback);
1138             napi_call_function(env, nullptr, callback, 1, &result, &undefine);
1139             napi_delete_reference(env, asyncCallbackInfo->callbackRef);
1140             napi_delete_async_work(env, asyncCallbackInfo->asyncWork);
1141             asyncCallbackInfo->dataAbilityHelper = nullptr;
1142             delete asyncCallbackInfo;
1143             SETTING_LOG_INFO("c_b set change complete");
1144         },
1145         (void*)asyncCallbackInfo,
1146         &asyncCallbackInfo->asyncWork
1147     );
1148     NAPI_CALL(env, napi_queue_async_work(env, asyncCallbackInfo->asyncWork));
1149     SETTING_LOG_INFO("c_b set end asy work");
1150     return wrap_void_to_js(env);
1151 }
1152 
SetValuePromise(napi_env env,AsyncCallbackInfo * asyncCallbackInfo)1153 napi_value SetValuePromise(napi_env env, AsyncCallbackInfo* asyncCallbackInfo)
1154 {
1155     SETTING_LOG_INFO("set do promise");
1156     napi_value promise;
1157     napi_deferred deferred;
1158     NAPI_CALL(env, napi_create_promise(env, &deferred, &promise));
1159     asyncCallbackInfo->deferred = deferred;
1160 
1161     napi_value resource = nullptr;
1162     NAPI_CALL(env, napi_create_string_utf8(env, __func__, NAPI_AUTO_LENGTH, &resource));
1163 
1164     napi_create_async_work(
1165         env,
1166         nullptr,
1167         resource,
1168         SetValueExecuteCB,
1169         [](napi_env env, napi_status status, void* data) {
1170             AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
1171             SETTING_LOG_INFO("p_m set end get c_b value is %{public}d",
1172                 asyncCallbackInfo->status);
1173             napi_value result = wrap_bool_to_js(env, ThrowError(env, asyncCallbackInfo->status));
1174             napi_resolve_deferred(asyncCallbackInfo->env, asyncCallbackInfo->deferred, result);
1175             napi_delete_async_work(env, asyncCallbackInfo->asyncWork);
1176             asyncCallbackInfo->dataAbilityHelper = nullptr;
1177             delete asyncCallbackInfo;
1178         },
1179         (void*)asyncCallbackInfo,
1180         &asyncCallbackInfo->asyncWork);
1181     napi_queue_async_work(env, asyncCallbackInfo->asyncWork);
1182     return promise;
1183 }
1184 
1185 /**
1186  * @brief setValue NAPI implementation.
1187  *
1188  * @param env the environment that the Node-API call is invoked under
1189  * @param info the callback info passed into the callback function
1190  * @return napi_value the return value from NAPI C++ to JS for the module.
1191  */
napi_set_value(napi_env env,napi_callback_info info)1192 napi_value napi_set_value(napi_env env, napi_callback_info info)
1193 {
1194     SETTING_LOG_INFO("set  napi_set_value");
1195 
1196     // getValue api need 3 parameters when Promise mode and need 4 parameters when callback mode
1197     const size_t paramOfCallback = ARGS_FOUR;
1198 
1199     size_t argc = ARGS_FIVE;
1200     napi_value args[ARGS_FIVE] = {nullptr};
1201     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, args, nullptr, nullptr));
1202     if (argc != ARGS_THREE && argc != ARGS_FOUR && argc != ARGS_FIVE) {
1203         SETTING_LOG_ERROR(
1204             "set %{public}s, wrong number of arguments, expect 3 or 4 or 5 but get %{public}zd",
1205             __func__,
1206             argc);
1207         return wrap_void_to_js(env);
1208     }
1209 
1210     SETTING_LOG_INFO("set  arg count is %{public}zd", argc);
1211     // Check the value type of the arguments
1212     AsyncCallbackInfo* asyncCallbackInfo = new AsyncCallbackInfo {
1213         .env = env,
1214         .asyncWork = nullptr,
1215         .deferred = nullptr,
1216         .callbackRef = nullptr,
1217         .dataAbilityHelper = nullptr,
1218         .key = "",
1219         .value = "",
1220         .uri = "",
1221         .status = false,
1222     };
1223     SETTING_LOG_INFO("set  aft create aysnc call back info");
1224     napi_valuetype valueType;
1225     NAPI_CALL(env, napi_typeof(env, args[PARAM0], &valueType));
1226     NAPI_ASSERT(env, valueType == napi_object, "Wrong argument[0] type. Object expected.");
1227     NAPI_CALL(env, napi_typeof(env, args[PARAM1], &valueType));
1228     NAPI_ASSERT(env, valueType == napi_string, "Wrong argument[1], type. String expected");
1229     NAPI_CALL(env, napi_typeof(env, args[PARAM2], &valueType));
1230     NAPI_ASSERT(env, valueType == napi_string, "Wrong argument[2], type. String expected");
1231 
1232     // api9 napi_set_value_ext
1233     bool stageMode = false;
1234     napi_status status = OHOS::AbilityRuntime::IsStageContext(env, args[PARAM0], stageMode);
1235     if (status == napi_ok) {
1236         SETTING_LOG_INFO("argv[0] is a context, Stage Model: %{public}d", stageMode);
1237         return napi_set_value_ext(env, info, stageMode);
1238     }
1239 
1240     NAPIDataAbilityHelperWrapper* wrapper = nullptr;
1241     NAPI_CALL(env, napi_unwrap(env, args[PARAM0], reinterpret_cast<void **>(&wrapper)));
1242     if (wrapper != nullptr) {
1243         asyncCallbackInfo->dataAbilityHelper = wrapper->GetDataAbilityHelper();
1244     }
1245 
1246     asyncCallbackInfo->key = unwrap_string_from_js(env, args[PARAM1]);
1247     asyncCallbackInfo->value = unwrap_string_from_js(env, args[PARAM2]);
1248     SETTING_LOG_INFO("set  input param is : (key %{public}s, value %{public}s)",
1249         asyncCallbackInfo->key.c_str(), asyncCallbackInfo->value.c_str());
1250 
1251     napi_value ret = nullptr;
1252     if (argc == paramOfCallback) {
1253         napi_create_reference(env, args[PARAM3], 1, &asyncCallbackInfo->callbackRef);
1254         ret = SetValueAsync(env, asyncCallbackInfo);
1255     } else {
1256         ret = SetValuePromise(env, asyncCallbackInfo);
1257     }
1258     SETTING_LOG_INFO("set  value end");
1259     return ret;
1260 }
1261 
napi_set_value_ext(napi_env env,napi_callback_info info,const bool stageMode)1262 napi_value napi_set_value_ext(napi_env env, napi_callback_info info, const bool stageMode)
1263 {
1264     AsyncCallbackInfo* asyncCallbackInfo = new AsyncCallbackInfo {
1265         .env = env,
1266         .asyncWork = nullptr,
1267         .deferred = nullptr,
1268         .callbackRef = nullptr,
1269         .dataAbilityHelper = nullptr,
1270         .key = "",
1271         .value = "",
1272         .uri = "",
1273         .status = false,
1274         .useSilent = false,
1275     };
1276 
1277     size_t argc = ARGS_FIVE;
1278     napi_value args[ARGS_FIVE] = {nullptr};
1279     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, args, nullptr, nullptr));
1280 
1281     asyncCallbackInfo->dataShareHelper = getDataShareHelper(env, args[PARAM0], stageMode, "global", asyncCallbackInfo);
1282     asyncCallbackInfo->key = unwrap_string_from_js(env, args[PARAM1]);
1283     asyncCallbackInfo->uri = unwrap_string_from_js(env, args[PARAM2]); //temp
1284     napi_value resource = nullptr;
1285     NAPI_CALL(env, napi_create_string_utf8(env, "napi_set_value_ext", NAPI_AUTO_LENGTH, &resource));
1286 
1287     // set call type and table name
1288     napi_valuetype valueType;
1289     if (argc == ARGS_THREE) {
1290         asyncCallbackInfo->callType = STAGE_PROMISE;
1291         asyncCallbackInfo->tableName = "global";
1292     } else if (argc == ARGS_FOUR) {
1293         NAPI_CALL(env, napi_typeof(env, args[PARAM3], &valueType));
1294         if (valueType == napi_string) {
1295             asyncCallbackInfo->tableName = unwrap_string_from_js(env, args[PARAM3]);
1296             if (IsTableNameInvalid(asyncCallbackInfo->tableName)) {
1297                 SETTING_LOG_ERROR("INVALID tableName [ARGS_FOUR]");
1298                 return wrap_void_to_js(env);
1299             } else {
1300                 asyncCallbackInfo->callType = STAGE_PROMISE_SPECIFIC;
1301             }
1302         } else {
1303             asyncCallbackInfo->callType = STAGE_CALLBACK;
1304             asyncCallbackInfo->tableName = "global";
1305         }
1306     } else if (argc == ARGS_FIVE) {
1307         asyncCallbackInfo->callType = STAGE_CALLBACK_SPECIFIC;
1308         asyncCallbackInfo->tableName = unwrap_string_from_js(env, args[PARAM4]);
1309     } else {
1310         asyncCallbackInfo->callType = INVALID_CALL;
1311     }
1312 
1313     // check whether invalid call
1314     if (asyncCallbackInfo->callType == INVALID_CALL) {
1315         SETTING_LOG_ERROR("INVALID CALL");
1316         return wrap_void_to_js(env);
1317     }
1318 
1319     if (asyncCallbackInfo->callType == STAGE_CALLBACK || asyncCallbackInfo->callType == STAGE_CALLBACK_SPECIFIC) {
1320         napi_create_reference(env, args[PARAM3], 1, &asyncCallbackInfo->callbackRef);
1321         napi_create_async_work(
1322             env,
1323             nullptr,
1324             resource,
1325             [](napi_env env, void* data) {
1326                 AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
1327                 SetValueExecuteExt(env, (void*)asyncCallbackInfo, asyncCallbackInfo->uri);
1328             },
1329             [](napi_env env, napi_status status, void* data) {
1330                 AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
1331                 napi_value result = wrap_bool_to_js(env, ThrowError(env, asyncCallbackInfo->status));
1332                 asyncCallbackInfo->status = napi_ok;
1333                 CompleteCall(env, status, data, result);
1334             },
1335             (void*)asyncCallbackInfo,
1336             &asyncCallbackInfo->asyncWork
1337         );
1338         NAPI_CALL(env, napi_queue_async_work(env, asyncCallbackInfo->asyncWork));
1339         SETTING_LOG_INFO("c_b end async work");
1340         return wrap_void_to_js(env);
1341     } else if (asyncCallbackInfo->callType != INVALID_CALL) {
1342         napi_value promise;
1343         napi_deferred deferred;
1344         NAPI_CALL(env, napi_create_promise(env, &deferred, &promise));
1345         asyncCallbackInfo->deferred = deferred;
1346         napi_create_async_work(
1347             env,
1348             nullptr,
1349             resource,
1350             [](napi_env env, void* data) {
1351                 AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
1352                 SETTING_LOG_INFO("in async work");
1353                 SetValueExecuteExt(env, (void*)asyncCallbackInfo, asyncCallbackInfo->uri);
1354             },
1355             [](napi_env env, napi_status status, void* data) {
1356                 AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
1357                 napi_value result = wrap_bool_to_js(env, asyncCallbackInfo->status != 0);
1358                 asyncCallbackInfo->status = napi_ok;
1359                 CompletePromise(env, status, data, result);
1360             },
1361             (void*)asyncCallbackInfo,
1362             &asyncCallbackInfo->asyncWork
1363         );
1364         NAPI_CALL(env, napi_queue_async_work(env, asyncCallbackInfo->asyncWork));
1365         return promise;
1366     } else {
1367         SETTING_LOG_ERROR("INVALID CALL");
1368         return wrap_void_to_js(env);
1369     }
1370 }
1371 /**
1372  * @brief enableAirplaneMode NAPI implementation.
1373  * @param env the environment that the Node-API call is invoked under
1374  * @param info the callback info passed into the callback function
1375  * @return napi_value the return value from NAPI C++ to JS for the module.
1376  */
napi_enable_airplane_mode(napi_env env,napi_callback_info info)1377 napi_value napi_enable_airplane_mode(napi_env env, napi_callback_info info)
1378 {
1379     const size_t paramOfPromise = ARGS_ONE;
1380     const size_t paramOfCallback = ARGS_TWO;
1381 
1382     size_t argc = ARGS_TWO;
1383     napi_value args[ARGS_TWO] = {nullptr};
1384     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, args, nullptr, nullptr));
1385     if (argc != paramOfCallback && argc != paramOfPromise) {
1386         SETTING_LOG_ERROR("%{public}s, wrong number of arguments, expect 1 or 2 but get %{public}zd",
1387             __func__, argc);
1388         return wrap_void_to_js(env);
1389     }
1390 
1391     SETTING_LOG_INFO("n_e_a_m arg count is %{public}zd", argc);
1392     AsyncCallbackInfo* asyncCallbackInfo = new AsyncCallbackInfo {
1393         .env = env,
1394         .asyncWork = nullptr,
1395         .deferred = nullptr,
1396         .callbackRef = nullptr,
1397         .dataAbilityHelper = nullptr,
1398         .key = "",
1399         .value = "",
1400         .uri = "",
1401         .status = 0,
1402     };
1403     SETTING_LOG_INFO("aft create aysnc call back info");
1404 
1405     napi_valuetype valueType;
1406     NAPI_CALL(env, napi_typeof(env, args[PARAM0], &valueType));
1407     NAPI_ASSERT(env, valueType == napi_boolean, "Wrong argument[0], type. Boolean expected");
1408 
1409     napi_value resource = nullptr;
1410     NAPI_CALL(env, napi_create_string_utf8(env, "enableAirplaneMode", NAPI_AUTO_LENGTH, &resource));
1411 
1412     if (argc == paramOfCallback) {
1413         SETTING_LOG_INFO("%{public}s, asyncCallback.", __func__);
1414 
1415         napi_create_reference(env, args[PARAM1], 1, &asyncCallbackInfo->callbackRef);
1416         napi_create_async_work(
1417             env,
1418             nullptr,
1419             resource,
1420             [](napi_env env, void* data) {},
1421             [](napi_env env, napi_status status, void* data) {
1422                 if (data == nullptr) {
1423                     SETTING_LOG_INFO("c_b asy end data is null");
1424                     return;
1425                 }
1426                 AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
1427 
1428                 napi_value callback = nullptr;
1429                 napi_value undefined;
1430                 napi_get_undefined(env, &undefined);
1431 
1432                 napi_value result[PARAM2] = {0};
1433 
1434                 // create error code
1435                 napi_value error = nullptr;
1436                 napi_create_object(env, &error);
1437                 int unSupportCode = 801;
1438                 napi_value errCode = nullptr;
1439                 napi_create_int32(env, unSupportCode, &errCode);
1440                 napi_set_named_property(env, error, "code", errCode);
1441                 result[0] = error;
1442                 napi_get_undefined(env, &result[1]);
1443 
1444                 napi_get_reference_value(env, asyncCallbackInfo->callbackRef, &callback);
1445                 napi_value callResult;
1446                 napi_call_function(env, undefined, callback, PARAM2, result, &callResult);
1447 
1448                 napi_delete_reference(env, asyncCallbackInfo->callbackRef);
1449                 napi_delete_async_work(env, asyncCallbackInfo->asyncWork);
1450                 delete asyncCallbackInfo;
1451                 SETTING_LOG_INFO("c_b change c_b complete");
1452             },
1453             (void*)asyncCallbackInfo,
1454             &asyncCallbackInfo->asyncWork
1455         );
1456         NAPI_CALL(env, napi_queue_async_work(env, asyncCallbackInfo->asyncWork));
1457         return wrap_void_to_js(env);
1458     } else {
1459         SETTING_LOG_INFO("%{public}s, promise.", __func__);
1460         napi_deferred deferred;
1461         napi_value promise;
1462         NAPI_CALL(env, napi_create_promise(env, &deferred, &promise));
1463         asyncCallbackInfo->deferred = deferred;
1464 
1465         napi_create_async_work(
1466             env,
1467             nullptr,
1468             resource,
1469             [](napi_env env, void *data) {},
1470             [](napi_env env, napi_status status, void *data) {
1471                 SETTING_LOG_INFO("%{public}s, promise complete", __func__);
1472                 AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
1473 
1474                 napi_value result;
1475                 napi_value error = nullptr;
1476                 napi_create_object(env, &error);
1477                 int unSupportCode = 801;
1478                 napi_value errCode = nullptr;
1479                 napi_create_int32(env, unSupportCode, &errCode);
1480                 napi_set_named_property(env, error, "code", errCode);
1481                 result = error;
1482 
1483                 napi_reject_deferred(env, asyncCallbackInfo->deferred, result);
1484                 napi_delete_async_work(env, asyncCallbackInfo->asyncWork);
1485                 delete asyncCallbackInfo;
1486             },
1487             (void *)asyncCallbackInfo,
1488             &asyncCallbackInfo->asyncWork);
1489         napi_queue_async_work(env, asyncCallbackInfo->asyncWork);
1490         return promise;
1491     }
1492 }
1493 
1494 /**
1495  * @brief canShowFloating NAPI implementation.
1496  * @param env the environment that the Node-API call is invoked under
1497  * @param info the callback info passed into the callback function
1498  * @return napi_value the return value from NAPI C++ to JS for the module.
1499  */
napi_can_show_floating(napi_env env,napi_callback_info info)1500 napi_value napi_can_show_floating(napi_env env, napi_callback_info info)
1501 {
1502     const size_t paramOfPromise = PARAM0;
1503     const size_t paramOfCallback = PARAM1;
1504 
1505     size_t argc = PARAM1;
1506     napi_value args[PARAM1] = {nullptr};
1507     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, args, nullptr, nullptr));
1508     if (argc != paramOfCallback && argc != paramOfPromise) {
1509         SETTING_LOG_ERROR("%{public}s, wrong number of arguments, expect 0 or 1 but get %{public}zd",
1510             __func__, argc);
1511         return wrap_void_to_js(env);
1512     }
1513 
1514     SETTING_LOG_INFO("n_e_a_m arg count is %{public}zd", argc);
1515     AsyncCallbackInfo* asyncCallbackInfo = new AsyncCallbackInfo {
1516         .env = env,
1517         .asyncWork = nullptr,
1518         .deferred = nullptr,
1519         .callbackRef = nullptr,
1520         .dataAbilityHelper = nullptr,
1521         .key = "",
1522         .value = "",
1523         .uri = "",
1524         .status = 0,
1525     };
1526 
1527     napi_value resource = nullptr;
1528     NAPI_CALL(env, napi_create_string_utf8(env, "enableAirplaneMode", NAPI_AUTO_LENGTH, &resource));
1529 
1530     if (argc == paramOfCallback) {
1531         SETTING_LOG_INFO("%{public}s, a_C_B.", __func__);
1532 
1533         napi_create_reference(env, args[PARAM0], 1, &asyncCallbackInfo->callbackRef);
1534         napi_create_async_work(
1535             env,
1536             nullptr,
1537             resource,
1538             [](napi_env env, void* data) {},
1539             [](napi_env env, napi_status status, void* data) {
1540                 if (data == nullptr) {
1541                     SETTING_LOG_INFO("c_b asy end data is null");
1542                     return;
1543                 }
1544                 AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
1545 
1546                 napi_value callback = nullptr;
1547                 napi_value undefined;
1548                 napi_get_undefined(env, &undefined);
1549 
1550                 napi_value result[PARAM2] = {0};
1551 
1552                 // create error code
1553                 napi_value error = nullptr;
1554                 napi_create_object(env, &error);
1555                 int unSupportCode = 801;
1556                 napi_value errCode = nullptr;
1557                 napi_create_int32(env, unSupportCode, &errCode);
1558                 napi_set_named_property(env, error, "code", errCode);
1559                 result[0] = error;
1560                 result[1] = wrap_bool_to_js(env, false);
1561 
1562                 napi_get_reference_value(env, asyncCallbackInfo->callbackRef, &callback);
1563                 napi_value callResult;
1564                 napi_call_function(env, undefined, callback, PARAM2, result, &callResult);
1565 
1566                 napi_delete_reference(env, asyncCallbackInfo->callbackRef);
1567                 napi_delete_async_work(env, asyncCallbackInfo->asyncWork);
1568                 delete asyncCallbackInfo;
1569                 SETTING_LOG_INFO("c_b change complete");
1570             },
1571             (void*)asyncCallbackInfo,
1572             &asyncCallbackInfo->asyncWork
1573         );
1574         NAPI_CALL(env, napi_queue_async_work(env, asyncCallbackInfo->asyncWork));
1575         return wrap_void_to_js(env);
1576     } else {
1577         SETTING_LOG_INFO("%{public}s, promise.", __func__);
1578         napi_deferred deferred;
1579         napi_value promise;
1580         NAPI_CALL(env, napi_create_promise(env, &deferred, &promise));
1581         asyncCallbackInfo->deferred = deferred;
1582 
1583         napi_create_async_work(
1584             env,
1585             nullptr,
1586             resource,
1587             [](napi_env env, void *data) {},
1588             [](napi_env env, napi_status status, void *data) {
1589                 SETTING_LOG_INFO("%{public}s, promise complete", __func__);
1590                 AsyncCallbackInfo* asyncCallbackInfo = (AsyncCallbackInfo*)data;
1591 
1592                 napi_value result;
1593                 napi_value error = nullptr;
1594                 napi_create_object(env, &error);
1595                 int unSupportCode = 801;
1596                 napi_value errCode = nullptr;
1597                 napi_create_int32(env, unSupportCode, &errCode);
1598                 napi_set_named_property(env, error, "code", errCode);
1599                 result = error;
1600 
1601                 napi_reject_deferred(env, asyncCallbackInfo->deferred, result);
1602                 napi_delete_async_work(env, asyncCallbackInfo->asyncWork);
1603                 delete asyncCallbackInfo;
1604             },
1605             (void *)asyncCallbackInfo,
1606             &asyncCallbackInfo->asyncWork);
1607         napi_queue_async_work(env, asyncCallbackInfo->asyncWork);
1608         return promise;
1609     }
1610 }
1611 
1612 // get uri for stage model
GetStageUriStr(std::string tableName,std::string idStr,std::string keyStr)1613 std::string GetStageUriStr(std::string tableName, std::string idStr, std::string keyStr)
1614 {
1615     if (std::stoi(idStr) < USERID_HELPER_NUMBER) {
1616         idStr = "100";
1617     }
1618     if (tableName == "global") {
1619         std::string retStr =
1620             "datashare:///com.ohos.settingsdata/entry/settingsdata/SETTINGSDATA?Proxy=true&key=" + keyStr;
1621         return retStr;
1622     } else if (tableName == "system") {
1623         std::string retStr = "datashare:///com.ohos.settingsdata/entry/settingsdata/USER_SETTINGSDATA_" + idStr +
1624                              "?Proxy=true&key=" + keyStr;
1625         return retStr;
1626     } else if (tableName == "secure") {
1627         std::string retStr = "datashare:///com.ohos.settingsdata/entry/settingsdata/USER_SETTINGSDATA_SECURE_" + idStr +
1628                              "?Proxy=true&key=" + keyStr;
1629         return retStr;
1630     } else {
1631         // return global uri
1632         std::string retStr =
1633             "datashare:///com.ohos.settingsdata/entry/settingsdata/SETTINGSDATA?Proxy=true&key=" + keyStr;
1634         return retStr;
1635     }
1636 }
1637 
1638 // get proxy uri
GetProxyUriStr(std::string tableName,std::string idStr)1639 std::string GetProxyUriStr(std::string tableName, std::string idStr)
1640 {
1641     if (std::stoi(idStr) < USERID_HELPER_NUMBER) {
1642         idStr = "100";
1643     }
1644     if (tableName == "global") {
1645         // return global uri
1646         std::string retStr = "datashare:///com.ohos.settingsdata/entry/settingsdata/SETTINGSDATA?Proxy=true";
1647         return retStr;
1648     } else if (tableName == "system") {
1649         std::string retStr =
1650             "datashare:///com.ohos.settingsdata/entry/settingsdata/USER_SETTINGSDATA_" + idStr + "?Proxy=true";
1651         return retStr;
1652     } else {
1653         std::string retStr =
1654             "datashare:///com.ohos.settingsdata/entry/settingsdata/USER_SETTINGSDATA_SECURE_" + idStr + "?Proxy=true";
1655         return retStr;
1656     }
1657 }
1658 
1659 // check whether tableName is invalid, invalid -> true valid -> false
IsTableNameInvalid(std::string tableName)1660 bool IsTableNameInvalid(std::string tableName)
1661 {
1662     if (tableName != "global" && tableName != "system" && tableName != "secure") {
1663         return true;
1664     } else {
1665         return false;
1666     }
1667 }
1668 
napi_get_value_sync_ext(bool stageMode,size_t argc,napi_env env,napi_value * args)1669 napi_value napi_get_value_sync_ext(bool stageMode, size_t argc, napi_env env, napi_value* args)
1670 {
1671     SETTING_LOG_INFO("argv[0] is a context, Stage Model: %{public}d", stageMode);
1672     AsyncCallbackInfo *asyncCallbackInfo = new AsyncCallbackInfo();
1673     if (asyncCallbackInfo == nullptr) {
1674         SETTING_LOG_ERROR("asyncCallbackInfo is null");
1675         return wrap_void_to_js(env);
1676     }
1677     napi_valuetype valueType;
1678 
1679     // define table name
1680     if (argc == ARGS_FOUR) {
1681         // check whether tableName is ok
1682         NAPI_CALL(env, napi_typeof(env, args[PARAM3], &valueType));
1683         if (valueType != napi_string) {
1684             SETTING_LOG_ERROR("tableName IS NOT STRING");
1685             return wrap_void_to_js(env);
1686         } else {
1687             asyncCallbackInfo->tableName = unwrap_string_from_js(env, args[PARAM3]);
1688             if (IsTableNameInvalid(asyncCallbackInfo->tableName)) {
1689                 SETTING_LOG_ERROR("INVALID tableName");
1690                 return wrap_void_to_js(env);
1691             }
1692         }
1693     } else {
1694         asyncCallbackInfo->tableName = "global";
1695     }
1696 
1697     asyncCallbackInfo->key = unwrap_string_from_js(env, args[PARAM1]);
1698     asyncCallbackInfo->dataShareHelper = getDataShareHelper(env, args[PARAM0], stageMode, asyncCallbackInfo->tableName);
1699     GetValueExecuteExt(env, (void *)asyncCallbackInfo);
1700     SETTING_LOG_INFO(
1701         "n_g_v return  %{public}s", asyncCallbackInfo->value.c_str());
1702     napi_value retVal = nullptr;
1703     if (asyncCallbackInfo->value.size() <= 0) {
1704         retVal = args[PARAM2];
1705         ThrowError(env, asyncCallbackInfo->status);
1706     } else {
1707         retVal = wrap_string_to_js(env, asyncCallbackInfo->value);
1708     }
1709     delete asyncCallbackInfo;
1710     return retVal;
1711 }
1712 
napi_set_value_sync_ext(bool stageMode,size_t argc,napi_env env,napi_value * args)1713 napi_value napi_set_value_sync_ext(bool stageMode, size_t argc, napi_env env, napi_value *args)
1714 {
1715     SETTING_LOG_INFO("argv[0] is a context, Stage Model: %{public}d", stageMode);
1716     AsyncCallbackInfo *asyncCallbackInfo = new AsyncCallbackInfo();
1717     asyncCallbackInfo->key = unwrap_string_from_js(env, args[PARAM1]);
1718     napi_valuetype valueType;
1719 
1720     // define table name
1721     if (argc == ARGS_FOUR) {
1722         NAPI_CALL(env, napi_typeof(env, args[PARAM3], &valueType));
1723         if (valueType != napi_string) {
1724             SETTING_LOG_ERROR("tableName IS NOT STRING");
1725             return wrap_void_to_js(env);
1726         } else {
1727             asyncCallbackInfo->tableName = unwrap_string_from_js(env, args[PARAM3]);
1728             if (IsTableNameInvalid(asyncCallbackInfo->tableName)) {
1729                 SETTING_LOG_ERROR("INVALID tableName");
1730                 return wrap_void_to_js(env);
1731             }
1732         }
1733     } else {
1734         asyncCallbackInfo->tableName = "global";
1735     }
1736     asyncCallbackInfo->dataShareHelper = getDataShareHelper(
1737         env, args[PARAM0], stageMode, asyncCallbackInfo->tableName, asyncCallbackInfo);
1738     SetValueExecuteExt(env, (void *)asyncCallbackInfo, unwrap_string_from_js(env, args[PARAM2]));
1739     napi_value result = wrap_bool_to_js(env, ThrowError(env, asyncCallbackInfo->status));
1740     delete asyncCallbackInfo;
1741     return result;
1742 }
1743 
napi_register_key_observer(napi_env env,napi_callback_info info)1744 napi_value napi_register_key_observer(napi_env env, napi_callback_info info)
1745 {
1746     return npai_settings_register_observer(env, info);
1747 }
1748 
napi_unregister_key_observer(napi_env env,napi_callback_info info)1749 napi_value napi_unregister_key_observer(napi_env env, napi_callback_info info)
1750 {
1751     return npai_settings_unregister_observer(env, info);
1752 }
1753 }  // namespace Settings
1754 }  // namespace OHOS
1755