融云即时通讯SDK集成 -- 通知检查
背景:
最近公司新上的app要加上即时通讯的功能, 自己快速实现一个当然是不可能的了(项目deadline也顶不住哇).就从各家成熟的SDK厂商选来选去的, 各有各的好也各有各的不足.最后点兵点将,选了融云家的SDK(老板说了算hhhh).
他家的官网和文档地址:
官网:https://www.rongcloud.cn/
文档:https://docs.rongcloud.cn/v4
这个任务当然还是落在我的头上. 集成完毕后, 也踩了不少坑. 所以这篇文章给大家总结下排查融云消息的本地通知和远端推送的办法. 希望可以帮助到正在看这篇文章的你.
什么是本地通知:
当我的App接入了融云的即时通讯sdk后, 便拥有了即时通讯的能力. sdk与融云服务器建立长连接, 当消息发出后, 先走到融云的服务器, 再转发给相应的用户. 这里移动端到服务端, 服务端到移动端, 走的通道都是长连接. 无论你的app是在前台还是在后台, 只要没有被杀死, 那么长连接是一直在的. 所以消息可以即时的发送到达给接收者. 融云把这种走长连接到达的消息, 在通知栏展示的通知叫做本地通知. 也就是消息是顺利发送到接收者端了, 逻辑可以走到消息接收监听那里. 融云sdk内部实现了消息到达后的本地通知, 也赋予了开发者自行实现消息到达后进行本地通知的权利.
本地通知的检查:
这里我总结了一下接入融云sdk后, 关于本地通知接收不顺利的排查. 大致可以分为这么几条:
1.是否设置了 setOnReceiveMessageListener 监听, 并且 onReceived 方法返回的为 true。
RongIM.setOnReceiveMessageListener(new RongIMClient.OnReceiveMessageListener() {
@Override
public boolean onReceived(Message message,
return true;
}
});
如果 onReceived 方法返回值为 true 则是监听做了拦截, 则不会走通知逻辑。 2.发送的消息是否是自定义消息。 如果是自定义消息, 则请查看自定义消息的 MessageTag 的注解是否设置了 flag 的值为 MessageTag.ISCOUNTED 或 MessageTag.ISPERSISTED) 。 以下面为例。
@MessageTag(value = "RC:TxtMsg", flag = MessageTag.ISCOUNTED)
@DestructionTag
public class TextMessage extends MessageContent {
...
}
如果没有设置其中之一,则不会走通知逻辑。
3.是否设置消息拦截器
设置代码如下:
/**
* 设置接收消息时的拦截器
*
* @param messageInterceptor 拦截器
*/
public void setMessageInterceptor(new RongIM.getInstance().MessageInterceptor() {
@Override
public boolean intercept(final Message message) {
return true;
}
});
如果设置了消息拦截器, 并且在 intercept() 方法中返回 true, 表示拦截此消息。 则不会走通知逻辑。
4.检查接收到的消息的 senderUserId 是否和当前用户的 id 相同。
如果 id 相同, 则不会走通知逻辑。 自己不可发给自己。
5.查看当前接收的消息是否是属于聊天室会话类型的
聊天室的消息目前不支持本地通知。
6.如果是自定义消息,请检查是否设置了自定义消息的 MessageProvider 。
如果没有,则不会走通知逻辑。
7.接收方本地是否有接收方的用户信息。 如果没有设置, 则不会走通知逻辑。
8.检查应用权限设置,看是否打开应用信任权限, 通知栏权限或者声音提示权限等。如果没有打开,请打开再试。
9.接收方没有发送方的用户信息,接收端不弹通知。用户信息通过用户信息提供者方式获取。
参考链接:https://docs.rongcloud.cn/v3/views/im/ui/guide/private/user/set/android.html
什么是远端推送:
集成了即时通讯的SDK, 我们的app不就能拥有像微信一样随时随地收到消息的即时通讯能力了? 说实话我一开始也是这么认为的. 可惜做开发也要按基本法来, Android平台回收app的这一关咱都过不了, app都给你杀死得透透的了你拿啥收消息呢? 咱又不是微信hhhh. 所以一番急赤白脸地阅读他家文档之后, 才发现app如果活着, 他融云能用自己的通道给你把消息推送到. 如果app被杀死了, 这个消息就在他家的服务端直接交给三方厂商了(也就是五大厂商蓝绿大厂华为小米FCM), 让这条消息走人家厂商的推送通道给送到你手机上.
远端推送的检查:
这里我总结了一下接入融云sdk后, 关于本地通知接收不顺利的排查. 大致可以分为这么几条:
- 退出应用的时候,只能调用融云的 disconnect() 方法,而不是 logout()。这样退出后融云才会启动push进程。
- push 进程的名字不能更改,必须是默认的名字,既 io.rong.push.
(2.6.0dev之后的版本,此进程名字可以修改)
- 通过 ddms 或者终端里敲入 adb shell ps|grep rong 查看终端里是否存在 io.rong.push 这个进程。
有些手机厂家做了特殊限制,不允许第三方后台进程启动,所以融云的后台进程起不来,导致收不到 push 消息。这种情况可以换个手机测试(如三星,大部分三星手机没有做权限限制)。另外大部分国产手机,有权限设置的菜单,比如小米,华为等,可以手动去安全中心,设置应用的自启动权限,后台运行权限等,就可以收到Push消息了。
不过 vivo 和 oppo 有些型号的手机,一旦应用退到后台,系统会很快把它杀死,这种没有办法解决。目前市面上所有推送都存在这个问题,除非系统把该应用加入白名单。
- push 进程存在,仍然收不到 push 消息。
如果你的应用有消息免打扰功能,那么请确认当前登录账号之前是否设置过消息免打扰。如果不太确定,那最好去你的应用设定里重新设置下消息免打扰时间。 这里要注意的是: 如果这个账号之前在别的手机上设置过消息免打扰,换一台手机登录或者卸载重装的时候,融云服务端记录的仍然是之前设置的消息免打扰状态,所以这种情况下是收不到push消息的。