默认
发表评论 13
想开发IM:买成品怕坑?租第3方怕贵?找开源自已撸?尽量别走弯路了... 找站长给点建议
[已回复] RainbowChat-Web上线下线通知监听器ChatServerEventListener疑问
需求是这样的:1、在好友列表显示在线状态;
2、好友上线、离线实时更新列表状态。

第一个问题,我看到有 missu_users.is_online 字段存储在线状态,但是发现这块代码没有生效。
首先,可以确认启动时ChatServerEventListener 已经注册了。
当好友上线时,onUserLoginVerify 和 onUserLoginSucess 都没有被调用,不知道是啥原因。
我拿到的代码很多逻辑是注释掉的,直接return 0。

@Override
public int onUserLoginVerify(String userId, String token, String extra, Channel session)
{
    return 0;
}

我有看了下,问题可能是:前端 HTTP 认证完成,通过 token 连接到 im 服务器时,没有触发 onUserLoginVerify 事件?
// 发起首次连接和认证
            this._socket = io.connect(wsUrl, {
                query: 'token='+JSON.stringify(w.IMSDK._loginInfo),
                forceNew:true,               // 20170110:加了此选项才能让客户端socketio.disconnect()生效!
                secure:supportSSL?true:false // 20170526:是否支持SSL/TLS
            });


function callBack_CheckAuthToken(loginInfo, fn) {

  //*********************************************************************** START
  // TODO 你可在此填写登陆/掉线重连认证代码实现:(true表示验证成功,false表示失败) START
  //var authOK = false; // 验证失败!
  var authOK = true;    // 验证成功!
  // TODO 你可在此填写登陆/掉线重连认证代码实现:(true表示验证成功,false表示失败) END
  //*********************************************************************** END

  logger.info('[IM应用层-回调] 已收到sdk的连接认证回调,loginInfo=%s, 认证结果=%s', JSON.stringify(loginInfo), authOK);

  // 此回调请原样照写,不可更改:即将认证结果传回第2层回调(fn回调函数来自SDK内部,原样传过去即可)
  fn(null, authOK);
}


到底怎么做才能触发 ChatServerEventListener.onUserLoginVerify?













即时通讯网 - 即时通讯开发者社区! 来源: - 即时通讯开发者社区!

推荐方案
评论 13
你这一会儿贴java代码,一会贴js代码,不要把思路搞乱了。
你如果是要给web端增加在线状态,只需要在服务端的js代码里去实现。你原版代码里,某人的登录和退出,服务端的回调里都会有log显示,不可能没反应,不然系统就不正常了,你可以跟读一下log
引用:JackJiang 发表于 2025-06-13 15:07
你这一会儿贴java代码,一会贴js代码,不要把思路搞乱了。
你如果是要给web端增加在线状态,只需要在服务 ...

现在的问题就是ChatServerEventListener 的 onUserLoginVerify 和 onUserLoginSucess 都没有被调用。能告诉我怎么触发这两个方法吗,有例子吗给我一个?
我需要在左边的好友列表,显示所有好友的在线离线状态。

前端的上线下线 log 是有的。
[已回复] RainbowChat-Web上线下线通知监听器ChatServerEventListener疑问_微信图片_20250614220236_204.png


引用:batizhao 发表于 2025-06-14 21:58
现在的问题就是ChatServerEventListener 的 onUserLoginVerify 和 onUserLoginSucess 都没有被调用。能告 ...

把交付给你的原版代码跑起来,看看这两个回调,一定能被调用:

[已回复] RainbowChat-Web上线下线通知监听器ChatServerEventListener疑问_QQ20250615-203213.png
引用:JackJiang 发表于 2025-06-15 20:33
把交付给你的原版代码跑起来,看看这两个回调,一定能被调用:

callBack_userOnline 和callBack_userOffline 这两个方法是被调用了,从我上个图的日志可以看出。

但是对于我的需求来说不够呀。我需要有所有人的在线离线状态,这个必须在后端存储吧?
我看了数据库是通过 missu_users.is_online 字段存储在线状态,但是这个字段是 ChatServerEventListener 的 onUserLoginVerify 和 onUserLoginSucess 方法有关系,而这两个方法,现在都没被调用到。
我看了下前端代码,应该在这里触发 onUserLoginVerify 的吧?但是这里直接跳过后端校验了。
function callBack_CheckAuthToken(loginInfo, fn) {

  //*********************************************************************** START
  // TODO 你可在此填写登陆/掉线重连认证代码实现:(true表示验证成功,false表示失败) START
  //var authOK = false; // 验证失败!
  var authOK = true;    // 验证成功!
  // TODO 你可在此填写登陆/掉线重连认证代码实现:(true表示验证成功,false表示失败) END
  //*********************************************************************** END

  logger.info('[IM应用层-回调] 已收到sdk的连接认证回调,loginInfo=%s, 认证结果=%s', JSON.stringify(loginInfo), authOK);

  // 此回调请原样照写,不可更改:即将认证结果传回第2层回调(fn回调函数来自SDK内部,原样传过去即可)
  fn(null, authOK);
}

引用:batizhao 发表于 2025-06-16 08:56
callBack_userOnline 和callBack_userOffline 这两个方法是被调用了,从我上个图的日志可以看出。

但 ...

怎么就不够了。
谁上线了,你就把它放到你的集合里,谁下线了,你就把它从集合里去掉,这集合里的人不就是所有在线的人了吗
引用:JackJiang 发表于 2025-06-16 09:52
怎么就不够了。
谁上线了,你就把它放到你的集合里,谁下线了,你就把它从集合里去掉,这集合里的人不就 ...

我看了下前端是有个userProcessor 来处理在线列表的,我让开发试试吧。

我是在后端看到missu_users表有个is_online 字段,跟代码看到有个UsersStatusManager,看到和 ChatServerEventListener 的 onUserLoginVerify、 onUserLoginSucess 方法有关系,所以在看后端这条路子。

【接口1008-2-7】获取好友列表过程,现在看下来,这个 is_online 根本没用到是吧?
// 遍历在线好友列表,看看该好友是否在线(在线用户列表中的key可能是user_uid也可能是user_mail,
					// 因为客户端允许用户使用uid和mail二种方式登陆)
					if(ChatServerEventListener.getInstance().getLiverUsersMgr().isOnline(friend_user_uid))
					{
						// 设置在线状态为“在线”
						friend.setLiveStatus(1);
					}

引用:batizhao 发表于 2025-06-16 10:25
我看了下前端是有个userProcessor 来处理在线列表的,我让开发试试吧。

我是在后端看到missu_users表 ...

那个数据库表里的字段不要去纠结,那只是app产品里用于后端运维系统时看看而已。

按我说的一定能实现,也是最佳实践,因为app产品里就是这么实现,这两个上线下线的回调在sdk里设计的目的也就是为了让你这么去用的
引用:JackJiang 发表于 2025-06-16 11:01
那个数据库表里的字段不要去纠结,那只是app产品里用于后端运维系统时看看而已。

按我说的一定能实现 ...

有代码可以参考吗?

1、在好友列表加载的时候可以区分在线、离线,并且在线用户排在前边;
2、好友上线离线,对列表进行实时更新。
引用:batizhao 发表于 2025-06-16 16:26
有代码可以参考吗?

1、在好友列表加载的时候可以区分在线、离线,并且在线用户排在前边;

最简单的办法:
1)谁上线,谁下线,在现有的服务端上线下线接口里,去更新这个人的数据库表is_online字段;
2)服务端好友列表读取时,同时读取is_online字段,并按is_online排序ORDER is_online DESC;
3)客户端实时上下线就是对好友列表进行数组重新排序,排序的同时在DOM里去更新ui

就这么点事
引用:JackJiang 发表于 2025-06-16 16:40
最简单的办法:
1)谁上线,谁下线,在现有的服务端上线下线接口里,去更新这个人的数据库表is_online字 ...

我原先就是这么想的,所以第一步,上线下线更新 is_online,我看代码是通过ChatServerEventListener这个监听器来实现的,但是这个监听器现在onUserLoginVerify、onUserLoginSucess、onUserLogout 这些方法都不起作用,不知道怎么触发啊。我不可能自己实现这个逻辑吧?

ChatServerEventListener - onUserLoginVerify(return 0) - onUserLoginSucess - ChatLogicManager.processUserLoginAction(更新 is_online,给在线好友发上线消息)

ChatServerEventListener - onUserLogout - ChatLogicManager.processUserLogoutAction(更新 is_online,给在线好友发下线消息)

实在不行,我就登录成功RosterElementEntity authedUser = MyControllerJSON.authrizationLogin(ai, req.getRemoteHost(), false);后,自己调用ChatLogicManager.processUserLoginAction(userId, extra, session)这个方法。
引用:JackJiang 发表于 2025-06-16 16:40
最简单的办法:
1)谁上线,谁下线,在现有的服务端上线下线接口里,去更新这个人的数据库表is_online字 ...

我现在是这么处理的:
上线 MyControllerJSON.authrizationLogin 方法,增加

ChatLogicManager.processUserLoginAction(userAuthedInfo.getUser_uid(), null, null);


离线 MyControllerJSON.authrizationLogout 方法,增加
ChatLogicManager.processUserLogoutAction(ao.getUid(), null, 0);


现在可以实现 is_online 字段的更新。

但是还有个问题,我需要发消息给所有的在线好友上线了,这里我看用到了这个集合:
ConcurrentMap<String, Channel> liveUsers = 
                                ChatServerEventListener.getInstance().getLiverUsersMgr().getLiveUsers();


那么需要维护这个集合:
OnlineProcessor.getInstance().putUser(userAuthedInfo.getUser_uid(), System.currentTimeMillis(), null);


现在的问题是:public boolean putUser(String user_id, long firstLoginTime, Channel newSession) 第三个参数怎么传?我试了 null 有问题。我想这里我不用liveUsers,直接用is_online 判断给谁发消息算了,可行吗?


引用:batizhao 发表于 2025-06-17 11:59
我现在是这么处理的:
上线 MyControllerJSON.authrizationLogin 方法,增加

完全没看明白你在干啥咧。
你不是搞web端的状态吗,怎么又搞到app的服务端来了,不能把逻辑理清了再动手吗。。不理解的逻辑可以先加Log看看它的执行逻辑
不是,你看懂我的目的了吗?
1、好友列表显示在线状态;
2、好友列表状态实时刷新。
你一会说:只需要在服务端的js代码里去实现;又说:去更新这个人的数据库表is_online字段
你搞清楚了吗?怎么这么费劲啊。
打赏楼主 ×
使用微信打赏! 使用支付宝打赏!

返回顶部