I'm following this (very good) DigitalOcean tutorial on how to serve a Flask app using Gunicorn, but cannot get Systemd to run with myproject.service
.
I've created a python environment (venv), pip installed gunicorn and flask, coded both myproject.py and wsgi.py and checked that all programs are executable. When I run the command:
(venv) dconran@dconran-VirtualBox:~/python/dg$ /home/dconran/python/dg/venv/bin/gunicorn --workers 3 --bind unix:myproject.sock -m 007 wsgi:app
from the command line, both within the python environment and after it has been deactivated, everything works fine and I can access the web page. However when I run sudo systemctl start myproject
I get the following error message when I do sudo systemctl status myproject
:
× myproject.service - Gunicorn instance to serve myproject
Loaded: loaded (/etc/systemd/system/myproject.service; enabled; preset: enabled)
Active: failed (Result: exit-code) since Fri 2025-02-14 12:40:11 GMT; 23s ago
Duration: 12ms
Main PID: 6526 (code=exited, status=2)
CPU: 5ms
Feb 14 12:40:11 dconran-VirtualBox systemd[1]: Started myproject.service - Gunicorn instance to serve myproject.
Feb 14 12:40:11 dconran-VirtualBox bash[6527]:
/home/dconran/python/dg/venv/bin/gunicorn: line 3: import: command not found
Feb 14 12:40:11 dconran-VirtualBox bash[6528]:
/home/dconran/python/dg/venv/bin/gunicorn: line 4: import: command not found
Feb 14 12:40:11 dconran-VirtualBox bash[6529]:
/home/dconran/python/dg/venv/bin/gunicorn: line 5: from: command not found
Feb 14 12:40:11 dconran-VirtualBox bash[6526]:
/home/dconran/python/dg/venv/bin/gunicorn: line 7: syntax error near unexpected token `('
Feb 14 12:40:11 dconran-VirtualBox bash[6526]:
/home/dconran/python/dg/venv/bin/gunicorn: line 7: ` sys.argv[0] = re.sub(r'(-script\.>
Feb 14 12:40:11 dconran-VirtualBox systemd[1]: myproject.service: Main process exited,
code=exited, status=2/INVALIDARGUMENT
Feb 14 12:40:11 dconran-VirtualBox systemd[1]: myproject.service: Failed with result
'exit-code'.
myproject.service
consists of:-
[Unit]
Description=Gunicorn instance to serve myproject
After=network.target
[Service]
User=dconran
Group=www-data
WorkingDirectory=/home/dconran/python/dg
Environment="PATH=/home/dconran/python/dg/venv/bin"
ExecStart=/usr/bin/bash /home/dconran/python/dg/venv/bin/gunicorn --workers 3 --bind
unix:myproject.sock -m 007 wsgi:app
[Install]
WantedBy=multi-user.target
I've confirmed that both python3 and gunicorn are in ...venv/bin and, indeed, gunicorn if fine when run from the command line - so why won't it run via systemd?
Any help/suggestions would be gratefully received.
Your service is trying to run the command:
/usr/bin/bash /home/dconran/python/dg/venv/bin/gunicorn
But gunicorn
is not a Bash script. It is a Python script. The error messages come from Bash trying to interpret each line of Python as if it were a shell command.
Either specify the correct interpreter (python
), or no interpreter at all – the file is already marked 'executable' and has the appropriate #!
line, meaning that the OS can be told to execute it directly (and will automatically run the necessary interpreter without you having to specify it)... exactly as you were already doing when you started gunicorn manually.
(Note also that there's a difference between bash <file>
and bash -c "<command>"
. The former interprets the contents of the specified path as shell commands; the latter interprets the path itself as a shell command – so I'm guessing you might have been thinking about bash -c /path/to/gunicorn
, which would have almost worked, but is really redundant since you can run gunicorn without bash anyway.)