Skip to main content
使用本指南了解并控制推送通知在设备上显示后的后续行为:点击和清除会发生什么、Android 何时会重新显示通知、徽章如何保持同步,以及哪些 SDK 工具可以让您在应用代码中管理通知栏。 本页涵盖移动推送(Android 和 iOS)。有关 Web 推送行为,请参阅 Web 推送通知行为

通知栏中的通知生命周期

SDK 会跟踪设备上显示的每条 OneSignal 通知。接下来发生的事情决定了它是否可能重新出现:
在 Android 上,请始终使用 OneSignal SDK 方法清除通知,而不是使用 Android 原生的 NotificationManager.cancel()cancelAll()。使用原生 API 取消的通知不会被标记为已清除,因此 SDK 会在应用下次重启时恢复它们。

点击和清除行为

点击通知会打开您的应用(或通知的启动 URL),从通知栏中移除该通知,并触发 addClickListener() 回调,回调携带通知载荷和被点击的操作按钮 ID。如果被点击的通知属于某个分组,SDK 会更新或移除分组摘要。已点击的通知绝不会被恢复。 清除通知(滑动删除或点按通知栏中的”全部清除”)会将其标记为已清除,并更新徽章计数和任何分组摘要。已清除的通知绝不会被恢复。SDK 不提供清除监听器;清除行为由内部跟踪。 当应用处于前台时显示的通知会先经过前台生命周期监听器,您可以在其中阻止显示。

恢复的通知(Android)

Android 可以在无用户操作的情况下强制移除通知:设备重启、应用更新和强制退出(包括某些设备上激进的电池管理器)。Android SDK 会在应用下次冷启动时自动重新显示(恢复)受影响的通知,因此用户从未看到或清除的已投递消息不会丢失。 恢复的通知会在低重要性的已恢复类别上静默地重新出现。只有未被点击或清除、仍在其 TTL 之内且在过去 7 天内收到的通知才会被恢复,最多 49 条。 完整的恢复资格规则和控制方法请参阅恢复的通知(Android)。要减少恢复,请在发送时使用较短的 ttl,或使用下面的 SDK 方法清除已被消费的通知。iOS 没有恢复行为。

徽章行为

iOS 上,徽章由通知载荷设置(ios_badgeTypeios_badgeCount),并且需要 App Group 以便服务扩展能够准确更新计数。默认情况下,SDK 会在应用打开时清除徽章。 Android 上,应用图标徽章反映通知栏中活动的 OneSignal 通知数量,并通过通知类别管理。SDK 会在通知被显示、清除、点击或清理时自动更新计数,并在您调用 clearAllNotifications() 时将其重置为 0 设置、各平台选项和故障排除请参阅通知徽章

以编程方式清除通知

请在通知内容已在应用中被消费时清除通知,而不是在应用生命周期事件上清除。常见模式:
  • 内容消费同步:用户打开了通知指向的界面(收件箱、消息中心或动态流),这些通知因此变得多余。清除所有通知,或者如果只有部分内容被消费,则使用定向方法。
  • 登出:清除所有内容,使上一个用户的通知不会被下一个用户看到。
避免在每次应用启动或进入前台时清除通知来”保持通知栏干净”。通知栏中的通知能带动再互动,清除它们会移除这一入口。如果您要控制通知堆积,请在发送时使用 collapse_id 来替换通知而不是堆叠它们,或使用较短的 TTL 让未投递的通知过期。

clearAllNotifications()

从通知栏中移除您应用的通知,并将徽章计数重置为 0。在 Android 上,这只会移除由 OneSignal 创建的通知,并将它们标记为已清除,因此不会被恢复。在 iOS 上,这会移除您应用的所有已投递通知,包括本地通知和来自其他提供商的推送。请参阅完整方法参考
如果您在应用启动时清除通知以防止恢复的通知,请在跨平台应用中将该调用限定为仅在 Android 上执行。在 iOS 上,它还会移除本地通知和来自其他提供商的推送。

removeNotification()removeGroupedNotifications()(Android)

按 Android 通知 ID 移除单条通知,或按分组键移除分组中的所有通知。被移除的通知会被标记为已清除且不会被恢复。当通知栏中只有部分内容被消费时(例如多个会话中的一个),请使用这些方法。请参阅方法参考

延迟后自动清除通知

没有发送时参数可以在设定时间后移除已显示的通知。各平台可实现的方式不同:
  • Android 8.0(API 26)及更新版本:在通知服务扩展中使用 setTimeoutAfter() 设置超时。超时到期后,Android 会将通知从通知栏中移除。在低于 API 26 的设备上,该调用会被忽略,通知会保留到用户与其交互为止。
  • iOS:不支持。iOS 无法让已投递的通知自动过期。最接近的选择是通过 collapse_id 用更新的通知替换它,或在收到后续推送时通过 Notification Service Extension 使用 Apple 的 removeDeliveredNotifications(withIdentifiers:) 移除它。
要让超时按消息设置而不是固定在代码中,请在发送时通过 additionalData 传入时长,并在服务扩展中从事件里读取。
setTimeoutAfter() 移除的通知由系统清除,因此 OneSignal SDK 不会恢复它。不要将其与 ttl 混淆——ttl 控制未投递的消息为离线设备等待多长时间,绝不会移除已显示的通知。

使用服务扩展自定义通知

服务扩展在通知显示之前运行,让您可以修改其外观、接收后台数据或完全阻止显示:
  • Android 上,实现 INotificationServiceExtension 并使用 setExtender() 更改 NotificationCompat 选项,或调用 event.preventDefault() 抑制显示。
  • iOS 上,使用 UNNotificationServiceExtension(设置期间创建的 OneSignalNotificationServiceExtension)实现富媒体、徽章递增和确认投递。
在 Android 上,您的服务扩展也会针对恢复的通知运行。onNotificationReceived 中的副作用(分析调用、API 请求、数据库写入)会在通知恢复时重新执行,而 setChannelId() 等 extender 更改同样适用于恢复的通知,这可能使它们大声提醒。请设计您的扩展,使提醒选项仅应用于新投递的通知。

常见问题

为什么在 Android 上打开应用时旧通知会重新出现?

Android SDK 会恢复被强制从通知栏中移除的通知,例如在设备重启、应用更新或强制退出之后。用户已清除或点击的通知不会被恢复。有关资格规则和控制方法,请参阅恢复的通知(Android)

TTL 过期后会将通知从通知栏中移除吗?

不会。TTL 控制未投递的消息为离线设备等待多长时间,在 Android 上它还限定哪些通知可以被恢复。它绝不会移除已在通知栏中显示的通知。要移除已显示的通知,请使用清除方法。要在 Android 上于设定时间后移除它们,请参阅延迟后自动清除通知

我可以在不清空通知栏的情况下清除徽章吗?

在 iOS 上可以:徽章会在应用打开时自动清除(除非已禁用),通知栏内容保持不变。在 Android 上,徽章反映通知栏中活动的通知,因此无法独立于它们进行设置。请参阅通知徽章

有用户清除通知时的监听器吗?

没有。SDK 在内部跟踪清除行为以防止恢复已清除的通知,但不公开清除事件。点击监听器仅涵盖点击。

移动 SDK 参考

通知方法和监听器的完整参考。

OSNotification 载荷

载荷字段和恢复通知规则。

移动服务扩展

在显示之前拦截和自定义通知。