Skip to content

Instantly share code, notes, and snippets.

@aabccd021
Created May 15, 2025 05:42
Show Gist options
  • Save aabccd021/35e572560aff8448de103da9e51ffb9b to your computer and use it in GitHub Desktop.
Save aabccd021/35e572560aff8448de103da9e51ffb9b to your computer and use it in GitHub Desktop.
systemd-monitor.sh
#!/bin/sh
webhook_url="https://discord.com/api/webhooks/your-webhook-url-here"
cursor_file="/var/lib/systemd-monitor/journal_cursor"
# Use journalctl cursor for more atomic and reliable tracking
if [ -f "$cursor_file" ]; then
journal_args="--cursor-file=$cursor_file"
else
# First run - check last 5 min then save cursor
since_time="$(date -d '5 minutes ago' +'%Y-%m-%d %H:%M:%S')"
journal_args="--since=\"$since_time\" --cursor-file=$cursor_file"
fi
all_services=$(systemctl list-units --type=service --state=loaded --no-legend | awk '{print $1}')
echo "$all_services" | while read -r service; do
case "$service" in
systemd-*|*.slice|*.socket|*.path|*.timer|*.mount|*.swap|*.scope|*.device)
continue
;;
esac
# Check service status
status=$(systemctl is-active "$service")
if [ "$status" = "active" ] || [ "$status" = "inactive" ]; then
# Check for restarts
restart_count=$(systemctl show "$service" --property=NRestarts | cut -d= -f2)
if [ "$restart_count" -gt "0" ]; then
curl -s -H "Content-Type: application/json" \
-d "{\"content\": \"Service Restart Alert: '$service' has restarted.\nCurrent status: $status\nRestart count: $restart_count\nTime: $(date)\"}" \
"$webhook_url"
fi
else
curl -s -H "Content-Type: application/json" \
-d "{\"content\": \"Service Alert: '$service' is $status.\nTime: $(date)\"}" \
"$webhook_url"
fi
# Set minimum priority based on service
minimum_priority="err"
if [ "$service" = "systemd.service" ] || [ "$service" = "kernel.service" ]; then
minimum_priority="crit"
fi
# Check for journal errors with minimum priority
service_errors=$(journalctl -u "$service" $journal_args --priority=$minimum_priority..emerg --no-pager)
if [ -n "$service_errors" ]; then
curl -s -H "Content-Type: application/json" \
-d "{\"content\": \"Journal Error Alert: '$service' logged errors.\n\`\`\`\n$service_errors\n\`\`\`\nTime: $(date)\"}" \
"$webhook_url"
fi
done
failed_units=$(systemctl list-units --state=failed --plain --no-legend | awk '{print $1}')
if [ -n "$failed_units" ]; then
echo "$failed_units" | while read -r unit; do
curl -s -H "Content-Type: application/json" \
-d "{\"content\": \"Service Alert: '$unit' has failed.\nTime: $(date)\"}" \
"$webhook_url"
done
fi
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment