1 /*
2 * Copyright (c) 2023 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "utils_log.h"
17 #include "ipc/cloud_download_callback_manager.h"
18
19 namespace OHOS::FileManagement::CloudSync {
20 using namespace std;
21
CloudDownloadCallbackManager()22 CloudDownloadCallbackManager::CloudDownloadCallbackManager()
23 {
24 callback_ = nullptr;
25 }
26
StartDonwload(const std::string path,const int32_t userId)27 void CloudDownloadCallbackManager::StartDonwload(const std::string path, const int32_t userId)
28 {
29 lock_guard<mutex> lock(downloadsMtx_);
30 downloads_[path].state = DownloadProgressObj::Status::RUNNING;
31 downloads_[path].path = path;
32 LOGI("download_file : %{public}d start download %{public}s callback success.", userId, path.c_str());
33 }
34
StopDonwload(const std::string path,const int32_t userId)35 void CloudDownloadCallbackManager::StopDonwload(const std::string path, const int32_t userId)
36 {
37 lock_guard<mutex> lock(downloadsMtx_);
38 if (downloads_.find(path) != downloads_.end()) {
39 downloads_[path].state = DownloadProgressObj::Status::STOPPED;
40 LOGI("download_file : %{public}d stop download %{public}s callback success.", userId, path.c_str());
41 } else {
42 LOGI("download_file : %{public}d stop download %{public}s callback fail, task not exist.",
43 userId, path.c_str());
44 }
45 }
46
RegisterCallback(const int32_t userId,const sptr<ICloudDownloadCallback> downloadCallback)47 void CloudDownloadCallbackManager::RegisterCallback(const int32_t userId,
48 const sptr<ICloudDownloadCallback> downloadCallback)
49 {
50 LOGI("download_file : %{public}d register download callback : %{public}d", userId,
51 downloadCallback != nullptr);
52 unique_lock<mutex> lock(callbackMutex_);
53 callback_ = downloadCallback;
54 }
55
UnregisterCallback(const int32_t userId)56 void CloudDownloadCallbackManager::UnregisterCallback(const int32_t userId)
57 {
58 LOGI("download_file : %{public}d unregister download callback", userId);
59 unique_lock<mutex> lock(callbackMutex_);
60 callback_ = nullptr;
61 }
62
OnDownloadedResult(const std::string path,std::vector<DriveKit::DKDownloadAsset> assetsToDownload,std::shared_ptr<DataHandler> handler,std::shared_ptr<DriveKit::DKContext> context,std::shared_ptr<const DriveKit::DKDatabase> database,const std::map<DriveKit::DKDownloadAsset,DriveKit::DKDownloadResult> & results,const DriveKit::DKError & err)63 void CloudDownloadCallbackManager::OnDownloadedResult(
64 const std::string path,
65 std::vector<DriveKit::DKDownloadAsset> assetsToDownload,
66 std::shared_ptr<DataHandler> handler,
67 std::shared_ptr<DriveKit::DKContext> context,
68 std::shared_ptr<const DriveKit::DKDatabase> database,
69 const std::map<DriveKit::DKDownloadAsset, DriveKit::DKDownloadResult> &results,
70 const DriveKit::DKError &err)
71 {
72 unique_lock<mutex> lock(downloadsMtx_);
73 auto res = downloads_.find(path);
74 bool isDownloading = (res != downloads_.end());
75
76 LOGI("download_file : [callback downloaded] %{public}s is downloading : %{public}d .",
77 path.c_str(), isDownloading);
78 if (!isDownloading) {
79 lock.unlock();
80 return;
81 }
82
83 auto download = res->second;
84 downloads_.erase(res);
85 lock.unlock();
86
87 LOGI("download_file : [callback downloaded] %{public}s state is %{public}s, localErr is %{public}d.",
88 path.c_str(), download.to_string().c_str(), static_cast<int>(err.dkErrorCode));
89 auto downloadedState = err.HasError() ? DownloadProgressObj::FAILED : DownloadProgressObj::COMPLETED;
90 /**
91 * Avoiding the issue of cloud service not returning a total error code.
92 * Currently, only single asset download is supported.
93 */
94 for (const auto &it : results) {
95 if (!it.second.IsSuccess()) {
96 LOGE("download file failed, localErr: %{public}d", it.second.GetDKError().dkErrorCode);
97 downloadedState = DownloadProgressObj::FAILED;
98 break;
99 }
100 }
101
102 if (callback_ != nullptr && download.state == DownloadProgressObj::RUNNING) {
103 download.state = downloadedState;
104 callback_->OnDownloadProcess(download);
105 if ((assetsToDownload.size() == 1) && (download.state == DownloadProgressObj::COMPLETED)) {
106 (void)handler->OnDownloadSuccess(assetsToDownload[0]);
107 }
108 }
109 }
110
OnDownloadProcess(const std::string path,std::shared_ptr<DriveKit::DKContext> context,DriveKit::DKDownloadAsset asset,DriveKit::TotalSize totalSize,DriveKit::DownloadSize downloadSize)111 void CloudDownloadCallbackManager::OnDownloadProcess(const std::string path,
112 std::shared_ptr<DriveKit::DKContext> context,
113 DriveKit::DKDownloadAsset asset,
114 DriveKit::TotalSize totalSize,
115 DriveKit::DownloadSize downloadSize)
116 {
117 unique_lock<mutex> lock(downloadsMtx_);
118 auto res = downloads_.find(path);
119 bool isDownloading = (res != downloads_.end());
120
121 LOGI("download_file : [callback downloading] %{public}s is downloading : %{public}d .",
122 path.c_str(), isDownloading);
123 if (!isDownloading) {
124 lock.unlock();
125 return;
126 }
127
128 auto download = res->second;
129 lock.unlock();
130
131 download.downloadedSize = downloadSize;
132 download.totalSize = totalSize;
133 LOGI("download_file : [callback downloading] %{public}s state is %{public}s.", path.c_str(),
134 download.to_string().c_str());
135 if (callback_ != nullptr && download.state == DownloadProgressObj::RUNNING) {
136 callback_->OnDownloadProcess(download);
137 }
138 }
139
140 } // namespace OHOS::FileManagement::CloudSync
141