From 8472fdf0ae3103e9b8c020cbd8799806c0629598 Mon Sep 17 00:00:00 2001 From: librelad Date: Mon, 25 May 2026 18:50:26 +0100 Subject: [PATCH] feat(uninstall): location-agnostic 'libreportal-uninstall' command (+ de-hardcode docs) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The docs were telling users to run /libreportal-system/install/uninstall.sh — a hardcoded data path, wrong for any custom --system-dir, contradicting the whole relocatable design. Fix it the way the CLI already works: install uninstall.sh to the FIXED footprint (/usr/local/lib/libreportal/uninstall.sh) and symlink it onto $PATH as 'libreportal-uninstall' (initLibrePortalCommand). It self-resolves the real data roots from the systemd unit, so the command is the same everywhere regardless of where data lives. Teardown removes the new symlink; FOOTPRINT.md lists it. Docs now say 'sudo libreportal-uninstall' — no data path. (Dev-from-clone still uses ./uninstall.sh / ./init.sh uninstall.) Co-Authored-By: Claude Opus 4.7 Signed-off-by: librelad --- docs/FOOTPRINT.md | 4 +++- docs/USER.md | 12 ++++++------ init.sh | 10 +++++++++- 3 files changed, 18 insertions(+), 8 deletions(-) diff --git a/docs/FOOTPRINT.md b/docs/FOOTPRINT.md index b734157..0bcf3f2 100644 --- a/docs/FOOTPRINT.md +++ b/docs/FOOTPRINT.md @@ -28,6 +28,7 @@ together in **`/usr/local/lib/libreportal/`**; everything else is named | File | Owner | Purpose | |------|-------|---------| | `libreportal` | root | the CLI wrapper (symlinked onto `$PATH`, see below) | +| `uninstall.sh` | root | the uninstaller (symlinked onto `$PATH` as `libreportal-uninstall`) | | `libreportal-ownership` | root | reconcile the three-root ownership model | | `libreportal-dns` | root | edit `/etc/resolv.conf` (nameservers) | | `libreportal-ssh-access` | root | manage admin `authorized_keys` + sshd `PasswordAuthentication` | @@ -47,6 +48,7 @@ quick-deploy). | Path | Owner | Purpose | |------|-------|---------| | `/usr/local/bin/libreportal` | root | **symlink** → `/usr/local/lib/libreportal/libreportal` (puts the CLI on `$PATH`) | +| `/usr/local/bin/libreportal-uninstall` | root | **symlink** → `/usr/local/lib/libreportal/uninstall.sh` (location-agnostic uninstall command) | | `/etc/sudoers.d/` | root | scoped least-privilege grant for the manager (drop-in named after the manager user) | | `/etc/systemd/system/libreportal.service` | root | the task-processor service (`User=`; bakes the roots as `Environment=LP_*_DIR`) | | `/etc/sysctl.d/99-libreportal-hardening.conf` | root | kernel LPE-surface hardening | @@ -73,7 +75,7 @@ config lives at `~/.config/docker/daemon.json`. sudo systemctl disable --now libreportal.service sudo rm -f /etc/systemd/system/libreportal.service /etc/sudoers.d/libreportal sudo rm -f /etc/sysctl.d/99-libreportal-*.conf -sudo rm -rf /usr/local/lib/libreportal /usr/local/bin/libreportal +sudo rm -rf /usr/local/lib/libreportal /usr/local/bin/libreportal /usr/local/bin/libreportal-uninstall sudo rm -rf /libreportal-system /libreportal-containers /libreportal-backups # optional: the backup-engine binaries and the two users ``` diff --git a/docs/USER.md b/docs/USER.md index dfeb57f..f05b657 100644 --- a/docs/USER.md +++ b/docs/USER.md @@ -85,15 +85,15 @@ the required ownership and will warn. ## Uninstall ```bash -sudo /libreportal-system/install/uninstall.sh +sudo libreportal-uninstall # keep the rootless Docker layer + image cache for a fast reinstall: -sudo /libreportal-system/install/uninstall.sh --skip-docker-images +sudo libreportal-uninstall --skip-docker-images ``` -`uninstall.sh` finds your install automatically (even with custom roots — it reads -the real locations from the installed service) and removes the three roots, the -system users, and the small out-of-tree footprint (`/usr/local/lib/libreportal`, -the `/etc` integration files). `sudo init.sh uninstall` does the same thing. +`libreportal-uninstall` is a fixed command on `$PATH` (no data path to type — it +reads the real install locations from the installed service, so it works even with +custom roots). It removes the three roots, the system users, and the small +out-of-tree footprint (`/usr/local/lib/libreportal`, the `/etc` integration files). > ⚠️ Uninstall permanently deletes all app data, configs, and the database. Take a > backup first if you want to keep anything. diff --git a/init.sh b/init.sh index 4321a42..7415ae2 100755 --- a/init.sh +++ b/init.sh @@ -1467,6 +1467,14 @@ EOF sudo chown root:root $command_script # Put it on $PATH via a symlink (replaces any older real file at this path). sudo ln -sfn "$command_script" "$command_symlink" + + # Install the uninstaller at the fixed footprint + put it on $PATH as + # `libreportal-uninstall` — a location-agnostic command (it resolves the real + # data roots from the systemd unit at run time), so users never type a data path. + if [[ -f "$script_dir/uninstall.sh" ]]; then + sudo install -m 0755 -o root -g root "$script_dir/uninstall.sh" "$lp_lib_dir/uninstall.sh" + sudo ln -sfn "$lp_lib_dir/uninstall.sh" /usr/local/bin/libreportal-uninstall + fi source $sudo_bashrc } @@ -1643,7 +1651,7 @@ runFullUninstall() fi # 3. Remove the out-of-/docker footprint (see docs/FOOTPRINT.md). - rm -f /usr/local/bin/libreportal + rm -f /usr/local/bin/libreportal /usr/local/bin/libreportal-uninstall rm -rf /usr/local/lib/libreportal rm -f "/etc/sudoers.d/$mgr" # Keep the sysctl drop-ins when preserving docker — removing + reloading them