112 lines
4.3 KiB
Python
Executable File
112 lines
4.3 KiB
Python
Executable File
#!/usr/bin/env python
|
|
# -*- coding: utf-8 -*-
|
|
|
|
"""
|
|
OpenERP cron jobs worker
|
|
|
|
This script executes OpenERP cron jobs. Normally, cron jobs are handled by the
|
|
OpenERP server but depending on deployment needs, independent worker processes
|
|
can be used. This is especially the case when the server is run via Gunicorn.
|
|
|
|
OpenERP cron jobs worker re-uses openerp-server command-line options but does
|
|
not honor all of them.
|
|
|
|
Meaningful options include:
|
|
|
|
-d, --database comma-separated list of databases to monitor for cron jobs
|
|
processing. If left empty, the worker monitors all databases
|
|
(given by `psql -ls`).
|
|
|
|
--addons-path as ususal.
|
|
|
|
--cpu-time-limit
|
|
--virtual-memory-limit
|
|
--virtual-memory-reset Those three options have the same meaning the for
|
|
the server with Gunicorn. The only catch is: To
|
|
not enable rlimits by default, those options are
|
|
honored only when --cpu-time-limte is different than
|
|
60 (its default value).
|
|
"""
|
|
|
|
import logging
|
|
import os
|
|
import signal
|
|
import sys
|
|
|
|
import openerp
|
|
|
|
# Also use the `openerp` logger for the main script.
|
|
_logger = logging.getLogger('openerp')
|
|
|
|
# Variable keeping track of the number of calls to the signal handler defined
|
|
# below. This variable is monitored by ``quit_on_signals()``.
|
|
quit_signals_received = 0
|
|
|
|
# TODO copy/pasted from openerp-server
|
|
def signal_handler(sig, frame):
|
|
""" Signal handler: exit ungracefully on the second handled signal.
|
|
|
|
:param sig: the signal number
|
|
:param frame: the interrupted stack frame or None
|
|
"""
|
|
global quit_signals_received
|
|
quit_signals_received += 1
|
|
import openerp.addons.base
|
|
openerp.addons.base.ir.ir_cron.quit_signal_received = True
|
|
if quit_signals_received == 1 and openerp.addons.base.ir.ir_cron.job_in_progress:
|
|
_logger.info("Waiting for the current job to complete.")
|
|
print "Waiting for the current job to complete."
|
|
print "Hit Ctrl-C again to force shutdown."
|
|
if quit_signals_received > 1:
|
|
# logging.shutdown was already called at this point.
|
|
sys.stderr.write("Forced shutdown.\n")
|
|
os._exit(0)
|
|
|
|
# TODO copy/pasted from openerp-server
|
|
def setup_signal_handlers():
|
|
""" Register the signal handler defined above. """
|
|
SIGNALS = map(lambda x: getattr(signal, "SIG%s" % x), "INT TERM".split())
|
|
if os.name == 'posix':
|
|
map(lambda sig: signal.signal(sig, signal_handler), SIGNALS)
|
|
elif os.name == 'nt':
|
|
import win32api
|
|
win32api.SetConsoleCtrlHandler(lambda sig: signal_handler(sig, None), 1)
|
|
|
|
def list_databases():
|
|
import subprocess
|
|
p1 = subprocess.Popen(["psql", "-lAt"], stdout=subprocess.PIPE)
|
|
p2 = subprocess.Popen(["cut", "-f", "1", "-d", "|"], stdin=p1.stdout, stdout=subprocess.PIPE)
|
|
p1.stdout.close() # Allow p1 to receive a SIGPIPE if p2 exits.
|
|
output = p2.communicate()[0]
|
|
databases = output.splitlines()
|
|
# TODO filter out non-OpenERP databases
|
|
databases = [d for d in databases if d not in ['template0', 'template1', 'postgres']]
|
|
databases = [d for d in databases if not d.startswith('postgres')]
|
|
return databases
|
|
|
|
if __name__ == '__main__':
|
|
os.environ['TZ'] = 'UTC'
|
|
openerp.tools.config.parse_config(sys.argv[1:])
|
|
config = openerp.tools.config
|
|
if config['log_handler'] == [':INFO']:
|
|
# Replace the default value, which is suitable for openerp-server.
|
|
config['log_handler'].append('openerp.addons.base.ir.ir_cron:DEBUG')
|
|
setup_signal_handlers()
|
|
openerp.modules.module.initialize_sys_path()
|
|
openerp.modules.loading.open_openerp_namespace()
|
|
openerp.netsvc.init_logger()
|
|
openerp.cron.enable_schedule_wakeup = False
|
|
openerp.multi_process = True # enable multi-process signaling
|
|
import openerp.addons.base
|
|
print "OpenERP cron jobs worker. Hit Ctrl-C to exit."
|
|
print "Documentation is available at the top of the `opener-cron-worker` file."
|
|
if config['db_name']:
|
|
db_names = config['db_name'].split(',')
|
|
print "Monitoring %s databases." % len(db_names)
|
|
else:
|
|
db_names = list_databases
|
|
print "Monitored databases are auto-discovered."
|
|
openerp.addons.base.ir.ir_cron.ir_cron._run(db_names)
|
|
|
|
# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
|