For some rather advanced isolation and automation work I am currently doing with Debian Code Search I needed to modify the ExecStart= line of a systemd service file programmatically.
The recommended interface for programmatically querying service file properties
is systemctl show -p ExecStart foo.service
, but with the
ExecStart= property in particular, the output cannot be parsed well:
$ systemctl show -p ExecStart dcs-batch0-source-backend.service --no-pager ExecStart={ path=/usr/bin/source-backend ; argv[]=/usr/bin/source-backend -unpacked_path=/dcs/unpacked-new/ -listen_address=localhost:30000 ; ignore_errors=no ; start_time=[Sat 2013-07-27 19:58:23 CEST] ; stop_time=[n/a] ; pid=12428 ; code=(null) ; status=0/0 }
Therefore, I decided to extract the ExecStart= line from the service file
directly instead of querying it from systemd. One might think that a simple
grep(1)
call like grep '^ExecStart=' foo.service
would be enough, but systemd supports line continuations in the service file
syntax and I make use of that in my service files.
It is a well-known truth that whenever grep(1)
fails,
perl(1)
saves the day:
perl -nlE 'say if /^ExecStart=.*[^\\]$/ || /^ExecStart=/ .. /[^\\]$/' < /lib/systemd/system/sudo.service ExecStart=/usr/bin/find /var/lib/sudo -exec /usr/bin/touch -t 198501010000 '{}' \073
perl -nlE 'say if /^ExecStart=.*[^\\]$/ || /^ExecStart=/ .. /[^\\]$/' < /run/systemd/system/dcs-batch0-source-backend.service ExecStart=/usr/bin/source-backend \ -unpacked_path=/dcs/unpacked/ \ -listen_address=localhost:30000
I run a blog since 2005, spreading knowledge and experience for almost 20 years! :)
If you want to support my work, you can buy me a coffee.
Thank you for your support! ❤️