If you remember in my last post, I have a solution where I do all of my blog writing in Neovim via my MacBook Air, that then is synced to my server via SyncThing. The problem was that I had to manually tell Hugo to rebuild my site when I was finished writing.

I was able to write the script and test it out a little bit yesterday; the next step is to have the Python script run continually. Enter a custom SystemD Service. Just like a Windows service, this will basically make the Python script run nonstop in the background so you don’t have to be logged in all the time.

Creating the Service

Creating a custom service is easy, but getting the details is the hard part.

  1. Create the service in the right place:
sudo nvim /etc/systemd/system/HugoAutoBuild.service
  1. Copy the script to the proper location:
sudo mkdir /usr/local/lib/HugoAutoBuild
sudo cp HugoWatch.py /usr/local/lib/HugoAutoBuild/HugoWatch.py
  1. Fill in the details of the .service file:
[Unit]
Description=Hugo Auto Build Script
After=multi-user.target

[Service]
Type=simple
ExecStart=/usr/bin/python3 /usr/local/lib/HugoAutoBuild/HugoWatch.py
Restart=always

[Install]
WantedBy=multi-user.target
  1. Reload the SystemD Daemon, Enable and Start the Service
sudo systemctl reload-daemon
sudo systemctl enable HugoAutoBuild.service
sudo systemctl start HugoAutoBuild.service

At this point, you have created the service file in the right place, copied the Python script in the right place, reloaded the daemon so it can see the custom service, enabled the service so it will run on system startup, and finally, start the service. Sounds like a lot but it’s not that bad at all.

You can then check the status of the service to see if things are going ok:

sudo systemctl status HugoAutoBuild.service

● HugoAutoBuild.service - Hugo Auto Build Script
     Loaded: loaded (/etc/systemd/system/HugoAutoBuild.service; enabled; vendor preset: enabled)
     Active: active (running) since Wed 2023-02-15 10:34:59 CST; 33min ago
   Main PID: 758709 (python3)
      Tasks: 1 (limit: 28519)
     Memory: 39.0M
     CGroup: /system.slice/HugoAutoBuild.service
             └─758709 /usr/bin/python3 /usr/local/lib/HugoAutoBuild/HugoWatch.py

Feb 15 11:07:15 shadow python3[762851]: -------------------+-----
Feb 15 11:07:15 shadow python3[762851]:   Pages            | 35
Feb 15 11:07:15 shadow python3[762851]:   Paginator pages  |  0
Feb 15 11:07:15 shadow python3[762851]:   Non-page files   |  0
Feb 15 11:07:15 shadow python3[762851]:   Static files     |  4
Feb 15 11:07:15 shadow python3[762851]:   Processed images |  0
Feb 15 11:07:15 shadow python3[762851]:   Aliases          |  0
Feb 15 11:07:15 shadow python3[762851]:   Sitemaps         |  1
Feb 15 11:07:15 shadow python3[762851]:   Cleaned          |  0
Feb 15 11:07:15 shadow python3[762851]: Total in 38 ms

The script is setup right now to check every minute and behold, you are seeing this blog post because the service/script works!

Other Things

I’m sure someone much more familiar with this topic is reading this and yelling at the screen on how I could have done this better. I’m also aware of some “gotchas”. For example, will this properly kill the process if the service fails? Should I have done something differently? If you have any tips on improvements, by all means reach out to me over at Mastodon or Matrix!

This is Day 6 of #100DaysToOffload.