From 261fd458fdf00dbe6eaa4d8a87ca4e2c1c782859 Mon Sep 17 00:00:00 2001 From: cort Date: Sun, 5 Oct 2025 17:59:05 -0500 Subject: [PATCH] feat: Add systemd service files for HBlink4 and dashboard - Add hblink4.service for main DMR server - Add hblink4-dash.service for web dashboard - Dashboard service depends on main service - Both use venv at /home/cort/hblink4/venv - Auto-restart on failure with 10s delay - Include security hardening (NoNewPrivileges, PrivateTmp) - Log to systemd journal - Add SYSTEMD.md with installation and management instructions --- SYSTEMD.md | 140 +++++++++++++++++++++++++++++++++++++++++++ hblink4-dash.service | 25 ++++++++ hblink4.service | 24 ++++++++ 3 files changed, 189 insertions(+) create mode 100644 SYSTEMD.md create mode 100644 hblink4-dash.service create mode 100644 hblink4.service diff --git a/SYSTEMD.md b/SYSTEMD.md new file mode 100644 index 0000000..8b1d594 --- /dev/null +++ b/SYSTEMD.md @@ -0,0 +1,140 @@ +# HBlink4 Systemd Service Installation + +This directory contains systemd service files for running HBlink4 and its dashboard as system services. + +## Service Files + +- `hblink4.service` - Main HBlink4 DMR server +- `hblink4-dash.service` - Web dashboard (depends on hblink4.service) + +## Installation + +### 1. Install the service files + +Copy the service files to systemd's system directory: + +```bash +sudo cp hblink4.service /etc/systemd/system/ +sudo cp hblink4-dash.service /etc/systemd/system/ +``` + +### 2. Reload systemd + +Tell systemd to reload its configuration: + +```bash +sudo systemctl daemon-reload +``` + +### 3. Enable services (optional) + +To start the services automatically at boot: + +```bash +sudo systemctl enable hblink4 +sudo systemctl enable hblink4-dash +``` + +### 4. Start the services + +```bash +sudo systemctl start hblink4 +sudo systemctl start hblink4-dash +``` + +## Service Management + +### Check service status + +```bash +sudo systemctl status hblink4 +sudo systemctl status hblink4-dash +``` + +### View logs + +```bash +# View logs for HBlink4 +sudo journalctl -u hblink4 -f + +# View logs for dashboard +sudo journalctl -u hblink4-dash -f + +# View last 100 lines +sudo journalctl -u hblink4 -n 100 +``` + +### Stop services + +```bash +sudo systemctl stop hblink4 +sudo systemctl stop hblink4-dash +``` + +### Restart services + +```bash +sudo systemctl restart hblink4 +sudo systemctl restart hblink4-dash +``` + +### Disable autostart + +```bash +sudo systemctl disable hblink4 +sudo systemctl disable hblink4-dash +``` + +## Configuration + +The service files are configured to: +- Run as user `cort` in group `cort` +- Use the Python virtual environment at `/home/cort/hblink4/venv` +- Automatically restart on failure (after 10 seconds) +- Log to systemd journal (view with `journalctl`) +- Start after network is available +- Dashboard starts after and depends on HBlink4 + +### Customization + +If you need to modify the services (different user, paths, etc.), edit the files before copying them: + +1. Edit `hblink4.service` and/or `hblink4-dash.service` +2. Change `User=`, `Group=`, `WorkingDirectory=`, or `ExecStart=` as needed +3. Copy to `/etc/systemd/system/` +4. Run `sudo systemctl daemon-reload` + +## Security Features + +Both services include security hardening: +- `NoNewPrivileges=true` - Prevents privilege escalation +- `PrivateTmp=true` - Isolates /tmp directory + +## Troubleshooting + +### Service won't start + +Check the status and logs: +```bash +sudo systemctl status hblink4 +sudo journalctl -u hblink4 -n 50 +``` + +Common issues: +- Virtual environment not found: Check path in `ExecStart=` +- Permission errors: Ensure user/group are correct +- Config file errors: Check HBlink4 configuration files +- Port conflicts: Another service using the same ports + +### Dashboard can't connect to HBlink4 + +1. Ensure HBlink4 is running: `sudo systemctl status hblink4` +2. Check dashboard config points to correct socket/host +3. Check logs: `sudo journalctl -u hblink4-dash -n 50` + +## Notes + +- The dashboard service has `Wants=hblink4.service`, so it will start after HBlink4 +- Both services have `Restart=always` for automatic recovery +- Logs are sent to systemd journal, not file-based logging +- Services run with the same privileges as the `cort` user diff --git a/hblink4-dash.service b/hblink4-dash.service new file mode 100644 index 0000000..b3936cc --- /dev/null +++ b/hblink4-dash.service @@ -0,0 +1,25 @@ +[Unit] +Description=HBlink4 Dashboard +After=network.target hblink4.service +Wants=hblink4.service + +[Service] +Type=simple +User=cort +Group=cort +WorkingDirectory=/home/cort/hblink4/dashboard +ExecStart=/home/cort/hblink4/venv/bin/python /home/cort/hblink4/run_dashboard.py +Restart=always +RestartSec=10 + +# Security hardening +NoNewPrivileges=true +PrivateTmp=true + +# Logging +StandardOutput=journal +StandardError=journal +SyslogIdentifier=hblink4-dash + +[Install] +WantedBy=multi-user.target diff --git a/hblink4.service b/hblink4.service new file mode 100644 index 0000000..888f3dd --- /dev/null +++ b/hblink4.service @@ -0,0 +1,24 @@ +[Unit] +Description=HBlink4 DMR Server +After=network.target + +[Service] +Type=simple +User=cort +Group=cort +WorkingDirectory=/home/cort/hblink4 +ExecStart=/home/cort/hblink4/venv/bin/python /home/cort/hblink4/run.py +Restart=always +RestartSec=10 + +# Security hardening +NoNewPrivileges=true +PrivateTmp=true + +# Logging +StandardOutput=journal +StandardError=journal +SyslogIdentifier=hblink4 + +[Install] +WantedBy=multi-user.target