Uninstalling
Decommission a deployment from the platform and remove the Fleetera Edge Runtime from the host.
Uninstalling a deployment is a two-sided flow:
- Cloud side — mark the deployment as decommissioned in the Fleetera platform so it stops appearing as an active site.
- Edge side — tear down the containers, remove the install directory, and (optionally) disconnect the host from the VPN.
The recommended path uses the Decommission Deployment button in the platform as the front door, then runs a cleanup script on the host that closes the loop with the cloud. A manual fallback is documented below for hosts that cannot reach the platform during cleanup.
This procedure stops all edge services and permanently deletes any local data buffered on the gateway, including telemetry that has not yet been forwarded to the cloud. Make sure the gateway has caught up before proceeding.
Recommended flow
1. Decommission the deployment in the platform
- Open the deployment detail page in the Fleetera platform.
- Click Decommission Deployment and confirm.
- The status badge changes to Decommissioning. The page polls live and shows the elapsed time since you started decommissioning.
At this point the deployment is soft-deleted but still visible in your deployment history. It will not flip to the terminal Decommissioned state until either:
- the cleanup script on the edge host completes and posts back to the platform (recommended — closes the loop in seconds), or
- the platform stops receiving heartbeats from the gateway for 30 minutes (fallback — used if the host cannot reach the cloud during cleanup).
2. Run the cleanup script on the edge host
SSH into the edge host as root, then run the following script. It tears down the container set, removes the install directory, optionally disconnects from the VPN, and posts a cleanup-complete notification back to the platform so the badge flips to Decommissioned without waiting for the 30-minute timeout.
#!/usr/bin/env bash
set -euo pipefail
# Read deployment-specific config from the install directory's .env
TOKEN="$(grep -E '^FLEETERA_BOOTSTRAP_TOKEN=' /opt/fleetera-edge/.env | cut -d= -f2-)"
API_URL="$(grep -E '^API_BASE_URL=' /opt/fleetera-edge/.env | cut -d= -f2- || echo 'https://api.fleetera.ai')"
# 1. Stop and remove the systemd auto-start unit
if systemctl is-enabled --quiet fleetera-edge.service 2>/dev/null; then
systemctl disable --now fleetera-edge.service
fi
rm -f /etc/systemd/system/fleetera-edge.service
systemctl daemon-reload
# 2. Tear down all Fleetera containers and named volumes
if [ -f /opt/fleetera-edge/docker-compose.yml ]; then
docker compose -f /opt/fleetera-edge/docker-compose.yml down -v --remove-orphans
fi
# 3. Remove the install directory
rm -rf /opt/fleetera-edge
# 4. (Optional) Disconnect this host from the Fleetera VPN
tailscale logout || true
# 5. Notify the platform that cleanup completed.
# `|| true` is intentional: cleanup has already succeeded locally,
# and the platform's 30-minute heartbeat timeout will close the loop
# even if this callback can't reach the API.
if [ -n "${TOKEN}" ]; then
curl -sSL -X POST "${API_URL}/api/edge/uninstall-complete" \
-H "Content-Type: application/json" \
-d "{\"token\":\"${TOKEN}\"}" || true
fi
echo "Cleanup complete."The platform updates the badge to Decommissioned · Edge fully cleaned up at HH:MM within seconds of receiving the callback.
The callback is best-effort. If the host has no internet access, or the platform is unreachable, the cleanup itself still succeeds — the platform automatically flips the deployment to Decommissioned after 30 minutes of heartbeat silence. You do not need to run the callback manually later.
3. Verify the result
Return to the deployment detail page in the platform. The status should now read Decommissioned, with a timestamp indicating when cleanup was confirmed. The deployment remains in your history for audit purposes; you can permanently remove it later from the deployment list.
Manual cleanup (fallback)
If you prefer to step through cleanup manually — for example, while debugging — follow the sections below in order. Each section maps to one step of the script above.
1. Stop the systemd service
The bootstrap script registers a fleetera-edge.service systemd unit that auto-starts the runtime on boot. Stop and remove it:
sudo systemctl disable --now fleetera-edge.service
sudo rm -f /etc/systemd/system/fleetera-edge.service
sudo systemctl daemon-reload2. Stop containers and remove volumes
Tear down the container set and its named volumes:
cd /opt/fleetera-edge
sudo docker compose down -v --remove-orphansThe -v flag removes the named Docker volumes (fleetera-data and alloy-data), which hold the runtime's per-install instance ID and the buffered log shipping queue. The --remove-orphans flag catches any containers from earlier compose revisions.
3. Remove leftover containers
Watchtower and other helper containers occasionally linger after docker compose down. Sweep them:
docker ps -a --filter "name=fleetera-"
docker rm -f fleetera-runtime fleetera-edge-crawler fleetera-watchtower 2>/dev/null || true4. Remove Docker images (optional)
If you want to free disk space, remove all Fleetera images. This is forward-compatible — it grabs whatever Fleetera images are present without hardcoding container names:
docker images --format '{{.Repository}}:{{.Tag}}' | \
grep -E 'ghcr\.io/fleetera|containrrr/watchtower|grafana/alloy' | \
xargs -r docker rmi -f
docker image prune -f
docker network prune -f5. Remove the installation directory
sudo rm -rf /opt/fleetera-edgeThis removes the docker-compose.yml, the .env file, the runtime config, and any locally cached state.
6. Disconnect from the VPN (optional)
The edge host connects to a private WireGuard-based VPN (Tailscale client connected to a Fleetera-operated Headscale coordinator) during installation. To disconnect:
sudo tailscale logoutLeaving the Tailscale client connected does no harm — the host simply remains reachable on the mesh network. The per-deployment auth key expires after the bootstrap, so no new devices can join using the same key.
7. Close the loop with the platform (optional)
If you skipped the cleanup-complete callback in the recommended flow, you can post it manually now to flip the deployment to Decommissioned immediately rather than waiting for the 30-minute heartbeat timeout. Run this before removing /opt/fleetera-edge/.env — the script needs the bootstrap token from that file:
TOKEN="$(grep -E '^FLEETERA_BOOTSTRAP_TOKEN=' /opt/fleetera-edge/.env | cut -d= -f2-)"
API_URL="$(grep -E '^API_BASE_URL=' /opt/fleetera-edge/.env | cut -d= -f2-)"
curl -sSL -X POST "${API_URL}/api/edge/uninstall-complete" \
-H "Content-Type: application/json" \
-d "{\"token\":\"${TOKEN}\"}"The endpoint is idempotent — safe to retry. A successful response is {"ok":true}.
If you have already removed /opt/fleetera-edge/, simply wait — the platform will flip to Decommissioned automatically once 30 minutes have passed since the last heartbeat.
After cleanup
- The deployment moves to Decommissioning the moment you click Decommission Deployment in the platform, and to Decommissioned within seconds (callback) or 30 minutes (fallback).
- The decommissioned deployment stays visible in your deployment list with a timestamp showing when cleanup was confirmed. It no longer counts toward your active deployment quota and stops receiving config updates.
- To redeploy on the same host, create a new deployment and run the bootstrap command again. A new deployment ID and bootstrap token are issued — the old token cannot be reused.
What is preserved
The cleanup procedure deliberately does not remove:
| Item | Reason |
|---|---|
| Docker Engine | The host may run other workloads that depend on Docker. |
| Tailscale client | The disconnect step is optional; the client may be used by other services on the host. |
| Other containers | Only Fleetera containers (fleetera-runtime, fleetera-edge-crawler, fleetera-watchtower, and the Grafana Alloy log shipper) are removed. |
| Cloud-side telemetry | Telemetry already forwarded to the cloud is retained according to your tenant's data retention policy. |