Android 客户端未从 node.js 服务器接收到 socket.io 消息

Posted

技术标签:

【中文标题】Android 客户端未从 node.js 服务器接收到 socket.io 消息【英文标题】:Android client not receiving socket.io message from node.js server 【发布时间】:2017-04-22 04:43:10 【问题描述】:

我已经使用 socket.io 将 android 客户端连接到 node.js 服务器,并且我能够向服务器发送消息但在客户端上无法接收。 对于客户端,我会做类似

Log.i("MainActivity: ", "sending message");
    final JSONObject sdpObj = new JSONObject();

    try 
        sdpObj.put("id","presenter");
        sdpObj.put("sdpOffer",localSdpOffer.description);
     catch (JSONException e) 
        e.printStackTrace();
    

    LoginActivity.mSocket.emit("new message", sdpObj);

在服务器上我收到这样的对象:

 io.sockets.on('connection',function(socket)

        socket.on('new message',function(message)
              // some logic
          socket.emit('created',object); 

然后在客户端:

     LoginActivity.mSocket.on("created", new Emitter.Listener() 

        @Override
        public void call(Object... args) 
            Log.i( TAG, "message back:received ");

            User user = new User();
            JSONObject obj = null;
            try 
                obj = new JSONObject((String) args[0]);
                //Log.i(TAG,"SdpAnswer: "+args[0].sdpAnswer+"id "+obj.sdpAnswer);

            Log.i(TAG, "Instance of"+args[0].toString());
        
    );

但由于某种原因,它永远不会收到消息。 任何人都有一些想法为什么会这样?谢谢!

【问题讨论】:

【参考方案1】:

如果您按照文档使用 nkzawa 的 socket.io 库,则必须使用 runonUIThread 方法处理调用方法的内部。

import com.github.nkzawa.emitter.Emitter;

private Emitter.Listener onNewMessage = new Emitter.Listener() 
    @Override
    public void call(final Object.. args) 
        getActivity().runOnUiThread(new Runnable() 
            @Override
            public void run() 
                JSONObject data = (JSONObject) args[0];
                String username;
                String message;
                try 
                    username = data.getString("username");
                    message = data.getString("message");
                 catch (JSONException e) 
                    return;
                

                // add the message to view
                addMessage(username, message);
            
        );
    
;

这就是 onNewMessage 的样子。监听器是 Emitter.Listener 的一个实例,必须实现 call 方法。您会注意到 call() 内部被 Activity#runOnUiThread() 包裹,这是因为回调总是在 Android UI 线程的另一个线程上调用,因此我们必须确保将消息添加到视图发生在界面线程。

有关更多信息,请参阅此链接: Native Socket.IO and Android

【讨论】:

我不同意在上面的示例中 runOnUiThread 是必需的。没有任何视图的操纵。在我看来,这就是为什么需要 Socket.IO 站点示例的原因。【参考方案2】:

好的,所以我经过更多搜索后才知道。似乎为了正确维护不同 android 活动的套接字连接,我必须实现一个已定义套接字连接的单例类。问题是我在一个活动中实例化了套接字连接并试图在另一个活动中使用该连接即使我可以在另一个活动上发送消息,除非我将套接字移动到接收消息的活动,否则我无法接收任何消息。你可以找到很多关于如何实现单例类的例子,所以它并不难,它解决了我的问题。祝你有美好的一天:)

【讨论】:

以上是关于Android 客户端未从 node.js 服务器接收到 socket.io 消息的主要内容,如果未能解决你的问题,请参考以下文章

数据未从 node.js 保存在 MongoDB 中

无法在 Android 客户端和 Node.js socket.io 服务器之间进行通信

带有 Node.js/Socket.IO 服务器和客户端的 Phonegap 应用程序中的 Android 的 WebSockets

如何将数据从 Android 中的数据报套接字发送到 Node js 服务器?

如何使用护照在我的 node.js 服务器上验证 android 应用程序的 GPGS 令牌

Node.js学习03:web开发的本质