从 java-smack 客户端连接到 Openfire 时发生 SSL 错误
我最近正在开发 Openfire 客户端。我遇到了这个奇怪的问题,到目前为止我还无法弄清楚(我有一些线索,但仍然没有可靠的解决方案)。 我们有 2 个 openfire 服务器:
- 首先,我们用于测试的服务器托管在通过 adsl 连接到互联网的普通电脑上,服务器位于 NAT 之后,一切配置顺利,工作完美。我们的客户连接没有任何问题。
- 第二台(我们称之为生产)专业专用服务器位于德国某处,安装了 OF,操作系统与测试服务器相同,OF 以完全相同的方式设置
现在,当从我们的客户端连接到生产时,我们在尝试进行身份验证时遇到了以下问题:
javax.net.ssl.SSLException:收到致命警报:internal_error 在 sun.security.ssl.Alerts.getSSLException(来源未知) 在 sun.security.ssl.Alerts.getSSLException(来源未知) 在 sun.security.ssl.SSLSocketImpl.recvAlert(来源未知) 在 sun.security.ssl.SSLSocketImpl.readRecord(来源未知) 在 sun.security.ssl.SSLSocketImpl.performInitialHandshake(来源未知) 在 sun.security.ssl.SSLSocketImpl.startHandshake(来源未知) 在 sun.security.ssl.SSLSocketImpl.startHandshake(来源未知) 在 org.jivesoftware.smack.XMPPConnection.proceedTLSReceived(XMPPConnection.java:806) 在 org.jivesoftware.smack.PacketReader.parsePackets(PacketReader.java:267) 在 org.jivesoftware.smack.PacketReader.access$000(PacketReader.java:43) 在 org.jivesoftware.smack.PacketReader$1.run(PacketReader.java:70) java.lang.IllegalStateException:未连接到服务器。 在 org.jivesoftware.smack.XMPPConnection.sendPacket(XMPPConnection.java:445) 在 org.jivesoftware.smack.NonSASLAuthentication.authenticate(NonSASLAuthentication.java:69) 在 org.jivesoftware.smack.SASLAuthentication.authenticate(SASLAuthentication.java:352) 在 org.jivesoftware.smack.XMPPConnection.login(XMPPConnection.java:203) 在 Main.connectToJabber(Main.java:31) 在 Main.main(Main.java:16) 线程“main”中出现异常 java.lang.IllegalStateException:未连接到服务器。 在 org.jivesoftware.smack.XMPPConnection.sendPacket(XMPPConnection.java:445) 在 org.jivesoftware.smack.NonSASLAuthentication.authenticate(NonSASLAuthentication.java:69) 在 org.jivesoftware.smack.SASLAuthentication.authenticate(SASLAuthentication.java:362) 在 org.jivesoftware.smack.XMPPConnection.login(XMPPConnection.java:203) 在 Main.connectToJabber(Main.java:31) 在 Main.main(Main.java:16)
现在最有趣的部分:当我使用我们的客户端从我的公寓连接到生产服务器时,我没有看到该错误,当我们从其他开发人员公寓连接到生产时,我们'出现此错误,我们有不同的互联网提供商(我不知道这是否与此有关)。 我们花了一晚上的时间看它,但到目前为止还没有任何线索。 我们编写基本代码只是为了检查连接:
public static void connect() {
ConnectionConfiguration cc = new ConnectionConfiguration("prod ip",
5222);
cc.setCompressionEnabled(true);
cc.setSASLAuthenticationEnabled(true);
Connection connection = new XMPPConnection(cc);
try {
connection.connect();
connection.login(login, pass, "resource");
System.out.println(connection.isSecureConnection() + " " + connection.isUsingCompression());
} catch (XMPPException e1) {
e1.getStackTrace();
}
}
一些观察结果:
- 当行 connection.login(...) 注释时,没有错误,因此导致错误的原因就在那里
- 当连接测试服务器 System.out... 写入时true false,
- 连接生产服务器时 System.out... 写入 false false
- 尝试了以下所有组合: cc.setCompressionEnabled() cc.setSASLAuthenticationEnabled(); (true, true, false true, true false, false false)
- 尽管出现错误,用户仍已登录 总结:
与测试环境的连接始终有效,在生产中:从我的位置 - 没问题,其他位置 - 提到的错误, 我们使用 SMACK API 3.2.1 的
想法之一是它必须对证书做一些事情。
任何提示或想法都受到高度重视
I am recently working on Openfire client. I've got this strange issue that I couldn't figure out so far (i've got some clues, but still no solid solution).
We've got 2 openfire servers:
- first that we were using for testing it was hosted on normal pc conected to the internet through adsl, server was behind NAT, everything configured smoothly, working perfect. Our client was connecting without any issues.
- second (let's call it production) professional dedicated server located somewhere in germany with OF instaled, same OS as on the testing one, OF set up in exactly the same way
Now when connecting to production from our client we experianced following issue when trying to authenticate:
javax.net.ssl.SSLException: Received fatal alert: internal_error
at sun.security.ssl.Alerts.getSSLException(Unknown Source)
at sun.security.ssl.Alerts.getSSLException(Unknown Source)
at sun.security.ssl.SSLSocketImpl.recvAlert(Unknown Source)
at sun.security.ssl.SSLSocketImpl.readRecord(Unknown Source)
at sun.security.ssl.SSLSocketImpl.performInitialHandshake(Unknown Source)
at sun.security.ssl.SSLSocketImpl.startHandshake(Unknown Source)
at sun.security.ssl.SSLSocketImpl.startHandshake(Unknown Source)
at org.jivesoftware.smack.XMPPConnection.proceedTLSReceived(XMPPConnection.java:806)
at org.jivesoftware.smack.PacketReader.parsePackets(PacketReader.java:267)
at org.jivesoftware.smack.PacketReader.access$000(PacketReader.java:43)
at org.jivesoftware.smack.PacketReader$1.run(PacketReader.java:70)
java.lang.IllegalStateException: Not connected to server.
at org.jivesoftware.smack.XMPPConnection.sendPacket(XMPPConnection.java:445)
at org.jivesoftware.smack.NonSASLAuthentication.authenticate(NonSASLAuthentication.java:69)
at org.jivesoftware.smack.SASLAuthentication.authenticate(SASLAuthentication.java:352)
at org.jivesoftware.smack.XMPPConnection.login(XMPPConnection.java:203)
at Main.connectToJabber(Main.java:31)
at Main.main(Main.java:16)
Exception in thread "main" java.lang.IllegalStateException: Not connected to server.
at org.jivesoftware.smack.XMPPConnection.sendPacket(XMPPConnection.java:445)
at org.jivesoftware.smack.NonSASLAuthentication.authenticate(NonSASLAuthentication.java:69)
at org.jivesoftware.smack.SASLAuthentication.authenticate(SASLAuthentication.java:362)
at org.jivesoftware.smack.XMPPConnection.login(XMPPConnection.java:203)
at Main.connectToJabber(Main.java:31)
at Main.main(Main.java:16)
Now the funniest part: when I connect to the production server using our client from my flat i don't see that error, when we are connecting to the production from other developer flat we've got this error, we've got different internet providers (i don't know if that may have something to do with that).
We've spent all night looking at it and so far no clue.
We wrote basic code just to check the connection:
public static void connect() {
ConnectionConfiguration cc = new ConnectionConfiguration("prod ip",
5222);
cc.setCompressionEnabled(true);
cc.setSASLAuthenticationEnabled(true);
Connection connection = new XMPPConnection(cc);
try {
connection.connect();
connection.login(login, pass, "resource");
System.out.println(connection.isSecureConnection() + " " + connection.isUsingCompression());
} catch (XMPPException e1) {
e1.getStackTrace();
}
}
Some observations:
- When line connection.login(...) commented, there is no error, so whatever is causing the error is there
- When connecting the testing server System.out... writes true false,
- When connecting the production server System.out... writes false false
- Tried with all combinations of: cc.setCompressionEnabled() cc.setSASLAuthenticationEnabled(); (true, true, false true, true false, false false)
- despite the error, user is logged in
To sum up:
Connection with testing environment works always, with production: from my location - no problem, other location - mentioned error,
we use SMACK API 3.2.1
One of the ideas was that it has to do something with the certificates.
Any hints or ideas highly appriciated
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
糟糕糟糕的解决方案!因为您不知道连接速度,并且如果在早期建立连接,您也会阻止您的应用程序继续登录。
我现在可以提供的解决方案是
addConnectionListener
并在 'reconnectionSuccessful()' 函数中调用login()
,我希望这个函数不会是第一次调用就在连接断开并再次连接后!如果没有,则表明 smack 库的架构很糟糕。Bad bad solution! because u don't know connection speed and also u stop your app from continuing to login if connection established at early moments.
A solution that I can offer for now is to
addConnectionListener
and calllogin()
in 'reconnectionSuccessful()' function, and I hope this function will call for the first time not just after connection dropped and connected again! if not, It shows the bad architecture of smack library.也许
connect()
和login()
调用之间的sleep(x)
可以解决此问题。sleep()
几秒钟就足够了。来源
Maybe a
sleep(x)
between theconnect()
and thelogin()
call could fix this. A few seconds for thesleep()
should be enough.Source
我还在 connect() 之后使用睡眠...这肯定不理想,但这是一个可靠的解决方法。
I also use a sleep after connect() also... it's not ideal sure, but it's a reliable workaround.