From 0998ba83319423e1c22e52f6e7147c627f87b2a6 Mon Sep 17 00:00:00 2001 From: Jim Fulton <jim@zope.com> Date: Tue, 28 Sep 2010 20:19:23 +0000 Subject: [PATCH] Bug Fixed - Logrotation/repoening via a SIGUSR2 signal wasn't implemented. (https://bugs.launchpad.net/zodb/+bug/143600) --- src/CHANGES.txt | 3 ++ src/ZEO/runzeo.py | 28 +++++++++++++++--- src/ZEO/tests/testZEO.py | 61 ++++++++++++++++++++++++++++++++++++++++ 3 files changed, 88 insertions(+), 4 deletions(-) diff --git a/src/CHANGES.txt b/src/CHANGES.txt index 7cb5ddfe..36deba30 100644 --- a/src/CHANGES.txt +++ b/src/CHANGES.txt @@ -15,6 +15,9 @@ Bugs Fixed Python 2.7 wasn't officially supported, but we were releasing binaries for it, so ... +- Logrotation/repoening via a SIGUSR2 signal wasn't implemented. + (https://bugs.launchpad.net/zodb/+bug/143600) + 3.9.6 (2010-09-21) ================== diff --git a/src/ZEO/runzeo.py b/src/ZEO/runzeo.py index ddfb49e3..98e67744 100644 --- a/src/ZEO/runzeo.py +++ b/src/ZEO/runzeo.py @@ -269,10 +269,30 @@ class ZEOServer: sys.exit(1) def handle_sigusr2(self): - # TODO: this used to reinitialize zLOG. How do I achieve - # the same effect with Python's logging package? - # Should we restart as with SIGHUP? - log("received SIGUSR2, but it was not handled!", level=logging.WARNING) + # log rotation signal - do the same as Zope 2.7/2.8... + if self.options.config_logger is None or os.name not in ("posix", "nt"): + log("received SIGUSR2, but it was not handled!", + level=logging.WARNING) + return + + loggers = [self.options.config_logger] + + if os.name == "posix": + for l in loggers: + l.reopen() + log("Log files reopened successfully", level=logging.INFO) + else: # nt - same rotation code as in Zope's Signals/Signals.py + for l in loggers: + for f in l.handler_factories: + handler = f() + if hasattr(handler, 'rotate') and callable(handler.rotate): + handler.rotate() + log("Log files rotation complete", level=logging.INFO) + + + + + def close_storages(self): for name, storage in self.storages.items(): diff --git a/src/ZEO/tests/testZEO.py b/src/ZEO/tests/testZEO.py index ac93bed2..82807d71 100644 --- a/src/ZEO/tests/testZEO.py +++ b/src/ZEO/tests/testZEO.py @@ -1299,6 +1299,67 @@ But, if we abort, we'll get up to date data and we'll see the changes. """ +script_template = """ +import sys +sys.path[:] = %(path)r + +%(src)s + +""" + +def generate_script(name, src): + open(name, 'w').write(script_template % dict( + exe=sys.executable, + path=sys.path, + src=src, + )) + +def runzeo_logrotate_on_sigusr2(): + """ + >>> port = get_port() + >>> open('c', 'w').write(''' + ... <zeo> + ... address %s + ... </zeo> + ... <mappingstorage> + ... </mappingstorage> + ... <eventlog> + ... <logfile> + ... path l + ... </logfile> + ... </eventlog> + ... ''' % port) + >>> generate_script('s', ''' + ... import ZEO.runzeo + ... ZEO.runzeo.main() + ... ''') + >>> import subprocess, signal + >>> p = subprocess.Popen([sys.executable, 's', '-Cc'], close_fds=True) + >>> forker.wait_until('started', + ... lambda : os.path.exists('l') and ('listening on' in open('l').read()) + ... ) + + >>> oldlog = open('l').read() + >>> os.rename('l', 'o') + >>> os.kill(p.pid, signal.SIGUSR2) + + >>> forker.wait_until('new file', lambda : os.path.exists('l')) + >>> s = ClientStorage(('', port)) + >>> s.close() + >>> forker.wait_until('See logging', + ... lambda : ('Log files ' in open('l').read())) + >>> open('o').read() == oldlog # No new data in old log + True + + # Cleanup: + + >>> os.kill(p.pid, signal.SIGKILL) + >>> _ = p.wait() + """ + +if sys.platform.startswith('win'): + del runzeo_logrotate_on_sigusr2 + def quick_close_doesnt_kill_server(): r""" -- 2.30.9