So I've been doing a bit of Python recently for a project I'm working on on a Raspberry Pi. There will be a longer blog post about that in the next few weeks. But one thing I ran up against was that I wanted to start my daemon, written in Python, using a systemd service on Raspbian.
Normally, you would just shove a script invocation into a systemd unit and call it good, but in my case I had made use of Pipenv, which is a bit like Bundler in the Ruby world and Composer in the PHP world, to manage my project's dependencies.
And the way you invoke a program using Pipenv is different from just invoking the script:
$ pipenv run python3 src/foo.py
So you might try something like this in a systemd unit:
ExecStart=/usr/local/bin/pipenv run python3 /path/to/src/foo.py
But that doesn't work. This is because Pipenv relies on the current working
directory to look for the
Pipfile. Fortunately, with systemd, you can specify
the current working directory in the unit file using the
directive. So your systemd unit file might look something like this:
[Unit] Description=My Python Service After=network.target [Service] User=user Restart=always Type=simple WorkingDirectory=/path/to ExecStart=/usr/local/bin/pipenv run python3 /path/to/src/foo.py [Install] WantedBy=multi-user.target