diff --git a/interfaces/kits/js/BUILD.gn b/interfaces/kits/js/BUILD.gn index 928421ec07e6f786d2a9ff6dad3b3b5add7f0fcd..128ae892202990a74c6329a320582256462022cf 100644 --- a/interfaces/kits/js/BUILD.gn +++ b/interfaces/kits/js/BUILD.gn @@ -681,6 +681,7 @@ ohos_shared_library("ani_file_fs") { "src/mod_fs/properties", "src/mod_fs/properties/ani", "src/mod_fs/properties/copy_listener", + "src/mod_fs/properties/copy_listener/ani", ] sources = [ "src/common/ani_helper/ani_signature.cpp", @@ -709,7 +710,9 @@ ohos_shared_library("ani_file_fs") { "src/mod_fs/class_stream/fs_stream.cpp", "src/mod_fs/class_stream/stream_instantiator.cpp", "src/mod_fs/class_tasksignal/ani/task_signal_ani.cpp", - "src/mod_fs/class_tasksignal/task_signal_entity_core.cpp", + "src/mod_fs/class_tasksignal/ani/task_signal_listener_ani.cpp", + "src/mod_fs/class_tasksignal/ani/task_signal_wrapper.cpp", + "src/mod_fs/class_tasksignal/fs_task_signal.cpp", "src/mod_fs/class_watcher/ani/fs_watcher_ani.cpp", "src/mod_fs/class_watcher/ani/fs_watcher_wrapper.cpp", "src/mod_fs/class_watcher/ani/watch_event_listener.cpp", @@ -755,6 +758,7 @@ ohos_shared_library("ani_file_fs") { "src/mod_fs/properties/copy_core.cpp", "src/mod_fs/properties/copy_dir_core.cpp", "src/mod_fs/properties/copy_file_core.cpp", + "src/mod_fs/properties/copy_listener/ani/progress_listener_ani.cpp", "src/mod_fs/properties/copy_listener/trans_listener_core.cpp", "src/mod_fs/properties/create_randomaccessfile_core.cpp", "src/mod_fs/properties/create_stream_core.cpp", diff --git a/interfaces/kits/js/src/mod_fs/ani/ets/@ohos.file.fs.ets b/interfaces/kits/js/src/mod_fs/ani/ets/@ohos.file.fs.ets index df9bfb23f058a74a382161bbace8dad9551b51b1..3eb1337782b97c77b4f8cbb537c17be1357f0e0a 100644 --- a/interfaces/kits/js/src/mod_fs/ani/ets/@ohos.file.fs.ets +++ b/interfaces/kits/js/src/mod_fs/ani/ets/@ohos.file.fs.ets @@ -1263,20 +1263,29 @@ export type ProgressListener = (progress: Progress) => void; export class TaskSignal { private nativeTaskSignal: long = 0; + private native onCancelNative(): void; - private onCancelResolve: (path: string) => void = (path: string): void => {}; + + private onCancelResolve: (path: string) => void; private onCancelCallback(path: string): void { if (this.onCancelResolve) { this.onCancelResolve(path); } } + native cancel(): void; + onCancel(): Promise { - return new Promise((resolve: (path: string) => void, reject: (e: BusinessError) => void): void => { + return new Promise((resolve: (result: string) => void, reject: (e: BusinessError) => void): void => { this.onCancelResolve = resolve; - this.onCancelNative(); + try { + this.onCancelNative(); + } catch (e: BusinessError) { + reject(e); + } }); } + } export interface CopyOptions { diff --git a/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_ani.cpp b/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_ani.cpp index f22a814f94d56868bfe4f8051093be06a053930e..2b1229a6947fdefd5f18346d83760f2ca312781e 100644 --- a/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_ani.cpp +++ b/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_ani.cpp @@ -19,7 +19,8 @@ #include "copy_core.h" #include "error_handler.h" #include "filemgmt_libhilog.h" -#include "task_signal_entity_core.h" +#include "fs_task_signal.h" +#include "task_signal_wrapper.h" #include "type_converter.h" namespace OHOS { @@ -29,84 +30,40 @@ namespace ANI { using namespace std; using namespace OHOS::FileManagement::ModuleFileIO; -static TaskSignalEntityCore *Unwrap(ani_env *env, ani_object object) -{ - ani_long entity; - auto ret = env->Object_GetFieldByName_Long(object, "nativeTaskSignal", &entity); - if (ret != ANI_OK) { - HILOGE("Unwrap taskSignalEntityCore err: %{private}d", ret); - return nullptr; - } - return reinterpret_cast(entity); -} - void TaskSignalAni::Cancel(ani_env *env, [[maybe_unused]] ani_object object) { - auto entity = Unwrap(env, object); - if (entity == nullptr) { + FsTaskSignal *copySignal = TaskSignalWrapper::Unwrap(env, object); + if (copySignal == nullptr) { + HILOGE("Cannot unwrap copySignal!"); ErrorHandler::Throw(env, EINVAL); return; } - if (entity->taskSignal_ == nullptr) { - HILOGE("Failed to get watcherEntity when stop."); - ErrorHandler::Throw(env, EINVAL); - return; - } - - auto ret = entity->taskSignal_->Cancel(); - if (ret != NO_ERROR) { - HILOGE("Failed to cancel the task."); - ErrorHandler::Throw(env, CANCEL_ERR); + auto ret = copySignal->Cancel(); + if (!ret.IsSuccess()) { + HILOGE("Cannot Cancel!"); + const auto &err = ret.GetError(); + ErrorHandler::Throw(env, err); return; } } void TaskSignalAni::OnCancel(ani_env *env, [[maybe_unused]] ani_object object) { - auto entity = Unwrap(env, object); - if (entity == nullptr) { + FsTaskSignal *copySignal = TaskSignalWrapper::Unwrap(env, object); + if (copySignal == nullptr) { + HILOGE("Cannot unwrap copySignal!"); ErrorHandler::Throw(env, EINVAL); return; } - if (entity->taskSignal_ == nullptr) { - HILOGE("Failed to get watcherEntity when stop."); - ErrorHandler::Throw(env, EINVAL); - return; - } - - ani_ref globalObj; - auto status = env->GlobalReference_Create(object, &globalObj); - if (status != ANI_OK) { - HILOGE("GlobalReference_Create, err: %{private}d", status); + auto ret = copySignal->OnCancel(); + if (!ret.IsSuccess()) { + HILOGE("Cannot Cancel!"); + const auto &err = ret.GetError(); + ErrorHandler::Throw(env, err); return; } - ani_vm *vm = nullptr; - env->GetVM(&vm); - auto cb = [vm, &globalObj](string filePath) -> void { - auto env = AniHelper::GetThreadEnv(vm); - if (env == nullptr) { - HILOGE("failed to GetThreadEnv"); - return; - } - - // std::vector vec; - auto [succPath, path] = TypeConverter::ToAniString(env, filePath); - if (!succPath) { - HILOGE("ToAniString failed"); - return; - } - - auto ret = env->Object_CallMethodByName_Void(static_cast(globalObj), - "onCancelCallback", nullptr, path); - if (ret != ANI_OK) { - HILOGE("Call onCancelCallback failed, err: %{private}d", ret); - return; - } - }; - auto callbackContext = std::make_shared(cb); - entity->callbackContextCore_ = callbackContext; - entity->taskSignal_->SetTaskSignalListener(entity); } + } // namespace ANI } // namespace ModuleFileIO } // namespace FileManagement diff --git a/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_ani.h b/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_ani.h index 6db3301ce5973d5a3605120510c340ee6dff2e2f..d27e5253882fa7fae16a068317cf914a75a03202 100644 --- a/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_ani.h +++ b/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_ani.h @@ -13,8 +13,8 @@ * limitations under the License. */ -#ifndef FILEMANAGEMENT_FILE_API_TASK_SIGNAL_ANI_H -#define FILEMANAGEMENT_FILE_API_TASK_SIGNAL_ANI_H +#ifndef INTERFACES_KITS_JS_SRC_MOD_FS_CLASS_TASKSIGNAL_ANI_TASK_SIGNAL_ANI_H +#define INTERFACES_KITS_JS_SRC_MOD_FS_CLASS_TASKSIGNAL_ANI_TASK_SIGNAL_ANI_H #include @@ -22,13 +22,15 @@ namespace OHOS { namespace FileManagement { namespace ModuleFileIO { namespace ANI { + class TaskSignalAni final { public: static void Cancel(ani_env *env, [[maybe_unused]] ani_object object); static void OnCancel(ani_env *env, [[maybe_unused]] ani_object object); }; + } // namespace ANI } // namespace ModuleFileIO } // namespace FileManagement } // namespace OHOS -#endif // FILEMANAGEMENT_FILE_API_TASK_SIGNAL_ANI_H \ No newline at end of file +#endif // INTERFACES_KITS_JS_SRC_MOD_FS_CLASS_TASKSIGNAL_ANI_TASK_SIGNAL_ANI_H \ No newline at end of file diff --git a/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_listener_ani.cpp b/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_listener_ani.cpp new file mode 100644 index 0000000000000000000000000000000000000000..a80010e9599dfbae9276413eaa6e15ed6308420a --- /dev/null +++ b/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_listener_ani.cpp @@ -0,0 +1,63 @@ +/* + * Copyright (c) 2025 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "task_signal_listener_ani.h" + +#include +#include "ani_helper.h" +#include "ani_signature.h" +#include "file_utils.h" +#include "filemgmt_libhilog.h" +#include "type_converter.h" + +namespace OHOS::FileManagement::ModuleFileIO::ANI { +using namespace std; +using namespace OHOS::FileManagement::ModuleFileIO::ANI::AniSignature; + +void TaskSignalListenerAni::OnCancel() +{ + auto filepath = taskSignal->filePath_; + auto task = [this, filepath]() { SendCancelEvent(filepath); }; + AniHelper::SendEventToMainThread(task); +} + +void TaskSignalListenerAni::SendCancelEvent(const string &filepath) const +{ + if (vm == nullptr) { + HILOGE("Cannot send cancel event because the vm is null."); + return; + } + if (signalObj == nullptr) { + HILOGE("Cannot send cancel event because the signalObj is null."); + return; + } + ani_env *env = AniHelper::GetThreadEnv(vm); + if (env == nullptr) { + HILOGE("Cannot send cancel event because the env is null."); + return; + } + auto [succ, aniPath] = TypeConverter::ToAniString(env, filepath); + if (!succ) { + HILOGE("Cannot convert filepath to ani string!"); + return; + } + auto ret = env->Object_CallMethodByName_Void(signalObj, "onCancelCallback", nullptr, aniPath); + if (ret != ANI_OK) { + HILOGE("Call onCancelCallback failed, err: %{private}d", ret); + return; + } +} + +} // namespace OHOS::FileManagement::ModuleFileIO::ANI diff --git a/interfaces/kits/js/src/mod_fs/class_tasksignal/task_signal_entity_core.h b/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_listener_ani.h similarity index 47% rename from interfaces/kits/js/src/mod_fs/class_tasksignal/task_signal_entity_core.h rename to interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_listener_ani.h index c301442c797799d4478a5829ad1241360c25a2cf..a11be571bade149138769b35292ac5f73392ab07 100644 --- a/interfaces/kits/js/src/mod_fs/class_tasksignal/task_signal_entity_core.h +++ b/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_listener_ani.h @@ -13,34 +13,35 @@ * limitations under the License. */ -#ifndef FILEMANAGEMENT_FILE_API_TASK_SIGNAL_ENTITY_CORE_H -#define FILEMANAGEMENT_FILE_API_TASK_SIGNAL_ENTITY_CORE_H +#ifndef INTERFACES_KITS_JS_SRC_MOD_FS_CLASS_TASKSIGNAL_ANI_TASK_SIGNAL_LISTENER_ANI_H +#define INTERFACES_KITS_JS_SRC_MOD_FS_CLASS_TASKSIGNAL_ANI_TASK_SIGNAL_LISTENER_ANI_H -#include "task_signal.h" +#include #include "task_signal_listener.h" +#include "task_signal.h" -namespace OHOS::FileManagement::ModuleFileIO { +namespace OHOS::FileManagement::ModuleFileIO::ANI { using namespace DistributedFS::ModuleTaskSignal; -typedef std::function TaskSignalCb; -class CallbackContextCore { +class TaskSignalListenerAni : public TaskSignalListener { public: - explicit CallbackContextCore(TaskSignalCb cb) : cb(cb) {} - ~CallbackContextCore() = default; - - TaskSignalCb cb; - std::string filePath_; -}; + TaskSignalListenerAni(ani_vm *vm, const ani_object &signalObj, std::shared_ptr taskSignal) + : vm(vm), signalObj(signalObj), taskSignal(taskSignal) {} + void OnCancel() override; -class TaskSignalEntityCore : public TaskSignalListener { public: - TaskSignalEntityCore() = default; - ~TaskSignalEntityCore() override; - void OnCancel() override; + TaskSignalListenerAni() = default; + ~TaskSignalListenerAni() = default; - std::shared_ptr taskSignal_ = nullptr; - std::shared_ptr callbackContextCore_ = nullptr; +private: + void SendCancelEvent(const std::string &filepath) const; + +private: + ani_vm *vm; + ani_object signalObj; + std::shared_ptr taskSignal; }; -} // namespace OHOS::FileManagement::ModuleFileIO -#endif // FILEMANAGEMENT_FILE_API_TASK_SIGNAL_ENTITY_CORE_H \ No newline at end of file +} // namespace OHOS::FileManagement::ModuleFileIO::ANI + +#endif // INTERFACES_KITS_JS_SRC_MOD_FS_CLASS_TASKSIGNAL_ANI_TASK_SIGNAL_LISTENER_ANI_H \ No newline at end of file diff --git a/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_wrapper.cpp b/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_wrapper.cpp new file mode 100644 index 0000000000000000000000000000000000000000..79be6423190c34796a9b015ac57405afc7f0bda5 --- /dev/null +++ b/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_wrapper.cpp @@ -0,0 +1,71 @@ +/* + * Copyright (c) 2025 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "task_signal_wrapper.h" + +#include "ani_signature.h" +#include "error_handler.h" +#include "filemgmt_libhilog.h" +#include "fs_task_signal.h" +#include "type_converter.h" + +namespace OHOS { +namespace FileManagement { +namespace ModuleFileIO { +namespace ANI { +using namespace std; +using namespace OHOS::FileManagement::ModuleFileIO; +using namespace OHOS::FileManagement::ModuleFileIO::ANI::AniSignature; + +FsTaskSignal *TaskSignalWrapper::Unwrap(ani_env *env, ani_object object) +{ + ani_long nativePtr; + auto status = env->Object_GetFieldByName_Long(object, "nativeTaskSignal", &nativePtr); + if (status != ANI_OK) { + HILOGE("Unwrap taskSignal obj failed! status: %{public}d", status); + return nullptr; + } + uintptr_t ptrValue = static_cast(nativePtr); + FsTaskSignal *copySignal = reinterpret_cast(ptrValue); + return copySignal; +} + +bool TaskSignalWrapper::Wrap(ani_env *env, ani_object object, const FsTaskSignal *signal) +{ + if (object == nullptr) { + HILOGE("TaskSignal obj is null!"); + return false; + } + + if (signal == nullptr) { + HILOGE("FsTaskSignal pointer is null!"); + return false; + } + + ani_long ptr = static_cast(reinterpret_cast(signal)); + + auto status = env->Object_SetFieldByName_Long(object, "nativeTaskSignal", ptr); + if (status != ANI_OK) { + HILOGE("Wrap taskSignal obj failed! status: %{public}d", status); + return false; + } + + return true; +} + +} // namespace ANI +} // namespace ModuleFileIO +} // namespace FileManagement +} // namespace OHOS \ No newline at end of file diff --git a/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_wrapper.h b/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_wrapper.h new file mode 100644 index 0000000000000000000000000000000000000000..2cfd04e4dafdef7c32aad7681a457addff5768b1 --- /dev/null +++ b/interfaces/kits/js/src/mod_fs/class_tasksignal/ani/task_signal_wrapper.h @@ -0,0 +1,37 @@ +/* + * Copyright (c) 2025 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef INTERFACES_KITS_JS_SRC_MOD_FS_CLASS_TASKSIGNAL_ANI_TASK_SIGNAL_WRAPPER_H +#define INTERFACES_KITS_JS_SRC_MOD_FS_CLASS_TASKSIGNAL_ANI_TASK_SIGNAL_WRAPPER_H + +#include +#include "fs_task_signal.h" + +namespace OHOS { +namespace FileManagement { +namespace ModuleFileIO { +namespace ANI { + +class TaskSignalWrapper final { +public: + static FsTaskSignal *Unwrap(ani_env *env, ani_object object); + static bool Wrap(ani_env *env, ani_object object, const FsTaskSignal *signal); +}; + +} // namespace ANI +} // namespace ModuleFileIO +} // namespace FileManagement +} // namespace OHOS +#endif // INTERFACES_KITS_JS_SRC_MOD_FS_CLASS_TASKSIGNAL_ANI_TASK_SIGNAL_WRAPPER_H \ No newline at end of file diff --git a/interfaces/kits/js/src/mod_fs/class_tasksignal/fs_task_signal.cpp b/interfaces/kits/js/src/mod_fs/class_tasksignal/fs_task_signal.cpp new file mode 100644 index 0000000000000000000000000000000000000000..d9b4b6ffe4608122c64ec35f99b2a6f6e1b598d2 --- /dev/null +++ b/interfaces/kits/js/src/mod_fs/class_tasksignal/fs_task_signal.cpp @@ -0,0 +1,79 @@ +/* + * Copyright (c) 2025 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "fs_task_signal.h" + +#include "file_utils.h" +#include "filemgmt_libhilog.h" +#include "fs_utils.h" + +namespace OHOS { +namespace FileManagement { +namespace ModuleFileIO { +using namespace std; + +FsResult> FsTaskSignal::Constructor( + shared_ptr taskSignal, shared_ptr signalListener) +{ + if (!taskSignal) { + HILOGE("Invalid taskSignal"); + return FsResult>::Error(EINVAL); + } + if (!signalListener) { + HILOGE("Invalid signalListener"); + return FsResult>::Error(EINVAL); + } + auto copySignal = CreateSharedPtr(); + if (copySignal == nullptr) { + HILOGE("Failed to request heap memory."); + return FsResult>::Error(ENOMEM); + } + copySignal->taskSignal_ = move(taskSignal); + copySignal->signalListener_ = move(signalListener); + return FsResult>::Success(copySignal); +} + +FsResult FsTaskSignal::Cancel() +{ + if (taskSignal_ == nullptr) { + HILOGE("Failed to get taskSignal"); + return FsResult::Error(EINVAL); + } + auto ret = taskSignal_->Cancel(); + if (ret != ERRNO_NOERR) { + HILOGE("Failed to cancel the task."); + return FsResult::Error(CANCEL_ERR); + } + return FsResult::Success(); +} + +FsResult FsTaskSignal::OnCancel() +{ + if (taskSignal_ == nullptr) { + HILOGE("Failed to get taskSignal"); + return FsResult::Error(EINVAL); + } + taskSignal_->SetTaskSignalListener(signalListener_.get()); + return FsResult::Success(); +} + +shared_ptr FsTaskSignal::GetTaskSignal() const +{ + return taskSignal_; +} + +} // namespace ModuleFileIO +} // namespace FileManagement +} // namespace OHOS \ No newline at end of file diff --git a/interfaces/kits/js/src/mod_fs/class_tasksignal/fs_task_signal.h b/interfaces/kits/js/src/mod_fs/class_tasksignal/fs_task_signal.h new file mode 100644 index 0000000000000000000000000000000000000000..33161108c3b9c231d61d346682654c80fc97094d --- /dev/null +++ b/interfaces/kits/js/src/mod_fs/class_tasksignal/fs_task_signal.h @@ -0,0 +1,50 @@ +/* + * Copyright (c) 2025 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef INTERFACES_KITS_JS_SRC_MOD_FS_CLASS_TASKSIGNAL_FS_TASK_SIGNAL_H +#define INTERFACES_KITS_JS_SRC_MOD_FS_CLASS_TASKSIGNAL_FS_TASK_SIGNAL_H + +#include "filemgmt_libfs.h" +#include "task_signal.h" + +namespace OHOS { +namespace FileManagement { +namespace ModuleFileIO { +using namespace std; +using namespace DistributedFS::ModuleTaskSignal; + +class FsTaskSignal { +public: + static FsResult> Constructor( + shared_ptr taskSignal, shared_ptr signalListener); + FsResult Cancel(); + FsResult OnCancel(); + shared_ptr GetTaskSignal() const; + +public: + FsTaskSignal() = default; + ~FsTaskSignal() = default; + FsTaskSignal(const FsTaskSignal &other) = delete; + FsTaskSignal &operator=(const FsTaskSignal &other) = delete; + +private: + shared_ptr taskSignal_ = nullptr; + shared_ptr signalListener_ = nullptr; +}; + +} // namespace ModuleFileIO +} // namespace FileManagement +} // namespace OHOS +#endif // INTERFACES_KITS_JS_SRC_MOD_FS_CLASS_TASKSIGNAL_FS_TASK_SIGNAL_H \ No newline at end of file diff --git a/interfaces/kits/js/src/mod_fs/properties/ani/copy_ani.cpp b/interfaces/kits/js/src/mod_fs/properties/ani/copy_ani.cpp index e086c5ee1f53cae4857b4f4e45f2a36547eb1db7..7e84bce8fa66de87b066d372c4b9b4481a4f008c 100644 --- a/interfaces/kits/js/src/mod_fs/properties/ani/copy_ani.cpp +++ b/interfaces/kits/js/src/mod_fs/properties/ani/copy_ani.cpp @@ -21,6 +21,10 @@ #include "error_handler.h" #include "file_utils.h" #include "filemgmt_libhilog.h" +#include "fs_task_signal.h" +#include "progress_listener_ani.h" +#include "task_signal_listener_ani.h" +#include "task_signal_wrapper.h" #include "type_converter.h" namespace OHOS { @@ -31,112 +35,100 @@ using namespace std; using namespace OHOS::FileManagement::ModuleFileIO; using namespace OHOS::FileManagement::ModuleFileIO::ANI::AniSignature; -static void SetProgressListenerCb(ani_env *env, ani_ref &callback, CopyOptions &opts) +static bool ParseListenerFromOptionArg(ani_env *env, const ani_object &options, CopyOptions &opts) { + ani_ref prog; + if (ANI_OK != env->Object_GetPropertyByName_Ref(options, "progressListener", &prog)) { + HILOGE("Illegal options.progressListener type"); + return false; + } + + ani_boolean isUndefined = true; + env->Reference_IsUndefined(prog, &isUndefined); + if (isUndefined) { + return true; + } + + ani_ref cbRef; + if (ANI_OK != env->GlobalReference_Create(prog, &cbRef)) { + HILOGE("Illegal options.progressListener type"); + return false; + } + ani_vm *vm = nullptr; env->GetVM(&vm); + auto listener = CreateSharedPtr(vm, cbRef); + if (listener == nullptr) { + HILOGE("Failed to request heap memory."); + return false; + } - opts.listenerCb = [vm, &callback](uint64_t progressSize, uint64_t totalSize) -> void { - ani_status ret; - ani_object progress = {}; - auto classDesc = FS::ProgressInner::classDesc.c_str(); - ani_class cls; - - auto env = AniHelper::GetThreadEnv(vm); - if (env == nullptr) { - HILOGE("failed to GetThreadEnv"); - return; - } - - if (progressSize > MAX_VALUE || totalSize > MAX_VALUE) { - HILOGE("progressSize or totalSize exceed MAX_VALUE: %{private}" PRIu64 " %{private}" PRIu64, progressSize, - totalSize); - } - - if ((ret = env->FindClass(classDesc, &cls)) != ANI_OK) { - HILOGE("Not found %{private}s, err: %{private}d", classDesc, ret); - return; - } - - auto ctorDesc = FS::ProgressInner::ctorDesc.c_str(); - auto ctorSig = FS::ProgressInner::ctorSig.c_str(); - ani_method ctor; - if ((ret = env->Class_FindMethod(cls, ctorDesc, ctorSig, &ctor)) != ANI_OK) { - HILOGE("Not found ctor, err: %{private}d", ret); - return; - } - - if ((ret = env->Object_New(cls, ctor, &progress, ani_double(static_cast(progressSize)), - ani_double(static_cast(totalSize)))) != ANI_OK) { - HILOGE("New ProgressInner Fail, err: %{private}d", ret); - return; - } - - std::vector vec; - vec.push_back(progress); - ani_ref result; - ret = env->FunctionalObject_Call(static_cast(callback), vec.size(), vec.data(), &result); - if (ret != ANI_OK) { - HILOGE("FunctionalObject_Call, err: %{private}d", ret); - return; - } - }; + opts.progressListener = move(listener); + return true; } -static bool SetTaskSignal(ani_env *env, ani_ref ©Signal, CopyOptions &opts) +static bool ParseCopySignalFromOptionArg(ani_env *env, const ani_object &options, CopyOptions &opts) { - ani_status ret; - auto taskSignalEntityCore = CreateSharedPtr(); - if (taskSignalEntityCore == nullptr) { + ani_ref prog; + if (ANI_OK != env->Object_GetPropertyByName_Ref(options, "copySignal", &prog)) { + HILOGE("Illegal options.CopySignal type"); + return false; + } + + ani_boolean isUndefined = true; + env->Reference_IsUndefined(prog, &isUndefined); + if (isUndefined) { + return true; + } + + auto taskSignal = CreateSharedPtr(); + if (taskSignal == nullptr) { HILOGE("Failed to request heap memory."); return false; } - ret = env->Object_SetFieldByName_Long(static_cast(copySignal), "nativeTaskSignal", - reinterpret_cast(taskSignalEntityCore.get())); - if (ret != ANI_OK) { - HILOGE("Object set nativeTaskSignal err: %{private}d", ret); + auto signalObj = static_cast(prog); + ani_vm *vm = nullptr; + env->GetVM(&vm); + auto listener = CreateSharedPtr(vm, signalObj, taskSignal); + if (listener == nullptr) { + HILOGE("Failed to request heap memory."); return false; } - taskSignalEntityCore->taskSignal_ = std::make_shared(); - opts.taskSignalEntityCore = move(taskSignalEntityCore); + auto result = FsTaskSignal::Constructor(taskSignal, listener); + if (!result.IsSuccess()) { + return false; + } + auto copySignal = result.GetData().value(); + auto succ = TaskSignalWrapper::Wrap(env, signalObj, copySignal.get()); + if (!succ) { + return false; + } + + opts.copySignal = move(copySignal); return true; } -static tuple> ParseOptions(ani_env *env, ani_ref &cb, ani_object &options) +static tuple> ParseOptions(ani_env *env, ani_object &options) { ani_boolean isUndefined; - ani_status ret; env->Reference_IsUndefined(options, &isUndefined); if (isUndefined) { return { true, nullopt }; } CopyOptions opts; - ani_ref prog; - if ((ret = env->Object_GetPropertyByName_Ref(options, "progressListener", &prog)) != ANI_OK) { - HILOGE("Object_GetPropertyByName_Ref progressListener, err: %{private}d", ret); + auto succ = ParseListenerFromOptionArg(env, options, opts); + if (!succ) { return { false, nullopt }; } - env->Reference_IsUndefined(prog, &isUndefined); - if (!isUndefined) { - env->GlobalReference_Create(prog, &cb); - SetProgressListenerCb(env, cb, opts); - } - ani_ref signal; - if ((ret = env->Object_GetPropertyByName_Ref(options, "copySignal", &signal)) != ANI_OK) { - HILOGE("Object_GetPropertyByName_Ref copySignal, err: %{private}d", ret); + succ = ParseCopySignalFromOptionArg(env, options, opts); + if (!succ) { return { false, nullopt }; } - env->Reference_IsUndefined(signal, &isUndefined); - if (!isUndefined) { - if (!SetTaskSignal(env, signal, opts)) { - return { false, nullopt }; - } - } return { true, make_optional(move(opts)) }; } @@ -146,24 +138,15 @@ void CopyAni::CopySync( { auto [succSrc, src] = TypeConverter::ToUTF8String(env, srcUri); auto [succDest, dest] = TypeConverter::ToUTF8String(env, destUri); - if (!succSrc || !succDest) { - HILOGE("The first/second argument requires filepath"); - ErrorHandler::Throw(env, EINVAL); - return; - } + auto [succOpts, opts] = ParseOptions(env, options); - ani_ref cb; - auto [succOpts, opts] = ParseOptions(env, cb, options); - if (!succOpts) { - HILOGE("Failed to parse opts"); - ErrorHandler::Throw(env, EINVAL); + if (!succSrc || !succDest || !succOpts) { + HILOGE("The first/second/third argument requires uri/uri/napi_function"); + ErrorHandler::Throw(env, E_PARAMS); return; } auto ret = CopyCore::DoCopy(src, dest, opts); - if (opts.has_value() && opts->listenerCb != nullptr) { - env->GlobalReference_Delete(cb); - } if (!ret.IsSuccess()) { HILOGE("DoCopy failed!"); const FsError &err = ret.GetError(); diff --git a/interfaces/kits/js/src/mod_fs/properties/copy_core.cpp b/interfaces/kits/js/src/mod_fs/properties/copy_core.cpp index f3d4613d75db7edeb16a31c7f39ba772ddd0c0f3..45403ca6d82752fcac6b36e2cf72b2f063305337 100644 --- a/interfaces/kits/js/src/mod_fs/properties/copy_core.cpp +++ b/interfaces/kits/js/src/mod_fs/properties/copy_core.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2023-2024 Huawei Device Co., Ltd. + * Copyright (c) 2025 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -60,25 +60,9 @@ constexpr int BUF_SIZE = 1024; constexpr size_t MAX_SIZE = 1024 * 1024 * 4; constexpr std::chrono::milliseconds NOTIFY_PROGRESS_DELAY(300); std::recursive_mutex CopyCore::mutex_; -std::map> CopyCore::jsCbMap_; +std::map> CopyCore::callbackMap_; -static string GetModeFromFlags(unsigned int flags) -{ - const string readMode = "r"; - const string writeMode = "w"; - const string appendMode = "a"; - const string truncMode = "t"; - string mode = readMode; - mode += (((flags & O_RDWR) == O_RDWR) ? writeMode : ""); - mode = (((flags & O_WRONLY) == O_WRONLY) ? writeMode : mode); - if (mode != readMode) { - mode += ((flags & O_TRUNC) ? truncMode : ""); - mode += ((flags & O_APPEND) ? appendMode : ""); - } - return mode; -} - -static int OpenSrcFile(const string &srcPth, std::shared_ptr infos, int32_t &srcFd) +static int OpenSrcFile(const string &srcPth, std::shared_ptr infos, int32_t &srcFd) { Uri uri(infos->srcUri); if (uri.GetAuthority() == MEDIA) { @@ -93,7 +77,7 @@ static int OpenSrcFile(const string &srcPth, std::shared_ptr info HILOGE("Failed to connect to datashare"); return E_PERMISSION; } - srcFd = dataShareHelper->OpenFile(uri, GetModeFromFlags(O_RDONLY)); + srcFd = dataShareHelper->OpenFile(uri, FsUtils::GetModeFromFlags(O_RDONLY)); if (srcFd < 0) { HILOGE("Open media uri by data share fail. ret = %{public}d", srcFd); return EPERM; @@ -108,18 +92,17 @@ static int OpenSrcFile(const string &srcPth, std::shared_ptr info return ERRNO_NOERR; } -static int SendFileCore(std::unique_ptr srcFdg, - std::unique_ptr destFdg, - std::shared_ptr infos) +static int SendFileCore(std::unique_ptr srcFdg, std::unique_ptr destFdg, + std::shared_ptr infos) { - std::unique_ptr sendFileReq = { - new (nothrow) uv_fs_t, FsUtils::FsReqCleanup }; + std::unique_ptr sendFileReq = { new (nothrow) uv_fs_t, + FsUtils::FsReqCleanup }; if (sendFileReq == nullptr) { HILOGE("Failed to request heap memory."); return ENOMEM; } int64_t offset = 0; - struct stat srcStat{}; + struct stat srcStat {}; if (fstat(srcFdg->GetFD(), &srcStat) < 0) { HILOGE("Failed to get stat of file by fd: %{public}d ,errno = %{public}d", srcFdg->GetFD(), errno); return errno; @@ -127,15 +110,13 @@ static int SendFileCore(std::unique_ptr srcFdg, int32_t ret = 0; int64_t size = static_cast(srcStat.st_size); while (size >= 0) { - ret = uv_fs_sendfile(nullptr, sendFileReq.get(), destFdg->GetFD(), srcFdg->GetFD(), - offset, MAX_SIZE, nullptr); + ret = uv_fs_sendfile(nullptr, sendFileReq.get(), destFdg->GetFD(), srcFdg->GetFD(), offset, MAX_SIZE, nullptr); if (ret < 0) { HILOGE("Failed to sendfile by errno : %{public}d", errno); return errno; } if (infos != nullptr && infos->taskSignal != nullptr) { if (infos->taskSignal->CheckCancelIfNeed(infos->srcPath)) { - HILOGE("===Copy Task Canceled Success"); return ECANCELED; } } @@ -159,10 +140,7 @@ bool CopyCore::IsValidUri(const std::string &uri) bool CopyCore::ValidOperand(std::string uriStr) { - if (IsValidUri(uriStr)) { - return true; - } - return false; + return IsValidUri(uriStr); } bool CopyCore::IsRemoteUri(const std::string &uri) @@ -228,7 +206,7 @@ int CopyCore::CheckOrCreatePath(const std::string &destPath) return ERRNO_NOERR; } -int CopyCore::CopyFile(const string &src, const string &dest, std::shared_ptr infos) +int CopyCore::CopyFile(const string &src, const string &dest, std::shared_ptr infos) { HILOGD("src = %{public}s, dest = %{public}s", GetAnonyString(src).c_str(), GetAnonyString(dest).c_str()); int32_t srcFd = -1; @@ -264,7 +242,7 @@ int CopyCore::MakeDir(const string &path) return ERRNO_NOERR; } -int CopyCore::CopySubDir(const string &srcPath, const string &destPath, std::shared_ptr infos) +int CopyCore::CopySubDir(const string &srcPath, const string &destPath, std::shared_ptr infos) { std::error_code errCode; if (!filesystem::exists(destPath, errCode) && errCode.value() == ERRNO_NOERR) { @@ -286,14 +264,14 @@ int CopyCore::CopySubDir(const string &srcPath, const string &destPath, std::sha } { std::lock_guard lock(CopyCore::mutex_); - auto iter = CopyCore::jsCbMap_.find(*infos); + auto iter = CopyCore::callbackMap_.find(*infos); auto receiveInfo = CreateSharedPtr(); if (receiveInfo == nullptr) { HILOGE("Failed to request heap memory."); return ENOMEM; } receiveInfo->path = destPath; - if (iter == CopyCore::jsCbMap_.end() || iter->second == nullptr) { + if (iter == CopyCore::callbackMap_.end() || iter->second == nullptr) { HILOGE("Failed to find infos, srcPath = %{public}s, destPath = %{public}s", GetAnonyString(infos->srcPath).c_str(), GetAnonyString(infos->destPath).c_str()); return UNKNOWN_ERR; @@ -329,11 +307,11 @@ static void Deleter(struct NameList *arg) arg = nullptr; } -std::string CopyCore::GetRealPath(const std::string& path) +std::string CopyCore::GetRealPath(const std::string &path) { fs::path tempPath(path); - fs::path realPath{}; - for (const auto& component : tempPath) { + fs::path realPath {}; + for (const auto &component : tempPath) { if (component == ".") { continue; } else if (component == "..") { @@ -345,7 +323,7 @@ std::string CopyCore::GetRealPath(const std::string& path) return realPath.string(); } -uint64_t CopyCore::GetDirSize(std::shared_ptr infos, std::string path) +uint64_t CopyCore::GetDirSize(std::shared_ptr infos, std::string path) { unique_ptr pNameList = { new (nothrow) struct NameList, Deleter }; if (pNameList == nullptr) { @@ -374,7 +352,7 @@ uint64_t CopyCore::GetDirSize(std::shared_ptr infos, std::string return size; } -int CopyCore::RecurCopyDir(const string &srcPath, const string &destPath, std::shared_ptr infos) +int CopyCore::RecurCopyDir(const string &srcPath, const string &destPath, std::shared_ptr infos) { unique_ptr pNameList = { new (nothrow) struct NameList, Deleter }; if (pNameList == nullptr) { @@ -404,7 +382,7 @@ int CopyCore::RecurCopyDir(const string &srcPath, const string &destPath, std::s return ERRNO_NOERR; } -int CopyCore::CopyDirFunc(const string &src, const string &dest, std::shared_ptr infos) +int CopyCore::CopyDirFunc(const string &src, const string &dest, std::shared_ptr infos) { HILOGD("CopyDirFunc in, src = %{public}s, dest = %{public}s", GetAnonyString(src).c_str(), GetAnonyString(dest).c_str()); @@ -421,7 +399,7 @@ int CopyCore::CopyDirFunc(const string &src, const string &dest, std::shared_ptr return CopySubDir(src, destStr, infos); } -int CopyCore::ExecLocal(std::shared_ptr infos, std::shared_ptr callback) +int CopyCore::ExecLocal(std::shared_ptr infos, std::shared_ptr callback) { if (infos->isFile) { if (infos->srcPath == infos->destPath) { @@ -446,8 +424,7 @@ int CopyCore::ExecLocal(std::shared_ptr infos, std::shared_ptr infos, - std::shared_ptr callback) +int CopyCore::SubscribeLocalListener(std::shared_ptr infos, std::shared_ptr callback) { infos->notifyFd = inotify_init(); if (infos->notifyFd < 0) { @@ -465,7 +442,7 @@ int CopyCore::SubscribeLocalListener(std::shared_ptr infos, if (newWd < 0) { auto errCode = errno; HILOGE("Failed to add watch, errno = %{public}d, notifyFd: %{public}d, destPath: %{public}s", errno, - infos->notifyFd, infos->destPath.c_str()); + infos->notifyFd, infos->destPath.c_str()); CloseNotifyFdLocked(infos, callback); return errCode; } @@ -489,66 +466,73 @@ int CopyCore::SubscribeLocalListener(std::shared_ptr infos, return err; } -std::shared_ptr CopyCore::RegisterListener(const std::shared_ptr &infos) +std::shared_ptr CopyCore::RegisterListener(const std::shared_ptr &infos) { - auto callback = CreateSharedPtr(infos->listenerCb); + auto callback = CreateSharedPtr(infos->listener); if (callback == nullptr) { HILOGE("Failed to request heap memory."); return nullptr; } std::lock_guard lock(mutex_); - auto iter = jsCbMap_.find(*infos); - if (iter != jsCbMap_.end()) { + auto iter = callbackMap_.find(*infos); + if (iter != callbackMap_.end()) { HILOGE("CopyCore::RegisterListener, already registered."); return nullptr; } - jsCbMap_.insert({ *infos, callback }); + callbackMap_.insert({ *infos, callback }); return callback; } -void CopyCore::UnregisterListener(std::shared_ptr fileInfos) +void CopyCore::UnregisterListener(std::shared_ptr fileInfos) { if (fileInfos == nullptr) { HILOGE("fileInfos is nullptr"); return; } std::lock_guard lock(mutex_); - auto iter = jsCbMap_.find(*fileInfos); - if (iter == jsCbMap_.end()) { + auto iter = callbackMap_.find(*fileInfos); + if (iter == callbackMap_.end()) { HILOGI("It is not be registered."); return; } - jsCbMap_.erase(*fileInfos); + callbackMap_.erase(*fileInfos); } -void CopyCore::ReceiveComplete(std::shared_ptr entry) +void CopyCore::ReceiveComplete(std::shared_ptr entry) { if (entry == nullptr) { HILOGE("entry pointer is nullptr."); return; } + if (entry->callback == nullptr) { + HILOGE("entry callback pointer is nullptr."); + return; + } auto processedSize = entry->progressSize; if (processedSize < entry->callback->maxProgressSize) { - HILOGE("enter ReceiveComplete2"); return; } entry->callback->maxProgressSize = processedSize; - - entry->callback->listenerCb(processedSize, entry->totalSize); + auto listener = entry->callback->listener; + if (listener == nullptr) { + HILOGE("listener pointer is nullptr."); + return; + } + listener->InvokeListener(processedSize, entry->totalSize); } -UvEntryCore *CopyCore::GetUVEntry(std::shared_ptr infos) +FsUvEntry *CopyCore::GetUVEntry(std::shared_ptr infos) { - UvEntryCore *entry = nullptr; + FsUvEntry *entry = nullptr; { std::lock_guard lock(mutex_); - auto iter = jsCbMap_.find(*infos); - if (iter == jsCbMap_.end()) { + auto iter = callbackMap_.find(*infos); + if (iter == callbackMap_.end()) { HILOGE("Failed to find callback"); return nullptr; } auto callback = iter->second; - entry = new (std::nothrow) UvEntryCore(iter->second, infos); + entry = new (std::nothrow) FsUvEntry(iter->second, infos); if (entry == nullptr) { HILOGE("entry ptr is nullptr."); return nullptr; @@ -559,9 +543,9 @@ UvEntryCore *CopyCore::GetUVEntry(std::shared_ptr infos) return entry; } -void CopyCore::OnFileReceive(std::shared_ptr infos) +void CopyCore::OnFileReceive(std::shared_ptr infos) { - std::shared_ptr entry(GetUVEntry(infos)); + std::shared_ptr entry(GetUVEntry(infos)); if (entry == nullptr) { HILOGE("failed to get uv entry"); return; @@ -569,25 +553,22 @@ void CopyCore::OnFileReceive(std::shared_ptr infos) ReceiveComplete(entry); } -std::shared_ptr CopyCore::GetReceivedInfo(int wd, std::shared_ptr callback) +std::shared_ptr CopyCore::GetReceivedInfo(int wd, std::shared_ptr callback) { - auto it = find_if(callback->wds.begin(), callback->wds.end(), [wd](const auto& item) { - return item.first == wd; - }); + auto it = find_if(callback->wds.begin(), callback->wds.end(), [wd](const auto &item) { return item.first == wd; }); if (it != callback->wds.end()) { return it->second; } return nullptr; } -bool CopyCore::CheckFileValid(const std::string &filePath, std::shared_ptr infos) +bool CopyCore::CheckFileValid(const std::string &filePath, std::shared_ptr infos) { return infos->filePaths.count(filePath) != 0; } -int CopyCore::UpdateProgressSize(const std::string &filePath, - std::shared_ptr receivedInfo, - std::shared_ptr callback) +int CopyCore::UpdateProgressSize( + const std::string &filePath, std::shared_ptr receivedInfo, std::shared_ptr callback) { auto [err, fileSize] = GetFileSize(filePath); if (err != ERRNO_NOERR) { @@ -608,18 +589,18 @@ int CopyCore::UpdateProgressSize(const std::string &filePath, return ERRNO_NOERR; } -std::shared_ptr CopyCore::GetRegisteredListener(std::shared_ptr infos) +std::shared_ptr CopyCore::GetRegisteredListener(std::shared_ptr infos) { std::lock_guard lock(mutex_); - auto iter = jsCbMap_.find(*infos); - if (iter == jsCbMap_.end()) { + auto iter = callbackMap_.find(*infos); + if (iter == callbackMap_.end()) { HILOGE("It is not registered."); return nullptr; } return iter->second; } -void CopyCore::CloseNotifyFd(std::shared_ptr infos, std::shared_ptr callback) +void CopyCore::CloseNotifyFd(std::shared_ptr infos, std::shared_ptr callback) { callback->closed = false; infos->eventFd = -1; @@ -631,7 +612,7 @@ void CopyCore::CloseNotifyFd(std::shared_ptr infos, std::shared_p } } -void CopyCore::CloseNotifyFdLocked(std::shared_ptr infos, std::shared_ptr callback) +void CopyCore::CloseNotifyFdLocked(std::shared_ptr infos, std::shared_ptr callback) { { lock_guard lock(callback->readMutex); @@ -645,7 +626,7 @@ void CopyCore::CloseNotifyFdLocked(std::shared_ptr infos, std::sh } tuple CopyCore::HandleProgress( - inotify_event *event, std::shared_ptr infos, std::shared_ptr callback) + inotify_event *event, std::shared_ptr infos, std::shared_ptr callback) { if (callback == nullptr) { return { true, EINVAL, false }; @@ -674,14 +655,15 @@ tuple CopyCore::HandleProgress( return { true, callback->errorCode, true }; } -void CopyCore::ReadNotifyEvent(std::shared_ptr infos) +void CopyCore::ReadNotifyEvent(std::shared_ptr infos) { char buf[BUF_SIZE] = { 0 }; struct inotify_event *event = nullptr; int len = 0; int64_t index = 0; auto callback = GetRegisteredListener(infos); - while (infos->run && ((len = read(infos->notifyFd, &buf, sizeof(buf))) < 0) && (errno == EINTR)) {} + while (infos->run && ((len = read(infos->notifyFd, &buf, sizeof(buf))) < 0) && (errno == EINTR)) { + } while (infos->run && index < len) { event = reinterpret_cast(buf + index); auto [needContinue, errCode, needSend] = HandleProgress(event, infos, callback); @@ -706,7 +688,7 @@ void CopyCore::ReadNotifyEvent(std::shared_ptr infos) } } -void CopyCore::ReadNotifyEventLocked(std::shared_ptr infos, std::shared_ptr callback) +void CopyCore::ReadNotifyEventLocked(std::shared_ptr infos, std::shared_ptr callback) { { std::lock_guard lock(callback->readMutex); @@ -728,7 +710,7 @@ void CopyCore::ReadNotifyEventLocked(std::shared_ptr infos, std:: } } -void CopyCore::GetNotifyEvent(std::shared_ptr infos) +void CopyCore::GetNotifyEvent(std::shared_ptr infos) { auto callback = GetRegisteredListener(infos); if (callback == nullptr) { @@ -760,17 +742,16 @@ void CopyCore::GetNotifyEvent(std::shared_ptr infos) } { std::unique_lock lock(callback->cvLock); - callback->cv.wait_for(lock, std::chrono::microseconds(SLEEP_TIME), [callback]() -> bool { - return callback->notifyFd == -1; - }); + callback->cv.wait_for( + lock, std::chrono::microseconds(SLEEP_TIME), [callback]() -> bool { return callback->notifyFd == -1; }); } } } -tuple> CopyCore::CreateFileInfos( - const std::string &srcUri, const std::string &destUri, std::optional options) +tuple> CopyCore::CreateFileInfos( + const std::string &srcUri, const std::string &destUri, const std::optional &options) { - auto infos = CreateSharedPtr(); + auto infos = CreateSharedPtr(); if (infos == nullptr) { HILOGE("Failed to request heap memory."); return { ENOMEM, nullptr }; @@ -785,29 +766,29 @@ tuple> CopyCore::CreateFileInfos( infos->destPath = GetRealPath(infos->destPath); infos->isFile = IsMediaUri(infos->srcUri) || IsFile(infos->srcPath); infos->notifyTime = std::chrono::steady_clock::now() + NOTIFY_PROGRESS_DELAY; - if (options != std::nullopt) { - if (options.value().listenerCb) { + if (options.has_value()) { + auto listener = options.value().progressListener; + if (listener) { infos->hasListener = true; - infos->listenerCb = options.value().listenerCb; + infos->listener = listener; } - if (options.value().taskSignalEntityCore != nullptr) { - infos->taskSignal = options.value().taskSignalEntityCore->taskSignal_; + auto copySignal = options.value().copySignal; + if (copySignal) { + infos->taskSignal = copySignal->GetTaskSignal(); } } return { ERRNO_NOERR, infos }; } -void CopyCore::StartNotify(std::shared_ptr infos, std::shared_ptr callback) +void CopyCore::StartNotify(std::shared_ptr infos, std::shared_ptr callback) { if (infos->hasListener && callback != nullptr) { - callback->notifyHandler = std::thread([infos] { - GetNotifyEvent(infos); - }); + callback->notifyHandler = std::thread([infos] { GetNotifyEvent(infos); }); } } -int CopyCore::ExecCopy(std::shared_ptr infos) +int CopyCore::ExecCopy(std::shared_ptr infos) { if (infos->isFile && IsFile(infos->destPath)) { // copyFile @@ -826,25 +807,18 @@ int CopyCore::ExecCopy(std::shared_ptr infos) return EINVAL; } -int CopyCore::ValidParam(const string& src, const string& dest, - std::optional options, - std::shared_ptr &fileInfos) +bool CopyCore::ValidParams(const string &src, const string &dest) { auto succSrc = ValidOperand(src); auto succDest = ValidOperand(dest); if (!succSrc || !succDest) { HILOGE("The first/second argument requires uri/uri"); - return E_PARAMS; - } - auto [errCode, infos] = CreateFileInfos(src, dest, options); - if (errCode != ERRNO_NOERR) { - return errCode; + return false; } - fileInfos = infos; - return ERRNO_NOERR; + return true; } -void CopyCore::WaitNotifyFinished(std::shared_ptr callback) +void CopyCore::WaitNotifyFinished(std::shared_ptr callback) { if (callback != nullptr) { if (callback->notifyHandler.joinable()) { @@ -853,7 +827,7 @@ void CopyCore::WaitNotifyFinished(std::shared_ptr callback) } } -void CopyCore::CopyComplete(std::shared_ptr infos, std::shared_ptr callback) +void CopyCore::CopyComplete(std::shared_ptr infos, std::shared_ptr callback) { if (callback != nullptr && infos->hasListener) { callback->progressSize = callback->totalSize; @@ -861,12 +835,16 @@ void CopyCore::CopyComplete(std::shared_ptr infos, std::shared_pt } } -FsResult CopyCore::DoCopy(const string& src, const string& dest, std::optional &options) +FsResult CopyCore::DoCopy(const string &src, const string &dest, std::optional &options) { - std::shared_ptr infos = nullptr; - auto result = ValidParam(src, dest, options, infos); - if (result != ERRNO_NOERR) { - return FsResult::Error(result); + auto isValid = ValidParams(src, dest); + if (!isValid) { + return FsResult::Error(E_PARAMS); + } + + auto [errCode, infos] = CreateFileInfos(src, dest, options); + if (errCode != ERRNO_NOERR) { + return FsResult::Error(errCode); } auto callback = RegisterListener(infos); @@ -878,23 +856,25 @@ FsResult CopyCore::DoCopy(const string& src, const string& dest, std::opti if (infos->taskSignal != nullptr) { infos->taskSignal->MarkRemoteTask(); } - auto ret = TransListenerCore::CopyFileFromSoftBus(infos->srcUri, infos->destUri, - infos, std::move(callback)); + auto ret = TransListenerCore::CopyFileFromSoftBus(infos->srcUri, infos->destUri, infos, std::move(callback)); + UnregisterListener(infos); if (ret != ERRNO_NOERR) { return FsResult::Error(ret); } else { return FsResult::Success(); } } - result = CopyCore::ExecLocal(infos, callback); + auto result = CopyCore::ExecLocal(infos, callback); CloseNotifyFdLocked(infos, callback); infos->run = false; WaitNotifyFinished(callback); if (result != ERRNO_NOERR) { infos->exceptionCode = result; + UnregisterListener(infos); return FsResult::Error(infos->exceptionCode); } CopyComplete(infos, callback); + UnregisterListener(infos); if (infos->exceptionCode != ERRNO_NOERR) { return FsResult::Error(infos->exceptionCode); } else { diff --git a/interfaces/kits/js/src/mod_fs/properties/copy_core.h b/interfaces/kits/js/src/mod_fs/properties/copy_core.h index 58aa4f999cc50d102a05f11db8e5e26eace0e053..38779226062c433f42bc60b371d88aa76e463e87 100644 --- a/interfaces/kits/js/src/mod_fs/properties/copy_core.h +++ b/interfaces/kits/js/src/mod_fs/properties/copy_core.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2023 Huawei Device Co., Ltd. + * Copyright (c) 2025 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -13,20 +13,20 @@ * limitations under the License. */ -#ifndef FILEMANAGEMENT_FILE_API_COPY_CORE_H -#define FILEMANAGEMENT_FILE_API_COPY_CORE_H +#ifndef INTERFACES_KITS_JS_SRC_MOD_FS_PROPERTIES_COPY_CORE_H +#define INTERFACES_KITS_JS_SRC_MOD_FS_PROPERTIES_COPY_CORE_H #include #include #include -#include #include +#include #include "bundle_mgr_client_impl.h" #include "filemgmt_libfs.h" #include "filemgmt_libhilog.h" -#include "task_signal.h" -#include "task_signal_entity_core.h" +#include "fs_task_signal.h" +#include "i_progress_listener.h" namespace OHOS { namespace FileManagement { @@ -34,12 +34,10 @@ namespace ModuleFileIO { using namespace std; using namespace OHOS::AppExecFwk; using namespace DistributedFS::ModuleTaskSignal; -const uint64_t MAX_VALUE = 0x7FFFFFFFFFFFFFFF; -typedef std::function ProgressListenerCb; struct CopyOptions { - ProgressListenerCb listenerCb; - std::shared_ptr taskSignalEntityCore; + std::shared_ptr progressListener; + std::shared_ptr copySignal; }; struct ReceiveInfo { @@ -47,8 +45,8 @@ struct ReceiveInfo { std::map fileList; // filename, proceededSize }; -struct CallbackObjectCore { - ProgressListenerCb listenerCb; +struct FsCallbackObject { + std::shared_ptr listener = nullptr; int32_t notifyFd = -1; int32_t eventFd = -1; std::vector>> wds; @@ -62,7 +60,7 @@ struct CallbackObjectCore { std::mutex cvLock; bool reading = false; bool closed = false; - explicit CallbackObjectCore(ProgressListenerCb cb) : listenerCb(cb) {} + explicit FsCallbackObject(std::shared_ptr listener) : listener(listener) {} void CloseFd() { @@ -80,13 +78,13 @@ struct CallbackObjectCore { notifyFd = -1; } - ~CallbackObjectCore() + ~FsCallbackObject() { CloseFd(); } }; -struct FileInfosCore { +struct FsFileInfos { std::string srcUri; std::string destUri; std::string srcPath; @@ -97,15 +95,15 @@ struct FileInfosCore { int32_t eventFd = -1; bool run = true; bool hasListener = false; - ProgressListenerCb listenerCb; + std::shared_ptr listener = nullptr; std::shared_ptr taskSignal = nullptr; std::set filePaths; - int exceptionCode = ERRNO_NOERR; // notify copy thread or listener thread has exceptions. - bool operator==(const FileInfosCore &infos) const + int exceptionCode = ERRNO_NOERR; // notify copy thread or listener thread has exceptions. + bool operator==(const FsFileInfos &infos) const { return (srcUri == infos.srcUri && destUri == infos.destUri); } - bool operator<(const FileInfosCore &infos) const + bool operator<(const FsFileInfos &infos) const { if (srcUri == infos.srcUri) { return destUri < infos.destUri; @@ -114,73 +112,65 @@ struct FileInfosCore { } }; -struct UvEntryCore { - std::shared_ptr callback; - std::shared_ptr fileInfos; +struct FsUvEntry { + std::shared_ptr callback; + std::shared_ptr fileInfos; uint64_t progressSize = 0; uint64_t totalSize = 0; - UvEntryCore(const std::shared_ptr &cb, std::shared_ptr fileInfos) + FsUvEntry(const std::shared_ptr &cb, std::shared_ptr fileInfos) : callback(cb), fileInfos(fileInfos) { } - explicit UvEntryCore(const std::shared_ptr &cb) : callback(cb) {} + explicit FsUvEntry(const std::shared_ptr &cb) : callback(cb) {} }; class CopyCore final { public: - static std::map> jsCbMap_; - static void UnregisterListener(std::shared_ptr fileInfos); - static std::recursive_mutex mutex_; - static FsResult DoCopy(const string& src, const string& dest, std::optional &options); + static FsResult DoCopy(const string &src, const string &dest, std::optional &options); private: - // operator of napi + // operator of params static bool ValidOperand(std::string uriStr); static int CheckOrCreatePath(const std::string &destPath); - static int ValidParam(const string& src, const string& dest, std::optional options, - std::shared_ptr &fileInfos); + static bool ValidParams(const string &src, const string &dest); // operator of local listener - static int ExecLocal(std::shared_ptr infos, std::shared_ptr callback); - static void CopyComplete(std::shared_ptr infos, std::shared_ptr callback); - static void WaitNotifyFinished(std::shared_ptr callback); - static void ReadNotifyEvent(std::shared_ptr infos); - static void ReadNotifyEventLocked(std::shared_ptr infos, - std::shared_ptr callback); - static int SubscribeLocalListener(std::shared_ptr infos, - std::shared_ptr callback); - static std::shared_ptr RegisterListener( - const std::shared_ptr &infos); - static void OnFileReceive(std::shared_ptr infos); - static void GetNotifyEvent(std::shared_ptr infos); - static void StartNotify(std::shared_ptr infos, std::shared_ptr callback); - static UvEntryCore *GetUVEntry(std::shared_ptr infos); - static void ReceiveComplete(std::shared_ptr entry); - static std::shared_ptr GetRegisteredListener(std::shared_ptr infos); - static void CloseNotifyFd(std::shared_ptr infos, std::shared_ptr callback); - static void CloseNotifyFdLocked(std::shared_ptr infos, - std::shared_ptr callback); + static std::shared_ptr RegisterListener(const std::shared_ptr &infos); + static std::shared_ptr GetRegisteredListener(std::shared_ptr infos); + static void UnregisterListener(std::shared_ptr fileInfos); + static int ExecLocal(std::shared_ptr infos, std::shared_ptr callback); + static void CopyComplete(std::shared_ptr infos, std::shared_ptr callback); + static void WaitNotifyFinished(std::shared_ptr callback); + static void ReadNotifyEvent(std::shared_ptr infos); + static void ReadNotifyEventLocked(std::shared_ptr infos, std::shared_ptr callback); + static int SubscribeLocalListener(std::shared_ptr infos, std::shared_ptr callback); + static void OnFileReceive(std::shared_ptr infos); + static void GetNotifyEvent(std::shared_ptr infos); + static void StartNotify(std::shared_ptr infos, std::shared_ptr callback); + static FsUvEntry *GetUVEntry(std::shared_ptr infos); + static void ReceiveComplete(std::shared_ptr entry); + static void CloseNotifyFd(std::shared_ptr infos, std::shared_ptr callback); + static void CloseNotifyFdLocked(std::shared_ptr infos, std::shared_ptr callback); // operator of file - static int RecurCopyDir(const string &srcPath, const string &destPath, std::shared_ptr infos); + static int RecurCopyDir(const string &srcPath, const string &destPath, std::shared_ptr infos); static tuple GetFileSize(const std::string &path); - static uint64_t GetDirSize(std::shared_ptr infos, std::string path); - static int CopyFile(const string &src, const string &dest, std::shared_ptr infos); + static uint64_t GetDirSize(std::shared_ptr infos, std::string path); + static int CopyFile(const string &src, const string &dest, std::shared_ptr infos); static int MakeDir(const string &path); - static int CopySubDir(const string &srcPath, const string &destPath, std::shared_ptr infos); - static int CopyDirFunc(const string &src, const string &dest, std::shared_ptr infos); - static tuple> CreateFileInfos( - const std::string &srcUri, const std::string &destUri, std::optional options); - static int ExecCopy(std::shared_ptr infos); + static int CopySubDir(const string &srcPath, const string &destPath, std::shared_ptr infos); + static int CopyDirFunc(const string &src, const string &dest, std::shared_ptr infos); + static tuple> CreateFileInfos( + const std::string &srcUri, const std::string &destUri, const std::optional &options); + static int ExecCopy(std::shared_ptr infos); // operator of file size - static int UpdateProgressSize(const std::string &filePath, - std::shared_ptr receivedInfo, - std::shared_ptr callback); + static int UpdateProgressSize(const std::string &filePath, std::shared_ptr receivedInfo, + std::shared_ptr callback); static tuple HandleProgress( - inotify_event *event, std::shared_ptr infos, std::shared_ptr callback); - static std::shared_ptr GetReceivedInfo(int wd, std::shared_ptr callback); - static bool CheckFileValid(const std::string &filePath, std::shared_ptr infos); + inotify_event *event, std::shared_ptr infos, std::shared_ptr callback); + static std::shared_ptr GetReceivedInfo(int wd, std::shared_ptr callback); + static bool CheckFileValid(const std::string &filePath, std::shared_ptr infos); // operator of uri or path static bool IsValidUri(const std::string &uri); @@ -189,10 +179,14 @@ private: static bool IsFile(const std::string &path); static bool IsMediaUri(const std::string &uriPath); static std::string ConvertUriToPath(const std::string &uri); - static std::string GetRealPath(const std::string& path); + static std::string GetRealPath(const std::string &path); + +private: + static std::recursive_mutex mutex_; + static std::map> callbackMap_; }; } // namespace ModuleFileIO } // namespace FileManagement } // namespace OHOS -#endif // FILEMANAGEMENT_FILE_API_COPY_CORE_H \ No newline at end of file +#endif // INTERFACES_KITS_JS_SRC_MOD_FS_PROPERTIES_COPY_CORE_H \ No newline at end of file diff --git a/interfaces/kits/js/src/mod_fs/properties/copy_listener/ani/progress_listener_ani.cpp b/interfaces/kits/js/src/mod_fs/properties/copy_listener/ani/progress_listener_ani.cpp new file mode 100644 index 0000000000000000000000000000000000000000..58be193379357bc9ea4fd41692e7eb32b86be8bc --- /dev/null +++ b/interfaces/kits/js/src/mod_fs/properties/copy_listener/ani/progress_listener_ani.cpp @@ -0,0 +1,93 @@ +/* + * Copyright (c) 2025 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "progress_listener_ani.h" + +#include +#include "ani_helper.h" +#include "ani_signature.h" +#include "file_utils.h" +#include "filemgmt_libhilog.h" +#include "type_converter.h" + +namespace OHOS::FileManagement::ModuleFileIO::ANI { +using namespace std; +using namespace OHOS::FileManagement::ModuleFileIO::ANI::AniSignature; + +void ProgressListenerAni::InvokeListener(uint64_t progressSize, uint64_t totalSize) const +{ + auto task = [this, progressSize, totalSize]() { SendCopyProgress(progressSize, totalSize); }; + AniHelper::SendEventToMainThread(task); +} + +static ani_object WrapCopyProgress(ani_env *env, uint64_t progressSize, uint64_t totalSize) +{ + auto classDesc = FS::ProgressInner::classDesc.c_str(); + ani_class cls; + if (ANI_OK != env->FindClass(classDesc, &cls)) { + HILOGE("Cannot find class %{private}s", classDesc); + return nullptr; + } + auto ctorDesc = FS::ProgressInner::ctorDesc.c_str(); + auto ctorSig = FS::ProgressInner::ctorSig.c_str(); + ani_method ctor; + if (ANI_OK != env->Class_FindMethod(cls, ctorDesc, ctorSig, &ctor)) { + HILOGE("Cannot find constructor method for class %{private}s", classDesc); + return nullptr; + } + + const ani_double aniProgressSize = static_cast(progressSize <= MAX_VALUE ? progressSize : 0); + const ani_double aniTotalSize = static_cast(totalSize <= MAX_VALUE ? totalSize : 0); + + ani_object obj; + if (ANI_OK != env->Object_New(cls, ctor, &obj, aniProgressSize, aniTotalSize)) { + HILOGE("Create %{private}s object failed!", classDesc); + return nullptr; + } + return obj; +} + +void ProgressListenerAni::SendCopyProgress(uint64_t progressSize, uint64_t totalSize) const +{ + if (vm == nullptr) { + HILOGE("Cannot send copy progress because the vm is null."); + return; + } + if (listener == nullptr) { + HILOGE("Cannot send copy progress because the listener is null."); + return; + } + ani_env *env = AniHelper::GetThreadEnv(vm); + if (env == nullptr) { + HILOGE("Cannot send copy progress because the env is null."); + return; + } + auto evtObj = WrapCopyProgress(env, progressSize, totalSize); + if (evtObj == nullptr) { + HILOGE("Create copy progress obj failed!"); + return; + } + vector args = { static_cast(evtObj) }; + auto argc = args.size(); + ani_ref result; + auto cbObj = static_cast(listener); + auto status = env->FunctionalObject_Call(cbObj, argc, args.data(), &result); + if (status != ANI_OK) { + HILOGE("Failed to call FunctionalObject_Call, status: %{public}d", static_cast(status)); + return; + } +} + +} // namespace OHOS::FileManagement::ModuleFileIO::ANI diff --git a/interfaces/kits/js/src/mod_fs/properties/copy_listener/ani/progress_listener_ani.h b/interfaces/kits/js/src/mod_fs/properties/copy_listener/ani/progress_listener_ani.h new file mode 100644 index 0000000000000000000000000000000000000000..07894982a3bdbf6ab135eeab6c97bb10aac81cf9 --- /dev/null +++ b/interfaces/kits/js/src/mod_fs/properties/copy_listener/ani/progress_listener_ani.h @@ -0,0 +1,39 @@ +/* + * Copyright (c) 2025 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef INTERFACES_KITS_JS_SRC_MOD_FS_PROPERTIES_COPY_LISTENER_ANI_PROGRESS_LISTENER_H +#define INTERFACES_KITS_JS_SRC_MOD_FS_PROPERTIES_COPY_LISTENER_ANI_PROGRESS_LISTENER_H + +#include +#include +#include "i_progress_listener.h" + +namespace OHOS::FileManagement::ModuleFileIO::ANI { + +class ProgressListenerAni final : public IProgressListener { +public: + ProgressListenerAni(ani_vm *vm, const ani_ref &listener) : vm(vm), listener(listener) {} + void InvokeListener(uint64_t progressSize, uint64_t totalSize) const override; + +private: + void SendCopyProgress(uint64_t progressSize, uint64_t totalSize) const; + +private: + ani_vm *vm; + ani_ref listener; +}; + +} // namespace OHOS::FileManagement::ModuleFileIO::ANI +#endif // INTERFACES_KITS_JS_SRC_MOD_FS_PROPERTIES_COPY_LISTENER_ANI_PROGRESS_LISTENER_H \ No newline at end of file diff --git a/interfaces/kits/js/src/mod_fs/class_tasksignal/task_signal_entity_core.cpp b/interfaces/kits/js/src/mod_fs/properties/copy_listener/i_progress_listener.h similarity index 50% rename from interfaces/kits/js/src/mod_fs/class_tasksignal/task_signal_entity_core.cpp rename to interfaces/kits/js/src/mod_fs/properties/copy_listener/i_progress_listener.h index 85dd60f91181d3f0d9bbe5030731c9cd3dd103b3..f51f4f421562c0e603d9fea87025c27a425a7f72 100644 --- a/interfaces/kits/js/src/mod_fs/class_tasksignal/task_signal_entity_core.cpp +++ b/interfaces/kits/js/src/mod_fs/properties/copy_listener/i_progress_listener.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2024 Huawei Device Co., Ltd. + * Copyright (c) 2025 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -13,18 +13,19 @@ * limitations under the License. */ -#include "task_signal_entity_core.h" -#include "filemgmt_libhilog.h" +#ifndef INTERFACES_KITS_JS_SRC_MOD_FS_PROPERTIES_COPY_LISTENER_I_PROGRESS_LISTENER_H +#define INTERFACES_KITS_JS_SRC_MOD_FS_PROPERTIES_COPY_LISTENER_I_PROGRESS_LISTENER_H + +#include namespace OHOS::FileManagement::ModuleFileIO { -TaskSignalEntityCore::~TaskSignalEntityCore() {} +const uint64_t MAX_VALUE = 0x7FFFFFFFFFFFFFFF; + +class IProgressListener { +public: + virtual ~IProgressListener() = default; + virtual void InvokeListener(uint64_t progressSize, uint64_t totalSize) const = 0; +}; -void TaskSignalEntityCore::OnCancel() -{ - if (!callbackContextCore_) { - return; - } - - callbackContextCore_->cb(taskSignal_->filePath_); -} -} // namespace OHOS::FileManagement::ModuleFileIO \ No newline at end of file +} // namespace OHOS::FileManagement::ModuleFileIO +#endif // INTERFACES_KITS_JS_SRC_MOD_FS_PROPERTIES_COPY_LISTENER_I_PROGRESS_LISTENER_H \ No newline at end of file diff --git a/interfaces/kits/js/src/mod_fs/properties/copy_listener/trans_listener_core.cpp b/interfaces/kits/js/src/mod_fs/properties/copy_listener/trans_listener_core.cpp index 431a4f9e1fe6ac65a58419c09a85ad98c3733cb2..0b8d32b788fa3c7acba5b86b378bb92d6e56ca19 100644 --- a/interfaces/kits/js/src/mod_fs/properties/copy_listener/trans_listener_core.cpp +++ b/interfaces/kits/js/src/mod_fs/properties/copy_listener/trans_listener_core.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2023 Huawei Device Co., Ltd. + * Copyright (c) 2025 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -19,10 +19,10 @@ #include #include +#include "dfs_event_dfx.h" #include "ipc_skeleton.h" #include "sandbox_helper.h" #include "uri.h" -#include "dfs_event_dfx.h" #include "utils_log.h" namespace OHOS { @@ -70,22 +70,20 @@ int TransListenerCore::HandleCopyFailure(CopyEvent ©Event, const Storage::Di auto it = softbusErr2ErrCodeTable.find(copyEvent.errorCode); if (it == softbusErr2ErrCodeTable.end()) { RADAR_REPORT(RadarReporter::DFX_SET_DFS, RadarReporter::DFX_SET_BIZ_SCENE, RadarReporter::DFX_FAILED, - RadarReporter::BIZ_STATE, RadarReporter::DFX_END, RadarReporter::ERROR_CODE, - RadarReporter::SEND_FILE_ERROR, RadarReporter::CONCURRENT_ID, currentId, - RadarReporter::PACKAGE_NAME, to_string(copyEvent.errorCode)); + RadarReporter::BIZ_STATE, RadarReporter::DFX_END, RadarReporter::ERROR_CODE, RadarReporter::SEND_FILE_ERROR, + RadarReporter::CONCURRENT_ID, currentId, RadarReporter::PACKAGE_NAME, to_string(copyEvent.errorCode)); return EIO; } if (copyEvent.errorCode != DFS_CANCEL_SUCCESS) { HILOGE("HandleCopyFailure failed, copyEvent.errorCode = %{public}d.", copyEvent.errorCode); RADAR_REPORT(RadarReporter::DFX_SET_DFS, RadarReporter::DFX_SET_BIZ_SCENE, RadarReporter::DFX_FAILED, - RadarReporter::BIZ_STATE, RadarReporter::DFX_END, RadarReporter::ERROR_CODE, - RadarReporter::SEND_FILE_ERROR, RadarReporter::CONCURRENT_ID, currentId, - RadarReporter::PACKAGE_NAME, to_string(copyEvent.errorCode)); + RadarReporter::BIZ_STATE, RadarReporter::DFX_END, RadarReporter::ERROR_CODE, RadarReporter::SEND_FILE_ERROR, + RadarReporter::CONCURRENT_ID, currentId, RadarReporter::PACKAGE_NAME, to_string(copyEvent.errorCode)); } return it->second; } -int TransListenerCore::WaitForCopyResult(TransListenerCore* transListener) +int TransListenerCore::WaitForCopyResult(TransListenerCore *transListener) { if (transListener == nullptr) { HILOGE("transListener is nullptr"); @@ -93,14 +91,13 @@ int TransListenerCore::WaitForCopyResult(TransListenerCore* transListener) } std::unique_lock lock(transListener->cvMutex_); transListener->cv_.wait(lock, [&transListener]() { - return transListener->copyEvent_.copyResult == SUCCESS || - transListener->copyEvent_.copyResult == FAILED; + return transListener->copyEvent_.copyResult == SUCCESS || transListener->copyEvent_.copyResult == FAILED; }); return transListener->copyEvent_.copyResult; } int TransListenerCore::CopyFileFromSoftBus(const std::string &srcUri, const std::string &destUri, - std::shared_ptr fileInfos, std::shared_ptr callback) + std::shared_ptr fileInfos, std::shared_ptr callback) { HILOGI("CopyFileFromSoftBus begin."); std::string currentId = "CopyFile_" + std::to_string(getpid()) + "_" + std::to_string(getSequenceId_); @@ -115,7 +112,7 @@ int TransListenerCore::CopyFileFromSoftBus(const std::string &srcUri, const std: } transListener->callback_ = std::move(callback); - Storage::DistributedFile::HmdfsInfo info{}; + Storage::DistributedFile::HmdfsInfo info {}; Uri uri(destUri); info.authority = uri.GetAuthority(); info.sandboxPath = SandboxHelper::Decode(uri.GetPath()); @@ -151,14 +148,11 @@ int TransListenerCore::CopyFileFromSoftBus(const std::string &srcUri, const std: return ERRNO_NOERR; } -int32_t TransListenerCore::PrepareCopySession(const std::string &srcUri, - const std::string &destUri, - TransListenerCore* transListener, - Storage::DistributedFile::HmdfsInfo &info, - std::string &disSandboxPath) +int32_t TransListenerCore::PrepareCopySession(const std::string &srcUri, const std::string &destUri, + TransListenerCore *transListener, Storage::DistributedFile::HmdfsInfo &info, std::string &disSandboxPath) { std::string tmpDir; - if (info.authority != FILE_MANAGER_AUTHORITY && info.authority != MEDIA_AUTHORITY) { + if (info.authority != FILE_MANAGER_AUTHORITY && info.authority != MEDIA_AUTHORITY) { tmpDir = CreateDfsCopyPath(); disSandboxPath = DISTRIBUTED_PATH + tmpDir; std::error_code errCode; @@ -181,8 +175,8 @@ int32_t TransListenerCore::PrepareCopySession(const std::string &srcUri, info.copyPath = tmpDir; auto networkId = GetNetworkIdFromUri(srcUri); HILOGI("dfs PrepareSession begin."); - auto ret = Storage::DistributedFile::DistributedFileDaemonManager::GetInstance().PrepareSession(srcUri, destUri, - networkId, transListener, info); + auto ret = Storage::DistributedFile::DistributedFileDaemonManager::GetInstance().PrepareSession( + srcUri, destUri, networkId, transListener, info); if (ret != ERRNO_NOERR) { HILOGE("PrepareSession failed, ret = %{public}d.", ret); if (info.authority != FILE_MANAGER_AUTHORITY && info.authority != MEDIA_AUTHORITY) { @@ -218,8 +212,8 @@ int32_t TransListenerCore::CopyToSandBox(const std::string &srcUri, const std::s RmDir(disSandboxPath); return EIO; } - std::filesystem::copy(disSandboxPath + fileName, sandboxPath, std::filesystem::copy_options::update_existing, - errCode); + std::filesystem::copy( + disSandboxPath + fileName, sandboxPath, std::filesystem::copy_options::update_existing, errCode); if (errCode.value() != 0) { HILOGE("Copy file failed: errCode: %{public}d", errCode.value()); RADAR_REPORT(RadarReporter::DFX_SET_DFS, RadarReporter::DFX_SET_BIZ_SCENE, RadarReporter::DFX_FAILED, @@ -250,14 +244,24 @@ std::string TransListenerCore::GetNetworkIdFromUri(const std::string &uri) return uri.substr(uri.find(NETWORK_PARA) + NETWORK_PARA.size(), uri.size()); } -void TransListenerCore::CallbackComplete(std::shared_ptr entry) +void TransListenerCore::CallbackComplete(std::shared_ptr entry) { if (entry == nullptr) { HILOGE("entry pointer is nullptr."); return; } - entry->callback->listenerCb(entry->progressSize, entry->totalSize); + if (entry->callback == nullptr) { + HILOGE("entry callback pointer is nullptr."); + return; + } + + auto listener = entry->callback->listener; + if (listener == nullptr) { + HILOGE("listener pointer is nullptr."); + return; + } + listener->InvokeListener(entry->progressSize, entry->totalSize); } int32_t TransListenerCore::OnFileReceive(uint64_t totalBytes, uint64_t processedBytes) @@ -268,7 +272,7 @@ int32_t TransListenerCore::OnFileReceive(uint64_t totalBytes, uint64_t processed return ENOMEM; } - std::shared_ptr entry = std::make_shared(callback_); + std::shared_ptr entry = std::make_shared(callback_); if (entry == nullptr) { HILOGE("entry ptr is nullptr"); return ENOMEM; diff --git a/interfaces/kits/js/src/mod_fs/properties/copy_listener/trans_listener_core.h b/interfaces/kits/js/src/mod_fs/properties/copy_listener/trans_listener_core.h index d5b8f95850f6533a28544f43dc3b5390668f470a..c797454def4fc350c5a416b991baa9d70d33c846 100644 --- a/interfaces/kits/js/src/mod_fs/properties/copy_listener/trans_listener_core.h +++ b/interfaces/kits/js/src/mod_fs/properties/copy_listener/trans_listener_core.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2023 Huawei Device Co., Ltd. + * Copyright (c) 2025 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -13,8 +13,8 @@ * limitations under the License. */ -#ifndef FILEMANAGEMENT_FILE_API_TRANS_LISTENER_CORE_H -#define FILEMANAGEMENT_FILE_API_TRANS_LISTENER_CORE_H +#ifndef INTERFACES_KITS_JS_SRC_MOD_FS_PROPERTIES_COPY_LISTENER_TRANS_LISTENER_CORE_H +#define INTERFACES_KITS_JS_SRC_MOD_FS_PROPERTIES_COPY_LISTENER_TRANS_LISTENER_CORE_H #include @@ -40,35 +40,31 @@ public: int32_t OnFileReceive(uint64_t totalBytes, uint64_t processedBytes) override; int32_t OnFinished(const std::string &sessionName) override; int32_t OnFailed(const std::string &sessionName, int32_t errorCode) override; - static int CopyFileFromSoftBus(const std::string &srcUri, - const std::string &destUri, - std::shared_ptr fileInfos, - std::shared_ptr callback); + static int CopyFileFromSoftBus(const std::string &srcUri, const std::string &destUri, + std::shared_ptr fileInfos, std::shared_ptr callback); + private: static std::string GetNetworkIdFromUri(const std::string &uri); - static void CallbackComplete(std::shared_ptr entry); + static void CallbackComplete(std::shared_ptr entry); static void RmDir(const std::string &path); static std::string CreateDfsCopyPath(); static std::string GetFileName(const std::string &path); static int32_t CopyToSandBox(const std::string &srcUri, const std::string &disSandboxPath, const std::string &sandboxPath, const std::string ¤tId); - static int32_t PrepareCopySession(const std::string &srcUri, - const std::string &destUri, - TransListenerCore* transListener, - Storage::DistributedFile::HmdfsInfo &info, - std::string &disSandboxPath); + static int32_t PrepareCopySession(const std::string &srcUri, const std::string &destUri, + TransListenerCore *transListener, Storage::DistributedFile::HmdfsInfo &info, std::string &disSandboxPath); static int HandleCopyFailure(CopyEvent ©Event, const Storage::DistributedFile::HmdfsInfo &info, const std::string &disSandboxPath, const std::string ¤tId); - static int WaitForCopyResult(TransListenerCore* transListener); + static int WaitForCopyResult(TransListenerCore *transListener); static std::atomic getSequenceId_; std::mutex cvMutex_; std::condition_variable cv_; CopyEvent copyEvent_; std::mutex callbackMutex_; - std::shared_ptr callback_; + std::shared_ptr callback_; }; } // namespace ModuleFileIO } // namespace FileManagement } // namespace OHOS -#endif // FILEMANAGEMENT_FILE_API_TRANS_LISTENER_CORE_H \ No newline at end of file +#endif // INTERFACES_KITS_JS_SRC_MOD_FS_PROPERTIES_COPY_LISTENER_TRANS_LISTENER_CORE_H \ No newline at end of file