Skip to content

Commit 5e88ef8

Browse files
authoredSep 28, 2021
Merge pull request #20 from garloff/feat/docu
Feat/docu
2 parents 9dd2762 + 6ceb61d commit 5e88ef8

File tree

2 files changed

+129
-14
lines changed

2 files changed

+129
-14
lines changed
 

‎README.md

+126-12
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,132 @@
11
# ucs2mailman.py
22

3-
Script to read LDAP directory on UCS server and manage
4-
appropriate mailman3 mailing lists.
3+
Script to read LDAP directory on a UCS server and manage
4+
mailman3 mailing lists corresponding to the LDAP groups.
55

6-
LDAP groups with mailAddress: that is not None will have
7-
should have mailman lists with the users subscribed.
6+
The straight forward use of this script is translating LDAP groups
7+
with mailAddress: (which is not None) to mailman lists with that
8+
name and all group members as subscribers. The subscription will
9+
happen with the main identity (uid @ domain), and all the other
10+
known user mail addresses from the LDAP users will be added as
11+
non-members which can post without being moderated.
812

9-
Purpose of the script is to sync from UCS to mailman:
10-
* Create missing lists
11-
* Add missing users
12-
* Remove extra users
13-
* Also create whitelist for other mail addresses
14-
of subscribers. These will not typically cleaned
15-
up as we don't know, whether these have been added
16-
by the admin and should stay ...
13+
As UCS does mail forwarding from the groups already (without
14+
offering a full feature set for mailing lists), it is a good
15+
idea to leave the normal UCS redistribution in place and create
16+
mailing lists with different names. Using a secondary domain
17+
(option ``-t``), adding a prefix (``-p``) or using arbitrary
18+
name replacements (``-r``) can be used to implement this.
1719

20+
It's also possible to only handle a subset of the LDAP groups
21+
by using filters (options ``-f`` and ``-x``). Lists can also
22+
be set to only ever have group members added but never removed
23+
(``-k``). Without this option, subscribers from the managed
24+
lists that are not (no longer) part of the respective LDAP
25+
group will be removed from the list.
1826

27+
ucs2mailman.py will only do changes to the lists that have
28+
mailAddress: set in the UCS group directory (after applying
29+
the translations from option ``-p``, ``-r``, ``-t`` -- in
30+
this order) and the filters (``-f``, ``-x``), so manually
31+
managed lists, partially managed lists (``-k``) and fully
32+
automatically managed lists can coexist on the same mailman3
33+
instance.
34+
35+
Note that the changes to the mailman3 config are performed
36+
with the user identity of mailman3 owner, ``list`` on Debian
37+
(UCS) systems. The script will change its euid/egid to this
38+
identity (unless overriden by ``-s``), so it needs to be started
39+
with this identity already or as root. (``-s ""`` would skip
40+
the switching, but you'll likely not be able to talk to mailman3
41+
this way.)
42+
43+
## Installation and usage
44+
45+
You need to have mailman3 installed and set up and an admin
46+
user configured which you pass with option ``-a`` as owner/
47+
admin for any newly created lists.
48+
49+
By default, the script calls ``udm`` to get UCS LDAP users
50+
and group lists -- note that this typically requires root privileges.
51+
You can instead use the options ``-u`` and ``-g`` to read the
52+
directory from files. (It is advisable to strip hashed passwords
53+
and jpegPhotos from dumps that end up on your disk.)
54+
55+
On UCS hosts, your postfix configuration is automatically generated
56+
by the univention scripts. To have mailman3 work, you need to tweak
57+
the config file creation logic. Apply the patch from
58+
``integration/postfix-mailman.diff``.
59+
60+
Next step is to monitor the user/group database and ensure that changes
61+
are automatically reflected in mailman subscriptions. On UCS, this can be
62+
done by calling ``integration/new_udm.sh`` every few minutes from a cron
63+
job as root. The script will then call ``/var/list/update_mls.sh`` as user
64+
``list`` *if* the user/group databases have changed. Copy
65+
``integration/update_mls.sh`` there (and make sure ``new_udm.sh`` and
66+
``update_mls.sh`` are executable by the respective users).
67+
68+
## Testing
69+
70+
You can use the options ``-d`` and ``-n`` to test and understand
71+
what changes ``ucs2mailman.py`` would to your mailings lists
72+
prior to having it performing changes.
73+
74+
There is a test script which tests creation of mailing lists, adding
75+
users and changing and removing users. See ``test/`` directory.
76+
77+
## TODO
78+
79+
The LDAP (LDIF) parsing does understand the formatting from
80+
``udm`` output as well as plain ``ldapsearch`` output (if you switch
81+
off line wrapping). However, ``ucs2mailman.py`` has really been
82+
developed for being run on a UCS instance, so expect a few tweaks
83+
to be required on non-UCS LDAP hosts for it to really be useful.
84+
Patches (pull requests) are welcome!
85+
86+
mailman3 has a REST interface -- from hindsight, it might have been
87+
cleaner to use it to create mailing lists and handle subscription
88+
management. This would have avoided to change the identity to
89+
the mailman3 user. I have not investigated whether the REST interface
90+
exposes all needed controls and is straight forward to talk to, so this
91+
may or may not be a practical approach.
92+
93+
The ``test/`` directory would likely benefit from more test cases.
94+
95+
UCS offers to run scripts via "listener plugins" after changes to the
96+
LDAP directory, see
97+
https://docs.software-univention.de/developer-reference-5.0.html#chap:listener
98+
We could filter group changes and implement a ``postrun`` action. This
99+
would seem cleaner than looking at the database file every few minutes
100+
from a cron job.
101+
102+
## Output from ``-h``
103+
104+
<pre>
105+
Usage: ucs2mailman.py [-d] [-n] [-h] [-a adminMail] [-t DOMAIN] [-p PREFIX]
106+
[-r SRC,DST [-r ...] [-f LIST[,LIST]] [-x LIST[,LIST]] [-u FILE] [-g FILE]
107+
(c) Kurt Garloff <garloff@osb-alliance.com>, 9/2021, AGPL-v3
108+
ucs2mailman.py calls udm to get lists of groups and users from UCS LDAP.
109+
Alternatively it can also process ldapsearch output (ldapsearch -o "ldif-wrap=255"),
110+
see options -u -g to read UDM/ldapsearch output from files.
111+
It then gets the mailing list with subscribers and nonMembers from Mailman3.
112+
It then ensures that all LDAP groups with mailAddress have a corresponding
113+
MailMan3 mailing list (ML) and that all group members are subscribed to it
114+
and all other known mail addresses from subscribers are added as non-members
115+
to allow them to have unmoderated posting. Extra subscribers (not in LDAP group)
116+
will be removed (unless -k is given), extra non-members are left alone.
117+
Extra lists are also left alone.
118+
Note that you will typically need to run this as root (with sudo).
119+
Options: -d => debug output
120+
-n => don't do any changes to MailMan, just print actions
121+
-k => keep subscribers, only add, don't delete (but print)
122+
-h => output this help an exit
123+
-a adminMail => use this user as owner/moderator for newly created lists (must exist!)
124+
-p PREFIX => prepend prefix to mailing list names
125+
-r SRC,DST => replace ML name SRC with DST (after -p, skips -t), can be used multiple times
126+
-t DOMAIN => replace mailAddress domain with DOMAIN for the ML
127+
-f LIST[,LIST] => only process mailing list LIST(s) (matching happens after applying -p/-r/-t)
128+
-x LIST[,LIST] => do not process mailing list LIST(s) (matching happens after applying -p/-r/-t)
129+
-u FILE => use user list from file (ldif) instead of calling udm
130+
-g FILE => use group list from file (ldif) instead of calling udm
131+
-s user => switch ID (uid and gid) to to user (name) for mm3 config, default list
132+
</pre>

‎integration/update_mls.sh

+3-2
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,9 @@
1212
# SPDX-License-Identifier: AGPL-3.0-or-later
1313
#
1414

15-
if test /var/list/udm.groups -nt stamp; then
16-
ucs2mailman.py -a ADMIN@DOMAIN -t MLDOMAIN -u /var/list/udm.users -g /var/list/udm.groups && touch stamp
15+
cd /var/list
16+
if test udm.groups -nt stamp; then
17+
ucs2mailman.py -a ADMIN@DOMAIN -t MLDOMAIN -u udm.users -g udm.groups && touch stamp
1718
fi
1819

1920

0 commit comments

Comments
 (0)
Please sign in to comment.