最近项目需要,在Javaweb项目中使用smack4.3.4作为xmpp的客户端,连接openfire服务端。过程中遇到许多问题,资料较少,特意整理出来。
一、连接服务器+登录
XMPPTCPConnectionConfiguration config = XMPPTCPConnectionConfiguration.builder()
.setUsernameAndPassword(username, password)
// 固定源,不固定将随机
.setResource(Resourcepart.from("Smack"))
// 开启通讯压缩
.setCompressionEnabled(true)
// 超时
// .setConnectTimeout(1000 * 10)
// 关闭
.setSecurityMode(SecurityMode.disabled)
// 必须设置
.setXmppDomain(JidCreate.domainBareFrom(serverName))
// 设置离线状态
// .setSendPresence(false)
// 调试
// .setDebuggerFactory(SmackConfiguration.getDefaultSmackDebuggerFactory())
// 主机
.setHost(hostName).setPort(port).build();
mConnection = new XMPPTCPConnection(config);
mConnection.connect();
if (mConnection.isConnected()) {
// 登录到服务器
SASLMechanism sm = new SASLPlainMechanism();
SASLAuthentication.registerSASLMechanism(sm.instanceForAuthentication(mConnection, config));
Presence presence2 = new Presence(Presence.Type.available);
presence2.setType(Type.available);
presence2.setStatus("在线");
mConnection.sendStanza(presence2);
mConnection.login(username, password);
}
二、监听:ConnectionListener +RosterListener+包监听
懒得写了。。。
三、主要问题
问题:
客户端连接上openfire后,客户端检查连接状态,一段时间后,客户端检测在线,而openfire显示已下线。即:mConnection.isConnected() && mConnection.isAuthenticated() 校验不起作用。
原因:
openfire默认隔360秒检测闲置连接,会发送ping给客户端,要求客户端响应,否则关闭连接(我响应了。。。。还是被关掉了,也许是响应的内容不对?)。
解决办法:
①增加ping,使用smack的PingManager设置ping的频率以及失败重连,(发现不起作用,还是会掉线)。
②在ConnectionListener中的connectionClosedOnError和connectionClosed中重连。
③在StanzaListener中监听如果接收的是用户下线的包,则重连。
④以上不放心,增加TimerTask任务,每30分钟检查连接状态,连接已断开则重连。
⑤重连操作使用TimerTask,以便失败10秒后重连。
⑥将①②③关于监听的都放在连接之前,即mConnection.connect()之前设置。