Search code examples
pythonuwsgisystemd

uWSGI not restarting after being idle


I'm using uwsgi with systemd on ubuntu 16.

I followed the instructions under one service per app from here: http://uwsgi-docs.readthedocs.io/en/latest/Systemd.html

If I start the systemd socket and go to the site, everythings works fine. But after the idle time (specified in the ini file), the uwsgi process gets killed and further requests don't seem to restart / reactivate the process.

workers have been inactive for more than 30 seconds (1501589319-1501589288)
SIGINT/SIGQUIT received...killing workers...
worker 1 buried after 1 seconds
worker 2 buried after 1 seconds
goodbye to uWSGI.

Here's my ini file:

[uwsgi]
module = wsgi

logto = /tmp/uwsgi.log

master = true
processes = 2
cheap = true
idle = 30
die-on-idle = true

manage-script-name = true

This is my systemd socket config:

[Unit]
Description=Socket for uWSGI app

[Socket]
ListenStream=/var/run/uwsgi/myapp.socket
SocketUser=www-data
SocketGroup=www-data
SocketMode=0666

[Install]
WantedBy=sockets.target

And this is my systemd service config:

[Unit]
Description=uWSGI app
After=syslog.target

[Service]
ExecStart=/home/myapp/venv/bin/uwsgi \
        --ini /home/myapp/uwsgi/uwsgi.ini \
        --socket /var/run/uwsgi/myapp.socket
User=www-data
Group=www-data
Restart=on-failure
KillSignal=SIGQUIT
Type=notify
StandardError=syslog
NotifyAccess=all
RuntimeDirectory=uwsgi
WorkingDirectory=/home/myapp

Solution

  • After fiddling around with this for almost a day I've found the answer in the documentation for a related setup. Although it isn't the same kind of setup because I don't use emperor, it did give me a clue of what is going on.

    The reason the socket activation only works the first time is because uwsgi overwrites the socket file created by the systemd socket.

    See the green "!" Important box on this page: http://uwsgi-docs.readthedocs.io/en/latest/OnDemandVassals.html

    It says:

    If you will define in your vassal config same socket as used by emperor for on demand action, vassal will override that socket file. That could lead to unexpected behaviour, for example on demand activation of that vassal will work only once.

    So in my case I don't have an emperor, but systemd acts like the emperor.

    So what is the solution?

    Get rid of the --socket parameter from the ExecStart in the systemd service file.

    Instead of having

    ExecStart=/home/myapp/venv/bin/uwsgi \
            --ini /home/myapp/uwsgi/uwsgi.ini \
            --socket /var/run/uwsgi/myapp.socket
    

    I changed it to

    ExecStart=/home/myapp/venv/bin/uwsgi \
            --ini /home/myapp/uwsgi/uwsgi.ini
    

    After that I stopped the systemd service and socket, did a systemctl daemon-reload and started the systemd socket again. Evrything started working as expected - systemd socket activation works with uwsgi! :)