Treating a Python Application as a Daemon on Debian
+++++++++++++++++++++++++++++++++++++++++++++++++++
:Posted: 2010-02-28 17:43
:Tags: Python, Debian
:Headline: A quick tutorial for making init scripts to run Python servers under Debian 5.
.. contents ::
There are two approaches to writing daemon applications like servers in Python.
The first is to handle all the tasks of sarting and stopping daemons in Python
code itself. The easiest way to do this is with the `python-daemon
`_ package which might eventually
make its way into the Python distribution. The other approach is to use the
tools supplied by the operating system. In the case of Debain, this means
writing an init script which makes use of the ``start-stop-daemon`` program.
A Python Server Daemon
======================
Let's consider the case where we have a server written in Python. The command
to start it looks like this (using absolute paths):
::
/home/james/env/bin/python /home/james/Desktop/Cur/Carbage/code/carbage/run /home/james/Desktop/Cur/Carbage/instance/dirac.3aims.com/test.conf serve
We'd like to be able to have the server run in the background, for it to be
started when Debian boots and to have a *process ID file* so that we can stop
the server, or check that it is running.
The bash script below achieves this:
::
#!/bin/bash
DAEMON=/root/Carbage/instance/bifferboard/env/bin/python
ARGS="/root/Carbage/code/carbage/run.py /root/Carbage/instance/bifferboard/app.conf serve"
PIDFILE=/root/Carbage/instance/bifferboard/serve.pid
case "$1" in
start)
echo "Starting server"
/sbin/start-stop-daemon --start --pidfile $PIDFILE \
--user www-data --group www-data \
-b --make-pidfile \
--chuid www-data \
--exec $DAEMON -- $ARGS
;;
stop)
echo "Stopping server"
/sbin/start-stop-daemon --stop --pidfile $PIDFILE --verbose
;;
*)
echo "Usage: /etc/init.d/carbage-serve {start|stop}"
exit 1
;;
esac
exit 0
Save this in the ``/etc/init.d`` directory. In this example we'll call it
``carbage``. You'll need to make the file executable:
::
chmod +x /etc/init.d/carbage
You can now start the server like this:
::
/etc/init.d/carbage start
and stop it like this:
::
/etc/init.d/carbage stop
Adding to Cron
==============
If you run the command to start the server when it is already running, the
command gets ignored. This means it is safe to have the start command run every
minute by a cron job so that if it stops for any reason, the downtime should be
at most 60 seconds.
You should run this:
::
sudo crontab -e
and add the following line to the root crontab:
::
* * * * * /etc/init.d/carbage start
Cron jobs run commands in a very minimal environment without ``/sbin`` on the
path so it is important that any commands in your init scripts use full paths.
In this case we specified ``/sbin/start-stop-daemon`` so the cron jobs work.
Starting Automatically
======================
Debian services get started as the operating system enters various runlevels.
To have a service started and stopped at a particular runlevel you need to add
symbolic links to the script from the various directories ``/etc/rc0.d``,
``/etc/rc1.d`` ... ``/etc/rc6.d``. The easiest way to do this is with the
``update-rc.d`` command.
To add the ``carbage`` command so it gets started automatically you would type this:
::
sudo update-rc.d -f carbage defaults
If you ever want to remove the symbolic links you can do so like this:
::
sudo update-rc.d -f carbage remove
You now have a daemon which can be started and stopped at will, gets checked
every minute and restarted if it stops and which is automatically started and
stopped as the system boots and shutsdown.
Further Reading
===============
Man Pages:
* `start-stop-daemon man page `_
* `update-rc.d man page `_
Articles:
* `How to manage services with update-rc.d `_.