2016-05-05 80 views
1

我想捕獲cntrl-c事件,以便我可以優雅地關閉我的服務器(使用瓶框架)。但是,當我測試這個時,我從來沒有在調試器中使用停止方法,並且我也得到了一個未封閉的套接字警告以確認這一點。我在這裏錯過了什麼。SIGINT不可捕捉,在python

class CFMServer(ServerAdapter): 

    def run(self, handler): 
     from wsgiref.simple_server import make_server, WSGIRequestHandler 
     self.server = make_server(self.host, self.port, handler, **self.options) 
     # set signal handlers 
     signal.signal(signal.SIGINT, self.stop) 
     signal.signal(signal.SIGTERM, self.stop) 
     try: 
      self.server.serve_forever() 
     except KeyboardInterrupt: 
      self.stop() 
      raise 

    def stop(self): 
     pdb.set_trace() 
     manager.save() 
     self.server.server_close() 


if __name__ == "__main__": 
    parser = argparse.ArgumentParser() 
    parser.add_argument('port', metavar='P', type=int, 
         help='Port to assign the server in localhost') 
    args = parser.parse_args() 
    port = args.port 
    server = CFMServer(host='localhost', port=port) 
    service.run(server=server, debug=True) 

這是我的shell輸出,當我中斷。

Bottle v0.13-dev server starting up (using CFMServer())... 
Listening on http://localhost:11245/ 
Hit Ctrl-C to quit. 

^CTraceback (most recent call last): 
    File "./cfm-service", line 127, in <module> 
    service.run(server=server, debug=True) 
    File "/repo/ekrmann/next-debugger/python/emca/gdbcmds/emca/core/third_party/bottle.py", line 881, in run 
    run(self, **kwargs) 
    File "/repo/ekrmann/next-debugger/python/emca/gdbcmds/emca/core/third_party/bottle.py", line 3476, in run 
    server.run(app) 
    File "./cfm-service", line 108, in run 
    self.server.serve_forever() 
    File "/app/vbuild/RHEL6-i686/python/3.5.0/lib/python3.5/socketserver.py", line 237, in serve_forever 
    ready = selector.select(poll_interval) 
    File "/app/vbuild/RHEL6-i686/python/3.5.0/lib/python3.5/selectors.py", line 367, in select 
    fd_event_list = self._poll.poll(timeout) 
TypeError: stop() takes 1 positional argument but 3 were given 
sys:1: ResourceWarning: unclosed <socket.socket fd=4, family=AddressFamily.AF_INET, type=SocketKind.SOCK_STREAM, proto=0, laddr=('127.0.0.1', 11245)> 

回答

0

您的stop方法沒有實現Python信號處理函數簽名。取而代之的

signal.signal(signal.SIGINT, self.stop) 

寫一個輔助函數的作用:

signal.signal(signal.SIGINT, lambda _signum, _stack: self.stop())