@cryptotaxi247 / netdata-1 / commits / 8649e9dae

Query systemd for unit file paths on install/uninstall. (#19346)

* Query systemd for unit file paths on install/uninstall. This makes our installation code more portable and more concise, and should make the uninstallation code significantly more robust. Also includes a number of other improvements to systemd handling and updater handling in the uninstaller that should make it much more thorough and reliable. * Fix issues brought up in code review, and better support old systemd versions. * Replace sed with AWK for readability. * Fix uninstaller loop. * Fix unit file detection in updater code.

Austin S. Hemmelgarn committed Jan 16, 2025 at 07:58 UTC 8649e9daea8ae96a90e470263e8b5db2e2c7573a
4 files changed +91 -39
packaging/installer/functions.sh
+15 -6
@@ -636,13 +636,22 @@ issystemd() {
636 }
637
638 get_systemd_service_dir() {
639 - if [ -w "/lib/systemd/system" ]; then
640 - echo "/lib/systemd/system"
641 - elif [ -w "/usr/lib/systemd/system" ]; then
642 - echo "/usr/lib/systemd/system"
643 - elif [ -w "/etc/systemd/system" ]; then
644 - echo "/etc/systemd/system"
639 + unit_paths="$(systemctl show -p UnitPath | cut -f 2- -d '=' | tr ' ' '\n')"
640 +
641 + if [ -n "${unit_paths}" ]; then
642 + lib_paths="$(echo "${unit_paths}" | grep -vE '^/(run|etc)' | awk '{line[NR] = $0} END {for (i = NR; i > 0; i--) print line[i]}')"
643 + etc_paths="$(echo "${unit_paths}" | grep -E '^/etc' | grep -vE '(attached|control)$')"
644 + else
645 + lib_paths="/usr/lib/systemd/system /lib/systemd/system /usr/local/lib/systemd/system"
646 + etc_paths="/etc/systemd/system"
647 fi
648 +
649 + for path in ${lib_paths} ${etc_paths}; do
650 + if [ -d "${path}" ] && [ -w "${path}" ]; then
651 + echo "${path}"
652 + return 0
653 + fi
654 + done
655 }
656
657 run_install_service_script() {
packaging/installer/netdata-uninstaller.sh
+35 -18
@@ -731,27 +731,45 @@ if [ "$(uname -s)" = "Darwin" ]; then
731 fi
732
733 #### REMOVE NETDATA FILES
734 +
735 +# Handle updater files first so that it doesn’t try to run while we
736 +# are uninstalling things.
737 +if [ -x "${NETDATA_PREFIX}/usr/libexec/netdata-updater.sh" ]; then
738 + "${NETDATA_PREFIX}/usr/libexec/netdata-updater.sh" --disable-auto-updates
739 +else
740 + rm_file /etc/periodic/daily/netdata-updater
741 + rm_file /etc/cron.daily/netdata-updater
742 + rm_file /etc/cron.d/netdata-updater
743 + rm_file /etc/cron.d/netdata-updater-daily
744 +fi
745 +
746 +if issystemd; then
747 + for unit in netdata.service netdata-updater.timer; do
748 + systemctl disable "${unit}"
749 + systemctl stop "${unit}"
750 + done
751 +
752 + for unit in netdata.service netdata-updater.service netdata-updater.timer; do
753 + unit_path="$(systemctl show -p FragmentPath "${unit}" | cut -f 2- -d '=')"
754 + override_paths="$(systemctl show -p DropInPaths "${unit}" | cut -f 2- -d '=')"
755 + for path in "${unit_path}" ${override_paths} ; do
756 + rm_file "${path}"
757 + done
758 + done
759 +
760 + rm_file /usr/lib/systemd/journald@netdata.conf.d/netdata.conf
761 + rm_file /lib/systemd/journald@netdata.conf.d/netdata.conf
762 + rm_dir /usr/lib/systemd/journald@netdata.conf.d/
763 + rm_file /usr/lib/systemd/system-preset/50-netdata.preset
764 + rm_file /lib/systemd/system-preset/50-netdata.preset
765 +
766 + systemctl daemon-reload
767 +fi
768 +
769 rm_file /etc/logrotate.d/netdata
735 -rm_file /usr/lib/systemd/journald@netdata.conf.d/netdata.conf
736 -rm_file /etc/systemd/system/netdata.service
737 -rm_file /lib/systemd/system/netdata.service
738 -rm_file /usr/lib/systemd/system/netdata.service
739 -rm_file /etc/systemd/system/netdata-updater.service
740 -rm_file /lib/systemd/system/netdata-updater.service
741 -rm_file /usr/lib/systemd/system/netdata-updater.service
742 -rm_file /etc/systemd/system/netdata-updater.timer
743 -rm_file /lib/systemd/system/netdata-updater.timer
744 -rm_file /usr/lib/systemd/system/netdata-updater.timer
745 -rm_file /usr/lib/systemd/system-preset/50-netdata.preset
746 -rm_file /lib/systemd/system-preset/50-netdata.preset
770 rm_file /etc/init.d/netdata
748 -rm_file /etc/periodic/daily/netdata-updater
749 -rm_file /etc/cron.daily/netdata-updater
750 -rm_file /etc/cron.d/netdata-updater
751 -rm_file /etc/cron.d/netdata-updater-daily
771 rm_file /Library/LaunchDaemons/com.github.netdata.plist
772
754 -
773 if [ -n "${NETDATA_PREFIX}" ] && [ -d "${NETDATA_PREFIX}" ] && [ "netdata" = "$(basename "$NETDATA_PREFIX")" ] ; then
774 rm_dir "${NETDATA_PREFIX}"
775 else
@@ -768,7 +786,6 @@ else
786 rm_dir "${NETDATA_PREFIX}/var/cache/netdata"
787 rm_dir "${NETDATA_PREFIX}/var/log/netdata"
788 rm_dir "${NETDATA_PREFIX}/etc/netdata"
771 - rm_dir /usr/lib/systemd/journald@netdata.conf.d/
789 fi
790
791 if [ -n "${tmpdir}" ]; then
packaging/installer/netdata-updater.sh
+22 -7
@@ -172,6 +172,14 @@ issystemd() {
172 return 1
173 }
174
175 +systemd_unit_exists() {
176 + if systemctl list-unit-files "${1}" 2>&1 | tail -n 1 | grep -qv '^0 '; then
177 + return 0
178 + else
179 + return 1
180 + fi
181 +}
182 +
183 # shellcheck disable=SC2009
184 running_under_anacron() {
185 pid="${1:-$$}"
@@ -307,11 +315,17 @@ enable_netdata_updater() {
315 case "${updater_type}" in
316 "systemd")
317 if issystemd; then
310 - systemctl enable netdata-updater.timer
311 -
312 - info "Auto-updating has been ENABLED using a systemd timer unit.\n"
313 - info "If the update process fails, the failure will be logged to the systemd journal just like a regular service failure."
314 - info "Successful updates should produce empty logs."
318 + if systemd_unit_exists netdata-updater.timer; then
319 + systemctl enable netdata-updater.timer
320 + systemctl start netdata-updater.timer
321 +
322 + info "Auto-updating has been ENABLED using a systemd timer unit.\n"
323 + info "If the update process fails, the failure will be logged to the systemd journal just like a regular service failure."
324 + info "Successful updates should produce empty logs."
325 + else
326 + error "Systemd-based auto-update scheduling requested, but the required timer unit does not exist. Auto-updates have NOT been enabled."
327 + return 1
328 + fi
329 else
330 error "Systemd-based auto-update scheduling requested, but this does not appear to be a systemd system. Auto-updates have NOT been enabled."
331 return 1
@@ -351,8 +365,9 @@ enable_netdata_updater() {
365 }
366
367 disable_netdata_updater() {
354 - if issystemd && ( systemctl list-units --full -all | grep -Fq "netdata-updater.timer" ) ; then
368 + if issystemd && systemd_unit_exists "netdata-updater.timer" ; then
369 systemctl disable netdata-updater.timer
370 + systemctl stop netdata-updater.timer
371 fi
372
373 if [ -d /etc/cron.daily ]; then
@@ -387,7 +402,7 @@ auto_update_status() {
402 enabled=""
403
404 if issystemd; then
390 - if systemctl list-units --full -all | grep -Fq "netdata-updater.timer"; then
405 + if systemd_unit_exists "netdata-updater.timer"; then
406 if systemctl is-enabled netdata-updater.timer; then
407 info "Auto-updates using a systemd timer unit are ENABLED"
408 enabled="systemd"
system/install-service.sh.in
+19 -8
@@ -229,16 +229,27 @@ check_systemd() {
229 }
230
231 get_systemd_service_dir() {
232 - if [ -w "/lib/systemd/system" ]; then
233 - echo "/lib/systemd/system"
234 - elif [ -w "/usr/lib/systemd/system" ]; then
235 - echo "/usr/lib/systemd/system"
236 - elif [ -w "/etc/systemd/system" ]; then
237 - echo "/etc/systemd/system"
232 + set +e
233 + unit_paths="$(systemctl show -p UnitPath | cut -f 2- -d '=' | tr ' ' '\n')"
234 + set -e
235 +
236 + if [ -n "${unit_paths}" ]; then
237 + lib_paths="$(echo "${unit_paths}" | grep -vE '^/(run|etc)' | awk '{line[NR] = $0} END {for (i = NR; i > 0; i--) print line[i]}')"
238 + etc_paths="$(echo "${unit_paths}" | grep -E '^/etc' | grep -vE '(attached|control)$')"
239 else
239 - error "Unable to detect systemd service directory."
240 - exit 4
240 + lib_paths="/usr/lib/systemd/system /lib/systemd/system /usr/local/lib/systemd/system"
241 + etc_paths="/etc/systemd/system"
242 fi
243 +
244 + for path in ${lib_paths} ${etc_paths}; do
245 + if [ -d "${path}" ] && [ -w "${path}" ]; then
246 + echo "${path}"
247 + return 0
248 + fi
249 + done
250 +
251 + error "Unable to detect usable systemd service directory."
252 + exit 4
253 }
254
255 install_systemd_service() {