• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# 获取并使用公共目录
2<!--Kit: Core File Kit-->
3<!--Subsystem: FileManagement-->
4<!--Owner: @wangke25; @gsl_1234; @wuchengjun5-->
5<!--Designer: @gsl_1234; @wangke25-->
6<!--Tester: @liuhonggang123; @yue-ye2; @juxiaopang-->
7<!--Adviser: @foryourself-->
8
9## 通过 ArkTS 接口获取并访问公共目录
10
11目录环境能力接口([ohos.file.environment](../reference/apis-core-file-kit/js-apis-file-environment.md))提供获取公共目录路径的能力,支持三方应用在公共文件用户目录下进行文件访问操作。
12
13 **约束限制**
14 - 使用此方式,需确认设备具有以下系统能力:SystemCapability.FileManagement.File.Environment.FolderObtain,当前仅支持2in1设备。
15   ```ts
16   if (!canIUse('SystemCapability.FileManagement.File.Environment.FolderObtain')) {
17       console.error('this api is not supported on this device');
18       return;
19   }
20   ```
21 - 公共目录获取接口仅用于获取公共目录路径,不对公共目录访问权限进行校验。若需访问公共目录需申请对应的公共目录访问权限。三方应用需要访问公共目录时,需通过弹窗授权向用户申请授予 Download 目录权限、Documents 目录权限或 Desktop 目录权限,具体参考[访问控制-向用户申请授权](../security/AccessToken/request-user-authorization.md)。
22   <!--RP1-->
23   ```json
24   "requestPermissions" : [
25       "ohos.permission.READ_WRITE_DOWNLOAD_DIRECTORY",
26       "ohos.permission.READ_WRITE_DOCUMENTS_DIRECTORY",
27       "ohos.permission.READ_WRITE_DESKTOP_DIRECTORY",
28   ]
29   ```
30   <!--RP1End-->
31
32### 示例
33
341.获取公共目录路径。
35
36```ts
37import { BusinessError } from '@kit.BasicServicesKit';
38import { Environment } from '@kit.CoreFileKit';
39
40function getUserDirExample() {
41    try {
42        const downloadPath = Environment.getUserDownloadDir();
43        console.info(`success to getUserDownloadDir: ${downloadPath}`);
44        const documentsPath = Environment.getUserDocumentDir();
45        console.info(`success to getUserDocumentDir: ${documentsPath}`);
46    } catch (error) {
47        const err: BusinessError = error as BusinessError;
48        console.error(`failed to get user dir, Error code: ${err.code}, message: ${err.message}`);
49    }
50}
51```
52
532.以 Download 目录为例,访问 Download 目录下的文件。
54
55```ts
56import { BusinessError } from '@kit.BasicServicesKit';
57import { Environment } from '@kit.CoreFileKit';
58import { fileIo as fs } from '@kit.CoreFileKit';
59import { common } from '@kit.AbilityKit';
60
61// 请在组件内获取context,确保this.getUIContext().getHostContext()返回结果为UIAbilityContext
62let context = this.getUIContext().getHostContext() as common.UIAbilityContext;
63
64function readUserDownloadDirExample(context: common.UIAbilityContext) {
65    // 检查是否具有 READ_WRITE_DOWNLOAD_DIRECTORY 权限,无权限则需要向用户申请授予权限。
66    try {
67        // 获取 Download 目录
68        const downloadPath = Environment.getUserDownloadDir();
69        console.info(`success to getUserDownloadDir: ${downloadPath}`);
70        const dirPath = context.filesDir;
71        console.info(`success to get filesDir: ${dirPath}`);
72        // 查看 Download 目录下的文件并拷贝到沙箱目录中
73        let fileList: string[] = fs.listFileSync(downloadPath);
74        fileList.forEach((file, index) => {
75            console.info(`${downloadPath} ${index}: ${file}`);
76            fs.copyFileSync(`${downloadPath}/${file}`, `${dirPath}/${file}`);
77        });
78        // 查看沙箱目录下对应的文件
79        fileList = fs.listFileSync(dirPath);
80        fileList.forEach((file, index) => {
81            console.info(`${dirPath} ${index}: ${file}`);
82        });
83    } catch (error) {
84        const err: BusinessError = error as BusinessError;
85        console.error(`Error code: ${err.code}, message: ${err.message}`);
86    }
87}
88```
89
903.以 Download 目录为例,保存文件到 Download 目录。
91
92```ts
93import { BusinessError } from '@kit.BasicServicesKit';
94import { Environment } from '@kit.CoreFileKit';
95import { fileIo as fs } from '@kit.CoreFileKit';
96
97function writeUserDownloadDirExample() {
98// 检查是否具有 READ_WRITE_DOWNLOAD_DIRECTORY 权限,无权限则需要向用户申请授予权限。
99    try {
100        // 获取 Download 目录
101        const downloadPath = Environment.getUserDownloadDir();
102        console.info(`success to getUserDownloadDir: ${downloadPath}`);
103        // 保存 temp.txt 到 Download 目录下
104        const file = fs.openSync(`${downloadPath}/temp.txt`, fs.OpenMode.CREATE | fs.OpenMode.READ_WRITE);
105        fs.writeSync(file.fd, 'write a message');
106        fs.closeSync(file);
107    } catch (error) {
108        const err: BusinessError = error as BusinessError;
109        console.error(`Error code: ${err.code}, message: ${err.message}`);
110    }
111}
112```
113
114
115
116## 通过 C/C++ 接口获取并使用公共目录
117
118除了通过 ArkTS 访问公共目录的方式,也可通过 C/C++ 接口进行目录访问,具体可以参考 [Environment](../reference/apis-core-file-kit/capi-oh-environment-h.md)。
119
120 **约束限制**
121 - 使用此接口,需确认设备具有以下系统能力:SystemCapability.FileManagement.File.Environment.FolderObtain122 - 三方应用需要访问公共目录时,需通过弹窗授权向用户申请授予 Download 目录权限、Documents 目录权限或 Desktop 目录权限,具体参考[访问控制-向用户申请授权](../security/AccessToken/request-user-authorization.md)。
123
124### 接口说明
125
126接口的详细说明,请参考[API参考](../reference/apis-core-file-kit/capi-oh-environment-h.md)。
127
128| 接口名称                                                                 | 描述                           |
129| ------------------------------------------------------------------------ | ------------------------------ |
130| FileManagement_ErrCode OH_Environment_GetUserDownloadDir (char **result) | 获取用户Download目录沙箱路径。只支持2in1设备 |
131| FileManagement_ErrCode OH_Environment_GetUserDesktopDir (char **result)  | 获取用户Desktop目录沙箱路径。只支持2in1设备  |
132| FileManagement_ErrCode OH_Environment_GetUserDocumentDir (char **result) | 获取用户Document目录沙箱路径。只支持2in1设备 |
133
134### 开发步骤
135
136**在CMake脚本中链接动态库**
137
138CMakeLists.txt中添加以下lib。
139
140```txt
141target_link_libraries(sample PUBLIC libohenvironment.so libhilog_ndk.z.so)
142```
143
144**添加头文件**
145
146```c++
147#include <filemanagement/environment/oh_environment.h>
148#include <filemanagement/fileio/oh_fileio.h>
149#include <hilog/log.h>
150```
151
1521.调用 OH_Environment_GetUserDownloadDir 接口获取用户 Download 目录沙箱路径,在接口中使用malloc申请的内存需要在使用完后释放因此需要free对应的内存。示例代码如下所示:
153
154```c++
155#include <cstdlib>
156
157void GetUserDownloadDirExample()
158{
159    char *downloadPath = nullptr;
160    FileManagement_ErrCode ret = OH_Environment_GetUserDownloadDir(&downloadPath);
161    if (ret == 0) {
162        OH_LOG_INFO(LOG_APP, "Download Path=%{public}s", downloadPath);
163        free(downloadPath);
164    } else {
165        OH_LOG_ERROR(LOG_APP, "GetDownloadPath fail, error code is %{public}d", ret);
166    }
167}
168```
169
1702.调用 OH_Environment_GetUserDownloadDir 接口获取用户 Download 目录沙箱路径,并查看 Download 目录下的文件。示例代码如下所示:
171
172```c++
173#include <cstdlib>
174#include <dirent.h>
175
176void ScanUserDownloadDirPathExample()
177{
178    // 获取 download 路径
179    char *downloadPath = nullptr;
180    FileManagement_ErrCode ret = OH_Environment_GetUserDownloadDir(&downloadPath);
181    if (ret == 0) {
182        OH_LOG_INFO(LOG_APP, "Download Path=%{public}s", downloadPath);
183    } else {
184        OH_LOG_ERROR(LOG_APP, "GetDownloadPath fail, error code is %{public}d", ret);
185        return;
186    }
187    // 查看文件夹下的文件
188    struct dirent **namelist = nullptr;
189    int num = scandir(downloadPath, &namelist, nullptr, nullptr);
190    if (num < 0) {
191        free(downloadPath);
192        OH_LOG_ERROR(LOG_APP, "Failed to scan dir");
193        return;
194    }
195    for (int i = 0; i < num; i++) {
196        OH_LOG_INFO(LOG_APP, "%{public}s", namelist[i]->d_name);
197    }
198    free(downloadPath);
199    for (int i = 0; i < num; i++) {
200        free(namelist[i]);
201    }
202    free(namelist);
203}
204```
205
2063.调用 OH_Environment_GetUserDownloadDir 接口获取用户 Download 目录沙箱路径,并保存 temp.txt 到 Download 目录下。示例代码如下所示:
207
208```c++
209#include <fstream>
210
211void WriteUserDownloadDirPathExample()
212{
213    // 获取 download 路径
214    char *downloadPath = nullptr;
215    FileManagement_ErrCode ret = OH_Environment_GetUserDownloadDir(&downloadPath);
216    if (ret == 0) {
217        OH_LOG_INFO(LOG_APP, "Download Path=%{public}s", downloadPath);
218    } else {
219        OH_LOG_ERROR(LOG_APP, "GetDownloadPath fail, error code is %{public}d", ret);
220        return;
221    }
222    // 保存文件到 download 目录下
223    std::string filePath = std::string(downloadPath) + "/temp.txt";
224    free(downloadPath);
225
226    std::ofstream outfile;
227    outfile.open(filePath.c_str());
228    if (!outfile) {
229        OH_LOG_ERROR(LOG_APP, "Failed to open file");
230        return;
231    }
232    std::string msg = "Write a message";
233    outfile.write(msg.c_str(), msg.size());
234    outfile.close();
235}
236```
237