gpt4 book ai didi

python - 如何根据客户请求干净地退出 Pyro 守护进程?

转载 作者:太空狗 更新时间:2023-10-29 23:59:00 24 4
gpt4 key购买 nike

我正在尝试使用 Pyro 来控制从机。我 rsync 必要的 python 文件,启动 Pyro 服务器,通过远程控制执行一些操作,然后我想告诉 Pyro 服务器关闭。

我无法让 Pryo 守护程序完全关闭。它要么卡在 Daemon.close() 调用中,要么如果我注释掉该行,它会在没有正确关闭其套接字的情况下退出,从而导致 socket.error: [Errno 98] Address already in use 如果我过早重启服务器。

它不认为 SO_REUSEADDR 是正确的解决方法,因为不干净的套接字关闭仍然会导致套接字在 TIME_WAIT 状态下徘徊,可能导致一些客户端遇到问题。我认为更好的解决方案是说服 Pyro Daemon 正确关闭其套接字。

从守护进程内部调用 Daemon.shutdown() 是否不合适?

如果我启动服务器然后在没有连接任何客户端的情况下按 CTRL-C,我不会遇到任何问题(没有 Address already in use 错误)。这使得在大多数情况下完全关闭似乎是可能的(假设客户端和服务器在其他方面是正常的)。

例子:server.py

import Pyro4

class TestAPI:
def __init__(self, daemon):
self.daemon = daemon
def hello(self, msg):
print 'client said {}'.format(msg)
return 'hola'
def shutdown(self):
print 'shutting down...'
self.daemon.shutdown()

if __name__ == '__main__':
daemon = Pyro4.Daemon(port=9999)
tapi = TestAPI(daemon)
uri = daemon.register(tapi, objectId='TestAPI')
daemon.requestLoop()
print 'exited requestLoop'
daemon.close() # this hangs
print 'daemon closed'

例子:client.py

import Pyro4

if __name__ == '__main__':
uri = 'PYRO:TestAPI@localhost:9999'
remote = Pyro4.Proxy(uri)
response = remote.hello('hello')
print 'server said {}'.format(response)
try:
remote.shutdown()
except Pyro4.errors.ConnectionClosedError:
pass
print 'client exiting'

最佳答案

我认为这可以在不使用超时或循环条件的情况下完成,方法是让您的 shutdown() 调用守护进程的 shutdown。根据http://pythonhosted.org/Pyro4/servercode.html#cleaning-up :

Another possibility is calling Pyro4.core.Daemon.shutdown() on the running bdaemon object. This will also break out of the request loop and allows your code to neatly clean up after itself, and will also work on the threaded server type without any other requirements.

以下适用于 Windows 上的 Python3.4.2。 @Pyro4.oneway 装饰器用于shutdown 这里不需要,但在某些情况下需要。

server.py

import Pyro4
# using Python3.4.2

@Pyro4.expose
class TestAPI:
def __init__(self, daemon):
self.daemon = daemon
def hello(self, msg):
print('client said {}'.format(msg))
return 'hola'
@Pyro4.oneway # in case call returns much later than daemon.shutdown
def shutdown(self):
print('shutting down...')
self.daemon.shutdown()

if __name__ == '__main__':
daemon = Pyro4.Daemon(port=9999)
tapi = TestAPI(daemon)
uri = daemon.register(tapi, objectId='TestAPI')
daemon.requestLoop()
print('exited requestLoop')
daemon.close()
print('daemon closed')

client.py

import Pyro4
# using Python3.4.2

if __name__ == '__main__':
uri = 'PYRO:TestAPI@localhost:9999'
remote = Pyro4.Proxy(uri)
response = remote.hello('hello')
print('server said {}'.format(response))
remote.shutdown()
remote._pyroRelease()
print('client exiting')

关于python - 如何根据客户请求干净地退出 Pyro 守护进程?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24461167/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com