I'm trying to set up a system init script on my Raspbian, just to send an HTTP POST request to a public web server (99,9% uptime), reporting that the Raspbian has just been started up (or rebooted). So far, I've done the following:
A. Approach A: System-V style startup script
A.1. Edited /etc/init.d/notify-startup (initial test T0) (showing only relevant lines):
...
# Required-Start: $remote_fs $syslog $time
# Required-Stop: $remote_fs $syslog
# Default-Start: 2 3 4 5
# Default-Stop: 0 1 6
...
case "$1" in
start)
logger -i "Starting Notify-Startup" || true
/opt/notify-startup/bin/notify-startup.sh &
...
A.2. And /opt/notify-startup/bin/notify-startup.sh:
#!/bin/sh
# First.
curl --insecure --include --request POST \
--url https://example.com/notify-startup.php \
--header "Content-Type: application/x-www-form-urlencoded" \
--data-urlencode "id=0" \
--data-urlencode "count=1" \
--data-urlencode "message=Starting up (1)" > /dev/null 2>&1
sleep 180
# Second.
curl --insecure --include --request POST \
--url https://example.com/notify-startup.php \
--header "Content-Type: application/x-www-form-urlencoded" \
--data-urlencode "id=0" \
--data-urlencode "count=2" \
--data-urlencode "message=Starting up (2)" > /dev/null 2>&1
exit 0
A.3. Run update-rc.d to create System-V style links under /etc/rc?.d:
$ sudo update-rc.d notify-startup defaults # Command [C1]
After this execution, my symlinks under /etc/rc?.d are the following:
/etc/rc0.d/K01notify-startup
/etc/rc1.d/K01notify-startup
/etc/rc2.d/S02notify-startup
/etc/rc3.d/S02notify-startup
/etc/rc4.d/S02notify-startup
/etc/rc5.d/S02notify-startup
/etc/rc6.d/K01notify-startup
A.4. Then I reboot my Raspbian.
Result is that the first HTTP POST request does not reach the public web server but the second one actually does, and I'd like both of them would do.
It's important to say that Ethernet interface and DNS resolver must be operative so that my HTTP POST request could reach the public web server. So I've tried the following combinations of LSB facility names [1] on my script with no success until now:
A.5. Test [T1]:
# Required-Start: $network $remote_fs $syslog $time
A.6. Test [T2]:
# Required-Start: $named $remote_fs $syslog $time
I also have noticed that, after re-running update-rc.d [C1], the symlinks under /etc/rc?.d are not re-numbered in order to satisfy the dependencies on facility names configured on tests [T1] and [T2].
My question is: Is there any way to ensure that my startup script gets run just after DNS resolution is available to my Raspbian system, by using facility name dependencies or by any other programmatic way (I would prefer the former)? Am I doing something wrong with command [C1] so that my startup script execution order does not get updated and does not ensure DNS resolution and network availability?
PS: I already know that this simple task could be achieved well by using just a @reboot crontab job, but I need it to be a System-V startup script as I would be upgrading it to add more and more functionality over time.
[1] https://refspecs.linuxfoundation.org/LSB_1.2.0/gLSB/facilname.html
B. Approach B: Systemd unit
As suggested in comments, I also tried systemd.unit
but had problems too. Steps follow:
B.1. Edit /opt/notify-startup/bin/notify-startup-02.sh:
$ sudo pico /opt/notify-startup/bin/notify-startup-02.sh
B.2. Same contents as in A.2.
B.3. Give execute permission:
$ sudo chmod ugo+x /opt/notify-startup/bin/notify-startup-02.sh
B.4. Edit service unit:
$ sudo pico /opt/notify-startup/etc/notify-startup-02.service
Contents:
[Unit]
Description=Test Service Unit
Before=runlevel2.target runlevel3.target runlevel4.target runlevel5.target shutdown.target
After=network-online.target nss-lookup.target remote-fs.target systemd-journald-dev-log.socket time-sync.target
Conflicts=shutdown.target
[Service]
Type=forking
Restart=no
TimeoutSec=5min
IgnoreSIGPIPE=no
KillMode=process
GuessMainPID=no
RemainAfterExit=yes
ExecStart=/opt/notify-startup/bin/notify-startup-02.sh
ExecStop=/usr/bin/logger -i "Stopping"
[Install]
WantedBy=default.target
B.5. Create symlinks:
$ cd /etc/systemd/system
$ sudo ln -s /opt/notify-startup/etc/notify-startup-02.service
$ cd /lib/systemd/system
$ sudo ln -s /opt/notify-startup/etc/notify-startup-02.service
B.6. Run a systemd reload and enable my unit (got stuck here):
$ sudo systemctl daemon-reload
$ sudo systemctl enable notify-startup-02.service
Got the following output:
Failed to execute operation: No such file or directory
C. Help/Solution
No matter which approach is choosen, I'd like to have a solution. Approach B, as suggested in comments, should be the best, but I got stuck in step B.6.
systemd
? It's easy to achieve what you want with it.man systemd-sysv-generator
. You shouldn't ride a dead horse./run/systemd/generator.late/notify-startup.service
, whose first line says:# Automatically generated by systemd-sysv-generator
. Do you think the contents of this file would be a good starting point to solve my problem using thesystemd
approach?WantedBy=default.target
) and something likeAfter=network-online.target
to the [Unit] section. Then you can enable it by runningsystemctl daemon-reload
andsystemctl enable <your>.service
. Put your service unit file in/etc/systemd/system/
./etc/systemd/user/
directory?man systemd.unit
describes it but I have seen it's empty, so I don't know if it is adequate.