0

Python zmqを使用してpub/subパターンを試しています。クライアント側で奇妙な問題に直面しています。クライアント側では、pyzmq、gevent-websocket、および bottle を wsgi サーバーとして使用しています。1 つのクライアントに対しては完全に機能しますが、他のクライアントは最初のクライアントが切断されるのを待っています。1 つのクライアントで作業しているときに、切断して再接続すると、再接続するたびにメッセージが 2 回以上表示されます。

#!/usr/bin/python
from gevent import monkey; monkey.patch_all()
import zmq
import gevent
from bottle import route, run, request, abort, Bottle ,static_file
from gevent import sleep
from gevent.pywsgi import WSGIServer
import geventwebsocket
from geventwebsocket import WebSocketHandler, WebSocketError

host = "127.0.0.1"
port = 8000
mqport = "8082"

context = zmq.Context()
socket = context.socket(zmq.SUB)

app = Bottle()

@app.route('/v1/streams/device/<id>')
def handle_websocket(id):
    socket.setsockopt(zmq.UNSUBSCRIBE, '')
    socket.connect ("tcp://localhost:%s" % mqport)
    socket.setsockopt(zmq.SUBSCRIBE, id)
    wsock = request.environ.get('wsgi.websocket')
    if wsock is None:
        logger.info("Error creating websocket")
    try :
        while True:
            string = socket.recv()
            logger.info("%s" % string)
            id, data = string.split("  ")
            wsock.send("%s" % data)
            sleep(0.1)
    except geventwebsocket.WebSocketError, ex:
        wsock.close()
        sock.close()
server = WSGIServer((host, port), app,
                handler_class=WebSocketHandler)
server.serve_forever()

私が見たすべての例では、メッセージを受信するために while ループを使用しています。私はこの while ループに慣れておらず、socket.on_message のようなコールバック関数を探しています。実験目的で、このような while ループを使用せずに同じ node.js バージョンを作成しましたが、プロジェクトではノードが除外されました。ノードのバージョンは次のとおりです。

var WebSocketServer = require('websocket').server;

var http = require('http');

global.client = 0;

var server = http.createServer(function(request, response) {

});

server.listen(8000, function() { });

wsServer = new WebSocketServer({

    httpServer: server

});



// WebSocket server

wsServer.on('request', function(request) {

    console.log("connected client :", global.client++)

    var connection = request.accept(null, request.origin); 

    var url = request.resourceURL.href

    var device_id = url.substr(url.lastIndexOf('/') + 1)

    var zeromq = require('zmq');

    var sock = zeromq.socket('sub');

    sock.connect('tcp://127.0.0.1:8082');

    sock.subscribe(device_id);

    sock.on('message', function(data) {
        console.log(data.toString());

        var msg = data.toString();

        var rjson = msg.split("  ") 

        connection.send(rjson.pop());

    });

    connection.on('close', function(connection) {
    });
});

ここでは while ループを使用しません。

Pythonコードで何が間違っていますか?

4

1 に答える 1

0

数日間壁にぶつかった後、gevent-zeromq と呼ばれるノンブロッキング zeromq クライアントを見つけました。

教訓は、zmq クライアントで gevent-websocket を使用する人は、pyzmq を使用せずに gevent-zeromq を使用することです。

現在、gevent-zeromq は pyzmq とマージされています。import zmqする代わりにfrom zmq.green import zmq

于 2013-11-16T14:14:07.677 に答える