the djb way


qmail-qstat service

Scenario: you are responsible for monitoring one or more qmail installations. You would like a tool to check up on each queue remotely, without having to login and su on every server.

You know what's coming next, don't you. We'll put up a qmail-qstat service on each of our qmail installations, and monitor them with a qstat client. Using the great daemontools and ucspi-tcp utilities, this client/server application will take all of about 2 minutes total to develop and install.

First, the qmail-qstat service. Make the directories for the service definition as usual:

# mkdir -p /var/svc.d/qmail-qstat/log

Now, install this daemontools "run" script in /var/svc.d/qmail-qstat/run:

# qmail-qstat/run
# daemontools run script for qmail-qstat service
# ===

exec 2>&1
echo "*** Starting qmail-qstat service on port ${PORT}..."
exec env -i PATH="/var/qmail/bin:$PATH" \
  envuidgid qmails soflimit -m3000000\
    tcpserver -v -RH -l0 \
    -U \
    -c ${CONLIMIT} \
    -x /etc/tcprules/qstat.cdb \
    0 ${PORT} \
      qmail-qstat && qmail-qread

### that's all, folks!

Make sure the run script is executable, chmod 755. Here we pick some arbitrary port number to bind the service to; "25025" is not a standard, just our own mnemonic.

We run the service with the envuidgid utility, to setup the unpriveleged user "qmails" for the -U option to tcpserver. Since qmail-qstat and qmail-qread utilities may run under either root or user "qmails", we'll drop priveleges to the latter.

Otherwise, this service is just another instance of our original howdyd daemon. It simply listens for a connection, then runs qmail's qmail-qstat and qmail-qread queue reporting utilities.

Note: since qmail-qread may generate voluminous output on busy systems, you may prefer to omit qmail-qread from this script and --optionally-- set up a separate qmail-qread service for it.

The matching multilog service, for /var/svc.d/qmail-qstat/log/run:

# qmail-qstat/log/run
# multilogger from qmail-stat service
exec setuidgid multilog multilog t /var/multilog/qmail-qstat

Make sure the script is executable. Then setup the multilog directory:

# mkdir /var/multilog/qmail-qstat
# chown multilog /var/multilog/qmail-qstat

The service run script we've shown here makes use of the -x option to tcpserver, to define access rules for the service. Set up the rules as you want in /etc/tcprules/qstat.rules:

# qstat.rules

Then compile the rules:

# (cd /etc/tcprules; make qstat.cdb)

Link the service to bring it up:

# ln -s /var/svc.d/qmail-qstat /service/qmail-qstat

Great! The service is now running. But what about a client?

The quick-and-dirty approach is to just use the tcpcat utility from ucspi-tcp:

# tcpcat 25025
[XXX show output]

Otherwise, if you like it, here's a version of tcpcat that is "customised" for the service; we'll call it "qstat":

# qstat
# client for qmail-qstat service
# ===
exec /usr/local/bin/tcpclient -vRHl0 -- \
  "${1:-0}" "${2:-${PORT}}" \
  /bin/sh -c 'exec cat <&6'

### that's all, folks!

Copy this file into an executable path and make it executable. If querying to your "standard" qmail-qstat port, just use:

$ qstat
[XXX show output]

If querying about the local queue, just run qstat without any host/port arguments:

$ qstat
[XXX show output]

Note the client can be run by any user, without root priveleges.

If you like qstat, you can symlink it to the mailq command, replacing the binary customarily found with sendmail installations.

Copyright © 2004, Wayne Marshall.
All rights reserved.

Last edit 2004.10.04, wcm.