2016-07-04 21 views
0

Ich versuche, einen Spiel-Server mit Python, Tornado zu machen.tornado wie man WebSockets mit wsgi verwendet

Das Problem ist, dass WebSockets nicht mit wsgi funktionieren.

wsgi_app = tornado.wsgi.WSGIAdapter(app) 
server = wsgiref.simple_server.make_server('', 5000, wsgi_app) 
server.serve_forever() 

Nach Trog suchen diese Antwort auf Stackoverflow, Running Tornado in apache, ich habe meinen Code aktualisiert, um eine HTTPServer zu verwenden, die mit WebSockets funktioniert.

server = tornado.httpserver.HTTPServer(app) 
server.listen(5000) 
tornado.ioloop.IOLoop.instance().start() 

Allerdings, wenn ich die Http verwenden, wird eine Fehlermeldung, dass aufkommt: TypeError: __call__() takes exactly 2 arguments (3 given)

diese Suche im Internet, fand ich eine Antwort auf die Frage hier: tornado.wsgi.WSGIApplication issue: __call__ takes exactly 3 arguments (2 given)

Aber nach dem Hinzufügen tornado.wsgi.WSGIContainer um app, der Fehler bleibt bestehen.

Wie kann ich dieses Problem lösen? Oder gibt es eine Möglichkeit, Tornado-Web-Sockets mit wsgi zu verwenden.

Hier ist mein Code im Moment:

import tornado.web 
import tornado.websocket 
import tornado.wsgi 
import tornado.template 
import tornado.httpserver 
#import wsgiref.simple_server 
import wsgiref 

print "setting up environment..." 

class TornadoApp(tornado.web.Application): 
    def __init__(self): 

     handlers = [ 

      (r"/chat", ChatPageHandler), 
      (r"/wschat", ChatWSHandler), 
      (r"/*", MainHandler) 

     ] 

     settings = { 

      "debug" : True, 
      "template_path" : "templates", 
      "static_path" : "static" 

     } 

     tornado.web.Application.__init__(self, handlers, **settings) 

class MainHandler(tornado.web.RequestHandler): 
    def get(self): 
     self.render("test.html", food = "pizza") 

class ChatPageHandler(tornado.web.RequestHandler): 
    def get(self): 
     self.render("chat.html") 

class ChatWSHandler(tornado.websocket.WebSocketHandler): 
    connections = [] 

    def open(self, *args): 
     print 'a' 
     self.connections.append(self) 
     print 'b' 
     self.write_message(u"@server: WebSocket opened!") 
     print 'c' 

    def on_message(self, message): 
     [con.write_message(u""+message) for con in self.connections] 

    def on_close(self): 
     self.connections.remove(self) 

print "done" 

if __name__ == "__main__": 
    app = TornadoApp() 
    server = tornado.httpserver.HTTPServer(tornado.wsgi.WSGIContainer(app)) 
    server.listen(5000) 
    tornado.ioloop.IOLoop.instance().start() 

das Thank in advace! Hilfe sehr geschätzt.

Antwort

1

HTTPServer benötigt eine tornado.web.Application, die nicht die gleiche wie eine WSGI-Anwendung ist (die Sie mit WSGIContainer verwenden könnten).

Es wird empfohlen, dass Sie sowohl WSGI als auch Websockets in zwei separaten Prozessen mit einem IPC-Mechanismus Ihrer Wahl ausführen (und anstelle von Tornados WSGIContainer einen echten WSGI-Server verwenden). Wenn Sie sie im selben Prozess ausführen müssen, können Sie eine FallbackHandler verwenden.

wsgi_container = tornado.wsgi.WSGIContainer(my_wsgi_app) 
application = tornado.web.Application([ 
    (r"/ws", MyWebSocketHandler), 
    (r".*", FallbackHandler, dict(fallback=wsgi_container), 
]) 
+0

Was ist 'my_wsgi_app'? –

+0

Das ist die App, die Sie erstellen, das Ergebnis des von Ihnen verwendeten WSGI-Frameworks. Die App, die du oben eingefügt hast, ist reiner Tornado; Es ist nicht nötig, etwas mit WSGI zu tun, wenn Ihre App so aussieht. Sie benötigen nur WSGI, wenn Sie ein WSGI-basiertes Framework wie Flask verwenden. –

+0

Ah, ich verstehe! Vielen Dank. Ich werde das bald versuchen. –