Sto provando ad usare Pyro per controllare una macchina slave. Rsync i file python necessari, avvio un server Pyro, eseguo alcune azioni con il controllo remoto, e poi voglio dire al server Pyro di spegnersi.Come posso uscire in modo pulito da un demone Pyro su richiesta del cliente?
Ho problemi a far spegnere Pryo Daemon in modo pulito. Si blocca o nella chiamata Daemon.close()
, o se commento fuori quella linea esce senza chiudere correttamente il suo socket, risultante in socket.error: [Errno 98] Address already in use
se riavvio il server troppo presto.
Non credo che SO_REUSEADDR sia la soluzione corretta, poiché l'arresto di socket non pulito porta ancora a un socket sospeso nello stato TIME_WAIT, causando potenzialmente l'esistenza di problemi in alcuni client. Penso che la soluzione migliore sia convincere Pyro Daemon a chiudere correttamente il socket.
Non è corretto chiamare Daemon.shutdown() dall'interno del daemon stesso?
Se avvio un server e quindi preme CTRL-C senza alcun client connesso, non ho alcun problema (nessun errore Address already in use
). Ciò rende possibile un arresto pulito, la maggior parte delle volte (assumendo un client e un server altrimenti sensati).
Esempio: 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'
Esempio: client.py
import Pyro4
if __name__ == '__main__':
uri = 'PYRO:[email protected]: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'
Hey Eric. Non ho mai avuto l'indirizzo in uso per il server Pyro, ma ottengo tutto il tempo per il 'Name Server'. Premendo CTRL + C sul NameServer si ha una probabilità del 50% di provocare quell'errore se eseguo nuovamente il server dei nomi entro 30 secondi. Hai avuto questo prima? –