【问题标题】:Using Socket IO and aiohttp for data transfer between node JS and Python使用 Socket IO 和 aiohttp 进行节点 JS 和 Python 之间的数据传输
【发布时间】:2019-04-22 01:24:33
【问题描述】:

我的总体目标是在 JavaScript 文件(使用节点运行)中生成随机数流,并以异步时间间隔将它们发送到 python 脚本。一旦数字在 python 中,脚本将确定数字是否是偶数。如果是,则将数字发送回 JavaScript 文件。我的主要关注点是获取 JavaScript 和 Python 之间的通信。

一旦我启动 JavaScript 文件和 python 服务器,它们将继续运行,直到我停止它们。

目前,我一直在学习位于此处 (https://tutorialedge.net/python/python-socket-io-tutorial/) 的教程。本教程使用 JS 的 socket io 和 python 的 aiohttp。

我将html代码操作成JS代码(index.js),如下:

// index.js    
var socket = require('socket.io-client')('http://localhost:8080');
socket.on('connect', function(){});

function generateNumber() {
   let n = Math.floor(Math.random() * 50);
   let json = {
       'number': n
   }
   console.log(json);
   return json;
}

(function loop() {
    var rand = Math.round(Math.random() * (3000 - 500)) + 500;
    setTimeout(function() {
            generateNumber();
            loop();  
    }, rand);
}());

function sendMsg() {
  socket.emit("message", generateNumber());
}

socket.on("message", function(data) {
console.log(data);
});

我创建了一个函数 (generateNumber) 来生成以 JSON 格式输出的随机数。我使用 JSON 是因为我相信当数字到达 python 脚本时,它可以轻松地将数据转换为列表和整数。循环函数允许以随机间隔连续创建数字,并取自这里:Randomize setInterval ( How to rewrite same random after random interval)

下面显示的python服务器(server.py)取自教程(https://tutorialedge.net/python/python-socket-io-tutorial/):

# server.py
from aiohttp import web
import socketio

# creates a new Async Socket IO Server
sio = socketio.AsyncServer()
# Creates a new Aiohttp Web Application
app = web.Application()
# Binds our Socket.IO server to our Web App
# instance
sio.attach(app)

# we can define aiohttp endpoints just as we normally
# would with no change
async def index(request):
    with open('index.html') as f:
        return web.Response(text=f.read(), content_type='text/html')

# If we wanted to create a new websocket endpoint,
# use this decorator, passing in the name of the
# event we wish to listen out for
@sio.on('message')
async def print_message(sid, message):
    # When we receive a new event of type
    # 'message' through a socket.io connection
    # we print the socket ID and the message
    print("Socket ID: " , sid)
    print(message)

# We bind our aiohttp endpoint to our app
# router
app.router.add_get('/', index)

# We kick off our server
if __name__ == '__main__':
    web.run_app(app)

截至目前,当我运行node index.js时,随机数会以随机间隔连续生成,并且可以在终端中看到输出。但我在服务器端没有得到响应。

我认为该问题与以下 2 个问题有关:

首先,我当前的 JS 代码 (index.js) 最初是一个 html 脚本,它通过“http://localhost:8080”上的按钮单击发送消息。我将脚本调整为 JS 脚本,并添加了附加功能。因此,在我设置套接字 io 的 index.js 的以下行中可能存在问题:

var socket = require('socket.io-client')('http://localhost:8080');
socket.on('connect', function(){});

为清楚起见,以下是 index.js 所基于的原始 html 代码 (index.html):

<!-- index.html -->
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <meta http-equiv="X-UA-Compatible" content="ie=edge" />
    <title>Document</title>
  </head>
  <body>
    <button onClick="sendMsg()">Hit Me</button>

    <script src="https://cdnjs.cloudflare.com/ajax/libs/socket.io/2.2.0/socket.io.js"></script>
    <script>
      const socket = io("http://localhost:8080");

      function sendMsg() {
        socket.emit("message", "HELLO WORLD");
      }
    </script>
  </body>
</html>

我还问了一个关于html到JS转换的问题(Syntax error when trying to convert HTML file to JavaScript containing socket io, SyntaxError: Unexpected token <

其次,由于教程最初使用的是html文件而不是JS,我相信python脚本(server.py)仍在等待html脚本的输出,所以我认为这些行在server.py 需要更改:

async def index(request):
    with open('index.html') as f:
        return web.Response(text=f.read(), content_type='text/html')

但我不确定如何进行适当的更改,在 aiohttp 网站 (https://aiohttp.readthedocs.io/en/stable/) 上查找对我的问题的引用时遇到问题,或者我可能不确定我在寻找什么。

server.pyindex.js 目前都可以正常运行,但它们没有通信。

总体而言,JS 文件 (index.js) 将使用 socket io 将数据发送到 python 服务器 (server.py),而 python 服务器使用aiohttp,会将分析后的数据发送回相同的 JS 脚本。这将持续发生,直到手动停止其中一个脚本。

如果需要任何澄清,请随时询问。

【问题讨论】:

    标签: javascript python node.js http aiohttp


    【解决方案1】:

    我相信,在 JS 部分,您应该在某处调用 sendMsg() 以发出消息。

    更新

    const io = require('socket.io-client');
    
    const socket = io('http://localhost:8080');
    
    socket.on('message', data => {
      console.log('Got from server: ');
      console.log(data);
    });
    
    function generateNumber() {
      const n = Math.floor(Math.random() * 50);
      return { number: n };
    }
    
    function sendMsg() {
      const json = generateNumber();
      console.log('Sending to server:');
      console.log(json);
    
      socket.emit('message', json);
    }
    
    function loop() {
      const rand = Math.round(Math.random() * (3000 - 500)) + 500;
      console.log(`Setting timeout ${rand}ms`);
      setTimeout(() => {
        sendMsg();
        loop();
      }, rand);
    }
    
    socket.on('connect', () => {
      console.log('Connected to server');
      loop();
    });

    我在两边都使用节点。服务器端只是发回每条收到的消息。 日志如下所示:

    Connected to server
    Setting timeout 1685ms
    Sending to server:
    { number: 21 }
    Setting timeout 1428ms
    Got from server: 
    { number: 21 }
    Sending to server:
    { number: 40 }
    Setting timeout 2955ms
    Got from server: 
    { number: 40 }
    

    【讨论】:

    • 您的建议奏效了。但是有一些问题,这些数字没有被一致地发送。有时只有几个号码会进入 python 服务器,有时可能会有一个号码通过。但是,有时前 10 个数字可能无法通过,然后脚本开始正常工作。我不断需要重新启动服务器和 JS 脚本以尝试让它们正常工作。你认为这可能是 JS 方面的事情吗?
    • @W.Churchill 请检查更新版本。我添加了更多日志和 .on('connect') 侦听器,以防止套接字连接到服务器之前的任何操作
    • 感谢更新版本,我一直在处理代码,还有一些问题。当您说您在双方都使用节点时,这是否意味着您正在使用 JavaScript 服务器?我想使用我的 Python 服务器,但是在运行代码的当前更新版本时遇到了一些问题,在运行它时(使用我的 python 服务器,server.py)我没有收到“从服务器获取:”消息JS 端,但我看到 Python 服务器端收到了数字。
    • 我注意到的一些事情:如果没有建立连接,JS端每分钟都会输出“连接到服务器”的消息,可能会通过1或2个数字,这个过程每隔一段时间就会重复一次直到建立一致的连接,但有时不会建立连接。
    • 所以JS脚本和python服务器都需要重启。在python服务器运行后启动JS脚本时,大约需要1到3分钟才能建立连接并发送一致的号码,如果没有,我必须不断重启两个脚本,直到建立连接。但是当建立连接时,它将连续运行而不会中断(我目前已经运行一个连接超过 3 天)。那么你认为这现在是 Python 方面的一个问题,并且与 server.py 有关系吗?
    猜你喜欢
    • 2015-03-06
    • 2016-06-04
    • 1970-01-01
    • 2014-10-18
    • 2018-11-13
    • 1970-01-01
    • 2020-04-28
    • 1970-01-01
    • 2017-02-25
    相关资源
    最近更新 更多