smack 使用之前的流 ID 连接到 xmpp 服务器
smack connect to xmpp server with previous stream id
我正在为服务器使用基于 Ejabbered 的 xmpp 和为 android 客户端
构建一个聊天应用程序
我已经建立了连接、登录、发送和接收消息,然后我遇到了用户网络断开和重新连接的问题,这已通过 smack 和 xmpp-0198 中的 Reconnecting Manger 解决,但是有一个我需要在 smack 中创建新连接但使用上一个会话(流)来获取存储在该会话中的所有消息的情况(它们不会存储到离线消息中)
,如果我用新的流 ID 创建一个新的连接,用户消息就会丢失。
是否有连接构造函数来实现此解决方案。
或服务器端配置以将千条消息存储到离线消息
我认为以下其中一项可以解决您的问题-
- 首先检查 mod_offline 在服务器端启用。
- 如果mod_offline启用,则检查服务器端的离线消息限制。它应该大于 0。
- 使用 PingManager 来稳定您的连接。我在这里放置示例代码以在 android-
中使用 PingManager
在 XMPPTcpConnection 启动期间-
pingManager = PingManager.getInstanceFor(this.connection);
pingManager.registerPingFailedListener(new PingFailedListener() {
@Override
public void pingFailed() {
// session dropped, request for reconnection
}
});
XMPPTcpCONnection 认证时-
@Override
public void authenticated(XMPPConnection connection, boolean resumed) {
configurePingManager();
}
private void configurePingManager() {
pingManager.setPingInterval(ACCORDING_SERVER_PING_INTERVAL);
pingManager.pingServerIfNecessary();
}
- 确保在服务器端和客户端都启用了stream_management。我在这里放了一个示例代码来为 android 客户端启用 stream_management-
xmppTcpConnection.setUseStreamManagement(true);
xmppTcpConnection.setUseStreamManagementResumption(true);
当 XMPPTcpCONnection 通过身份验证检查会话状态时,使用以下代码发送和请求所有待处理的流-
@Override
public void authenticated(XMPPConnection connection, boolean resumed) {
configurePingManager();
if (!resumed) {
try {
xmppTcpConnection.sendSmAcknowledgement();
xmppTcpConnection.requestSmAcknowledgement();
} catch (SmackException.NotConnectedException | StreamManagementException.StreamManagementNotEnabledException e) {
e.printStackTrace();
}
}
}
希望按照所有这些步骤解决您的问题。
经过大量搜索,我终于将 Ejabberd 服务器升级到最新版本 17.03
他们添加了新模块 mod_stream_mgmt 并更改了流管理的行为,所以当我创建新连接时,它会重新绑定到旧连接并接收未发送和未处理的消息
激活 mod_stream_mgmt 我使用了以下配置:
mod_stream_mgmt :
resume_timeout :60
resend_on_timeout: true
注意:
我还在服务器端激活了 mod_ping,我不知道这是否对这个过程和案例有直接影响,但现在我的客户没有丢失任何消息。
我正在为服务器使用基于 Ejabbered 的 xmpp 和为 android 客户端
构建一个聊天应用程序我已经建立了连接、登录、发送和接收消息,然后我遇到了用户网络断开和重新连接的问题,这已通过 smack 和 xmpp-0198 中的 Reconnecting Manger 解决,但是有一个我需要在 smack 中创建新连接但使用上一个会话(流)来获取存储在该会话中的所有消息的情况(它们不会存储到离线消息中) ,如果我用新的流 ID 创建一个新的连接,用户消息就会丢失。
是否有连接构造函数来实现此解决方案。 或服务器端配置以将千条消息存储到离线消息
我认为以下其中一项可以解决您的问题-
- 首先检查 mod_offline 在服务器端启用。
- 如果mod_offline启用,则检查服务器端的离线消息限制。它应该大于 0。
- 使用 PingManager 来稳定您的连接。我在这里放置示例代码以在 android- 中使用 PingManager
在 XMPPTcpConnection 启动期间-
pingManager = PingManager.getInstanceFor(this.connection);
pingManager.registerPingFailedListener(new PingFailedListener() {
@Override
public void pingFailed() {
// session dropped, request for reconnection
}
});
XMPPTcpCONnection 认证时-
@Override
public void authenticated(XMPPConnection connection, boolean resumed) {
configurePingManager();
}
private void configurePingManager() {
pingManager.setPingInterval(ACCORDING_SERVER_PING_INTERVAL);
pingManager.pingServerIfNecessary();
}
- 确保在服务器端和客户端都启用了stream_management。我在这里放了一个示例代码来为 android 客户端启用 stream_management-
xmppTcpConnection.setUseStreamManagement(true); xmppTcpConnection.setUseStreamManagementResumption(true);
当 XMPPTcpCONnection 通过身份验证检查会话状态时,使用以下代码发送和请求所有待处理的流-
@Override
public void authenticated(XMPPConnection connection, boolean resumed) {
configurePingManager();
if (!resumed) {
try {
xmppTcpConnection.sendSmAcknowledgement();
xmppTcpConnection.requestSmAcknowledgement();
} catch (SmackException.NotConnectedException | StreamManagementException.StreamManagementNotEnabledException e) {
e.printStackTrace();
}
}
}
希望按照所有这些步骤解决您的问题。
经过大量搜索,我终于将 Ejabberd 服务器升级到最新版本 17.03
他们添加了新模块 mod_stream_mgmt 并更改了流管理的行为,所以当我创建新连接时,它会重新绑定到旧连接并接收未发送和未处理的消息
激活 mod_stream_mgmt 我使用了以下配置:
mod_stream_mgmt :
resume_timeout :60
resend_on_timeout: true
注意: 我还在服务器端激活了 mod_ping,我不知道这是否对这个过程和案例有直接影响,但现在我的客户没有丢失任何消息。