summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Mailman/Defaults.py.in56
-rw-r--r--Mailman/Queue/HTTPRunner.py7
-rw-r--r--Mailman/bin/mailmanctl.py2
-rw-r--r--Mailman/bin/qrunner.py6
-rw-r--r--Mailman/configuration.py47
-rw-r--r--misc/mailman.cfg.sample2
6 files changed, 66 insertions, 54 deletions
diff --git a/Mailman/Defaults.py.in b/Mailman/Defaults.py.in
index 4c4a0a822..554bb1050 100644
--- a/Mailman/Defaults.py.in
+++ b/Mailman/Defaults.py.in
@@ -1,6 +1,6 @@
# -*- python -*-
-# Copyright (C) 1998-2006 by the Free Software Foundation, Inc.
+# Copyright (C) 1998-2007 by the Free Software Foundation, Inc.
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
@@ -671,38 +671,24 @@ MAX_AUTORESPONSES_PER_DAY = 10
# Qrunner defaults
#####
-# Which queues should the qrunner master watchdog spawn? This is a list of
-# 2-tuples containing the name of the qrunner class (which must live in a
-# module of the same name within the Mailman.Queue package), and the number of
-# parallel processes to fork for each qrunner. If more than one process is
-# used, each will take an equal subdivision of the hash space.
-
-# BAW: Eventually we may support weighted hash spaces.
-# BAW: Although not enforced, the # of slices must be a power of 2
-
-QRUNNERS = [
- ('ArchRunner', 1), # messages for the archiver
- ('BounceRunner', 1), # for processing the qfile/bounces directory
- ('CommandRunner', 1), # commands and bounces from the outside world
- ('IncomingRunner', 1), # posts from the outside world
- ('NewsRunner', 1), # outgoing messages to the nntpd
- ('OutgoingRunner', 1), # outgoing messages to the smtpd
- ('VirginRunner', 1), # internally crafted (virgin birth) messages
- ('RetryRunner', 1), # retry temporarily failed deliveries
- ]
-
+# Which queues should the qrunner master watchdog spawn? add_qrunners() takes
+# one required argument, which is the name of the qrunner to start
+# (capitalized and without the 'Runner' suffix). Optional second argument
+# specifies the number of parallel processes to fork for each qrunner. If
+# more than one process is used, each will take an equal subdivision of the
+# hash space, so the number must be a power of 2.
+#
+# del_qrunners() takes one argument which is the name of the qrunner not to
+# start. This is used because by default, Mailman starts the Arch, Bounce,
+# Command, Incoming, News, Outgoing, Retry, and Virgin queues.
+#
# Set this to Yes to use the `Maildir' delivery option. If you change this
# you will need to re-run bin/genaliases for MTAs that don't use list
# auto-detection.
#
# WARNING: If you want to use Maildir delivery, you /must/ start Mailman's
# qrunner as root, or you will get permission problems.
-#
-# NOTE: Maildir delivery is experimental for Mailman 2.1.
USE_MAILDIR = No
-# NOTE: If you set USE_MAILDIR = Yes, add the following line to your mm_cfg.py
-# file (uncommented of course!)
-# QRUNNERS.append(('MaildirRunner', 1))
# Set this to Yes to use the `LMTP' delivery option. If you change this
# you will need to re-run bin/genaliases for MTAs that don't use list
@@ -712,21 +698,15 @@ USE_MAILDIR = No
# transport_maps = hash:<prefix>/data/transport
# Also needed is following line if your list is in $mydestination:
# alias_maps = hash:/etc/aliases, hash:<prefix>/data/aliases
-#
-# NOTE: LMTP delivery is experimental for Mailman 2.2.
USE_LMTP = No
-# NOTE: If you set USE_LMTP = Yes, add the following line to your mailman.cfg
-# file (uncommented of course!)
-# add_runner('LMTPRunner')
-# Change LMTP_HOST and LMTP_PORT for your convenience.
-# You should be careful enough to use firewall if you
-# open your port on global address interface.
+# Change LMTP_HOST and LMTP_PORT for your convenience. You should be careful
+# enough to use a firewall if you open your port on global address interface.
LMTP_HOST = 'localhost'
LMTP_PORT = 8025
-# Name of the domains which operate on LMTP mailman only.
-# Currently valid only for Postfix alias generation.
+# Name of the domains which operate on LMTP Mailman only. Currently valid
+# only for Postfix alias generation.
LMTP_ONLY_DOMAINS = []
# If the list is not present in LMTP_ONLY_DOMAINS, LMTPRunner would return
@@ -736,7 +716,7 @@ LMTP_ONLY_DOMAINS = []
# LMTP_ERR_550 = '250 Ok. But, blackholed because mailbox unavailable'.
LMTP_ERR_550 = '550 Requested action not taken: mailbox unavailable'
-# Experimental WSGI Server.
+# WSGI Server.
#
# You must enable PROXY of Apache httpd server and configure to pass Mailman
# CGI requests to this WSGI Server:
@@ -748,7 +728,7 @@ LMTP_ERR_550 = '550 Requested action not taken: mailbox unavailable'
# ProxyPassReverseCookiePath
#
# Also you have to add following line to <prefix>/etc/mailman.cfg
-# add_runner('HTTPRunner')
+# add_qrunner('HTTP')
HTTP_HOST = 'localhost'
HTTP_PORT = 2580
diff --git a/Mailman/Queue/HTTPRunner.py b/Mailman/Queue/HTTPRunner.py
index 1858cff58..b4de67fd7 100644
--- a/Mailman/Queue/HTTPRunner.py
+++ b/Mailman/Queue/HTTPRunner.py
@@ -64,8 +64,9 @@ qlog.info('HTTPRunner qrunner started.')
hlog.info('HTTPRunner listening on %s:%s', config.HTTP_HOST, config.HTTP_PORT)
try:
server.serve_forever()
-# Do it this way because of exception hierarchy changes in Python 2.5. XXX
-# Change this to BaseException for Python 2.5.
-except (Exception, KeyboardInterrupt):
+except KeyboardInterrupt:
+ qlog.exception('HTTPRunner qrunner exiting.')
+ sys.exit(signal.SIGTERM)
+except:
qlog.exception('HTTPRunner qrunner exiting.')
raise
diff --git a/Mailman/bin/mailmanctl.py b/Mailman/bin/mailmanctl.py
index db74214c0..2c79797d8 100644
--- a/Mailman/bin/mailmanctl.py
+++ b/Mailman/bin/mailmanctl.py
@@ -266,7 +266,7 @@ def start_runner(qrname, slice, count):
def start_all_runners():
kids = {}
- for qrname, count in config.QRUNNERS:
+ for qrname, count in config.qrunners.items():
for slice in range(count):
# queue runner name, slice, numslices, restart count
info = (qrname, slice, count, 0)
diff --git a/Mailman/bin/qrunner.py b/Mailman/bin/qrunner.py
index 3b71bf448..2e6c4138e 100644
--- a/Mailman/bin/qrunner.py
+++ b/Mailman/bin/qrunner.py
@@ -1,4 +1,4 @@
-# Copyright (C) 2001-2006 by the Free Software Foundation, Inc.
+# Copyright (C) 2001-2007 by the Free Software Foundation, Inc.
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
@@ -53,7 +53,7 @@ def r_callback(option, opt, value, parser):
print >> sys.stderr, _('Bad runner specification: $value')
sys.exit(1)
if runner == 'All':
- for runnername, slices in config.QRUNNERS:
+ for runnername, slices in config.qrunners.items():
dest.append((runnername, rslice, rrange))
elif not runner.endswith('Runner'):
runner += 'Runner'
@@ -190,7 +190,7 @@ def main():
log = logging.getLogger('mailman.qrunner')
if opts.list:
- for runnername, slices in config.QRUNNERS:
+ for runnername, slices in config.qrunners.items():
if runnername.endswith('Runner'):
name = runnername[:-len('Runner')]
else:
diff --git a/Mailman/configuration.py b/Mailman/configuration.py
index 6825d5792..a489025ca 100644
--- a/Mailman/configuration.py
+++ b/Mailman/configuration.py
@@ -1,4 +1,4 @@
-# Copyright (C) 2006 by the Free Software Foundation, Inc.
+# Copyright (C) 2006-2007 by the Free Software Foundation, Inc.
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
@@ -25,12 +25,24 @@ from Mailman import Errors
_missing = object()
+DEFAULT_QRUNNERS = (
+ 'Arch',
+ 'Bounce',
+ 'Command',
+ 'Incoming',
+ 'News',
+ 'Outgoing',
+ 'Retry',
+ 'Virgin',
+ )
+
class Configuration(object):
def __init__(self):
self.domains = {} # email host -> web host
self._reverse = None
+ self.qrunners = {}
def load(self, filename=None):
# Load the configuration from the named file, or if not given, search
@@ -49,8 +61,13 @@ class Configuration(object):
del ns['__file__']
del ns['__name__']
del ns['__doc__']
- ns['add_domain'] = self.add_domain
- ns['add_runner'] = self.add_runner
+ ns['add_domain'] = self.add_domain
+ ns['add_qrunner'] = self.add_qrunner
+ ns['del_qrunner'] = self.del_qrunner
+ # Set up the default list of qrunners so that the mailman.cfg file may
+ # add or delete them.
+ for name in DEFAULT_QRUNNERS:
+ self.add_qrunner(name)
# Attempt our first choice
path = os.path.abspath(os.path.expanduser(filename))
try:
@@ -61,6 +78,11 @@ class Configuration(object):
# The file didn't exist, so try mm_cfg.py
from Mailman import mm_cfg
ns.update(mm_cfg.__dict__)
+ # Based on values possibly set in mailman.cfg, add additional qrunners
+ if ns['USE_MAILDIR']:
+ self.add_qrunner('Maildir')
+ if ns['USE_LMTP']:
+ self.add_qrunner('LMTP')
# Pull out the defaults
PREFIX = ns['PREFIX']
VAR_PREFIX = ns['VAR_PREFIX']
@@ -141,14 +163,23 @@ class Configuration(object):
self._reverse = dict([(v, k) for k, v in self.domains.items()])
return self._reverse.get(url_host, default)
- def add_runner(self, name, count=1):
+ def add_qrunner(self, name, count=1):
"""Convenient interface for adding additional qrunners.
- name is the qrunner name, and must include the 'Runner' suffix.
- E.g. 'HTTPRunner' or 'LMTPRunner'. count is the number of qrunner
- slices to create, by default, 1.
+ name is the qrunner name and it must not include the 'Runner' suffix.
+ E.g. 'HTTP' or 'LMTP'. count is the number of qrunner slices to
+ create, by default, 1.
+ """
+ name += 'Runner'
+ self.qrunners[name] = count
+
+ def del_qrunner(self, name):
+ """Remove the named qrunner so that it does not start.
+
+ name is the qrunner name and it must not include the 'Runner' suffix.
"""
- self.QRUNNERS.append((name, count))
+ name += 'Runner'
+ self.qrunners.pop(name)
@property
def paths(self):
diff --git a/misc/mailman.cfg.sample b/misc/mailman.cfg.sample
index dcf38e313..3aab3d61e 100644
--- a/misc/mailman.cfg.sample
+++ b/misc/mailman.cfg.sample
@@ -1,6 +1,6 @@
# -*- python -*-
-# Copyright (C) 2006 by the Free Software Foundation, Inc.
+# Copyright (C) 2006-2007 by the Free Software Foundation, Inc.
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License