Contents
Introduction
There are several ways to execute a piece of code when your Raspberry Pi boots. You can, for instance, use the nickname @reboot
in crontab
in order to launch an script after rebooting your machine. You can also configure crontab
to run the script every X minutes. However, if you want to create a Raspberry Pi service that runs at boot time, considers dependencies and keeps on running in the background, you should use systemd
.
Creating a Raspberry Pi service
Systemd
is an init system used in Linux distributions to bootstrap the user space and to manage system processes after booting. It includes a collection of tools for a range of different tasks. Its primary purpose is to initialise, manage and track system services and daemons, both during start-up and while the system is running.
Monitoring Raspberry temperature with a service
In this example we will create a service that monitors the Raspberry temperature. This service will send an IFTTT notification to the configured smartphone containing the Raspberry’s Pi temperature when this is greater than a certain value. We want to run this script automatically when booting the system, and let it running forever. This is the bash code of our script:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
#/bin/bash maxTemp=65 minuteEnd=1 tag="tempMonitor" while true do GPUTemp=$(echo $(/opt/vc/bin/vcgencmd measure_temp) | egrep -o '[0-9]{2}.[0-9]{1}') CPUTemp=$(sed "s/\(...\)$/.\1/" < /sys/class/thermal/thermal_zone0/temp | egrep -o '[0-9]{2}.[0-9]{1}') if (( $(echo "$GPUTemp $maxTemp" | awk '{print ($1 > $2)}') )) || (( $(echo "$CPUTemp $maxTemp" | awk '{print ($1 > $2)}') )); then logger -t $tag "Sending alarm. CPU Temp: $CPUTemp. GPU Temp: $GPUTemp" curl -X POST -H "Content-Type: application/json" -d '{"value1":"'$CPUTemp'", "value2":"'$GPUTemp'"}' https://maker.ifttt.com/trigger/[YOUR_EVENT_NAME]/with/key/[YOUR_IFTTT_KEY] 2>1 fi loopWaitTime=$(( (((60 * (10 - ($(date +%-M) % 10))) + ((( minuteEnd * 60 )) - $(date +%-S))) % 300 ) )) sleep $loopWaitTime done |
In order to know more about the IFTTT applets, read this post. I have used egrep
to extract the temperatures with one decimal and awk
to compare floating numbers. logger
is used to log the sent alarms, as well as the temperatures recorded, in the system log syslog
with the tag tempMonitor
. The script will sleep and wake up in the minutes ended in 1 or 6 (01, 06, 11, 16, etc.). To know more about how to calculate this sleep time, see the following post.
Creating a service
To convert the previous script into a service, start creating a .service
file with the following structure:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
vi /home/dani/scripts/tempMonitor/tempMonitor.service [Unit] Description=Raspberry Temperature Monitor After=network-online.target [Service] ExecStart=/bin/bash /home/dani/scripts/tempMonitor/tempMonitor.sh WorkingDirectory=/home/dani/scripts/tempMonitor/ StandardOutput=inherit StandardError=inherit Restart=always User=dani [Install] WantedBy=multi-user.target |
Just adapt the code to the path used in your system. The line After=network-online.target
will postpone the start of the service until the network is in up status. If you want to know more about some of the options used, I recommend you to read the following article.
Now copy the file into /lib/systemd/system
with root user:
1 |
sudo cp /home/dani/scripts/tempMonitor/tempMonitor.service /lib/systemd/system/ |
Testing the service
Once this has been copied, you can attempt to start the service using the following command:
1 |
sudo systemctl start tempMonitor.service |
Check if it is running correctly by doing:
1 2 3 4 5 6 7 8 9 10 11 |
sudo systemctl status tempMonitor.service ● tempMonitor.service - Raspberry Temperature Monitor Loaded: loaded (/lib/systemd/system/tempMonitor.service; disabled) Active: active (running) since dom 2018-02-04 19:43:11 CET; 2s ago Main PID: 5709 (bash) CGroup: /system.slice/tempMonitor.service ├─5709 /bin/bash /home/dani/scripts/tempMonitor/tempMonitor.sh └─5728 sleep 300 feb 04 19:43:11 TrastoRaspberry systemd[1]: Started Raspberry Temperature Monitor. |
Stop it using the following command:
1 |
sudo systemctl stop tempMonitor.service |
And check again if the script is correctly stopped. Once everything is checked, you can configure your service to start automatically on reboot by using the following command:
1 |
sudo systemctl enable tempMonitor.service |
From now on, you can check easier the status of the service by doing:
1 |
sudo service tempMonitor status/start/stop |
Nice write up. Been searching most of the day on getting a script to run at bootup. Kept failing. Your instructions came up in a search and it worked.
Thanks for the cool description. Worded perfect for me.