• 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 "js_datashare_ext_ability.h"
17 
18 #include "ability_info.h"
19 #include "accesstoken_kit.h"
20 #include "dataobs_mgr_client.h"
21 #include "datashare_stub_impl.h"
22 #include "hilog_wrapper.h"
23 #include "ipc_skeleton.h"
24 #include "js_datashare_ext_ability_context.h"
25 #include "js_runtime.h"
26 #include "js_runtime_utils.h"
27 #include "napi/native_api.h"
28 #include "napi/native_node_api.h"
29 #include "napi_common_util.h"
30 #include "napi_common_want.h"
31 #include "napi_remote_object.h"
32 
33 namespace OHOS {
34 namespace AbilityRuntime {
35 namespace {
36 constexpr size_t ARGC_ONE = 1;
37 constexpr size_t ARGC_TWO = 2;
38 constexpr size_t ARGC_THREE = 3;
39 constexpr int INVALID_VALUE = -1;
40 #if BINDER_IPC_32BIT
41 const std::string LIB_RDB_PATH = "/system/lib/module/data/librdb.z.so";
42 const std::string LIB_DATA_ABILITY_PATH = "/system/lib/module/data/libdataability.z.so";
43 #else
44 const std::string LIB_RDB_PATH = "/system/lib64/module/data/librdb.z.so";
45 const std::string LIB_DATA_ABILITY_PATH = "/system/lib64/module/data/libdataability.z.so";
46 #endif
47 }
48 
49 using namespace OHOS::AppExecFwk;
50 using OHOS::Security::AccessToken::AccessTokenKit;
51 using DataObsMgrClient = OHOS::AAFwk::DataObsMgrClient;
52 
Create(const std::unique_ptr<Runtime> & runtime)53 JsDataShareExtAbility* JsDataShareExtAbility::Create(const std::unique_ptr<Runtime>& runtime)
54 {
55     return new JsDataShareExtAbility(static_cast<JsRuntime&>(*runtime));
56 }
57 
JsDataShareExtAbility(JsRuntime & jsRuntime)58 JsDataShareExtAbility::JsDataShareExtAbility(JsRuntime& jsRuntime) : jsRuntime_(jsRuntime) {}
59 
~JsDataShareExtAbility()60 JsDataShareExtAbility::~JsDataShareExtAbility()
61 {
62     UnloadLibrary();
63 }
64 
Init(const std::shared_ptr<AbilityLocalRecord> & record,const std::shared_ptr<OHOSApplication> & application,std::shared_ptr<AbilityHandler> & handler,const sptr<IRemoteObject> & token)65 void JsDataShareExtAbility::Init(const std::shared_ptr<AbilityLocalRecord> &record,
66     const std::shared_ptr<OHOSApplication> &application, std::shared_ptr<AbilityHandler> &handler,
67     const sptr<IRemoteObject> &token)
68 {
69     DataShareExtAbility::Init(record, application, handler, token);
70     std::string srcPath = "";
71     GetSrcPath(srcPath);
72     if (srcPath.empty()) {
73         HILOG_ERROR("Failed to get srcPath");
74         return;
75     }
76 
77     std::string moduleName(Extension::abilityInfo_->moduleName);
78     moduleName.append("::").append(abilityInfo_->name);
79     HILOG_INFO("%{public}s module:%{public}s, srcPath:%{public}s.", __func__, moduleName.c_str(), srcPath.c_str());
80     HandleScope handleScope(jsRuntime_);
81     auto& engine = jsRuntime_.GetNativeEngine();
82 
83     jsObj_ = jsRuntime_.LoadModule(moduleName, srcPath);
84     if (jsObj_ == nullptr) {
85         HILOG_ERROR("Failed to get jsObj_");
86         return;
87     }
88     HILOG_INFO("JsDataShareExtAbility::Init ConvertNativeValueTo.");
89     NativeObject* obj = ConvertNativeValueTo<NativeObject>(jsObj_->Get());
90     if (obj == nullptr) {
91         HILOG_ERROR("Failed to get JsDataShareExtAbility object");
92         return;
93     }
94 
95     LoadLibrary();
96 
97     auto context = GetContext();
98     if (context == nullptr) {
99         HILOG_ERROR("Failed to get context");
100         return;
101     }
102     HILOG_INFO("JsDataShareExtAbility::Init CreateJsDataShareExtAbilityContext.");
103     NativeValue* contextObj = CreateJsDataShareExtAbilityContext(engine, context);
104     auto contextRef = jsRuntime_.LoadSystemModule("application.DataShareExtensionAbilityContext",
105         &contextObj, ARGC_ONE);
106     contextObj = contextRef->Get();
107     HILOG_INFO("JsDataShareExtAbility::Init Bind.");
108     context->Bind(jsRuntime_, contextRef.release());
109     HILOG_INFO("JsDataShareExtAbility::SetProperty.");
110     obj->SetProperty("context", contextObj);
111 
112     auto nativeObj = ConvertNativeValueTo<NativeObject>(contextObj);
113     if (nativeObj == nullptr) {
114         HILOG_ERROR("Failed to get datashare extension ability native object");
115         return;
116     }
117 
118     HILOG_INFO("Set datashare extension ability context pointer: %{public}p", context.get());
119 
120     nativeObj->SetNativePointer(new std::weak_ptr<AbilityRuntime::Context>(context),
121         [](NativeEngine*, void* data, void*) {
122             HILOG_INFO("Finalizer for weak_ptr datashare extension ability context is called");
123             delete static_cast<std::weak_ptr<AbilityRuntime::Context>*>(data);
124         }, nullptr);
125 
126     HILOG_INFO("JsDataShareExtAbility::Init end.");
127 }
128 
LoadLibrary()129 void JsDataShareExtAbility::LoadLibrary()
130 {
131     libRdbHandle_ = dlopen(LIB_RDB_PATH.c_str(), RTLD_LAZY);
132     if (libRdbHandle_ == nullptr) {
133         HILOG_ERROR("dlopen failed: %{public}s", dlerror());
134     } else {
135         rdbValueBucketNewInstance_ = reinterpret_cast<RdbValueBucketNewInstance>(
136             dlsym(libRdbHandle_, "NAPI_OHOS_Data_RdbJsKit_ValuesBucketProxy_NewInstance"));
137         if (rdbValueBucketNewInstance_ == nullptr) {
138             HILOG_ERROR("symbol not found: %{public}s", dlerror());
139         }
140 
141         rdbResultSetProxyGetNativeObject_ = reinterpret_cast<RdbResultSetProxyGetNativeObject>(
142             dlsym(libRdbHandle_, "NAPI_OHOS_Data_RdbJsKit_ResultSetProxy_GetNativeObject"));
143         if (rdbResultSetProxyGetNativeObject_ == nullptr) {
144             HILOG_ERROR("symbol not found: %{public}s", dlerror());
145         }
146     }
147 
148     libDataAbilityHandle_ = dlopen(LIB_DATA_ABILITY_PATH.c_str(), RTLD_LAZY);
149     if (libDataAbilityHandle_ == nullptr) {
150         HILOG_ERROR("dlopen failed: %{public}s", dlerror());
151     } else {
152         dataAbilityPredicatesNewInstance_ = reinterpret_cast<DataAbilityPredicatesNewInstance>(
153             dlsym(libDataAbilityHandle_, "NAPI_OHOS_Data_DataAbilityJsKit_DataAbilityPredicatesProxy_NewInstance"));
154         if (dataAbilityPredicatesNewInstance_ == nullptr) {
155             HILOG_ERROR("symbol not found: %{public}s", dlerror());
156         }
157     }
158 }
159 
UnloadLibrary()160 void JsDataShareExtAbility::UnloadLibrary()
161 {
162     if (libRdbHandle_ != nullptr) {
163         dlclose(libRdbHandle_);
164     }
165     if (libDataAbilityHandle_ != nullptr) {
166         dlclose(libDataAbilityHandle_);
167     }
168 }
169 
OnStart(const AAFwk::Want & want)170 void JsDataShareExtAbility::OnStart(const AAFwk::Want &want)
171 {
172     HILOG_INFO("%{public}s begin.", __func__);
173     Extension::OnStart(want);
174     HandleScope handleScope(jsRuntime_);
175     napi_env env = reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine());
176     napi_value napiWant = OHOS::AppExecFwk::WrapWant(env, want);
177     NativeValue* nativeWant = reinterpret_cast<NativeValue*>(napiWant);
178     NativeValue* argv[] = {nativeWant};
179     CallObjectMethod("onCreate", argv, ARGC_ONE);
180     HILOG_INFO("%{public}s end.", __func__);
181 }
182 
OnConnect(const AAFwk::Want & want)183 sptr<IRemoteObject> JsDataShareExtAbility::OnConnect(const AAFwk::Want &want)
184 {
185     HILOG_INFO("%{public}s begin.", __func__);
186     Extension::OnConnect(want);
187     sptr<DataShareStubImpl> remoteObject = new (std::nothrow) DataShareStubImpl(
188         std::static_pointer_cast<JsDataShareExtAbility>(shared_from_this()),
189         reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine()));
190     if (remoteObject == nullptr) {
191         HILOG_ERROR("%{public}s No memory allocated for DataShareStubImpl", __func__);
192         return nullptr;
193     }
194     HILOG_INFO("%{public}s end. ", __func__);
195     return remoteObject->AsObject();
196 }
197 
CallObjectMethod(const char * name,NativeValue * const * argv,size_t argc)198 NativeValue* JsDataShareExtAbility::CallObjectMethod(const char* name, NativeValue* const* argv, size_t argc)
199 {
200     HILOG_INFO("JsDataShareExtAbility::CallObjectMethod(%{public}s), begin", name);
201 
202     if (!jsObj_) {
203         HILOG_WARN("Not found DataShareExtAbility.js");
204         return nullptr;
205     }
206 
207     HandleScope handleScope(jsRuntime_);
208     auto& nativeEngine = jsRuntime_.GetNativeEngine();
209 
210     NativeValue* value = jsObj_->Get();
211     NativeObject* obj = ConvertNativeValueTo<NativeObject>(value);
212     if (obj == nullptr) {
213         HILOG_ERROR("Failed to get DataShareExtAbility object");
214         return nullptr;
215     }
216 
217     NativeValue* method = obj->GetProperty(name);
218     if (method == nullptr) {
219         HILOG_ERROR("Failed to get '%{public}s' from DataShareExtAbility object", name);
220         return nullptr;
221     }
222     HILOG_INFO("JsDataShareExtAbility::CallFunction(%{public}s), success", name);
223     return handleScope.Escape(nativeEngine.CallFunction(value, method, argv, argc));
224 }
225 
GetSrcPath(std::string & srcPath)226 void JsDataShareExtAbility::GetSrcPath(std::string &srcPath)
227 {
228     if (!Extension::abilityInfo_->isStageBasedModel) {
229         /* temporary compatibility api8 + config.json */
230         srcPath.append(Extension::abilityInfo_->package);
231         srcPath.append("/assets/js/");
232         if (!Extension::abilityInfo_->srcPath.empty()) {
233             srcPath.append(Extension::abilityInfo_->srcPath);
234         }
235         srcPath.append("/").append(Extension::abilityInfo_->name).append(".abc");
236         return;
237     }
238 
239     if (!Extension::abilityInfo_->srcEntrance.empty()) {
240         srcPath.append(Extension::abilityInfo_->moduleName + "/");
241         srcPath.append(Extension::abilityInfo_->srcEntrance);
242         srcPath.erase(srcPath.rfind('.'));
243         srcPath.append(".abc");
244     }
245 }
246 
GetFileTypes(const Uri & uri,const std::string & mimeTypeFilter)247 std::vector<std::string> JsDataShareExtAbility::GetFileTypes(const Uri &uri, const std::string &mimeTypeFilter)
248 {
249     HILOG_INFO("%{public}s begin.", __func__);
250     auto ret = DataShareExtAbility::GetFileTypes(uri, mimeTypeFilter);
251     HandleScope handleScope(jsRuntime_);
252     napi_env env = reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine());
253 
254     napi_value napiUri = nullptr;
255     napi_create_string_utf8(env, uri.ToString().c_str(), NAPI_AUTO_LENGTH, &napiUri);
256     napi_value napiMimeTypeFilter = nullptr;
257     napi_create_string_utf8(env, mimeTypeFilter.c_str(), NAPI_AUTO_LENGTH, &napiMimeTypeFilter);
258 
259     NativeValue* nativeUri = reinterpret_cast<NativeValue*>(napiUri);
260     NativeValue* nativeMimeTypeFilter = reinterpret_cast<NativeValue*>(napiMimeTypeFilter);
261     NativeValue* argv[] = {nativeUri, nativeMimeTypeFilter};
262     NativeValue* nativeResult = CallObjectMethod("getFileTypes", argv, ARGC_TWO);
263     if (nativeResult == nullptr) {
264         HILOG_ERROR("%{public}s call getFileTypes with return null.", __func__);
265         return ret;
266     }
267 
268     if (!OHOS::AppExecFwk::UnwrapArrayStringFromJS(env, reinterpret_cast<napi_value>(nativeResult), ret)) {
269         HILOG_ERROR("%{public}s call UnwrapArrayStringFromJS failed", __func__);
270         return ret;
271     }
272 
273     HILOG_INFO("%{public}s end.", __func__);
274     return ret;
275 }
276 
OpenFile(const Uri & uri,const std::string & mode)277 int JsDataShareExtAbility::OpenFile(const Uri &uri, const std::string &mode)
278 {
279     HILOG_INFO("%{public}s begin.", __func__);
280     auto ret = DataShareExtAbility::OpenFile(uri, mode);
281     HandleScope handleScope(jsRuntime_);
282     napi_env env = reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine());
283 
284     napi_value napiUri = nullptr;
285     napi_create_string_utf8(env, uri.ToString().c_str(), NAPI_AUTO_LENGTH, &napiUri);
286     napi_value napiMode = nullptr;
287     napi_create_string_utf8(env, mode.c_str(), NAPI_AUTO_LENGTH, &napiMode);
288 
289     NativeValue* nativeUri = reinterpret_cast<NativeValue*>(napiUri);
290     NativeValue* nativeMode = reinterpret_cast<NativeValue*>(napiMode);
291     NativeValue* argv[] = {nativeUri, nativeMode};
292     NativeValue* nativeResult = CallObjectMethod("openFile", argv, ARGC_TWO);
293     if (nativeResult == nullptr) {
294         HILOG_ERROR("%{public}s call openFile with return null.", __func__);
295         return ret;
296     }
297 
298     ret = OHOS::AppExecFwk::UnwrapInt32FromJS(env, reinterpret_cast<napi_value>(nativeResult));
299     HILOG_INFO("%{public}s end.", __func__);
300     return ret;
301 }
302 
OpenRawFile(const Uri & uri,const std::string & mode)303 int JsDataShareExtAbility::OpenRawFile(const Uri &uri, const std::string &mode)
304 {
305     HILOG_INFO("%{public}s begin.", __func__);
306     auto ret = DataShareExtAbility::OpenRawFile(uri, mode);
307     HandleScope handleScope(jsRuntime_);
308     napi_env env = reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine());
309 
310     napi_value napiUri = nullptr;
311     napi_create_string_utf8(env, uri.ToString().c_str(), NAPI_AUTO_LENGTH, &napiUri);
312     napi_value napiMode = nullptr;
313     napi_create_string_utf8(env, mode.c_str(), NAPI_AUTO_LENGTH, &napiMode);
314 
315     NativeValue* nativeUri = reinterpret_cast<NativeValue*>(napiUri);
316     NativeValue* nativeMode = reinterpret_cast<NativeValue*>(napiMode);
317     NativeValue* argv[] = {nativeUri, nativeMode};
318     NativeValue* nativeResult = CallObjectMethod("openRawFile", argv, ARGC_TWO);
319     if (nativeResult == nullptr) {
320         HILOG_ERROR("%{public}s call openRawFile with return null.", __func__);
321         return ret;
322     }
323 
324     ret = OHOS::AppExecFwk::UnwrapInt32FromJS(env, reinterpret_cast<napi_value>(nativeResult));
325     HILOG_INFO("%{public}s end.", __func__);
326     return ret;
327 }
328 
Insert(const Uri & uri,const NativeRdb::ValuesBucket & value)329 int JsDataShareExtAbility::Insert(const Uri &uri, const NativeRdb::ValuesBucket &value)
330 {
331     HILOG_INFO("%{public}s begin.", __func__);
332     int ret = INVALID_VALUE;
333     if (!CheckCallingPermission(abilityInfo_->writePermission)) {
334         HILOG_ERROR("%{public}s Check calling permission failed.", __func__);
335         return ret;
336     }
337 
338     ret = DataShareExtAbility::Insert(uri, value);
339     if (rdbValueBucketNewInstance_ == nullptr) {
340         HILOG_ERROR("%{public}s invalid instance of rdb value bucket.", __func__);
341         return ret;
342     }
343     HandleScope handleScope(jsRuntime_);
344     napi_env env = reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine());
345     napi_value napiUri = nullptr;
346     napi_create_string_utf8(env, uri.ToString().c_str(), NAPI_AUTO_LENGTH, &napiUri);
347     napi_value napiValue = rdbValueBucketNewInstance_(env, const_cast<OHOS::NativeRdb::ValuesBucket&>(value));
348     if (napiValue == nullptr) {
349         HILOG_ERROR("%{public}s failed to make new instance of rdbValueBucket.", __func__);
350         return ret;
351     }
352 
353     NativeValue* nativeUri = reinterpret_cast<NativeValue*>(napiUri);
354     NativeValue* nativeValue = reinterpret_cast<NativeValue*>(napiValue);
355     NativeValue* argv[] = {nativeUri, nativeValue};
356     NativeValue* nativeResult = CallObjectMethod("insert", argv, ARGC_TWO);
357     if (nativeResult == nullptr) {
358         HILOG_ERROR("%{public}s call insert with return null.", __func__);
359         return ret;
360     }
361 
362     ret = OHOS::AppExecFwk::UnwrapInt32FromJS(env, reinterpret_cast<napi_value>(nativeResult));
363     HILOG_INFO("%{public}s end.", __func__);
364     return ret;
365 }
366 
Update(const Uri & uri,const NativeRdb::ValuesBucket & value,const NativeRdb::DataAbilityPredicates & predicates)367 int JsDataShareExtAbility::Update(const Uri &uri, const NativeRdb::ValuesBucket &value,
368     const NativeRdb::DataAbilityPredicates &predicates)
369 {
370     HILOG_INFO("%{public}s begin.", __func__);
371     int ret = INVALID_VALUE;
372     if (!CheckCallingPermission(abilityInfo_->writePermission)) {
373         HILOG_ERROR("%{public}s Check calling permission failed.", __func__);
374         return ret;
375     }
376 
377     ret = DataShareExtAbility::Update(uri, value, predicates);
378     if (rdbValueBucketNewInstance_ == nullptr) {
379         HILOG_ERROR("%{public}s invalid instance of ValuesBucket.", __func__);
380         return ret;
381     }
382 
383     HandleScope handleScope(jsRuntime_);
384     napi_env env = reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine());
385     napi_value napiUri = nullptr;
386     napi_create_string_utf8(env, uri.ToString().c_str(), NAPI_AUTO_LENGTH, &napiUri);
387     napi_value napiValue = rdbValueBucketNewInstance_(env, const_cast<OHOS::NativeRdb::ValuesBucket&>(value));
388     if (napiValue == nullptr) {
389         HILOG_ERROR("%{public}s failed to make new instance of rdbValueBucket.", __func__);
390         return ret;
391     }
392 
393     napi_value napiPredicates = MakePredicates(env, predicates);
394     if (napiPredicates == nullptr) {
395         HILOG_ERROR("%{public}s failed to make new instance of dataAbilityPredicates.", __func__);
396         return ret;
397     }
398 
399     NativeValue* nativeUri = reinterpret_cast<NativeValue*>(napiUri);
400     NativeValue* nativeValue = reinterpret_cast<NativeValue*>(napiValue);
401     NativeValue* nativePredicates = reinterpret_cast<NativeValue*>(napiPredicates);
402     NativeValue* argv[] = {nativeUri, nativeValue, nativePredicates};
403     NativeValue* nativeResult = CallObjectMethod("update", argv, ARGC_THREE);
404     if (nativeResult == nullptr) {
405         HILOG_ERROR("%{public}s call update with return null.", __func__);
406         return ret;
407     }
408 
409     ret = OHOS::AppExecFwk::UnwrapInt32FromJS(env, reinterpret_cast<napi_value>(nativeResult));
410     HILOG_INFO("%{public}s end.", __func__);
411     return ret;
412 }
413 
Delete(const Uri & uri,const NativeRdb::DataAbilityPredicates & predicates)414 int JsDataShareExtAbility::Delete(const Uri &uri, const NativeRdb::DataAbilityPredicates &predicates)
415 {
416     HILOG_INFO("%{public}s begin.", __func__);
417     int ret = INVALID_VALUE;
418     if (!CheckCallingPermission(abilityInfo_->writePermission)) {
419         HILOG_ERROR("%{public}s Check calling permission failed.", __func__);
420         return ret;
421     }
422 
423     ret = DataShareExtAbility::Delete(uri, predicates);
424     HandleScope handleScope(jsRuntime_);
425     napi_env env = reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine());
426     napi_value napiUri = nullptr;
427     napi_create_string_utf8(env, uri.ToString().c_str(), NAPI_AUTO_LENGTH, &napiUri);
428 
429     napi_value napiPredicates = MakePredicates(env, predicates);
430     if (napiPredicates == nullptr) {
431         HILOG_ERROR("%{public}s failed to make new instance of dataAbilityPredicates.", __func__);
432         return ret;
433     }
434 
435     NativeValue* nativeUri = reinterpret_cast<NativeValue*>(napiUri);
436     NativeValue* nativePredicates = reinterpret_cast<NativeValue*>(napiPredicates);
437     NativeValue* argv[] = {nativeUri, nativePredicates};
438     NativeValue* nativeResult = CallObjectMethod("delete", argv, ARGC_TWO);
439     if (nativeResult == nullptr) {
440         HILOG_ERROR("%{public}s call delete with return null.", __func__);
441         return ret;
442     }
443 
444     ret = OHOS::AppExecFwk::UnwrapInt32FromJS(env, reinterpret_cast<napi_value>(nativeResult));
445     HILOG_INFO("%{public}s end.", __func__);
446     return ret;
447 }
448 
Query(const Uri & uri,std::vector<std::string> & columns,const NativeRdb::DataAbilityPredicates & predicates)449 std::shared_ptr<NativeRdb::AbsSharedResultSet> JsDataShareExtAbility::Query(const Uri &uri,
450     std::vector<std::string> &columns, const NativeRdb::DataAbilityPredicates &predicates)
451 {
452     HILOG_INFO("%{public}s begin.", __func__);
453     std::shared_ptr<NativeRdb::AbsSharedResultSet> ret;
454     if (!CheckCallingPermission(abilityInfo_->readPermission)) {
455         HILOG_ERROR("%{public}s Check calling permission failed.", __func__);
456         return ret;
457     }
458 
459     ret = DataShareExtAbility::Query(uri, columns, predicates);
460     if (rdbResultSetProxyGetNativeObject_ == nullptr) {
461         HILOG_ERROR("%{public}s invalid instance of RdbResultSet.", __func__);
462         return ret;
463     }
464     HandleScope handleScope(jsRuntime_);
465     napi_env env = reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine());
466     napi_value napiUri = nullptr;
467     napi_create_string_utf8(env, uri.ToString().c_str(), NAPI_AUTO_LENGTH, &napiUri);
468 
469     napi_value napiColumns = nullptr;
470     napi_create_array(env, &napiColumns);
471     bool isArray = false;
472     if (napi_is_array(env, napiColumns, &isArray) != napi_ok || !isArray) {
473         HILOG_ERROR("JsDataShareExtAbility create array failed");
474         return ret;
475     }
476     int32_t index = 0;
477     for (const auto &column : columns) {
478         napi_value result = nullptr;
479         napi_create_string_utf8(env, column.c_str(), column.length(), &result);
480         napi_set_element(env, napiColumns, index++, result);
481     }
482 
483     napi_value napiPredicates = MakePredicates(env, predicates);
484     if (napiPredicates == nullptr) {
485         HILOG_ERROR("%{public}s failed to make new instance of dataAbilityPredicates.", __func__);
486         return ret;
487     }
488 
489     NativeValue* nativeUri = reinterpret_cast<NativeValue*>(napiUri);
490     NativeValue* nativeColumns = reinterpret_cast<NativeValue*>(napiColumns);
491     NativeValue* nativePredicates = reinterpret_cast<NativeValue*>(napiPredicates);
492     NativeValue* argv[] = {nativeUri, nativeColumns, nativePredicates};
493     NativeValue* nativeResult = CallObjectMethod("query", argv, ARGC_THREE);
494     if (nativeResult == nullptr) {
495         HILOG_ERROR("%{public}s call query with return null.", __func__);
496         return ret;
497     }
498 
499     auto nativeObject = rdbResultSetProxyGetNativeObject_(env, reinterpret_cast<napi_value>(nativeResult));
500     if (nativeObject == nullptr) {
501         return ret;
502     }
503 
504     ret.reset(nativeObject);
505     HILOG_INFO("%{public}s end.", __func__);
506     return ret;
507 }
508 
GetType(const Uri & uri)509 std::string JsDataShareExtAbility::GetType(const Uri &uri)
510 {
511     HILOG_INFO("%{public}s begin.", __func__);
512     auto ret = DataShareExtAbility::GetType(uri);
513     HandleScope handleScope(jsRuntime_);
514     napi_env env = reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine());
515 
516     napi_value napiUri = nullptr;
517     napi_create_string_utf8(env, uri.ToString().c_str(), NAPI_AUTO_LENGTH,
518         &napiUri);
519     NativeValue* nativeUri = reinterpret_cast<NativeValue*>(napiUri);
520     NativeValue* argv[] = {nativeUri};
521     NativeValue* nativeResult = CallObjectMethod("getType", argv, ARGC_ONE);
522     if (nativeResult == nullptr) {
523         HILOG_ERROR("%{public}s call getType with return null.", __func__);
524         return ret;
525     }
526 
527     ret = OHOS::AppExecFwk::UnwrapStringFromJS(env, reinterpret_cast<napi_value>(nativeResult));
528     HILOG_INFO("%{public}s end.", __func__);
529     return ret;
530 }
531 
BatchInsert(const Uri & uri,const std::vector<NativeRdb::ValuesBucket> & values)532 int JsDataShareExtAbility::BatchInsert(const Uri &uri, const std::vector<NativeRdb::ValuesBucket> &values)
533 {
534     HILOG_INFO("%{public}s begin.", __func__);
535     int ret = INVALID_VALUE;
536     if (!CheckCallingPermission(abilityInfo_->writePermission)) {
537         HILOG_ERROR("%{public}s Check calling permission failed.", __func__);
538         return ret;
539     }
540 
541     ret = DataShareExtAbility::BatchInsert(uri, values);
542     if (rdbValueBucketNewInstance_ == nullptr) {
543         HILOG_ERROR("%{public}s invalid instance of rdb value bucket.", __func__);
544         return ret;
545     }
546     HandleScope handleScope(jsRuntime_);
547     napi_env env = reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine());
548     napi_value napiUri = nullptr;
549     napi_create_string_utf8(env, uri.ToString().c_str(), NAPI_AUTO_LENGTH, &napiUri);
550 
551     napi_value napiValues = nullptr;
552     napi_create_array(env, &napiValues);
553     bool isArray = false;
554     if (napi_is_array(env, napiValues, &isArray) != napi_ok || !isArray) {
555         HILOG_ERROR("JsDataShareExtAbility create array failed");
556         return ret;
557     }
558     int32_t index = 0;
559     for (const auto &value : values) {
560         napi_value result = rdbValueBucketNewInstance_(env, const_cast<OHOS::NativeRdb::ValuesBucket&>(value));
561         if (result == nullptr) {
562             HILOG_ERROR("%{public}s failed to make new instance of rdbValueBucket.", __func__);
563             return ret;
564         }
565         napi_set_element(env, napiValues, index++, result);
566     }
567 
568     NativeValue* nativeUri = reinterpret_cast<NativeValue*>(napiUri);
569     NativeValue* nativeValues = reinterpret_cast<NativeValue*>(napiValues);
570     NativeValue* argv[] = {nativeUri, nativeValues};
571     NativeValue* nativeResult = CallObjectMethod("batchInsert", argv, ARGC_TWO);
572     if (nativeResult == nullptr) {
573         HILOG_ERROR("%{public}s call batchInsert with return null.", __func__);
574         return ret;
575     }
576 
577     ret = OHOS::AppExecFwk::UnwrapInt32FromJS(env, reinterpret_cast<napi_value>(nativeResult));
578     HILOG_INFO("%{public}s end.", __func__);
579     return ret;
580 }
581 
RegisterObserver(const Uri & uri,const sptr<AAFwk::IDataAbilityObserver> & dataObserver)582 bool JsDataShareExtAbility::RegisterObserver(const Uri &uri, const sptr<AAFwk::IDataAbilityObserver> &dataObserver)
583 {
584     HILOG_INFO("%{public}s begin.", __func__);
585     DataShareExtAbility::RegisterObserver(uri, dataObserver);
586     auto obsMgrClient = DataObsMgrClient::GetInstance();
587     if (obsMgrClient == nullptr) {
588         HILOG_ERROR("%{public}s obsMgrClient is nullptr", __func__);
589         return false;
590     }
591 
592     ErrCode ret = obsMgrClient->RegisterObserver(uri, dataObserver);
593     if (ret != ERR_OK) {
594         HILOG_ERROR("%{public}s obsMgrClient->RegisterObserver error return %{public}d", __func__, ret);
595         return false;
596     }
597     HILOG_INFO("%{public}s end.", __func__);
598     return true;
599 }
600 
UnregisterObserver(const Uri & uri,const sptr<AAFwk::IDataAbilityObserver> & dataObserver)601 bool JsDataShareExtAbility::UnregisterObserver(const Uri &uri, const sptr<AAFwk::IDataAbilityObserver> &dataObserver)
602 {
603     HILOG_INFO("%{public}s begin.", __func__);
604     DataShareExtAbility::UnregisterObserver(uri, dataObserver);
605     auto obsMgrClient = DataObsMgrClient::GetInstance();
606     if (obsMgrClient == nullptr) {
607         HILOG_ERROR("%{public}s obsMgrClient is nullptr", __func__);
608         return false;
609     }
610 
611     ErrCode ret = obsMgrClient->UnregisterObserver(uri, dataObserver);
612     if (ret != ERR_OK) {
613         HILOG_ERROR("%{public}s obsMgrClient->UnregisterObserver error return %{public}d", __func__, ret);
614         return false;
615     }
616     HILOG_INFO("%{public}s end.", __func__);
617     return true;
618 }
619 
NotifyChange(const Uri & uri)620 bool JsDataShareExtAbility::NotifyChange(const Uri &uri)
621 {
622     HILOG_INFO("%{public}s begin.", __func__);
623     DataShareExtAbility::NotifyChange(uri);
624     auto obsMgrClient = DataObsMgrClient::GetInstance();
625     if (obsMgrClient == nullptr) {
626         HILOG_ERROR("%{public}s obsMgrClient is nullptr", __func__);
627         return false;
628     }
629 
630     ErrCode ret = obsMgrClient->NotifyChange(uri);
631     if (ret != ERR_OK) {
632         HILOG_ERROR("%{public}s obsMgrClient->NotifyChange error return %{public}d", __func__, ret);
633         return false;
634     }
635     HILOG_INFO("%{public}s end.", __func__);
636     return true;
637 }
638 
NormalizeUri(const Uri & uri)639 Uri JsDataShareExtAbility::NormalizeUri(const Uri &uri)
640 {
641     HILOG_INFO("%{public}s begin.", __func__);
642     auto ret = DataShareExtAbility::NormalizeUri(uri);
643     HandleScope handleScope(jsRuntime_);
644     napi_env env = reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine());
645 
646     napi_value napiUri = nullptr;
647     napi_create_string_utf8(env, uri.ToString().c_str(), NAPI_AUTO_LENGTH, &napiUri);
648     NativeValue* nativeUri = reinterpret_cast<NativeValue*>(napiUri);
649     NativeValue* argv[] = {nativeUri};
650     NativeValue* nativeResult = CallObjectMethod("normalizeUri", argv, ARGC_ONE);
651     if (nativeResult == nullptr) {
652         HILOG_ERROR("%{public}s call normalizeUri with return null.", __func__);
653         return ret;
654     }
655 
656     ret = Uri(OHOS::AppExecFwk::UnwrapStringFromJS(env, reinterpret_cast<napi_value>(nativeResult)));
657     HILOG_INFO("%{public}s end.", __func__);
658     return ret;
659 }
660 
DenormalizeUri(const Uri & uri)661 Uri JsDataShareExtAbility::DenormalizeUri(const Uri &uri)
662 {
663     HILOG_INFO("%{public}s begin.", __func__);
664     auto ret = DataShareExtAbility::DenormalizeUri(uri);
665     HandleScope handleScope(jsRuntime_);
666     napi_env env = reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine());
667 
668     napi_value napiUri = nullptr;
669     napi_create_string_utf8(env, uri.ToString().c_str(), NAPI_AUTO_LENGTH, &napiUri);
670     NativeValue* nativeUri = reinterpret_cast<NativeValue*>(napiUri);
671     NativeValue* argv[] = {nativeUri};
672     NativeValue* nativeResult = CallObjectMethod("denormalizeUri", argv, ARGC_ONE);
673     if (nativeResult == nullptr) {
674         HILOG_ERROR("%{public}s call denormalizeUri with return null.", __func__);
675         return ret;
676     }
677 
678     ret = Uri(OHOS::AppExecFwk::UnwrapStringFromJS(env, reinterpret_cast<napi_value>(nativeResult)));
679     HILOG_INFO("%{public}s end.", __func__);
680     return ret;
681 }
682 
ExecuteBatch(const std::vector<std::shared_ptr<AppExecFwk::DataAbilityOperation>> & operations)683 std::vector<std::shared_ptr<AppExecFwk::DataAbilityResult>> JsDataShareExtAbility::ExecuteBatch(
684     const std::vector<std::shared_ptr<AppExecFwk::DataAbilityOperation>> &operations)
685 {
686     HILOG_INFO("%{public}s begin.", __func__);
687     auto ret = DataShareExtAbility::ExecuteBatch(operations);
688     HILOG_INFO("%{public}s end.", __func__);
689     return ret;
690 }
691 
CheckCallingPermission(const std::string & permission)692 bool JsDataShareExtAbility::CheckCallingPermission(const std::string &permission)
693 {
694     HILOG_INFO("%{public}s begin, permission:%{public}s", __func__, permission.c_str());
695     if (!permission.empty() && AccessTokenKit::VerifyAccessToken(IPCSkeleton::GetCallingTokenID(), permission)
696         != AppExecFwk::Constants::PERMISSION_GRANTED) {
697         HILOG_ERROR("%{public}s permission not granted.", __func__);
698         return false;
699     }
700     HILOG_INFO("%{public}s end.", __func__);
701     return true;
702 }
703 
MakePredicates(napi_env env,const NativeRdb::DataAbilityPredicates & predicates)704 napi_value JsDataShareExtAbility::MakePredicates(napi_env env, const NativeRdb::DataAbilityPredicates &predicates)
705 {
706     HILOG_INFO("%{public}s begin.", __func__);
707     if (dataAbilityPredicatesNewInstance_ == nullptr) {
708         HILOG_ERROR("%{public}s invalid instance of DataAbilityPredicates.", __func__);
709         return nullptr;
710     }
711     OHOS::NativeRdb::DataAbilityPredicates* predicatesPtr = new (std::nothrow) OHOS::NativeRdb::DataAbilityPredicates();
712     if (predicatesPtr == nullptr) {
713         HILOG_ERROR("%{public}s No memory allocated for predicates", __func__);
714         return nullptr;
715     }
716     *predicatesPtr = predicates;
717     napi_value napiPredicates = dataAbilityPredicatesNewInstance_(env, predicatesPtr);
718     if (napiPredicates == nullptr) {
719         HILOG_ERROR("%{public}s failed to make new instance of dataAbilityPredicates.", __func__);
720         delete predicatesPtr;
721     }
722     HILOG_INFO("%{public}s end.", __func__);
723     return napiPredicates;
724 }
725 } // namespace AbilityRuntime
726 } // namespace OHOS