你还想“退到后台继续跑”?系统不打你就不错了——后台任务、通知、提醒代理一次讲透!

🏆本文收录于「滚雪球学SpringBoot」专栏(全网一个名),手把手带你零基础入门Spring Boot,从入门到就业,助你早日登顶实现财富自由🚀;同时,欢迎大家关注&&收藏&&订阅!持续更新中,up!up!up!!
环境说明:Windows 10 + IntelliJ IDEA 2021.3.2 + Jdk 1.8
🧩先把话说清楚:后台“能跑多久”,不是你说了算🙃
鸿蒙的后台策略很现实:你一退后台,过一会儿就会被挂起,除非你按规矩申请后台任务。短时任务负责“给你喘口气”,长时任务负责“我允许你长期干,但必须用户可感知”。官方把这套规则写得很明确:短时任务用于挂起前补尾巴(保存状态/发消息等),长时任务用于后台长期运行且用户可感知的业务(播放、导航、录制、下载等)。
1️⃣ 🏃后台任务申请:短时 vs 长时(别选错,不然要么卡死要么被管控)
🕐短时任务(Transient Task):给你“最多几分钟”的收尾时间
适用场景(特别像现实生活):
- 你刚退后台,得保存草稿、写本地日志、上报一次埋点、发最后一条消息
- 总之:耗时不长,但必须在挂起前做完
硬性规则(不听真的会翻车):
- 申请时机:必须在前台或
onBackground回调内申请,否则会失败。 - 数量限制:同一时刻最多 3 个短时任务。
- 配额机制:默认单日 10 分钟,单次最多 3 分钟;低电量单次默认 1 分钟;超时不取消会被系统管控(挂起/终止)。
- 任务用完要主动 cancel,不然浪费当天配额,等于“把自己活活饿死”。
🧪ArkTS 示例:申请短时任务 + 超时回调 + 主动取消
import { backgroundTaskManager } from '@kit.BackgroundTasksKit';
import { BusinessError } from '@kit.BasicServicesKit';
let requestId: number | undefined;
export function startTransientTask() {
try {
const info = backgroundTaskManager.requestSuspendDelay('save_draft', () => {
// ⏳系统提示“快到点了”,你得赶紧收尾并取消
console.info('⏰ transient task is expiring, cancel now!');
if (requestId !== undefined) {
backgroundTaskManager.cancelSuspendDelay(requestId);
requestId = undefined;
}
});
requestId = info.requestId;
console.info(`✅ transient task granted, requestId=${requestId}`);
} catch (e) {
const err = e as BusinessError;
console.error(`❌ requestSuspendDelay failed: ${err.code}, ${err.message}`);
}
}
export async function logRemainingTime() {
if (requestId === undefined) return;
const left = await backgroundTaskManager.getRemainingDelayTime(requestId);
console.info(`🕐 remaining(ms)=${left}`);
}
export function stopTransientTask() {
if (requestId !== undefined) {
backgroundTaskManager.cancelSuspendDelay(requestId);
requestId = undefined;
console.info('🧹 transient task canceled');
}
}
接口与约束(requestSuspendDelay / getRemainingDelayTime / cancelSuspendDelay、配额与超时行为)是官方短时任务指南的核心内容。
🕰️长时任务(Continuous Task):想长期跑?可以,但你得“让用户看得见”
适用场景(系统认可的“正经后台”):
- 🎵 音视频播放/投播
- 🎤 录音/录屏
- 📍 导航定位
- 📤 数据传输(上传下载)
- 🔵 蓝牙交互
- 🔗 多设备互联
- 📞 VoIP(部分版本)
……这些类型与限制、校验机制,官方文档写得非常细:申请成功后通知栏会显示关联通知;用户删除通知,系统会自动停止长时任务。
Stage 模型的关键点:
- 长时任务在 Stage 模型里一般由 UIAbility 申请。
- 需要权限
ohos.permission.KEEP_BACKGROUND_RUNNING,并在module.json5的backgroundModes里声明业务类型(比如 audioPlayback、location、dataTransfer 等)。
🧩module.json5 关键配置(示例)
{
"module": {
"abilities": [
{
"name": "EntryAbility",
"type": "page",
"backgroundModes": [
"audioPlayback",
"dataTransfer"
]
}
],
"requestPermissions": [
{ "name": "ohos.permission.KEEP_BACKGROUND_RUNNING" }
]
}
}
(配置项与权限要求来自官方长时任务指南。)
🧪ArkTS 示例:申请/取消长时任务(最常用的那一套)
import { backgroundTaskManager } from '@kit.BackgroundTasksKit';
import wantAgent from '@ohos.wantAgent'; // 不同工程模板导入方式可能略有差异
import { BusinessError } from '@kit.BasicServicesKit';
export async function startContinuousTask(context: any) {
try {
// ✅通常需要 WantAgent 来关联通知点击后的跳转
const agentInfo: wantAgent.WantAgentInfo = {
wants: [{
bundleName: context.bundleName,
abilityName: 'EntryAbility'
}],
operationType: wantAgent.OperationType.START_ABILITY,
requestCode: 0
};
const agent = await wantAgent.getWantAgent(agentInfo);
// 申请单个长时任务(不同 API 版本也支持“多个任务一次申请”的 request 形式)
await backgroundTaskManager.startBackgroundRunning(
context,
backgroundTaskManager.BackgroundMode.AUDIO_PLAYBACK,
agent
);
console.info('✅ continuous task started');
} catch (e) {
const err = e as BusinessError;
console.error(`❌ startBackgroundRunning failed: ${err.code}, ${err.message}`);
}
}
export async function stopContinuousTask(context: any) {
try {
await backgroundTaskManager.stopBackgroundRunning(context);
console.info('🛑 continuous task stopped');
} catch (e) {
const err = e as BusinessError;
console.error(`❌ stopBackgroundRunning failed: ${err.code}, ${err.message}`);
}
}
长时任务的类型、通知栏行为、以及 startBackgroundRunning/stopBackgroundRunning 等接口,都在官方“长时任务(ArkTS)”指南里。
😄老司机提醒一句:
长时任务不是“免死金牌”。系统会做一致性校验:你申请了播放却没播放、申请了数据传输却不更新进度……都可能被管控。
2️⃣ 🔔Notification API:通知不是“想发就发”,先拿授权!
通知这块的基本流程是:
- 请求用户授权
requestEnableNotification()(没授权你发不出去) - 组装
NotificationRequest notificationManager.publish()发布(相同 id/label 会替换旧通知)
🧪ArkTS:请求通知授权 + 发一条最小通知
import { notificationManager } from '@kit.NotificationKit';
import { BusinessError } from '@kit.BasicServicesKit';
export async function ensureNotificationEnabled(): Promise<boolean> {
try {
await notificationManager.requestEnableNotification(); // 弹窗询问用户
return true;
} catch (e) {
const err = e as BusinessError;
console.error(`❌ requestEnableNotification failed: ${err.code}, ${err.message}`);
return false;
}
}
export async function publishSimpleNotification() {
const ok = await ensureNotificationEnabled();
if (!ok) return;
const req: notificationManager.NotificationRequest = {
id: 1001,
content: {
notificationContentType: notificationManager.ContentType.NOTIFICATION_CONTENT_BASIC_TEXT,
normal: {
title: '🎉 任务完成啦',
text: '我在后台把活儿干完了~'
}
}
};
await notificationManager.publish(req);
console.info('✅ notification published');
}
授权要求来自“请求通知授权”指南;发布接口与替换规则见 Notification Kit 说明与 publish 描述。
😅小坑提前说:
requestEnableNotification()通常只弹一次,用户拒了以后要引导去系统设置重新开(官方与社区 FAQ 都在强调这个现象)。
3️⃣ ⏰提醒代理(Reminder Agent):App 被杀了也能准点叫你起床
如果你的需求是:
- App 退后台/甚至进程退出后
- 还要在某个时间点提醒用户
那就别硬扛后台常驻了,直接用 代理提醒 reminderAgentManager:系统会代替你计时,到点后通过通知中心弹出提醒。
关键限制(别踩红线):
- 支持类型:倒计时 / 日历 / 闹钟
- 数量限制:三方应用最多 30 个有效提醒
- 需要通知授权 + 权限
ohos.permission.PUBLISH_AGENT_REMINDER - 部分设备/场景会有“管控机制”(防广告营销滥用),官方给了适配/申请说明。
🧪ArkTS:发布一个倒计时提醒(系统代发)
import { reminderAgentManager } from '@kit.BackgroundTasksKit';
import { notificationManager } from '@kit.NotificationKit';
export async function publishTimerReminder() {
// 1) 先确保通知开关已授权(否则会报“Notification is not enabled”)
await notificationManager.requestEnableNotification(); // 官方要求先做这步:contentReference[oaicite:21]{index=21}
// 2) 组装 ReminderRequest(倒计时类型)
const req: reminderAgentManager.ReminderRequestTimer = {
reminderType: reminderAgentManager.ReminderType.REMINDER_TYPE_TIMER,
triggerTimeInSeconds: 10, // 10 秒后提醒
title: '⏲️ 到点啦',
content: '别拖了,快去喝口水~',
ringDuration: 0 // >0 可播放自定义铃声(按文档规则)
};
const reminderId = await reminderAgentManager.publishReminder(req);
console.info(`✅ reminder published, id=${reminderId}`);
}
代理提醒的能力定义、类型、数量限制、以及 publishReminder 的权限/前置授权要求都在官方指南与 API 参考中。
🧠选型口诀(我真心希望你少走弯路)
- ✅ 短时任务:退后台“补尾巴”,最多几分钟,做完就 cancel。
- ✅ 长时任务:后台长期跑且用户可感知,必须配套通知与类型声明。
- ✅ 通知:先授权再 publish,不要硬发。
- ✅ 提醒代理:App 被杀也要准点提醒,用系统代发,别自己死扛常驻。
🧧福利赠与你🧧
无论你是计算机专业的学生,还是对编程有兴趣的小伙伴,都建议直接毫无顾忌的学习此专栏「滚雪球学SpringBoot」专栏(全网一个名),bug菌郑重承诺,凡是学习此专栏的同学,均能获取到所需的知识和技能,全网最快速入门SpringBoot,就像滚雪球一样,越滚越大, 无边无际,指数级提升。
最后,如果这篇文章对你有所帮助,帮忙给作者来个一键三连,关注、点赞、收藏,您的支持就是我坚持写作最大的动力。
同时欢迎大家关注公众号:「猿圈奇妙屋」 ,以便学习更多同类型的技术文章,免费白嫖最新BAT互联网公司面试题、4000G pdf电子书籍、简历模板、技术文章Markdown文档等海量资料。
✨️ Who am I?
我是bug菌(全网一个名),CSDN | 掘金 | InfoQ | 51CTO | 华为云 | 阿里云 | 腾讯云 等社区博客专家,C站博客之星Top30,华为云多年度十佳博主/价值贡献奖,掘金多年度人气作者Top40,掘金等各大社区平台签约作者,51CTO年度博主Top12,掘金/InfoQ/51CTO等社区优质创作者;全网粉丝合计 30w+;更多精彩福利点击这里;硬核微信公众号「猿圈奇妙屋」,欢迎你的加入!免费白嫖最新BAT互联网公司面试真题、4000G PDF电子书籍、简历模板等海量资料,你想要的我都有,关键是你不来拿。

-End-
- 点赞
- 收藏
- 关注作者
评论(0)