• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 #include "command/recv_command_v10.h"
16 
17 #include <cerrno>
18 #include <fcntl.h>
19 #include <set>
20 #include <sys/stat.h>
21 #include <sys/types.h>
22 #include <unistd.h>
23 
24 #include "constant.h"
25 #include "datashare_result_set.h"
26 #include "directory_ex.h"
27 #include "media_file_utils.h"
28 #include "medialibrary_errno.h"
29 #include "userfile_client_ex.h"
30 
31 namespace OHOS {
32 namespace Media {
33 namespace MediaTool {
34 constexpr mode_t OPEN_MODE = 0664;
GetWriteFilePath(const ExecEnv & env,const FileAsset & fileAsset,std::string & wFilePath)35 static bool GetWriteFilePath(const ExecEnv &env, const FileAsset &fileAsset, std::string &wFilePath)
36 {
37     wFilePath = env.recvParam.recvPath;
38     if (!MediaFileUtils::IsDirectory(wFilePath)) {
39         if (env.recvParam.isRecvAll) {
40             printf("RecvFilePath:%s is not a directory.\n", wFilePath.c_str());
41             return false;
42         }
43     } else {
44         wFilePath = IncludeTrailingPathDelimiter(wFilePath);
45         string displayName = fileAsset.GetDisplayName();
46         if (displayName.empty()) {
47             printf("RecvFile displayName is null.\n");
48             return false;
49         }
50         wFilePath += displayName;
51     }
52     return true;
53 }
54 
RecvFile(const ExecEnv & env,const FileAsset & fileAsset)55 static int32_t RecvFile(const ExecEnv &env, const FileAsset &fileAsset)
56 {
57     std::string wFilePath;
58     if (!GetWriteFilePath(env, fileAsset, wFilePath)) {
59         return Media::E_ERR;
60     }
61     auto wfd = open(wFilePath.c_str(), O_CREAT | O_WRONLY | O_CLOEXEC, OPEN_MODE);
62     if (wfd <= 0) {
63         printf("%s open file failed. errno:%d, fileName:%s\n", STR_FAIL.c_str(), errno, wFilePath.c_str());
64         return Media::E_ERR;
65     }
66     auto rfd = UserFileClientEx::Open(fileAsset.GetUri(), Media::MEDIA_FILEMODE_READONLY);
67     if (rfd <= 0) {
68         printf("%s open failed. uri:%s\n", STR_FAIL.c_str(), fileAsset.GetUri().c_str());
69         close(wfd);
70         return Media::E_ERR;
71     }
72     auto ret = MediaFileUtils::CopyFile(rfd, wfd);
73     if (!ret) {
74         printf("%s receive data failed. uri:%s\n", STR_FAIL.c_str(), fileAsset.GetUri().c_str());
75     } else {
76         printf("%s\n", wFilePath.c_str());
77     }
78     UserFileClientEx::Close(fileAsset.GetUri(), rfd, Media::MEDIA_FILEMODE_READONLY);
79     close(wfd);
80     return ret ? Media::E_OK : Media::E_ERR;
81 }
82 
RecvAsset(const ExecEnv & env,const std::string & tableName,const std::string & uri)83 static int32_t RecvAsset(const ExecEnv &env, const std::string &tableName, const std::string &uri)
84 {
85     if (tableName.empty()) {
86         printf("%s can not get query table, uri:%s\n", STR_FAIL.c_str(), uri.c_str());
87         return Media::E_ERR;
88     }
89     printf("Table Name: %s\n", tableName.c_str());
90     std::shared_ptr<DataShare::DataShareResultSet> resultSet;
91     auto res = UserFileClientEx::Query(tableName, uri, resultSet);
92     std::shared_ptr<FetchResult<FileAsset>> fetchResult = std::make_shared<FetchResult<FileAsset>>(resultSet);
93     fetchResult->SetResultNapiType(ResultNapiType::TYPE_USERFILE_MGR);
94     if (res != Media::E_OK) {
95         printf("%s query issue. tableName:%s, uri:%s\n", STR_FAIL.c_str(), tableName.c_str(), uri.c_str());
96         return Media::E_ERR;
97     }
98     if (fetchResult == nullptr) {
99         return Media::E_OK;
100     }
101     auto count = fetchResult->GetCount();
102     if (count > 1) {
103         printf("%s get result count=%d, failed, uri:%s\n", STR_FAIL.c_str(), count, uri.c_str());
104     } else if (count == 0) {
105         printf("WARN: get result count 0, uri:%s\n", uri.c_str());
106     } else {
107         auto fileAsset = fetchResult->GetFirstObject();
108         RecvFile(env, *fileAsset);
109     }
110     fetchResult->Close();
111     return Media::E_OK;
112 }
113 
RecvAssets(const ExecEnv & env,const std::string & tableName)114 static int32_t RecvAssets(const ExecEnv &env, const std::string &tableName)
115 {
116     if (tableName.empty()) {
117         printf("%s table name is empty.\n", STR_FAIL.c_str());
118         return Media::E_ERR;
119     }
120     printf("Table Name: %s\n", tableName.c_str());
121     std::shared_ptr<DataShare::DataShareResultSet> resultSet;
122     auto res = UserFileClientEx::Query(tableName, "", resultSet);
123     std::shared_ptr<FetchResult<FileAsset>> fetchResult = std::make_shared<FetchResult<FileAsset>>(resultSet);
124     fetchResult->SetResultNapiType(ResultNapiType::TYPE_USERFILE_MGR);
125     if (res != Media::E_OK) {
126         printf("%s query issue. tableName:%s\n", STR_FAIL.c_str(), tableName.c_str());
127         return Media::E_ERR;
128     }
129     if (fetchResult == nullptr) {
130         return Media::E_OK;
131     }
132     auto count = fetchResult->GetCount();
133     for (int32_t index = 0; index < count; index++) {
134         auto fileAsset = fetchResult->GetObjectAtPosition(index);
135         RecvFile(env, *fileAsset);
136     }
137     fetchResult->Close();
138     return Media::E_OK;
139 }
140 
Start(const ExecEnv & env)141 int32_t RecvCommandV10::Start(const ExecEnv &env)
142 {
143     if (env.recvParam.isRecvAll) {
144         bool hasError = false;
145         auto tables = UserFileClientEx::GetSupportTables();
146         for (auto tableName : tables) {
147             if (RecvAssets(env, tableName) != Media::E_OK) {
148                 hasError = true;
149             }
150             printf("\n");
151         }
152         return hasError ? Media::E_ERR : Media::E_OK;
153     } else {
154         string tableName = UserFileClientEx::GetTableNameByUri(env.recvParam.recvUri);
155         return RecvAsset(env, tableName, env.recvParam.recvUri);
156     }
157 }
158 } // namespace MediaTool
159 } // namespace Media
160 } // namespace OHOS
161