HarmonyOS 鸿蒙Next中离线下载
HarmonyOS 鸿蒙Next中离线下载
如何实现文件下载存储内容,并实时获取下载进度用于展示,同时保持后台下载功能
开发者您好,可参考示例代码中的多文件下载监听,使用request.agent.create创建上传任务,通过on(‘progress’)监听下载进度。由于使用@ohos.request (上传下载)退至后台由系统托管,因此不用申请长时任务权限,也可以保持后台下载。文件保存目录在request.agent.Config的saveas字段中设置,示例中设置为默认的沙箱目录。如果想设置为其他目录,可参考应用文件上传下载,其中有案例设置下载目录为应用文件目录或用户文件目录。
更多关于HarmonyOS 鸿蒙Next中离线下载的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html
我要下载存储的是接口返回的一个个json数据,每一个json对象包含但不限于{时间,唯一id,几千字的文本内容}等等属性,根据我的选择接口会返回几个到几千个不等的json对象
开发者您好,请问您具体的场景是怎样的,请详细说明。若需要写入沙箱,直接使用fs.open打开或创建文件,使用fs.write写入即可。如果已有接口返回信息,那写入沙箱应展示写入进度,而非下载进度,请说明。
有要学HarmonyOS AI的同学吗,联系我:https://www.itying.com/goods-1206.html
你好,可以参考示例代码:
你可以看一下这个地方:长时任务
import http from '@ohos.net.http';
import { fileIo as fs } from '@kit.CoreFileKit';
import { common } from '@kit.AbilityKit';
import backgroundTaskManager from '@kit.Ability.BackgroundTaskManager';
// 文件下载工具类
class DownloadUtil {
// 启动后台长时任务
private async startBackgroundTask(): Promise<number> {
try {
const bgTaskId = await backgroundTaskManager.startBackgroundRunning({
backgroundMode: backgroundTaskManager.BackgroundMode.DATA_TRANSFER
});
return bgTaskId;
} catch (error) {
console.error(`后台任务启动失败: ${error.code}, ${error.message}`);
return -1;
}
}
// 下载文件主逻辑
public async downloadFile(url: string, fileName: string) {
const context = getContext() as common.UIAbilityContext;
const savePath = `${context.filesDir}/${fileName}`;
let bgTaskId = -1;
// 1. 启动后台任务
bgTaskId = await this.startBackgroundTask();
// 2. 创建HTTP请求
const httpRequest = http.createHttp();
const fileStream = fs.createStreamSync(savePath, "w+");
// 3. 进度监听回调
httpRequest.on('dataReceiveProgress', (progressData: http.DataReceiveProgressInfo) => {
const percent = Math.round((progressData.receiveSize / progressData.totalSize) * 100);
// 此处更新UI进度(示例)
console.info(`下载进度: ${percent}%`);
});
// 4. 数据接收处理
httpRequest.on('dataReceive', (buffer: ArrayBuffer) => {
fileStream.writeSync(buffer);
});
try {
// 5. 发起下载请求
await httpRequest.request(url, {
method: http.RequestMethod.GET,
readTimeout: 60000 * 30 // 延长超时时间
});
// 6. 下载完成处理
fileStream.flushSync();
fileStream.closeSync();
} finally {
// 7. 停止后台任务
if (bgTaskId !== -1) {
backgroundTaskManager.stopBackgroundRunning(bgTaskId);
}
}
}
}
-
后台下载保障
- 使用
BackgroundMode.DATA_TRANSFER长时任务类型 - 通过
startBackgroundRunning()申请后台权限 - 下载完成后调用
stopBackgroundRunning()释放资源 - 参考:1应用前台切后台下载需与长时任务协同
- 使用
-
实时进度监控
- 监听
dataReceiveProgress事件 - 通过
receiveSize/totalSize计算百分比 - 使用OnDownloadProgress接口监听进度
- 监听
-
文件存储处理
- 使用
@kit.CoreFileKit文件操作模块 - 通过
createStreamSync()创建文件流 - 分块写入避免内存溢出(
dataReceive事件)
- 使用
三、配置要求
- 权限声明(
module.json5)
"requestPermissions": [
{
"name": "ohos.permission.INTERNET"
},
{
"name": "ohos.permission.KEEP_BACKGROUND_RUNNING"
}
]
- 后台模式声明
"abilities": [
{
"backgroundModes": ["dataTransfer"]
}
]
还可以参考:
鸿蒙Next的离线下载功能通过分布式数据管理实现,支持无网络环境下应用与数据同步。该功能基于HarmonyOS的分布式软总线技术,允许设备间直接传输数据。开发者可使用DataShare或DistributedDataKit接口进行跨设备数据访问,系统会自动管理数据同步与冲突解决。离线状态下,应用通过本地数据库操作数据,网络恢复后自动同步至其他设备。
在HarmonyOS Next中实现文件下载、进度监控与后台任务,核心是使用@ohos.request和@ohos.taskpool模块。以下是关键实现步骤:
1. 下载与存储实现
使用request.downloadFile()接口:
import request from '@ohos.request';
import fs from '@ohos.file.fs';
async function downloadFile(url: string, fileName: string) {
let downloadConfig: request.DownloadConfig = {
url: url,
filePath: getContext().filesDir + '/' + fileName, // 应用沙箱路径
overwrite: true
};
let task: request.DownloadTask = await request.downloadFile(getContext(), downloadConfig);
return task;
}
2. 实时进度获取
通过DownloadTask的订阅机制:
task.on('progress', (receivedSize: number, totalSize: number) => {
let progress = (receivedSize / totalSize * 100).toFixed(2);
// 更新UI进度显示
updateProgress(progress);
});
task.on('complete', () => {
console.log('下载完成');
});
task.on('fail', (err: BusinessError) => {
console.error('下载失败:', err.code);
});
3. 后台下载保持
需配置后台任务与持续化存储:
(1)声明后台权限:
在module.json5中添加:
"abilities": [
{
"name": "ServiceAbility",
"srcEntry": "./ets/serviceability/ServiceAbility.ets",
"backgroundModes": ["dataTransfer"]
}
]
(2)使用TaskPool保持后台执行:
import taskpool from '@ohos.taskpool';
@Concurrent
async function backgroundDownload(url: string, path: string) {
// 下载逻辑
}
let task: taskpool.Task = new taskpool.Task(backgroundDownload, url, filePath);
taskpool.execute(task);
(3)状态持久化:
使用Preferences存储下载状态:
import preferences from '@ohos.data.preferences';
// 存储进度
let prefs = await preferences.getPreferences(getContext(), 'downloadPrefs');
await prefs.put('progress', progress);
await prefs.flush();
4. 完整示例结构
class DownloadManager {
private task: request.DownloadTask | null = null;
async startDownload(url: string, fileName: string) {
// 1. 创建下载任务
this.task = await request.downloadFile(getContext(), {
url: url,
filePath: getContext().filesDir + '/' + fileName
});
// 2. 订阅进度
this.task.on('progress', this.handleProgress.bind(this));
// 3. 启动后台任务
this.runInBackground();
}
private handleProgress(received: number, total: number) {
// 更新进度并持久化
let progress = (received / total * 100);
this.saveProgress(progress);
}
private async runInBackground() {
// TaskPool后台执行
}
}
关键注意事项:
- 网络权限需在
module.json5中配置ohos.permission.INTERNET - 大文件下载建议使用
fs.createStream()分片处理 - 后台任务需合理管理生命周期,避免资源泄漏
- 应用退到后台时,下载任务会自动转入后台执行队列
这种实现方式能确保下载任务在应用前后台切换时持续执行,同时通过事件订阅机制实时反馈进度。

