Yves Dorfsman wrote:
I did a few tests with this script:
class byebye:
def __del__(self):
print 'Bye, bye...'
x = byebye()
x.del() gets executed if:
-I del x, then run gc.collect()
-simply exit the script
-get the script to abort on an exception
But if I kill it with the default signal TERM, the script dies, but I
don't get the message, so I am assuming that python isn't taking the
time to cleanup, even though that is (was) what TERM was intended for.
TERM signal is unix specific. There is no special syntax/programming
structure for signals inside the Python language, since it would be
platform dependent. For simple client programs, usually it is not needed
to setup signal handlers because they can easily be controlled in other
ways.
For sensitive resources, instead of writing __del__ methods, you should
create a "close()" method. Python does this with file objects, DB API
2.0 with database connection objects etc. Then you can do
res = create_resource ()
try:
use_resource()
finally:
res.close() # Must free resource, but the object can still be alive...
It is more common to use signals when you have more threads or child
processes. You can use something like:
import threading
import signal
stop_requested = threading.Event ()
exited_on_sigte rm = False
def free_all_resour ces():
pass # Free your resources here!
def sigterm_handler (signum, frame):
"""Stop the server gracefully when on SIGTERM."""
global stop_requested
global exited_on_sigte rm
exited_on_sigte rm = True
stop_requested. set()
free_all_resour ces()
def main():
global stop_requested
global exited_on_sigte rm
logger = servicelog.getL ogger('main',fi lename=LOGFILEN AME)
logger.info('Se tting up the SIGTERM signal handler.')
signal.signal(s ignal.SIGTERM, sigterm_handler ) # Setup signal handler
logger.info('St arting watchdog thread')
watchdog = WatchDog()
watchdog.start( )
worker1 = create_worker(s top_requested)
worker2 = create_worker(s top_requested)
# etc. Prepare things here...
try:
try:
server = create_my_serve r()
server.serve_un til_not_stopped ()
except Exception, e:
logger.error(du mpexc(e))
raise e
finally:
stop_requested. set() # Ask other threads to stop cooperatively
# Join all threads here
watchdog.join()
worker1.join()
worder2.join()
# etc. wait for all threads to exit cooperatively.
if exited_on_sigte rm:
logger.warning( 'Exited on SIGTERM!')
Best,
Laszlo