4

大家好,我是 android 新手,我目前被困在这个问题上。我必须返回在 xmpp 服务器上创建的公共房间列表。我遇到的问题是下面的代码适用于java,但在android的情况下存在空指针异常。对此的任何帮助将不胜感激。

我正在使用 openfire 服务器并在本地机器上对其进行测试,这就是我使用 ip 地址而不是域名的原因。

我正在使用 JAVA 的 smack 库和 android 的 Asmack 库

String server_name = "192.168.3.113";
    ConnectionConfiguration config = new ConnectionConfiguration(
            server_name, 5222);
    XMPPConnection connection = new XMPPConnection(config);
    try {
        connection.connect();

        connection.login("s1", "123");

        Collection<HostedRoom> rooms = MultiUserChat.getHostedRooms(
                connection, "conference.geekoid");
        for (HostedRoom room : rooms) {
            System.out.println(room.getName());
        }

    } catch (XMPPException e) {
        System.out.println("Error" + e.getMessage() + "\n"); //for JAVA
                    log.e("Android Error",e.getmessage());  // For Android
    }
4

2 回答 2

6

问题是必须在创建任何连接之前评估ServiceDiscoveryManager 类的静态块。在 smack 中,这是通过配置文件完成的,但这种方法不适用于 Android,因此不适用于 aSmack。

答案中提到的解决方法有点难看,因为您真的不想使用构造函数来获取 SDM 对象,而是应该使用 get() 方法。但是 get() 方法只有在实际为连接创建了 SDM 时才有效。

因此,为了在 Android 上正确初始化 SDM,您需要在创建第一个 (XMPP)Connection 对象之前调用完整的 forName 表示法来初始化类的静态块。

Class.forName("org.jivesoftware.smackx.ServiceDiscoveryManager", true, ClassLoader.getSystemClassLoader()):

这被跟踪为aSmack 问题 8

于 2012-07-24T15:24:28.543 回答
6

我找到了问题的解决方案。

Android asmack 库在 getHostedRooms(Connection connection, String serviceName)方法中使用它

ServiceDiscoveryManager discoManager =ServiceDiscoveryManager.getInstanceFor(connection);

我把它换成了

ServiceDiscoveryManager discoManager = new ServiceDiscoveryManager(connection);

对于那些对这种方法在哪里感到困惑的人

包:org.jivesoftware.smackx.muc

文件:MultiUserChat.java

完成此操作后。我们必须在 Android 中注册所有提供程序,其详细信息可在此处找到。这些提供程序在使用 JAVA 的 smack 库(在 java 开发中)时会自动注册,但在 Android 中我们必须自己注册。

于 2012-07-26T07:16:13.630 回答