- Lets you delegate administration of a portion of a virtual domain map to the user(s) responsible for the domain.
- User-friendly interface resembling an Excel spreadsheet
- Meant to run as a standalone service owned by the Postfix user (or at least a user or group with write access to the Postfix config files), and thus does not require granting your web server any particular privileges.
- Fully self-contained executable, no dependencies
- Will allow users to create aliases for valid RFC-5322 email addresses or use existing local addresses, but not dangerous functionality like command delivery
- manages a spam map file in access(5) format when the recipient starts with
550
- optionally run a script after the map files are updated, e.g. to sort the files, commit changes in git, etc.
- Go 1.16 or later
- Git
- Run "make".
Postmapweb is configured using a JSON file, by default
/etc/postfix/postmapweb.json
. It can handle multiple domains, but only one
map file per domain.
To create the config file (if it does not already exist), add a domain to it and set up a password for it (or change the password):
postmapweb -c <config file> -d <domain> -m <Postfix map file>
To start the server:
postmapweb -c <config file> -p :<port>
Warning: postmapweb must be run behind a HTTPS reverse proxy server, e.g. nginx or HAProxy. Do not run it without encryption or expose it to the Internet by binding it elsewhere than localhost!
The config files in /etc/postfix
are owned by root
, not postfix
, and it
is not good practice to run a server such as this as root
. Fortunately the
virtual_alias_maps
Postfix configuration directive accepts multiple maps. My
recommended configuration is to create a new user postmapweb
in the
postfix
group, create a subdirectory /etc/postfix/domains
owned by
postmapweb
and create one virtual map file per domain there. Make sure you
remove any entries from /etc/postfix/virtual
when you migrate them to
/etc/postfix/domains/<example.com>
as Postfix looks up aliases in the order
of the files, and thus any change to an alias in
/etc/postfix/domains/<example.com>
would be preempted by the leftover entry
in /etc/postfix/virtual
.
Thus:
(backup your /etc/postfix directory)
useradd -d /etc/postfix/domains -s /bin/sh -G postfix postmapweb
(or whatever the equivalent is on your operating system)
mkdir /etc/postfix/domains
grep example.com /etc/postfix/virtual > /etc/postfix/domains/example.com
postmap /etc/postfix/domains/example.com
chown -R postmapweb:postfix /etc/postfix/domains
(assuming your existing virtual_alias_maps = dbm:/etc/postfix/virtual, adjust to taste)
postconf -e virtual_alias_maps=dbm:/etc/postfix/virtual,dbm:/etc/postfix/domains/example.com
postfix reload
grep -v example.com /etc/postfix/virtual > /tmp/foo;cat /tmp/foo > /etc/postfix/virtual
postmap /etc/postfix/virtual
postfix reload
postmapweb -c /etc/postfix/postmapweb.json -d example.com -m /etc/postfix/domains/example.com
postmapweb -v -c /etc/postfix/postmapweb.json
You can set the script
key in the JSON config file (manual edit of the file
is required). It will be run in the same working directory as postmapweb
,
and the domain name of the changes will be passed as argument 1.
Here is the script I use to sort my files. I have one $domain
and one $domain.spam
file per domain under /etc/postfix/domains
:
#!/bin/sh
cd /etc/postfix/domains
for x in *.dir; do
f=`echo $x|sed -e 's/.dir$//g'`
echo sorting $f
case $f in
*.spam)
gsort $f > $f.tmp
;;
*)
head -1 $f > $f.tmp
tail +2 $f | gsort >> $f.tmp
;;
esac
mv $f.tmp $f
postmap $f
chown postmapweb:postfix $f*
done
postfix reload
-c string
config file to use (default "/etc/postfix/postmapweb.json")
-cpuprofile string
write cpu profile to file
-d string
add domain user
-m string
virtual domain map to use with -d (default "/etc/postfix/virtual")
-p string
host address and port to bind to (default "localhost:8080")
-v verbose logging
-w string
password to use with -d (insecure!)
- Go: https://golang.org/
- HandsOnTable: http://handsontable.com/
- And of course Wietse Venema's Postfix: http://www.postfix.org/