微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

Stop() gevent 网络服务器永远不会被调用

如何解决Stop() gevent 网络服务器永远不会被调用

我无法停止我的 Gevent 网络服务器,因为我的 stop() 函数从未被调用过。

我的 Gevent 网络服务器 (serve_forever()) 在单个 QThread 线程中运行。 我的主要应用程序是 (QCoreApplication) 用 pyside2 编写的。

我尝试了什么

  • 从主应用程序向线程发出停止信号 -> 线程中调用 stop() 的插槽从未被激活 -> 我认为 server_forever() 正在阻塞它?!
  • 我在谷歌上搜索stop() 不得从同一线程内调用 -> 不幸的是,我不知道如何安全地从另一个线程调用方法。我认为这正是信号/插槽的用途
  • 我尝试使用 gevent.signal.signal() 而不是 @QtCore.Slot()。 -> 此函数不接受自定义信号,或者我做错了

更新工作示例:

ma​​in.py

import sys
from pyside2.QtCore import QCoreApplication,QTimer
from T_CTRL import T_CTRL

def main():

    # create application
    app = QCoreApplication.instance()
    if app is None: 
        app = QCoreApplication(sys.argv)
    
    # connect: cleanup application before quitting
    app.aboutToQuit.connect(app.deleteLater)

    # create my control object
    myCtrl = T_CTRL() 
    
    # # create helper timer,so that quit signals can be received
    timerHelper = QTimer()
    timerHelper.start(500)
    timerHelper.timeout.connect(lambda: None)  # Let the interpreter run each 500 ms.

    # run application and create main event handler
    return app.exec_()
    
if __name__ == '__main__':
    main()

T_CTRL.py

from pyside2 import QtCore
from pyside2.QtCore import QThread,QCoreApplication

from T_Web_Worker import ThreadWorker
import signal
from functools import partial

class T_CTRL(QtCore.QObject): 
    
    # signals    
    sigShutdown = QtCore.Signal()   
    
    def __init__(self):  
        # init 
        super(T_CTRL,self).__init__()      

        # create objects
        self.t = QThread()
        self.worker = ThreadWorker()
    
        # connect quit signals to sigint_handler
        signal.signal(signal.SIGINT,partial(self.sigint_handler,str1=""))
        signal.signal(signal.SIGTERM,str1=""))
        
        # move worker to thread
        self.worker.movetoThread(self.t)        
        
        # connect: startServer() when thread has started
        self.t.started.connect(self.worker.startServer)
                
        # connect: requestServerStop() when Sigint handler has been activated
        self.sigShutdown.connect(self.worker.requestServerStop)
        
        # connect: webserver told that is has shut down,Now stop the thread
        self.worker.sigServerShutdownFinished.connect(self.t.quit)
        self.worker.sigServerShutdownFinished.connect(self.worker.deleteLater)

        # connect: thread has finished,Now quit the application        
        self.t.finished.connect(self.t.deleteLater)
        self.t.finished.connect(self.quit_Now)
       
        # start the thread
        self.t.start()

    def sigint_handler(self,signal,frame,str1):
       print ("T_CTRL: Slot 'sigint_handler' activated. Emitting signal 'sigShutdown'")
       self.sigShutdown.emit()
       QCoreApplication.processEvents()

    @QtCore.Slot()
    def quit_Now(self): 
       print ("_CTRL: slot 'quit_Now' activated,quitting application")
       QCoreApplication.quit()         

T_Web_Worker

from pyside2 import QtCore
from pyside2.QtCore import QCoreApplication
from flask import Flask
from gevent.pywsgi import WsgiServer

class ThreadWorker(QtCore.QObject): 
    
    # init flask & tornado
    app = Flask(__name__)
    http_server = None
    
    # signal to Feedback,that worker has finished
    sigServerShutdownFinished = QtCore.Signal()
    
        
    def __init__(self):
        super(ThreadWorker,self).__init__() 
        
    # start requested by main thread
    @QtCore.Slot()
    def startServer(self):
        print ("T_Web_Worker: Slot 'startServer' activated")
        self.http_server = WsgiServer(('127.0.0.1',5000),self.app)       
        self.http_server.serve_forever()
        QCoreApplication.processEvents()

    # shutdown requested by main thread
    @QtCore.Slot()
    def requestServerStop(self):   
        print("T_Web_Worker: Slot 'requestServerStop' activated. Emitting signal 'sigServerShutdownFinished'")
        self.http_server.stop(timeout=5)
        self.sigServerShutdownFinished.emit()
        QCoreApplication.processEvents()

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。