推送通知是 App 标配。uni-push 是 DCloud 与个推合作的统一推送服务,聚合华为、小米、OPPO、VIVO、魅族、荣耀、Google 等厂商的推送通道。鸿蒙平台从 uni-push 4.61 开始支持。鸿蒙推送走华为 HMS Push 通道,在 UniPush 2.0 后台配置时需要开通华为厂商通道。需要注意,鸿蒙推送机制与 Android 不完全相同,Android 的通知渠道管理 getPushChannelManager 在鸿蒙不支持。
一、鸿蒙平台核心 API 支持情况
在鸿蒙平台,uni-push 4.61 起支持:
1. getPushClientId:获取客户端唯一推送标识 cid,上报服务端用于指定目标设备。
2. onPushMessage:监听推送消息,type 为 receive 表示收到推送,click 表示用户点击系统通知栏消息启动应用。
3. offPushMessage:移除推送监听。
4. createPushMessage:创建本地通知,不依赖服务端。
5. setAppBadgeNumber:设置或清除应用角标。
6. getPushChannelManager:不支持,这是 Android 专属 API;鸿蒙有自己的通知管理机制,不需要手动创建通知渠道。
二、基础调用
获取 cid:- uni.getPushClientId({
- success: (res) => {
- console.log('推送标识:', res.cid)
- },
- fail: (err) => {
- console.log('获取推送标识失败:', err)
- }
- })
复制代码
监听与移除:- uni.onPushMessage((res) => {
- if (res.type == 'receive') {
- console.log('收到推送消息:', res.data)
- } else if (res.type == 'click') {
- console.log('用户点击了推送消息:', res.data)
- }
- })
- uni.offPushMessage(callback)
复制代码 如果多次监听 onPushMessage,事件会多次触发,不需要时要用 offPushMessage 移除。
创建本地通知:- uni.createPushMessage({
- title: '新消息',
- content: '你有一条新的订单消息',
- payload: { orderId: '12345' },
- sound: 'system',
- cover: false,
- delay: 0
- })
复制代码
设置角标:传 0 表示清除角标。
三、鸿蒙平台重点避坑
1. content 必填。Android 和 iOS 上 title、content 都可以不填或有默认值,但鸿蒙平台 createPushMessage 的 content 是必填。错误写法:- uni.createPushMessage({
- title: '通知'
- // 缺少 content,鸿蒙会报错
- })
复制代码 正确写法:- uni.createPushMessage({
- title: '通知',
- content: '通知内容'
- })
复制代码
2. getPushChannelManager 不可用。它是 Android 专属 API,鸿蒙平台不支持,调用会返回 null 或不支持。鸿蒙不需要手动创建通知渠道。
3. 角标显示受设备规则影响。setAppBadgeNumber 在鸿蒙支持,但不同设备角标显示规则可能不同,有些设备还需要在应用通知管理里开启“桌面角标”配置才会生效。
4. 推送通道配置。鸿蒙推送走华为 HMS Push,UniPush 2.0 后台需要开通华为厂商通道。客户端拿到 cid 后要上报到服务端,服务端推送时用 cid 指定目标设备。如果服务端使用 uniCloud,原文提到可结合 uni-cloud-push 云端配合方案,具体以官方文档为准。
四、实战场景
1. 启动时获取 cid 并上报:- const initPush = () => {
- uni.getPushClientId({
- success: (res) => {
- uni.request({
- url: 'https://your-server.com/api/report-cid',
- method: 'POST',
- data: {
- cid: res.cid,
- platform: 'harmony'
- },
- success: () => {
- console.log('cid 上报成功')
- },
- fail: (err) => {
- console.log('cid 上报失败:', err)
- }
- })
- },
- fail: (err) => {
- console.log('获取推送标识失败:', err)
- }
- })
- }
复制代码
2. 监听 receive 和 click,点击后按 payload 跳转:- const setupPushListener = () => {
- uni.onPushMessage((res) => {
- if (res.type == 'receive') {
- console.log('收到推送:', res.data)
- uni.showToast({
- title: '收到新消息',
- icon: 'none'
- })
- } else if (res.type == 'click') {
- const data = res.data as UTSJSONObject
- const page = data['page'] as string
- if (page != null) {
- uni.navigateTo({
- url: page
- })
- }
- }
- })
- }
复制代码
3. 本地通知、延迟通知、覆盖旧通知、静默通知:- uni.createPushMessage({
- title: '订单提醒',
- content: '您的订单已发货,请注意查收',
- payload: {
- orderId: '12345',
- type: 'order'
- },
- sound: 'system',
- cover: false
- })
- uni.createPushMessage({
- title: '活动提醒',
- content: '您关注的商品即将开始限时特惠',
- delay: 60,
- payload: {
- activityId: 'activity_001'
- }
- })
- const createCoverNotification = (content: string) => {
- uni.createPushMessage({
- title: '新消息',
- content: content,
- cover: true,
- payload: {
- type: 'message'
- }
- })
- }
- uni.createPushMessage({
- title: '后台同步',
- content: '数据同步完成',
- sound: 'none',
- payload: {
- type: 'sync'
- }
- })
复制代码
4. 角标更新与清除:- const updateBadge = (count: number) => {
- uni.setAppBadgeNumber(count, {
- title: '新消息',
- content: '您有' + count + '条未读消息'
- })
- }
- const clearBadge = () => {
- uni.setAppBadgeNumber(0)
- }
复制代码
五、页面级监听管理
实际页面中,建议用变量保存回调,开始监听时 onPushMessage,停止或页面卸载时 offPushMessage,避免重复监听。核心逻辑可参考:- let pushCallback: ((res: OnPushMessageCallbackResult) => void) | null = null
- const startListening = () => {
- pushCallback = (res: OnPushMessageCallbackResult) => {
- if (res.type == 'receive') {
- // 处理收到消息
- } else if (res.type == 'click') {
- // 处理点击跳转
- }
- }
- uni.onPushMessage(pushCallback)
- }
- const stopListening = () => {
- if (pushCallback != null) {
- uni.offPushMessage(pushCallback)
- pushCallback = null
- }
- }
- onUnload(() => {
- stopListening()
- })
复制代码
六、与鸿蒙原生推送的差异
鸿蒙原生开发中,推送对接需要使用 @kit.PushKit,例如通过 pushService.getToken() 获取 token,并处理 Push Kit 回调:- import { pushService } from '@kit.PushKit'
- pushService.getToken().then((token) => {
- console.log('推送 token:', token)
- })
复制代码 相比之下,uni-app x 的 uni-push 把 cid 获取、消息监听和厂商通道聚合封装起来,鸿蒙走 HMS Push,少处理不少原生 SDK 差异。对于已经使用 uni-app x 的项目,可以优先用 uni-push 完成推送能力接入;如果要做深度系统集成或特殊通知能力,再评估原生方案。
总结
鸿蒙平台接入 uni-push 的关键点有三个:版本从 uni-push 4.61 起支持;createPushMessage 的 content 必填;getPushChannelManager 不可用。落地时先获取 cid 并上报服务端,再监听 receive/click 处理业务跳转,本地通知、延迟、覆盖、静默和角标按需组合。配置侧记得在 UniPush 2.0 后台开通华为厂商通道,角标不显示时检查设备通知管理中的“桌面角标”开关。 |