1 /*
2 * Copyright (c) 2022-2024 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_file_access_ext_ability.h"
17
18 #include "ability_info.h"
19 #include "accesstoken_kit.h"
20 #include "extension_context.h"
21 #include "file_access_check_util.h"
22 #include "file_access_ext_stub_impl.h"
23 #include "file_access_extension_info.h"
24 #include "file_access_framework_errno.h"
25 #include "file_access_observer_common.h"
26 #include "file_access_service_client.h"
27 #include "hilog_wrapper.h"
28 #include "hitrace_meter.h"
29 #include "if_system_ability_manager.h"
30 #include "ipc_skeleton.h"
31 #include "iservice_registry.h"
32 #include "js_runtime.h"
33 #include "js_runtime_utils.h"
34 #include "n_error.h"
35 #include "napi/native_api.h"
36 #include "napi/native_node_api.h"
37 #include "napi_common_util.h"
38 #include "napi_common_want.h"
39 #include "napi_remote_object.h"
40 #include "system_ability_definition.h"
41 #include "user_access_common_utils.h"
42 #include "user_access_tracer.h"
43
44 namespace OHOS {
45 namespace FileAccessFwk {
46 namespace {
47 constexpr size_t ARGC_ZERO = 0;
48 constexpr size_t ARGC_ONE = 1;
49 constexpr size_t ARGC_TWO = 2;
50 constexpr size_t ARGC_THREE = 3;
51 constexpr size_t ARGC_FOUR = 4;
52 constexpr size_t MAX_ARG_COUNT = 5;
53 constexpr int EXCEPTION = -1;
54 constexpr int NOEXCEPTION = -2;
55 }
56
57 using namespace OHOS::AppExecFwk;
58 using namespace OHOS::AbilityRuntime;
59 using namespace OHOS::FileManagement::LibN;
60 using OHOS::Security::AccessToken::AccessTokenKit;
61
Create(const std::unique_ptr<Runtime> & runtime)62 JsFileAccessExtAbility *JsFileAccessExtAbility::Create(const std::unique_ptr<Runtime> &runtime)
63 {
64 return new JsFileAccessExtAbility(static_cast<JsRuntime &>(*runtime));
65 }
66
JsFileAccessExtAbility(JsRuntime & jsRuntime)67 JsFileAccessExtAbility::JsFileAccessExtAbility(JsRuntime &jsRuntime) : jsRuntime_(jsRuntime) {}
68
~JsFileAccessExtAbility()69 JsFileAccessExtAbility::~JsFileAccessExtAbility()
70 {
71 jsRuntime_.FreeNativeReference(std::move(jsObj_));
72 }
73
Init(const std::shared_ptr<AbilityLocalRecord> & record,const std::shared_ptr<OHOSApplication> & application,std::shared_ptr<AbilityHandler> & handler,const sptr<IRemoteObject> & token)74 void JsFileAccessExtAbility::Init(const std::shared_ptr<AbilityLocalRecord> &record,
75 const std::shared_ptr<OHOSApplication> &application, std::shared_ptr<AbilityHandler> &handler,
76 const sptr<IRemoteObject> &token)
77 {
78 UserAccessTracer trace;
79 trace.Start("Init");
80 FileAccessExtAbility::Init(record, application, handler, token);
81 std::string srcPath = "";
82 GetSrcPath(srcPath);
83 if (srcPath.empty()) {
84 HILOG_ERROR("Failed to get srcPath");
85 return;
86 }
87 if (abilityInfo_ == nullptr) {
88 HILOG_ERROR("abilityInfo_ is nullptr");
89 return;
90 }
91 std::string moduleName(Extension::abilityInfo_->moduleName);
92 moduleName.append("::").append(abilityInfo_->name);
93 HandleScope handleScope(jsRuntime_);
94 jsObj_ = jsRuntime_.LoadModule(moduleName, srcPath, abilityInfo_->hapPath,
95 abilityInfo_->compileMode == AbilityRuntime::CompileMode::ES_MODULE);
96 if (jsObj_ == nullptr) {
97 HILOG_ERROR("Failed to get jsObj_");
98 return;
99 }
100
101 if (jsObj_->GetNapiValue() == nullptr) {
102 HILOG_ERROR("Failed to get JsFileAccessExtAbility value");
103 return;
104 }
105 }
106
OnStart(const AAFwk::Want & want)107 void JsFileAccessExtAbility::OnStart(const AAFwk::Want &want)
108 {
109 UserAccessTracer trace;
110 trace.Start("OnStart");
111 Extension::OnStart(want);
112 HandleScope handleScope(jsRuntime_);
113 napi_env env = reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine());
114 napi_value napiWant = OHOS::AppExecFwk::WrapWant(env, want);
115 napi_value argv[] = { napiWant };
116 CallObjectMethod("onCreate", argv, ARGC_ONE);
117 }
118
OnConnect(const AAFwk::Want & want)119 sptr<IRemoteObject> JsFileAccessExtAbility::OnConnect(const AAFwk::Want &want)
120 {
121 UserAccessTracer trace;
122 trace.Start("OnConnect");
123 Extension::OnConnect(want);
124 sptr<FileAccessExtStubImpl> remoteObject(
125 new (std::nothrow) FileAccessExtStubImpl(std::static_pointer_cast<JsFileAccessExtAbility>(shared_from_this()),
126 reinterpret_cast<napi_env>(&jsRuntime_.GetNativeEngine())));
127 if (remoteObject == nullptr) {
128 HILOG_ERROR("No memory allocated for FileExtStubImpl");
129 return nullptr;
130 }
131
132 return remoteObject->AsObject();
133 }
134
CallObjectMethod(const char * name,napi_value const * argv,size_t argc)135 napi_value JsFileAccessExtAbility::CallObjectMethod(const char *name, napi_value const *argv, size_t argc)
136 {
137 UserAccessTracer trace;
138 trace.Start("CallObjectMethod");
139 if (!jsObj_) {
140 HILOG_ERROR("JsFileAccessExtAbility::CallObjectMethod jsObj Not found FileAccessExtAbility.js");
141 return nullptr;
142 }
143
144 HandleEscape handleEscape(jsRuntime_);
145 auto &nativeEngine = jsRuntime_.GetNativeEngine();
146 auto env = reinterpret_cast<napi_env>(&nativeEngine);
147
148 napi_value value = jsObj_->GetNapiValue();
149 if (value == nullptr) {
150 HILOG_ERROR("Failed to get FileAccessExtAbility value");
151 return nullptr;
152 }
153
154 napi_value method = nullptr;
155 napi_get_named_property(env, value, name, &method);
156 if (method == nullptr) {
157 HILOG_ERROR("Failed to get '%{public}s' from FileAccessExtAbility object", name);
158 return nullptr;
159 }
160
161 napi_value result = nullptr;
162 if (napi_call_function(env, value, method, argc, argv, &result) != napi_ok) {
163 HILOG_ERROR("Call function fail");
164 return nullptr;
165 }
166 return handleEscape.Escape(result);
167 }
168
DoCallJsMethod(CallJsParam * param)169 static int DoCallJsMethod(CallJsParam *param)
170 {
171 UserAccessTracer trace;
172 trace.Start("DoCallJsMethod");
173 if (param == nullptr || param->jsRuntime == nullptr) {
174 HILOG_ERROR("failed to get jsRuntime.");
175 return EINVAL;
176 }
177 JsRuntime *jsRuntime = param->jsRuntime;
178
179 HandleEscape handleEscape(*jsRuntime);
180 auto &nativeEngine = jsRuntime->GetNativeEngine();
181 auto env = reinterpret_cast<napi_env>(&nativeEngine);
182 size_t argc = 0;
183 napi_value argv[MAX_ARG_COUNT] = { nullptr };
184 if (param->argParser != nullptr) {
185 if (!param->argParser(env, argv, argc)) {
186 HILOG_ERROR("failed to get params.");
187 return EINVAL;
188 }
189 }
190
191 napi_value value = nullptr;
192 auto ref = reinterpret_cast<napi_ref>(param->jsObj);
193 napi_get_reference_value(env, ref, &value);
194 if (value == nullptr) {
195 HILOG_ERROR("failed to get native value object.");
196 return EINVAL;
197 }
198 napi_value method = nullptr;
199 napi_get_named_property(env, value, param->funcName.c_str(), &method);
200 if (method == nullptr) {
201 HILOG_ERROR("failed to get %{public}s from FileExtAbility object.", param->funcName.c_str());
202 return EINVAL;
203 }
204 if (param->retParser == nullptr) {
205 HILOG_ERROR("ResultValueParser must not null.");
206 return EINVAL;
207 }
208 napi_value result = nullptr;
209 napi_call_function(env, value, method, argc, argv, &result);
210 if (result == nullptr) {
211 HILOG_ERROR("Napi call function fail.");
212 return E_GETRESULT;
213 }
214 if (!param->retParser(env, handleEscape.Escape(result))) {
215 HILOG_ERROR("Parser js result fail.");
216 return E_GETRESULT;
217 }
218 return ERR_OK;
219 }
220
CallJsMethod(const std::string & funcName,JsRuntime & jsRuntime,NativeReference * jsObj,InputArgsParser argParser,ResultValueParser retParser)221 int JsFileAccessExtAbility::CallJsMethod(const std::string &funcName, JsRuntime &jsRuntime, NativeReference *jsObj,
222 InputArgsParser argParser, ResultValueParser retParser)
223 {
224 UserAccessTracer trace;
225 trace.Start("CallJsMethod");
226 uv_loop_s *loop = nullptr;
227 napi_status status = napi_get_uv_event_loop(reinterpret_cast<napi_env>(&jsRuntime.GetNativeEngine()), &loop);
228 if (status != napi_ok) {
229 HILOG_ERROR("failed to get uv event loop.");
230 return EINVAL;
231 }
232 auto param = std::make_shared<CallJsParam>(funcName, &jsRuntime, jsObj, argParser, retParser);
233 if (param == nullptr) {
234 HILOG_ERROR("failed to new param.");
235 return EINVAL;
236 }
237
238 auto task = [param {param.get()}]() {
239 if (param == nullptr || param->jsRuntime == nullptr) {
240 HILOG_ERROR("failed to get CallJsParam.");
241 return;
242 }
243
244 napi_handle_scope scope = nullptr;
245 napi_env env = reinterpret_cast<napi_env>(&(param->jsRuntime->GetNativeEngine()));
246 napi_open_handle_scope(env, &scope);
247
248 if (DoCallJsMethod(param) != ERR_OK) {
249 HILOG_ERROR("failed to call DoCallJsMethod.");
250 }
251
252 std::unique_lock<std::mutex> lock(param->fileOperateMutex);
253 param->isReady = true;
254 param->fileOperateCondition.notify_one();
255 napi_close_handle_scope(env, scope);
256 };
257 auto ret = napi_send_event(jsRuntime.GetNapiEnv(), task, napi_eprio_high);
258 if (ret != napi_ok) {
259 HILOG_ERROR("failed to napi_send_event, ret:%{public}d.", ret);
260 return EINVAL;
261 }
262 std::unique_lock<std::mutex> lock(param->fileOperateMutex);
263 param->fileOperateCondition.wait(lock, [param]() { return param->isReady; });
264 return ERR_OK;
265 }
266
GetSrcPath(std::string & srcPath)267 void JsFileAccessExtAbility::GetSrcPath(std::string &srcPath)
268 {
269 UserAccessTracer trace;
270 trace.Start("GetSrcPath");
271 if (!Extension::abilityInfo_->isStageBasedModel) {
272 /* temporary compatibility api8 + config.json */
273 srcPath.append(Extension::abilityInfo_->package);
274 srcPath.append("/assets/js/");
275 if (!Extension::abilityInfo_->srcPath.empty()) {
276 srcPath.append(Extension::abilityInfo_->srcPath);
277 }
278 srcPath.append("/").append(Extension::abilityInfo_->name).append(".abc");
279 return;
280 }
281
282 if (!Extension::abilityInfo_->srcEntrance.empty()) {
283 srcPath.append(Extension::abilityInfo_->moduleName + "/");
284 srcPath.append(Extension::abilityInfo_->srcEntrance);
285 srcPath.erase(srcPath.rfind('.'));
286 srcPath.append(".abc");
287 }
288 }
289
OpenFile(const Uri & uri,int flags,int & fd)290 int JsFileAccessExtAbility::OpenFile(const Uri &uri, int flags, int &fd)
291 {
292 UserAccessTracer trace;
293 trace.Start("OpenFile");
294 auto value = std::make_shared<Value<int>>();
295 if (value == nullptr) {
296 HILOG_ERROR("OpenFile value is nullptr.");
297 return E_GETRESULT;
298 }
299
300 auto argParser = [uri, flags](napi_env &env, napi_value argv[], size_t &argc) -> bool {
301 napi_value nativeUri = nullptr;
302 napi_create_string_utf8(env, uri.ToString().c_str(), uri.ToString().length(), &nativeUri);
303 napi_value nativeFlags = nullptr;
304 napi_create_int32(env, flags, &nativeFlags);
305 if (nativeUri == nullptr || nativeFlags == nullptr) {
306 HILOG_ERROR("create uri or flags native js value fail.");
307 return false;
308 }
309 argv[ARGC_ZERO] = nativeUri;
310 argv[ARGC_ONE] = nativeFlags;
311 argc = ARGC_TWO;
312 return true;
313 };
314 auto retParser = [value](napi_env &env, napi_value result) -> bool {
315 if (GetFdAndCodeFromJs(env, result, value) != napi_ok) {
316 HILOG_ERROR("Convert js object fail.");
317 return false;
318 }
319 return true;
320 };
321
322 auto errCode = CallJsMethod("openFile", jsRuntime_, jsObj_.get(), argParser, retParser);
323 if (errCode != ERR_OK) {
324 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
325 return errCode;
326 }
327
328 if (value->code != ERR_OK) {
329 HILOG_ERROR("fileio fail.");
330 return value->code;
331 }
332
333 fd = value->data;
334 if (fd < ERR_OK) {
335 HILOG_ERROR("Failed to get file descriptor fd: %{public}d", fd);
336 return E_GETRESULT;
337 }
338 return ERR_OK;
339 }
340
CreateFile(const Uri & parent,const std::string & displayName,Uri & newFile)341 int JsFileAccessExtAbility::CreateFile(const Uri &parent, const std::string &displayName, Uri &newFile)
342 {
343 UserAccessTracer trace;
344 trace.Start("CreateFile");
345 auto value = std::make_shared<Value<std::string>>();
346 if (!value) {
347 HILOG_ERROR("CreateFile value is nullptr.");
348 return E_GETRESULT;
349 }
350
351 auto argParser = [parent, displayName](napi_env &env, napi_value argv[], size_t &argc) -> bool {
352 napi_value nativeParent = nullptr;
353 napi_create_string_utf8(env, parent.ToString().c_str(), parent.ToString().length(), &nativeParent);
354 napi_value nativeDisplayName = nullptr;
355 napi_create_string_utf8(env, displayName.c_str(), displayName.length(), &nativeDisplayName);
356 if (nativeParent == nullptr || nativeDisplayName == nullptr) {
357 HILOG_ERROR("create parent uri or displayName native js value fail.");
358 return false;
359 }
360 argv[ARGC_ZERO] = nativeParent;
361 argv[ARGC_ONE] = nativeDisplayName;
362 argc = ARGC_TWO;
363 return true;
364 };
365 auto retParser = [value](napi_env &env, napi_value result) -> bool {
366 if (GetUriAndCodeFromJs(env, result, value) != napi_ok) {
367 HILOG_ERROR("Convert js object fail.");
368 return false;
369 }
370 return true;
371 };
372
373 auto errCode = CallJsMethod("createFile", jsRuntime_, jsObj_.get(), argParser, retParser);
374 if (errCode != ERR_OK) {
375 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
376 return errCode;
377 }
378
379 if (value->code != ERR_OK) {
380 HILOG_ERROR("fileio fail.");
381 return value->code;
382 }
383
384 if ((value->data).empty()) {
385 HILOG_ERROR("call CreateFile with return empty.");
386 return E_GETRESULT;
387 }
388
389 newFile = Uri(value->data);
390 return ERR_OK;
391 }
392
Mkdir(const Uri & parent,const std::string & displayName,Uri & newFile)393 int JsFileAccessExtAbility::Mkdir(const Uri &parent, const std::string &displayName, Uri &newFile)
394 {
395 UserAccessTracer trace;
396 trace.Start("Mkdir");
397 auto value = std::make_shared<Value<std::string>>();
398 if (!value) {
399 HILOG_ERROR("Mkdir value is nullptr.");
400 return E_GETRESULT;
401 }
402
403 auto argParser = [parent, displayName](napi_env &env, napi_value *argv, size_t &argc) -> bool {
404 napi_value nativeParent = nullptr;
405 napi_create_string_utf8(env, parent.ToString().c_str(), parent.ToString().length(), &nativeParent);
406 napi_value nativeDisplayName = nullptr;
407 napi_create_string_utf8(env, displayName.c_str(), displayName.length(), &nativeDisplayName);
408 if (nativeParent == nullptr || nativeDisplayName == nullptr) {
409 HILOG_ERROR("create parent uri native js value fail.");
410 return false;
411 }
412 argv[ARGC_ZERO] = nativeParent;
413 argv[ARGC_ONE] = nativeDisplayName;
414 argc = ARGC_TWO;
415 return true;
416 };
417
418 auto retParser = [value](napi_env &env, napi_value result) -> bool {
419 if (GetUriAndCodeFromJs(env, result, value) != napi_ok) {
420 HILOG_ERROR("Convert js object fail.");
421 return false;
422 }
423 return true;
424 };
425
426 auto errCode = CallJsMethod("mkdir", jsRuntime_, jsObj_.get(), argParser, retParser);
427 if (errCode != ERR_OK) {
428 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
429 return errCode;
430 }
431
432 if (value->code != ERR_OK) {
433 HILOG_ERROR("fileio fail.");
434 return value->code;
435 }
436
437 if ((value->data).empty()) {
438 HILOG_ERROR("call Mkdir with return empty.");
439 return E_GETRESULT;
440 }
441 newFile = Uri(value->data);
442 return ERR_OK;
443 }
444
Delete(const Uri & sourceFile)445 int JsFileAccessExtAbility::Delete(const Uri &sourceFile)
446 {
447 UserAccessTracer trace;
448 trace.Start("Delete");
449 auto ret = std::make_shared<int>();
450 if (!ret) {
451 HILOG_ERROR("Delete value is nullptr.");
452 return E_GETRESULT;
453 }
454
455 auto argParser = [uri = sourceFile](napi_env &env, napi_value *argv, size_t &argc) -> bool {
456 napi_value nativeUri = nullptr;
457 napi_create_string_utf8(env, uri.ToString().c_str(), uri.ToString().length(), &nativeUri);
458 if (nativeUri == nullptr) {
459 HILOG_ERROR("create sourceFile uri native js value fail.");
460 return false;
461 }
462 argv[ARGC_ZERO] = nativeUri;
463 argc = ARGC_ONE;
464 return true;
465 };
466
467 auto retParser = [ret](napi_env &env, napi_value result) -> bool {
468 if (napi_get_value_int32(env, result, ret.get()) != napi_ok) {
469 HILOG_ERROR("Convert js value fail.");
470 return false;
471 }
472 return true;
473 };
474
475 auto errCode = CallJsMethod("delete", jsRuntime_, jsObj_.get(), argParser, retParser);
476 if (errCode != ERR_OK) {
477 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
478 return errCode;
479 }
480
481 if (*ret != ERR_OK) {
482 HILOG_ERROR("fileio fail.");
483 return *ret;
484 }
485
486 return ERR_OK;
487 }
488
Move(const Uri & sourceFile,const Uri & targetParent,Uri & newFile)489 int JsFileAccessExtAbility::Move(const Uri &sourceFile, const Uri &targetParent, Uri &newFile)
490 {
491 UserAccessTracer trace;
492 trace.Start("Move");
493 auto value = std::make_shared<Value<std::string>>();
494 if (value == nullptr) {
495 HILOG_ERROR("Move value is nullptr.");
496 return E_GETRESULT;
497 }
498
499 auto argParser = [sourceFile, targetParent](napi_env &env, napi_value *argv, size_t &argc) -> bool {
500 napi_value srcUri = nullptr;
501 napi_create_string_utf8(env, sourceFile.ToString().c_str(), sourceFile.ToString().length(), &srcUri);
502 napi_value dstUri = nullptr;
503 napi_create_string_utf8(env, targetParent.ToString().c_str(), targetParent.ToString().length(), &dstUri);
504 if (srcUri == nullptr || dstUri == nullptr) {
505 HILOG_ERROR("create sourceFile uri native js value fail.");
506 return false;
507 }
508 argv[ARGC_ZERO] = srcUri;
509 argv[ARGC_ONE] = dstUri;
510 argc = ARGC_TWO;
511 return true;
512 };
513
514 auto retParser = [value](napi_env &env, napi_value result) -> bool {
515 if (GetUriAndCodeFromJs(env, result, value) != napi_ok) {
516 HILOG_ERROR("Convert js object fail.");
517 return false;
518 }
519 return true;
520 };
521
522 auto errCode = CallJsMethod("move", jsRuntime_, jsObj_.get(), argParser, retParser);
523 if (errCode != ERR_OK) {
524 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
525 return errCode;
526 }
527
528 if (value->code != ERR_OK) {
529 HILOG_ERROR("fileio fail.");
530 return value->code;
531 }
532
533 if ((value->data).empty()) {
534 HILOG_ERROR("call move with return empty.");
535 return E_GETRESULT;
536 }
537 newFile = Uri(value->data);
538 return ERR_OK;
539 }
540
TranslateResult(Result & result)541 static void TranslateResult(Result &result)
542 {
543 if (errCodeTable.find(result.errCode) != errCodeTable.end()) {
544 result.errCode = errCodeTable.at(result.errCode).first;
545 if (result.errMsg.empty()) {
546 result.errMsg = errCodeTable.at(result.errCode).second;
547 }
548 }
549 }
550
GetResultByJs(napi_env & env,napi_value nativeResult,Result & result,const int & ret)551 static bool GetResultByJs(napi_env &env, napi_value nativeResult, Result &result, const int &ret)
552 {
553 UserAccessTracer trace;
554 trace.Start("GetResultsByJs");
555 if (nativeResult == nullptr) {
556 HILOG_ERROR("Convert js object fail.");
557 return false;
558 }
559
560 if (ret == NOEXCEPTION) {
561 napi_value sourceUri = nullptr;
562 napi_get_named_property(env, nativeResult, "sourceUri", &sourceUri);
563 if (GetStringValue(env, sourceUri, result.sourceUri) != napi_ok) {
564 HILOG_ERROR("Convert sourceUri fail.");
565 return false;
566 }
567
568 napi_value destUri = nullptr;
569 napi_get_named_property(env, nativeResult, "destUri", &destUri);
570 if (GetStringValue(env, destUri, result.destUri) != napi_ok) {
571 HILOG_ERROR("Convert destUri fail.");
572 return false;
573 }
574 }
575 if ((ret == NOEXCEPTION) || (ret == EXCEPTION)) {
576 napi_value errCode = nullptr;
577 napi_get_named_property(env, nativeResult, "errCode", &errCode);
578 if (napi_get_value_int32(env, errCode, &result.errCode) != napi_ok) {
579 HILOG_ERROR("Convert errCode fail.");
580 return false;
581 }
582 }
583 return true;
584 }
585
ParserGetJsResult(napi_env & env,napi_value nativeValue,std::vector<Result> & result,int & copyRet)586 static bool ParserGetJsResult(napi_env &env, napi_value nativeValue, std::vector<Result> &result,
587 int ©Ret)
588 {
589 UserAccessTracer trace;
590 trace.Start("ParserGetJsResult");
591 if (nativeValue == nullptr) {
592 HILOG_ERROR("Convert js object fail.");
593 return false;
594 }
595
596 napi_value code = nullptr;
597 napi_get_named_property(env, nativeValue, "code", &code);
598 if (napi_get_value_int32(env, code, ©Ret) != napi_ok) {
599 HILOG_ERROR("Convert js value fail.");
600 return false;
601 }
602
603 if (copyRet == ERR_OK) {
604 return true;
605 }
606
607 napi_value nativeArray = nullptr;
608 napi_create_array(env, &nativeArray);
609 napi_get_named_property(env, nativeValue, "results", &nativeArray);
610 if (nativeArray == nullptr) {
611 HILOG_ERROR("nativeArray is nullptr");
612 return false;
613 }
614
615 uint32_t length = 0;
616 if (napi_get_array_length(env, nativeArray, &length) != napi_ok) {
617 HILOG_ERROR("Get nativeArray length fail");
618 return false;
619 }
620
621 for (uint32_t i = 0; i < length; i++) {
622 napi_value nativeResult = nullptr;
623 napi_get_element(env, nativeArray, i, &nativeResult);
624 if (nativeResult == nullptr) {
625 HILOG_ERROR("get native FileInfo fail.");
626 return false;
627 }
628
629 Result res;
630 bool ret = GetResultByJs(env, nativeResult, res, copyRet);
631 if (ret) {
632 TranslateResult(res);
633 result.push_back(res);
634 }
635 }
636
637 return true;
638 }
639
Copy(const Uri & sourceUri,const Uri & destUri,std::vector<Result> & copyResult,bool force)640 int JsFileAccessExtAbility::Copy(const Uri &sourceUri, const Uri &destUri, std::vector<Result> ©Result,
641 bool force)
642 {
643 UserAccessTracer trace;
644 trace.Start("Copy");
645 auto argParser = [sourceUri, destUri, force](napi_env &env, napi_value *argv, size_t &argc) -> bool {
646 napi_value srcNativeUri = nullptr;
647 napi_create_string_utf8(env, sourceUri.ToString().c_str(), sourceUri.ToString().length(), &srcNativeUri);
648
649 napi_value dstNativeUri = nullptr;
650 napi_create_string_utf8(env, destUri.ToString().c_str(), destUri.ToString().length(), &dstNativeUri);
651
652 napi_value forceCopy = nullptr;
653 napi_get_boolean(env, force, &forceCopy);
654 if (srcNativeUri == nullptr || dstNativeUri == nullptr || forceCopy == nullptr) {
655 HILOG_ERROR("create arguments native js value fail.");
656 return false;
657 }
658 argv[ARGC_ZERO] = srcNativeUri;
659 argv[ARGC_ONE] = dstNativeUri;
660 argv[ARGC_TWO] = forceCopy;
661 argc = ARGC_THREE;
662 return true;
663 };
664
665 int copyRet = EXCEPTION;
666 auto retParser = [©Result, ©Ret](napi_env &env, napi_value result) -> bool {
667 return ParserGetJsResult(env, result, copyResult, copyRet);
668 };
669
670 auto errCode = CallJsMethod("copy", jsRuntime_, jsObj_.get(), argParser, retParser);
671 if (errCode != ERR_OK) {
672 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
673 Result result{ "", "", errCode, "" };
674 TranslateResult(result);
675 copyResult.push_back(result);
676 return EXCEPTION;
677 }
678
679 return copyRet;
680 }
681
CopyFile(const Uri & sourceUri,const Uri & destUri,const std::string & fileName,Uri & newFileUri)682 int JsFileAccessExtAbility::CopyFile(const Uri &sourceUri, const Uri &destUri, const std::string &fileName,
683 Uri &newFileUri)
684 {
685 UserAccessTracer trace;
686 trace.Start("CopyFile");
687 auto value = std::make_shared<Value<std::string>>();
688 if (value == nullptr) {
689 HILOG_ERROR("Move value is nullptr.");
690 return E_GETRESULT;
691 }
692
693 auto argParser = [sourceUri, destUri, fileName](napi_env &env, napi_value *argv, size_t &argc) -> bool {
694 napi_value srcNativeUri = nullptr;
695 napi_create_string_utf8(env, sourceUri.ToString().c_str(), sourceUri.ToString().length(), &srcNativeUri);
696
697 napi_value dstNativeUri = nullptr;
698 napi_create_string_utf8(env, destUri.ToString().c_str(), destUri.ToString().length(), &dstNativeUri);
699
700 napi_value fileNativeName = nullptr;
701 napi_create_string_utf8(env, fileName.c_str(), fileName.length(), &fileNativeName);
702 if (srcNativeUri == nullptr || dstNativeUri == nullptr || fileNativeName == nullptr) {
703 HILOG_ERROR("create arguments native js value fail.");
704 return false;
705 }
706 argv[ARGC_ZERO] = srcNativeUri;
707 argv[ARGC_ONE] = dstNativeUri;
708 argv[ARGC_TWO] = fileNativeName;
709 argc = ARGC_THREE;
710 return true;
711 };
712
713 auto retParser = [value](napi_env &env, napi_value result) -> bool {
714 if (GetUriAndCodeFromJs(env, result, value) != napi_ok) {
715 HILOG_ERROR("Convert js object fail.");
716 return false;
717 }
718 return true;
719 };
720
721 auto errCode = CallJsMethod("copyFileByFileName", jsRuntime_, jsObj_.get(), argParser, retParser);
722 if (errCode != ERR_OK) {
723 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
724 return errCode;
725 }
726
727 if (value->code != ERR_OK) {
728 HILOG_ERROR("fileio fail.");
729 return value->code;
730 }
731
732 if ((value->data).empty()) {
733 HILOG_ERROR("call copyFileByFileName with return empty.");
734 return E_GETRESULT;
735 }
736 newFileUri = Uri(value->data);
737
738 return ERR_OK;
739 }
740
Rename(const Uri & sourceFile,const std::string & displayName,Uri & newFile)741 int JsFileAccessExtAbility::Rename(const Uri &sourceFile, const std::string &displayName, Uri &newFile)
742 {
743 UserAccessTracer trace;
744 trace.Start("Rename");
745 auto value = std::make_shared<Value<std::string>>();
746 if (value == nullptr) {
747 HILOG_ERROR("Rename value is nullptr.");
748 return E_GETRESULT;
749 }
750 auto argParser = [sourceFile, displayName](napi_env &env, napi_value *argv, size_t &argc) -> bool {
751 napi_value nativeSourceFile = nullptr;
752 napi_create_string_utf8(env, sourceFile.ToString().c_str(), sourceFile.ToString().length(), &nativeSourceFile);
753
754 napi_value nativeDisplayName = nullptr;
755 napi_create_string_utf8(env, displayName.c_str(), displayName.length(), &nativeDisplayName);
756 if (nativeSourceFile == nullptr || nativeDisplayName == nullptr) {
757 HILOG_ERROR("create sourceFile uri or displayName native js value fail.");
758 return false;
759 }
760 argv[ARGC_ZERO] = nativeSourceFile;
761 argv[ARGC_ONE] = nativeDisplayName;
762 argc = ARGC_TWO;
763 return true;
764 };
765
766 auto retParser = [value](napi_env &env, napi_value result) -> bool {
767 if (GetUriAndCodeFromJs(env, result, value) != napi_ok) {
768 HILOG_ERROR("Convert js object fail.");
769 return false;
770 }
771 return true;
772 };
773
774 auto errCode = CallJsMethod("rename", jsRuntime_, jsObj_.get(), argParser, retParser);
775 if (errCode != ERR_OK) {
776 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
777 return errCode;
778 }
779
780 if (value->code != ERR_OK) {
781 HILOG_ERROR("fileio fail.");
782 return value->code;
783 }
784
785 if ((value->data).empty()) {
786 HILOG_ERROR("call Rename with return empty.");
787 return E_GETRESULT;
788 }
789 newFile = Uri(value->data);
790 return ERR_OK;
791 }
792
ParserListFileJsResult(napi_env & env,napi_value nativeValue,Value<std::vector<FileInfo>> & result)793 bool JsFileAccessExtAbility::ParserListFileJsResult(napi_env &env, napi_value nativeValue,
794 Value<std::vector<FileInfo>> &result)
795 {
796 napi_value code = nullptr;
797 napi_get_named_property(env, nativeValue, "code", &code);
798 if (napi_get_value_int32(env, code, &result.code) != napi_ok) {
799 HILOG_ERROR("Convert code fail.");
800 return false;
801 }
802
803 napi_value nativeArray = nullptr;
804 napi_create_array(env, &nativeArray);
805 napi_get_named_property(env, nativeValue, "infos", &nativeArray);
806 if (nativeArray == nullptr) {
807 HILOG_ERROR("Convert js array object fail.");
808 return false;
809 }
810
811 uint32_t length = 0;
812 if (napi_get_array_length(env, nativeArray, &length) != napi_ok) {
813 HILOG_ERROR("Get nativeArray length fail.");
814 return false;
815 }
816 for (uint32_t i = 0; i < length; i++) {
817 napi_value nativeFileInfo = nullptr;
818 napi_get_element(env, nativeArray, i, &nativeFileInfo);
819 if (nativeFileInfo == nullptr) {
820 HILOG_ERROR("get native FileInfo fail.");
821 return false;
822 }
823
824 FileInfo fileInfo;
825 if (GetFileInfoFromJs(env, nativeFileInfo, fileInfo) != napi_ok) {
826 HILOG_ERROR("Convert fileInfo js value fail.");
827 return false;
828 }
829
830 result.data.emplace_back(std::move(fileInfo));
831 }
832 return true;
833 }
834
MakeStringNativeArray(napi_env & env,std::vector<std::string> & inputArray,napi_value resultArray)835 int JsFileAccessExtAbility::MakeStringNativeArray(napi_env &env, std::vector<std::string> &inputArray,
836 napi_value resultArray)
837 {
838 if (resultArray == nullptr) {
839 HILOG_ERROR("Create NativeArray nullptr");
840 return E_GETRESULT;
841 }
842
843 for (uint32_t i = 0; i < inputArray.size(); i++) {
844 napi_value nativeValue = nullptr;
845 napi_create_string_utf8(env, inputArray[i].c_str(), inputArray[i].length(), &nativeValue);
846 if (nativeValue == nullptr) {
847 HILOG_ERROR("Create NativeValue fail.");
848 return E_GETRESULT;
849 }
850
851 if (napi_set_element(env, resultArray, i, nativeValue) != napi_ok) {
852 HILOG_ERROR("Add NativeValue to NativeArray fail.");
853 return E_IPCS;
854 }
855 }
856
857 return ERR_OK;
858 }
859
CreateNativeValue(napi_env & env,const FileFilter & filter,struct FileFilterValue & fileFilter)860 int JsFileAccessExtAbility::CreateNativeValue(napi_env &env, const FileFilter &filter,
861 struct FileFilterValue &fileFilter)
862 {
863 napi_create_array_with_length(env, filter.GetSuffix().size(), &fileFilter.suffixArray);
864 CHECK_STATUS_RETURN(fileFilter.suffixArray != nullptr, E_GETRESULT,
865 "Create Suffix native array value fail.");
866
867 std::vector<std::string> suffixVec = filter.GetSuffix();
868 int errorCode = MakeStringNativeArray(env, suffixVec, fileFilter.suffixArray);
869 CHECK_STATUS_RETURN(errorCode == ERR_OK, errorCode,
870 "Create Suffix native array value fail, code:%{public}d.", errorCode);
871
872 napi_create_array_with_length(env, filter.GetDisplayName().size(), &fileFilter.displayNameArray);
873 CHECK_STATUS_RETURN(fileFilter.displayNameArray != nullptr, E_GETRESULT,
874 "Create DisplayName native array value fail.");
875
876 std::vector<std::string> displayNameVec = filter.GetDisplayName();
877 errorCode = MakeStringNativeArray(env, displayNameVec, fileFilter.displayNameArray);
878 CHECK_STATUS_RETURN(errorCode == ERR_OK, errorCode,
879 "Create DisplayName native array value fail, code:%{public}d.", errorCode);
880
881 napi_create_array_with_length(env, filter.GetMimeType().size(), &fileFilter.mimeTypeArray);
882 CHECK_STATUS_RETURN(fileFilter.mimeTypeArray != nullptr, E_GETRESULT,
883 "Create MimeType native array value fail.");
884
885 std::vector<std::string> mimeTypeVec = filter.GetMimeType();
886 errorCode = MakeStringNativeArray(env, mimeTypeVec, fileFilter.mimeTypeArray);
887 CHECK_STATUS_RETURN(errorCode == ERR_OK, errorCode,
888 "Create MimeType native array value fail, code:%{public}d.", errorCode);
889
890 napi_create_int64(env, filter.GetFileSizeOver(), &fileFilter.nativeFileSizeOver);
891 CHECK_STATUS_RETURN(fileFilter.nativeFileSizeOver != nullptr, E_GETRESULT,
892 "Create NativeFileSizeOver native js value fail.");
893
894 napi_create_double(env, filter.GetLastModifiedAfter(), &fileFilter.nativeLastModifiedAfter);
895 CHECK_STATUS_RETURN(fileFilter.nativeLastModifiedAfter != nullptr, E_GETRESULT,
896 "Create NativeLastModifiedAfter native js value fail.");
897
898 napi_get_boolean(env, filter.GetExcludeMedia(), &fileFilter.nativeExcludeMedia);
899 CHECK_STATUS_RETURN(fileFilter.nativeExcludeMedia != nullptr, E_GETRESULT,
900 "Create NativeExcludeMedia native js value fail.");
901
902 return ERR_OK;
903 }
904
MakeJsNativeFileFilter(napi_env & env,const FileFilter & filter,napi_value nativeFilter)905 int JsFileAccessExtAbility::MakeJsNativeFileFilter(napi_env &env, const FileFilter &filter, napi_value nativeFilter)
906 {
907 struct FileFilterValue fileFilter;
908 int ret = CreateNativeValue(env, filter, fileFilter);
909 if (ret != ERR_OK) {
910 return ret;
911 }
912
913 if (napi_set_named_property(env, nativeFilter, "suffix", fileFilter.suffixArray) != napi_ok) {
914 HILOG_ERROR("Set suffix property to Filter NativeValue fail.");
915 return EINVAL;
916 }
917
918 if (napi_set_named_property(env, nativeFilter, "displayName", fileFilter.displayNameArray) != napi_ok) {
919 HILOG_ERROR("Set displayName property to Filter NativeValue fail.");
920 return EINVAL;
921 }
922
923 if (napi_set_named_property(env, nativeFilter, "mimeType", fileFilter.mimeTypeArray) != napi_ok) {
924 HILOG_ERROR("Set mimeType property to Filter NativeValue fail.");
925 return EINVAL;
926 }
927
928 if (napi_set_named_property(env, nativeFilter, "fileSizeOver", fileFilter.nativeFileSizeOver) != napi_ok) {
929 HILOG_ERROR("Set fileSizeOver property to Filter NativeValue fail.");
930 return EINVAL;
931 }
932
933 if (napi_set_named_property(env, nativeFilter, "lastModifiedAfter",
934 fileFilter.nativeLastModifiedAfter) != napi_ok) {
935 HILOG_ERROR("Set lastModifiedAfter property to Filter NativeValue fail.");
936 return EINVAL;
937 }
938
939 if (napi_set_named_property(env, nativeFilter, "excludeMedia", fileFilter.nativeExcludeMedia) != napi_ok) {
940 HILOG_ERROR("Set excludeMedia property to Filter NativeValue fail.");
941 return EINVAL;
942 }
943 return ERR_OK;
944 }
945
BuildFileInfoNumParam(napi_env & env,FileInfoNumParam & param,napi_value * argv,size_t & argc)946 bool JsFileAccessExtAbility::BuildFileInfoNumParam(napi_env &env, FileInfoNumParam ¶m,
947 napi_value *argv, size_t &argc)
948 {
949 napi_value nativeSrcUri = nullptr;
950 napi_create_string_utf8(env, param.sourceFileUri.c_str(), param.sourceFileUri.length(), &nativeSrcUri);
951
952 napi_value nativeFilter = nullptr;
953 if (param.filter.GetHasFilter()) {
954 napi_create_object(env, &nativeFilter);
955 if (nativeFilter == nullptr) {
956 HILOG_ERROR("Create js NativeValue object fail.");
957 return false;
958 }
959 int ret = MakeJsNativeFileFilter(env, param.filter, nativeFilter);
960 if (ret != ERR_OK) {
961 HILOG_ERROR("Make js nativeFilter fail.");
962 return false;
963 }
964 } else {
965 nativeFilter = nullptr;
966 napi_get_null(env, &nativeFilter);
967 if (nativeFilter == nullptr) {
968 HILOG_ERROR("Create js NativeValue null fail.");
969 return false;
970 }
971 }
972
973 napi_value nativeRecursion = nullptr;
974 napi_get_boolean(env, param.recursion, &nativeRecursion);
975 if (nativeSrcUri == nullptr || nativeFilter == nullptr || nativeRecursion == nullptr) {
976 HILOG_ERROR("create arguments native js value fail.");
977 return false;
978 }
979 argv[ARGC_ZERO] = nativeSrcUri;
980 argv[ARGC_ONE] = nativeFilter;
981 argv[ARGC_TWO] = nativeRecursion;
982 argc = ARGC_THREE;
983 return true;
984 }
985
ParserFileInfoNumJsResult(napi_env & env,napi_value & nativeValue,bool & success,uint32_t & counts)986 bool JsFileAccessExtAbility::ParserFileInfoNumJsResult(napi_env &env, napi_value &nativeValue, bool &success,
987 uint32_t &counts)
988 {
989 napi_value nativeSuccess = nullptr;
990 napi_get_named_property(env, nativeValue, "success", &nativeSuccess);
991 if (napi_get_value_bool(env, nativeSuccess, &success) != napi_ok) {
992 HILOG_ERROR("Convert js value fail.");
993 return false;
994 }
995 if (!success) {
996 return false;
997 }
998
999 napi_value nativeCounts = nullptr;
1000 napi_get_named_property(env, nativeValue, "counts", &nativeCounts);
1001 if (napi_get_value_uint32(env, nativeCounts, &counts) != napi_ok) {
1002 HILOG_ERROR("Convert js value fail.");
1003 return false;
1004 }
1005 HILOG_ERROR("left data is counts: %{public}u in storage media", counts);
1006 return true;
1007 }
1008
GetFileInfoNum(const std::string & sourceFileUri,const FileFilter & filter,bool recursion,uint32_t & counts)1009 int JsFileAccessExtAbility::GetFileInfoNum(const std::string &sourceFileUri, const FileFilter &filter, bool recursion,
1010 uint32_t &counts)
1011 {
1012 UserAccessTracer trace;
1013 trace.Start("GetFileInfoNum");
1014 auto argParser = [sourceFileUri, filter, recursion](napi_env &env, napi_value *argv, size_t &argc) -> bool {
1015 struct FileInfoNumParam param = {
1016 sourceFileUri,
1017 filter,
1018 recursion,
1019 };
1020 return BuildFileInfoNumParam(env, param, argv, argc);
1021 };
1022
1023 bool success = false;
1024 auto retParser = [&success, &counts](napi_env &env, napi_value result) -> bool {
1025 return ParserFileInfoNumJsResult(env, result, success, counts);
1026 };
1027
1028 auto errCode = CallJsMethod("getFileInfoNum", jsRuntime_, jsObj_.get(), argParser, retParser);
1029 if (errCode != ERR_OK) {
1030 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
1031 return errCode;
1032 }
1033 return ERR_OK;
1034 }
1035
BuildFilterParam(napi_env & env,const FileFilter & filter,const FilterParam & param,napi_value * argv,size_t & argc)1036 bool JsFileAccessExtAbility::BuildFilterParam(napi_env &env, const FileFilter &filter, const FilterParam ¶m,
1037 napi_value *argv, size_t &argc)
1038 {
1039 string uriStr = param.fileInfo.uri;
1040 napi_value uri = nullptr;
1041 napi_create_string_utf8(env, uriStr.c_str(), uriStr.length(), &uri);
1042 if (uri == nullptr) {
1043 HILOG_ERROR("Create sourceFile uri native js value fail.");
1044 return false;
1045 }
1046
1047 napi_value nativeOffset = nullptr;
1048 napi_create_int64(env, param.offset, &nativeOffset);
1049 if (nativeOffset == nullptr) {
1050 HILOG_ERROR("Create offset native js value fail.");
1051 return false;
1052 }
1053
1054 napi_value nativeMaxCount = nullptr;
1055 napi_create_int64(env, param.maxCount, &nativeMaxCount);
1056 if (nativeMaxCount == nullptr) {
1057 HILOG_ERROR("Create maxCount native js value fail.");
1058 return false;
1059 }
1060
1061 napi_value nativeFilter = nullptr;
1062 if (filter.GetHasFilter()) {
1063 napi_create_object(env, &nativeFilter);
1064 if (nativeFilter == nullptr) {
1065 HILOG_ERROR("Create js NativeValue fail.");
1066 return false;
1067 }
1068 int ret = MakeJsNativeFileFilter(env, filter, nativeFilter);
1069 if (ret != ERR_OK) {
1070 HILOG_ERROR("Create js NativeValue fail.");
1071 return false;
1072 }
1073 } else {
1074 nativeFilter = nullptr;
1075 napi_get_null(env, &nativeFilter);
1076 if (nativeFilter == nullptr) {
1077 HILOG_ERROR("Create js NativeValue fail.");
1078 return false;
1079 }
1080 }
1081
1082 argv[ARGC_ZERO] = uri;
1083 argv[ARGC_ONE] = nativeOffset;
1084 argv[ARGC_TWO] = nativeMaxCount;
1085 argv[ARGC_THREE] = nativeFilter;
1086 argc = ARGC_FOUR;
1087 return true;
1088 }
1089
ListFile(const FileInfo & fileInfo,const int64_t offset,const int64_t maxCount,const FileFilter & filter,std::vector<FileInfo> & fileInfoVec)1090 int JsFileAccessExtAbility::ListFile(const FileInfo &fileInfo, const int64_t offset, const int64_t maxCount,
1091 const FileFilter &filter, std::vector<FileInfo> &fileInfoVec)
1092 {
1093 UserAccessTracer trace;
1094 trace.Start("ListFile");
1095 auto value = std::make_shared<Value<std::vector<FileInfo>>>();
1096 if (value == nullptr) {
1097 HILOG_ERROR("ListFile value is nullptr.");
1098 return E_GETRESULT;
1099 }
1100
1101 auto argParser = [fileInfo, offset, maxCount, filter](napi_env &env, napi_value *argv, size_t &argc) -> bool {
1102 struct FilterParam param;
1103 param.fileInfo = fileInfo;
1104 param.offset = offset;
1105 param.maxCount = maxCount;
1106
1107 return BuildFilterParam(env, filter, param, argv, argc);
1108 };
1109
1110 auto retParser = [this, value](napi_env &env, napi_value result) -> bool {
1111 Value<std::vector<FileInfo>> fileInfo;
1112 bool ret = ParserListFileJsResult(env, result, fileInfo);
1113 if (!ret) {
1114 HILOG_ERROR("Parser js value fail.");
1115 return ret;
1116 }
1117
1118 *value = std::move(fileInfo);
1119 return true;
1120 };
1121
1122 auto errCode = CallJsMethod("listFile", jsRuntime_, jsObj_.get(), argParser, retParser);
1123 if (errCode != ERR_OK) {
1124 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
1125 return errCode;
1126 }
1127
1128 if (value->code != ERR_OK) {
1129 HILOG_ERROR("fileio fail.");
1130 return value->code;
1131 }
1132
1133 fileInfoVec = std::move(value->data);
1134 return ERR_OK;
1135 }
1136
ScanFile(const FileInfo & fileInfo,const int64_t offset,const int64_t maxCount,const FileFilter & filter,std::vector<FileInfo> & fileInfoVec)1137 int JsFileAccessExtAbility::ScanFile(const FileInfo &fileInfo, const int64_t offset, const int64_t maxCount,
1138 const FileFilter &filter, std::vector<FileInfo> &fileInfoVec)
1139 {
1140 UserAccessTracer trace;
1141 trace.Start("ScanFile");
1142 auto value = std::make_shared<Value<std::vector<FileInfo>>>();
1143 if (value == nullptr) {
1144 HILOG_ERROR("ScanFile value is nullptr.");
1145 return E_GETRESULT;
1146 }
1147
1148 auto argParser = [fileInfo, offset, maxCount, filter](napi_env &env, napi_value *argv, size_t &argc) -> bool {
1149 struct FilterParam param;
1150 param.fileInfo = fileInfo;
1151 param.offset = offset;
1152 param.maxCount = maxCount;
1153
1154 return BuildFilterParam(env, filter, param, argv, argc);
1155 };
1156
1157 auto retParser = [value](napi_env &env, napi_value result) -> bool {
1158 Value<std::vector<FileInfo>> fileInfo;
1159 bool ret = ParserListFileJsResult(env, result, fileInfo);
1160 if (!ret) {
1161 HILOG_ERROR("Parser js value fail.");
1162 return ret;
1163 }
1164
1165 *value = std::move(fileInfo);
1166 return true;
1167 };
1168
1169 auto errCode = CallJsMethod("scanFile", jsRuntime_, jsObj_.get(), argParser, retParser);
1170 if (errCode != ERR_OK) {
1171 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
1172 return errCode;
1173 }
1174
1175 if (value->code != ERR_OK) {
1176 HILOG_ERROR("fileio fail.");
1177 return value->code;
1178 }
1179
1180 fileInfoVec = std::move(value->data);
1181 return ERR_OK;
1182 }
1183
ChangeCurrentDir(RootInfo & rootInfo)1184 void ChangeCurrentDir(RootInfo &rootInfo)
1185 {
1186 // 获取用户名
1187 std::string userName;
1188 if (!GetUserName(userName) || userName == "") {
1189 HILOG_WARN("get userName fail");
1190 return;
1191 }
1192 HILOG_DEBUG("GetuserName: %{private}s", userName.c_str());
1193 if (rootInfo.uri.rfind("file://docs/storage/Users/currentUser") == 0) {
1194 rootInfo.uri = "file://docs/storage/Users/" + userName;
1195 }
1196 if (rootInfo.relativePath.rfind("/storage/Users/currentUser") == 0) {
1197 rootInfo.relativePath = "/storage/Users/" + userName;
1198 }
1199 }
1200
ParserGetRootsJsResult(napi_env & env,napi_value nativeValue,Value<std::vector<RootInfo>> & result)1201 bool JsFileAccessExtAbility::ParserGetRootsJsResult(napi_env &env, napi_value nativeValue,
1202 Value<std::vector<RootInfo>> &result)
1203 {
1204 napi_value code = nullptr;
1205 napi_get_named_property(env, nativeValue, "code", &code);
1206 if (napi_get_value_int32(env, code, &result.code) != napi_ok) {
1207 HILOG_ERROR("Get code fail");
1208 return false;
1209 }
1210
1211 napi_value nativeArray = nullptr;
1212 napi_create_array(env, &nativeArray);
1213 napi_get_named_property(env, nativeValue, "roots", &nativeArray);
1214 if (nativeArray == nullptr) {
1215 HILOG_ERROR("nativeArray is nullptr");
1216 return false;
1217 }
1218
1219 uint32_t length = 0;
1220 if (napi_get_array_length(env, nativeArray, &length) != napi_ok) {
1221 HILOG_ERROR("Get nativeArray length fail");
1222 return false;
1223 }
1224
1225 for (uint32_t i = 0; i < length; i++) {
1226 napi_value nativeRootInfo = nullptr;
1227 napi_get_element(env, nativeArray, i, &nativeRootInfo);
1228 if (nativeRootInfo == nullptr) {
1229 HILOG_ERROR("Get native FileInfo fail.");
1230 return false;
1231 }
1232
1233 RootInfo rootInfo;
1234 if (GetRootInfo(env, nativeRootInfo, rootInfo) != napi_ok) {
1235 HILOG_ERROR("Get native rootInfo fail.");
1236 return false;
1237 }
1238
1239 if (IsFullMountEnable()) {
1240 ChangeCurrentDir(rootInfo);
1241 }
1242 result.data.emplace_back(std::move(rootInfo));
1243 }
1244 return true;
1245 }
1246
GetRoots(std::vector<RootInfo> & rootInfoVec)1247 int JsFileAccessExtAbility::GetRoots(std::vector<RootInfo> &rootInfoVec)
1248 {
1249 UserAccessTracer trace;
1250 trace.Start("GetRoots");
1251 auto value = std::make_shared<Value<std::vector<RootInfo>>>();
1252 if (value == nullptr) {
1253 HILOG_ERROR("GetRoots value is nullptr.");
1254 return E_GETRESULT;
1255 }
1256
1257 auto argParser = [](napi_env &env, napi_value *argv, size_t &argc) -> bool {
1258 argc = ARGC_ZERO;
1259 return true;
1260 };
1261
1262 auto retParser = [value](napi_env &env, napi_value result) -> bool {
1263 Value<std::vector<RootInfo>> rootInfoVec;
1264 bool ret = ParserGetRootsJsResult(env, result, rootInfoVec);
1265 if (!ret) {
1266 HILOG_ERROR("Parser js value fail.");
1267 return ret;
1268 }
1269
1270 *value = std::move(rootInfoVec);
1271 return true;
1272 };
1273
1274 auto errCode = CallJsMethod("getRoots", jsRuntime_, jsObj_.get(), argParser, retParser);
1275 if (errCode != ERR_OK) {
1276 HILOG_ERROR("CallJsMethod error, code:%{public}d", errCode);
1277 return errCode;
1278 }
1279
1280 if (value->code != ERR_OK) {
1281 HILOG_ERROR("fileio fail.");
1282 return value->code;
1283 }
1284
1285 rootInfoVec = std::move(value->data);
1286 return ERR_OK;
1287 }
1288
Access(const Uri & uri,bool & isExist)1289 int JsFileAccessExtAbility::Access(const Uri &uri, bool &isExist)
1290 {
1291 UserAccessTracer trace;
1292 trace.Start("Access");
1293 auto value = std::make_shared<Value<bool>>();
1294 if (value == nullptr) {
1295 HILOG_ERROR("Access value is nullptr.");
1296 return E_GETRESULT;
1297 }
1298
1299 auto argParser = [uri](napi_env &env, napi_value *argv, size_t &argc) -> bool {
1300 napi_value nativeUri = nullptr;
1301 napi_create_string_utf8(env, uri.ToString().c_str(), uri.ToString().length(), &nativeUri);
1302 argv[ARGC_ZERO] = nativeUri;
1303 argc = ARGC_ONE;
1304 return true;
1305 };
1306
1307 auto retParser = [value](napi_env &env, napi_value result) -> bool {
1308 napi_value isExist = nullptr;
1309 napi_get_named_property(env, result, "isExist", &isExist);
1310 if (napi_get_value_bool(env, isExist, &value->data) != napi_ok) {
1311 HILOG_ERROR("Convert js value fail.");
1312 return false;
1313 }
1314
1315 napi_value code = nullptr;
1316 napi_get_named_property(env, result, "code", &code);
1317 if (napi_get_value_int32(env, code, &value->code) != napi_ok) {
1318 HILOG_ERROR("Convert js value fail.");
1319 return false;
1320 }
1321 return true;
1322 };
1323
1324 auto errCode = CallJsMethod("access", jsRuntime_, jsObj_.get(), argParser, retParser);
1325 if (errCode != ERR_OK) {
1326 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
1327 return errCode;
1328 }
1329
1330 if (value->code != ERR_OK) {
1331 HILOG_ERROR("fileio fail.");
1332 return value->code;
1333 }
1334
1335 isExist = value->data;
1336 return ERR_OK;
1337 }
1338
ParserQueryFileJsResult(napi_env & env,napi_value nativeValue,Value<std::vector<std::string>> & results)1339 bool JsFileAccessExtAbility::ParserQueryFileJsResult(napi_env &env, napi_value nativeValue,
1340 Value<std::vector<std::string>> &results)
1341 {
1342 napi_value code = nullptr;
1343 napi_get_named_property(env, nativeValue, "code", &code);
1344 if (napi_get_value_int32(env, code, &results.code) != napi_ok) {
1345 HILOG_ERROR("Convert code fail.");
1346 return false;
1347 }
1348
1349 napi_value nativeArray = nullptr;
1350 napi_create_array(env, &nativeArray);
1351 napi_get_named_property(env, nativeValue, "results", &nativeArray);
1352 if (nativeArray == nullptr) {
1353 HILOG_ERROR("Convert js array object fail.");
1354 return false;
1355 }
1356
1357 uint32_t length = 0;
1358 if (napi_get_array_length(env, nativeArray, &length) != napi_ok) {
1359 HILOG_ERROR("Get nativeArray length fail.");
1360 return false;
1361 }
1362 for (uint32_t i = 0; i < length; i++) {
1363 napi_value queryResult = nullptr;
1364 napi_get_element(env, nativeArray, i, &queryResult);
1365 if (queryResult == nullptr) {
1366 HILOG_ERROR("Get native queryResult fail.");
1367 return false;
1368 }
1369
1370 std::string tempValue;
1371 if (GetStringValue(env, queryResult, tempValue) != napi_ok) {
1372 HILOG_ERROR("Convert js value fail.");
1373 return false;
1374 }
1375 results.data.emplace_back(std::move(tempValue));
1376 }
1377 return true;
1378 }
1379
ConvertColumn(std::vector<std::string> & columns)1380 static void ConvertColumn(std::vector<std::string> &columns)
1381 {
1382 for (auto &column : columns) {
1383 for (auto &it : CONVERT_FILE_COLUMN) {
1384 if (column == it.first) {
1385 column = it.second;
1386 }
1387 }
1388 }
1389 }
1390
Query(const Uri & uri,std::vector<std::string> & columns,std::vector<std::string> & results)1391 int JsFileAccessExtAbility::Query(const Uri &uri, std::vector<std::string> &columns, std::vector<std::string> &results)
1392 {
1393 UserAccessTracer trace;
1394 trace.Start("Query");
1395 auto value = std::make_shared<Value<std::vector<std::string>>>();
1396 if (value == nullptr) {
1397 HILOG_ERROR("Query value is nullptr.");
1398 return E_GETRESULT;
1399 }
1400
1401 std::vector<std::string> newColumns = columns;
1402 ConvertColumn(newColumns);
1403 auto argParser = [uri, &newColumns](napi_env &env, napi_value *argv, size_t &argc) -> bool {
1404 if (ConstructQueryArg(env, argv, argc, uri, newColumns) != napi_ok) {
1405 HILOG_ERROR("Construct arg fail.");
1406 return false;
1407 }
1408 return true;
1409 };
1410
1411 auto retParser = [value](napi_env &env, napi_value result) -> bool {
1412 Value<std::vector<std::string>> queryResult;
1413 bool ret = ParserQueryFileJsResult(env, result, queryResult);
1414 if (!ret) {
1415 HILOG_ERROR("Parser js value fail.");
1416 return ret;
1417 }
1418 value->code = queryResult.code;
1419 value->data = queryResult.data;
1420 return ret;
1421 };
1422
1423 auto errCode = CallJsMethod("query", jsRuntime_, jsObj_.get(), argParser, retParser);
1424 if (errCode != ERR_OK) {
1425 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
1426 return errCode;
1427 }
1428
1429 if (value->code != ERR_OK) {
1430 HILOG_ERROR("fileio fail.");
1431 return value->code;
1432 }
1433
1434 results = std::move(value->data);
1435 return ERR_OK;
1436 }
1437
GetFileInfoFromUri(const Uri & selectFile,FileInfo & fileInfo)1438 int JsFileAccessExtAbility::GetFileInfoFromUri(const Uri &selectFile, FileInfo &fileInfo)
1439 {
1440 UserAccessTracer trace;
1441 trace.Start("GetFileInfoFromUri");
1442 auto value = std::make_shared<Value<FileInfo>>();
1443 CHECK_STATUS_RETURN(value != nullptr, E_GETRESULT, "GetFileInfoFromUri value is nullptr.");
1444
1445 auto argParser = [selectFile](napi_env &env, napi_value *argv, size_t &argc) -> bool {
1446 napi_value nativeUri = nullptr;
1447 napi_create_string_utf8(env, selectFile.ToString().c_str(), selectFile.ToString().length(), &nativeUri);
1448 if (nativeUri == nullptr) {
1449 HILOG_ERROR("create selectFile uri native js value fail.");
1450 return false;
1451 }
1452 argv[ARGC_ZERO] = nativeUri;
1453 argc = ARGC_ONE;
1454 return true;
1455 };
1456
1457 auto retParser = [value](napi_env &env, napi_value result) -> bool {
1458 napi_value code = nullptr;
1459 napi_get_named_property(env, result, "code", &code);
1460 if (napi_get_value_int32(env, code, &value->code) != napi_ok) {
1461 HILOG_ERROR("Convert js value fail.");
1462 return false;
1463 }
1464
1465 FileInfo fileInfo;
1466 napi_value nativeFileInfo = nullptr;
1467 if (napi_get_named_property(env, result, "fileInfo", &nativeFileInfo) != napi_ok) {
1468 HILOG_INFO("Convert fileInfo js value failed");
1469 return false;
1470 }
1471
1472 if (GetFileInfoFromJs(env, nativeFileInfo, fileInfo) != napi_ok) {
1473 HILOG_ERROR("Convert fileInfo js value fail.");
1474 return false;
1475 }
1476 value->data = std::move(fileInfo);
1477 return true;
1478 };
1479
1480 auto errCode = CallJsMethod("getFileInfoFromUri", jsRuntime_, jsObj_.get(), argParser, retParser);
1481 CHECK_STATUS_RETURN(errCode == ERR_OK, errCode, "CallJsMethod error, code:%{public}d.", errCode);
1482
1483 CHECK_STATUS_RETURN(value->code == ERR_OK, value->code, "fileio fail.");
1484
1485 fileInfo = std::move(value->data);
1486 return ERR_OK;
1487 }
1488
GetFileInfoFromRelativePath(const std::string & selectFileRealtivePath,FileInfo & fileInfo)1489 int JsFileAccessExtAbility::GetFileInfoFromRelativePath(const std::string &selectFileRealtivePath, FileInfo &fileInfo)
1490 {
1491 UserAccessTracer trace;
1492 trace.Start("GetFileInfoFromRelativePath");
1493 auto value = std::make_shared<Value<FileInfo>>();
1494 CHECK_STATUS_RETURN((value != nullptr), E_GETRESULT, "GetFileInfoFromRelativePath value is nullptr.");
1495
1496 auto argParser = [selectFileRealtivePath](napi_env &env, napi_value *argv, size_t &argc) -> bool {
1497 napi_value nativePath = nullptr;
1498 napi_create_string_utf8(env, selectFileRealtivePath.c_str(), selectFileRealtivePath.length(), &nativePath);
1499 if (nativePath == nullptr) {
1500 HILOG_ERROR("create selectFileRealtivePath native js value fail.");
1501 return false;
1502 }
1503 argv[ARGC_ZERO] = nativePath;
1504 argc = ARGC_ONE;
1505 return true;
1506 };
1507
1508 auto retParser = [value](napi_env &env, napi_value result) -> bool {
1509 napi_value code = nullptr;
1510 napi_get_named_property(env, result, "code", &code);
1511 if (napi_get_value_int32(env, code, &value->code) != napi_ok) {
1512 HILOG_ERROR("Convert js value fail.");
1513 return false;
1514 }
1515
1516 FileInfo fileInfo;
1517 napi_value nativeFileInfo = nullptr;
1518 if (napi_get_named_property(env, result, "fileInfo", &nativeFileInfo) != napi_ok) {
1519 HILOG_INFO("Convert fileInfo js value failed");
1520 return false;
1521 }
1522
1523 if (GetFileInfoFromJs(env, nativeFileInfo, fileInfo) != napi_ok) {
1524 HILOG_ERROR("Convert fileInfo js value fail.");
1525 return false;
1526 }
1527 value->data = std::move(fileInfo);
1528 return true;
1529 };
1530
1531 auto errCode = CallJsMethod("getFileInfoFromRelativePath", jsRuntime_, jsObj_.get(), argParser, retParser);
1532 CHECK_STATUS_RETURN((errCode == ERR_OK), errCode, "CallJsMethod error, code:%{public}d.", errCode);
1533
1534 CHECK_STATUS_RETURN((value->code == ERR_OK), value->code, "fileio fail.");
1535
1536 fileInfo = std::move(value->data);
1537 return ERR_OK;
1538 }
1539
FuncCallback(napi_env env,napi_callback_info info)1540 napi_value JsFileAccessExtAbility::FuncCallback(napi_env env, napi_callback_info info)
1541 {
1542 UserAccessTracer trace;
1543 trace.Start("FuncCallback");
1544 if (env == nullptr) {
1545 HILOG_ERROR("NativeEngine pointer is null.");
1546 return nullptr;
1547 }
1548
1549 if (info == nullptr) {
1550 HILOG_ERROR("invalid param.");
1551 return GetUndefinedValue(env);
1552 }
1553
1554 size_t argc = ARGC_TWO;
1555 napi_value argv[ARGC_TWO] = { nullptr };
1556 napi_status status = napi_get_cb_info(env, info, &argc, argv, nullptr, nullptr);
1557 if (status != napi_ok) {
1558 HILOG_ERROR("napi_get_cb_info fail.");
1559 return GetUndefinedValue(env);
1560 }
1561
1562 if (argc != ARGC_TWO) {
1563 HILOG_ERROR("invalid args.");
1564 return GetUndefinedValue(env);
1565 }
1566
1567 std::string uriString;
1568 if (GetStringValue(env, argv[ARGC_ZERO], uriString) != napi_ok) {
1569 HILOG_ERROR("Get uri fail.");
1570 return GetUndefinedValue(env);
1571 }
1572 int32_t event = UnwrapInt32FromJS(env, argv[ARGC_ONE]);
1573
1574 Uri uri(uriString);
1575 NotifyType notifyType = static_cast<NotifyType>(event);
1576 auto ret = Notify(uri, notifyType);
1577 if (ret != ERR_OK) {
1578 HILOG_ERROR("JsFileAccessExtAbility notify error, ret:%{public}d", ret);
1579 }
1580 return GetUndefinedValue(env);
1581 }
1582
StartWatcher(const Uri & uri)1583 int JsFileAccessExtAbility::StartWatcher(const Uri &uri)
1584 {
1585 UserAccessTracer trace;
1586 trace.Start("StartWatcher");
1587 auto ret = std::make_shared<int>();
1588 if (ret == nullptr) {
1589 HILOG_ERROR("StartWatcher value is nullptr.");
1590 return E_GETRESULT;
1591 }
1592
1593 auto argParser = [uri, this](napi_env &env, napi_value *argv, size_t &argc) -> bool {
1594 napi_value nativeUri = nullptr;
1595 napi_create_string_utf8(env, uri.ToString().c_str(), uri.ToString().length(), &nativeUri);
1596 if (nativeUri == nullptr) {
1597 HILOG_ERROR("create uri native js value fail.");
1598 return false;
1599 }
1600 const std::string funcName = "FuncCallback";
1601 napi_value func = nullptr;
1602 napi_create_function(env, funcName.c_str(), funcName.length(), JsFileAccessExtAbility::FuncCallback, nullptr,
1603 &func);
1604 if (func == nullptr) {
1605 HILOG_ERROR("Create function fail.");
1606 return false;
1607 }
1608 argv[ARGC_ZERO] = nativeUri;
1609 argv[ARGC_ONE] = func;
1610 argc = ARGC_TWO;
1611 return true;
1612 };
1613
1614 auto retParser = [ret](napi_env &env, napi_value result) -> bool {
1615 if (napi_get_value_int32(env, result, ret.get()) != napi_ok) {
1616 HILOG_ERROR("Convert js value fail.");
1617 return false;
1618 }
1619 return true;
1620 };
1621
1622 auto errCode = CallJsMethod("startWatcher", jsRuntime_, jsObj_.get(), argParser, retParser);
1623 if (errCode != ERR_OK) {
1624 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
1625 return errCode;
1626 }
1627
1628 if (*ret != ERR_OK) {
1629 HILOG_ERROR("fileio fail.");
1630 return *ret;
1631 }
1632
1633 return ERR_OK;
1634 }
1635
StopWatcher(const Uri & uri)1636 int JsFileAccessExtAbility::StopWatcher(const Uri &uri)
1637 {
1638 UserAccessTracer trace;
1639 trace.Start("StopWatcher");
1640 auto ret = std::make_shared<int>();
1641 if (ret == nullptr) {
1642 HILOG_ERROR("StopWatcher value is nullptr.");
1643 return E_GETRESULT;
1644 }
1645
1646 auto argParser = [uri](napi_env &env, napi_value *argv, size_t &argc) -> bool {
1647 napi_value nativeUri = nullptr;
1648 napi_create_string_utf8(env, uri.ToString().c_str(), uri.ToString().length(), &nativeUri);
1649 if (nativeUri == nullptr) {
1650 HILOG_ERROR("create uri native js value fail.");
1651 return false;
1652 }
1653
1654 argv[ARGC_ZERO] = nativeUri;
1655 argc = ARGC_ONE;
1656 return true;
1657 };
1658
1659 auto retParser = [ret](napi_env &env, napi_value result) -> bool {
1660 if (napi_get_value_int32(env, result, ret.get()) != napi_ok) {
1661 HILOG_ERROR("Convert js value fail.");
1662 return false;
1663 }
1664 return true;
1665 };
1666
1667 auto errCode = CallJsMethod("stopWatcher", jsRuntime_, jsObj_.get(), argParser, retParser);
1668 if (errCode != ERR_OK) {
1669 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
1670 return errCode;
1671 }
1672
1673 if (*ret != ERR_OK) {
1674 HILOG_ERROR("fileio fail.");
1675 return *ret;
1676 }
1677
1678 return ERR_OK;
1679 }
1680
Notify(Uri & uri,NotifyType notifyType)1681 int JsFileAccessExtAbility::Notify(Uri &uri, NotifyType notifyType)
1682 {
1683 UserAccessTracer trace;
1684 trace.Start("Notify");
1685 auto proxy = FileAccessServiceClient::GetInstance();
1686 if (proxy == nullptr) {
1687 HILOG_ERROR("Notify get SA failed");
1688 return E_LOAD_SA;
1689 }
1690 auto ret = proxy->OnChange(uri, notifyType);
1691 if (ret != ERR_OK) {
1692 HILOG_ERROR("notify error, ret:%{public}d", ret);
1693 return ret;
1694 }
1695 return ERR_OK;
1696 }
1697
GetFileInfoFromJs(napi_env & env,napi_value obj,FileInfo & fileInfo)1698 napi_status JsFileAccessExtAbility::GetFileInfoFromJs(napi_env &env, napi_value obj, FileInfo &fileInfo)
1699 {
1700 napi_value uri = nullptr;
1701 napi_get_named_property(env, obj, "uri", &uri);
1702 if (GetStringValue(env, uri, fileInfo.uri) != napi_ok) {
1703 HILOG_ERROR("Convert uri fail");
1704 return napi_generic_failure;
1705 }
1706
1707 napi_value relativePath = nullptr;
1708 napi_get_named_property(env, obj, "relativePath", &relativePath);
1709 if (GetStringValue(env, relativePath, fileInfo.relativePath) != napi_ok) {
1710 HILOG_ERROR("Convert relativePath fail");
1711 return napi_generic_failure;
1712 }
1713
1714 napi_value fileName = nullptr;
1715 napi_get_named_property(env, obj, "fileName", &fileName);
1716 if (GetStringValue(env, fileName, fileInfo.fileName) != napi_ok) {
1717 HILOG_ERROR("Convert fileName fail");
1718 return napi_generic_failure;
1719 }
1720
1721 napi_value mode = nullptr;
1722 napi_get_named_property(env, obj, "mode", &mode);
1723 if (napi_get_value_int32(env, mode, &fileInfo.mode) != napi_ok) {
1724 HILOG_ERROR("Convert mode fail");
1725 return napi_generic_failure;
1726 }
1727
1728 napi_value size = nullptr;
1729 napi_get_named_property(env, obj, "size", &size);
1730 if (napi_get_value_int64(env, size, &fileInfo.size) != napi_ok) {
1731 HILOG_ERROR("Convert size fail");
1732 return napi_generic_failure;
1733 }
1734
1735 napi_value mtime = nullptr;
1736 napi_get_named_property(env, obj, "mtime", &mtime);
1737 if (napi_get_value_int64(env, mtime, &fileInfo.mtime) != napi_ok) {
1738 HILOG_ERROR("Convert mtime fail");
1739 return napi_generic_failure;
1740 }
1741
1742 napi_value mimeType = nullptr;
1743 napi_get_named_property(env, obj, "mimeType", &mimeType);
1744 if (GetStringValue(env, mimeType, fileInfo.mimeType) != napi_ok) {
1745 HILOG_ERROR("Convert mimeType fail");
1746 return napi_generic_failure;
1747 }
1748
1749 return napi_ok;
1750 }
1751
GetUriAndCodeFromJs(napi_env & env,napi_value result,const std::shared_ptr<Value<std::string>> & value)1752 napi_status JsFileAccessExtAbility::GetUriAndCodeFromJs(napi_env &env, napi_value result,
1753 const std::shared_ptr<Value<std::string>> &value)
1754 {
1755 if (value == nullptr) {
1756 HILOG_ERROR("Value is null.");
1757 return napi_generic_failure;
1758 }
1759 napi_value uri = nullptr;
1760 napi_get_named_property(env, result, "uri", &uri);
1761 if (GetStringValue(env, uri, value->data) != napi_ok) {
1762 HILOG_ERROR("Convert js value fail.");
1763 return napi_generic_failure;
1764 }
1765
1766 napi_value code = nullptr;
1767 napi_get_named_property(env, result, "code", &code);
1768 if (napi_get_value_int32(env, code, &value->code) != napi_ok) {
1769 HILOG_ERROR("Convert js value fail.");
1770 return napi_generic_failure;
1771 }
1772
1773 return napi_ok;
1774 }
1775
GetFdAndCodeFromJs(napi_env & env,napi_value result,const std::shared_ptr<Value<int>> & value)1776 napi_status JsFileAccessExtAbility::GetFdAndCodeFromJs(napi_env &env, napi_value result,
1777 const std::shared_ptr<Value<int>> &value)
1778 {
1779 napi_value fd = nullptr;
1780 napi_get_named_property(env, result, "fd", &fd);
1781 if (value == nullptr) {
1782 HILOG_ERROR("Value is null.");
1783 return napi_generic_failure;
1784 }
1785 if (napi_get_value_int32(env, fd, &value->data) != napi_ok) {
1786 HILOG_ERROR("Convert js value fail.");
1787 return napi_generic_failure;
1788 }
1789
1790 napi_value code = nullptr;
1791 napi_get_named_property(env, result, "code", &code);
1792 if (napi_get_value_int32(env, code, &value->code) != napi_ok) {
1793 HILOG_ERROR("Convert js value fail.");
1794 return napi_generic_failure;
1795 }
1796
1797 return napi_ok;
1798 }
1799
ConstructQueryArg(napi_env & env,napi_value * argv,size_t & argc,const Uri & uri,std::vector<std::string> & columns)1800 napi_status JsFileAccessExtAbility::ConstructQueryArg(napi_env &env, napi_value *argv, size_t &argc, const Uri &uri,
1801 std::vector<std::string> &columns)
1802 {
1803 napi_value nativeUri = nullptr;
1804 napi_create_string_utf8(env, uri.ToString().c_str(), uri.ToString().length(), &nativeUri);
1805 if (nativeUri == nullptr) {
1806 HILOG_ERROR("create uri native js value fail.");
1807 return napi_generic_failure;
1808 }
1809
1810 napi_value resultArray = nullptr;
1811 napi_create_array_with_length(env, columns.size(), &resultArray);
1812 if (resultArray == nullptr) {
1813 HILOG_ERROR("Create MimeType native array value fail.");
1814 return napi_generic_failure;
1815 }
1816 int errorCode = MakeStringNativeArray(env, columns, resultArray);
1817 if (errorCode != ERR_OK) {
1818 HILOG_ERROR("Create native array value fail, code:%{public}d.", errorCode);
1819 return napi_generic_failure;
1820 }
1821 argv[ARGC_ZERO] = nativeUri;
1822 argv[ARGC_ONE] = resultArray;
1823 argc = ARGC_TWO;
1824 return napi_ok;
1825 }
1826
GetRootInfo(napi_env env,napi_value nativeRootInfo,RootInfo & rootInfo)1827 napi_status JsFileAccessExtAbility::GetRootInfo(napi_env env, napi_value nativeRootInfo, RootInfo &rootInfo)
1828 {
1829 napi_value deviceType = nullptr;
1830 napi_get_named_property(env, nativeRootInfo, "deviceType", &deviceType);
1831 if (napi_get_value_int32(env, deviceType, &rootInfo.deviceType) != napi_ok) {
1832 HILOG_ERROR("Get deviceType value fail.");
1833 return napi_generic_failure;
1834 }
1835
1836 napi_value uri = nullptr;
1837 napi_get_named_property(env, nativeRootInfo, "uri", &uri);
1838 if (GetStringValue(env, uri, rootInfo.uri) != napi_ok) {
1839 HILOG_ERROR("Get uri value fail.");
1840 return napi_generic_failure;
1841 }
1842
1843 napi_value relativePath = nullptr;
1844 napi_get_named_property(env, nativeRootInfo, "relativePath", &relativePath);
1845 if (GetStringValue(env, relativePath, rootInfo.relativePath) != napi_ok) {
1846 HILOG_ERROR("Get relativePath value fail.");
1847 return napi_generic_failure;
1848 }
1849
1850 napi_value displayName = nullptr;
1851 napi_get_named_property(env, nativeRootInfo, "displayName", &displayName);
1852 if (GetStringValue(env, displayName, rootInfo.displayName) != napi_ok) {
1853 HILOG_ERROR("Get displayName value fail.");
1854 return napi_generic_failure;
1855 }
1856
1857 napi_value deviceFlags = nullptr;
1858 napi_get_named_property(env, nativeRootInfo, "deviceFlags", &deviceFlags);
1859 if (napi_get_value_int32(env, deviceFlags, &rootInfo.deviceFlags) != napi_ok) {
1860 HILOG_ERROR("Get deviceFlags value fail.");
1861 return napi_generic_failure;
1862 }
1863
1864 return napi_ok;
1865 }
1866
MoveItem(const Uri & sourceFile,const Uri & targetParent,std::vector<Result> & moveResult,bool force)1867 int JsFileAccessExtAbility::MoveItem(const Uri &sourceFile, const Uri &targetParent,
1868 std::vector<Result> &moveResult, bool force)
1869 {
1870 UserAccessTracer trace;
1871 trace.Start("MoveItem");
1872 auto argParser = [sourceFile, targetParent, force](napi_env &env, napi_value *argv, size_t &argc) -> bool {
1873 HILOG_ERROR("MoveItem argParser start");
1874 napi_value srcNativeUri = nullptr;
1875 napi_create_string_utf8(env, sourceFile.ToString().c_str(), sourceFile.ToString().length(), &srcNativeUri);
1876
1877 napi_value dstNativeUri = nullptr;
1878 napi_create_string_utf8(env, targetParent.ToString().c_str(), targetParent.ToString().length(), &dstNativeUri);
1879
1880 napi_value forceMove = nullptr;
1881 napi_get_boolean(env, force, &forceMove);
1882 if (srcNativeUri == nullptr || dstNativeUri == nullptr || forceMove == nullptr) {
1883 HILOG_ERROR("create arguments native js value fail.");
1884 return false;
1885 }
1886 argv[ARGC_ZERO] = srcNativeUri;
1887 argv[ARGC_ONE] = dstNativeUri;
1888 argv[ARGC_TWO] = forceMove;
1889 argc = ARGC_THREE;
1890 return true;
1891 };
1892
1893 int ret = EXCEPTION;
1894 auto retParser = [&moveResult, &ret](napi_env &env, napi_value result) -> bool {
1895 return ParserGetJsResult(env, result, moveResult, ret);
1896 };
1897
1898 auto errCode = CallJsMethod("moveItem", jsRuntime_, jsObj_.get(), argParser, retParser);
1899 if (errCode != ERR_OK) {
1900 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
1901 Result result { "", "", errCode, ""};
1902 TranslateResult(result);
1903 moveResult.push_back(result);
1904 return EXCEPTION;
1905 }
1906
1907 return ret;
1908 }
1909
MoveFile(const Uri & sourceFile,const Uri & targetParent,std::string & fileName,Uri & newFile)1910 int JsFileAccessExtAbility::MoveFile(const Uri &sourceFile, const Uri &targetParent, std::string &fileName,
1911 Uri &newFile)
1912 {
1913 UserAccessTracer trace;
1914 trace.Start("MoveFile");
1915 auto value = std::make_shared<Value<std::string>>();
1916 if (value == nullptr) {
1917 HILOG_ERROR("MoveFile value is nullptr.");
1918 return E_GETRESULT;
1919 }
1920
1921 auto argParser = [sourceFile, targetParent, fileName](napi_env &env, napi_value *argv, size_t &argc) -> bool {
1922 napi_value srcUri = nullptr;
1923 napi_create_string_utf8(env, sourceFile.ToString().c_str(), sourceFile.ToString().length(), &srcUri);
1924 napi_value dstUri = nullptr;
1925 napi_create_string_utf8(env, targetParent.ToString().c_str(), targetParent.ToString().length(), &dstUri);
1926 napi_value name = nullptr;
1927 napi_create_string_utf8(env, fileName.c_str(), fileName.length(), &name);
1928 if (srcUri == nullptr || dstUri == nullptr || name == nullptr) {
1929 HILOG_ERROR("create sourceFile uri native js value fail.");
1930 return false;
1931 }
1932 argv[ARGC_ZERO] = srcUri;
1933 argv[ARGC_ONE] = dstUri;
1934 argv[ARGC_TWO] = name;
1935 argc = ARGC_THREE;
1936 return true;
1937 };
1938
1939 auto retParser = [value](napi_env &env, napi_value result) -> bool {
1940 if (GetUriAndCodeFromJs(env, result, value) != napi_ok) {
1941 HILOG_ERROR("Convert js object fail.");
1942 return false;
1943 }
1944 return true;
1945 };
1946
1947 auto errCode = CallJsMethod("moveFile", jsRuntime_, jsObj_.get(), argParser, retParser);
1948 if (errCode != ERR_OK) {
1949 HILOG_ERROR("CallJsMethod error, code:%{public}d.", errCode);
1950 return errCode;
1951 }
1952
1953 if (value->code != ERR_OK) {
1954 HILOG_ERROR("fileio fail.");
1955 return value->code;
1956 }
1957
1958 if ((value->data).empty()) {
1959 HILOG_ERROR("call move with return empty.");
1960 return E_GETRESULT;
1961 }
1962 newFile = Uri(value->data);
1963 return ERR_OK;
1964 }
1965 } // namespace FileAccessFwk
1966 } // namespace OHOS
1967