Files
homey/scripts/mount-longhorn-volume.sh
T
2026-04-15 16:49:18 +03:00

147 lines
3.9 KiB
Bash
Executable File

#!/usr/bin/env bash
set -euo pipefail
BACKUP_DIR="${BACKUP_DIR:-/mnt2/homey-backup}"
MOUNT_BASE="${MOUNT_BASE:-/mnt/longhorn-volumes}"
usage() {
echo "Usage: $0 <pvc-name-or-friendly-name> [mount-point]"
echo ""
echo "Mounts a Longhorn volume backup for exploration."
echo ""
echo "Arguments:"
echo " pvc-name-or-friendly-name The PVC ID or friendly name (e.g., 'nextcloud-data-pvc')"
echo " mount-point Optional custom mount point (default: $MOUNT_BASE/<name>)"
echo ""
echo "Examples:"
echo " $0 nextcloud-data-pvc"
echo " $0 pvc-5c1f48e3-346f-4c35-8e6a-8fc0c4c3a842-96d72815"
echo " $0 nextcloud-data-pvc /mnt/my-mount"
echo ""
echo "To unmount, run:"
echo " sudo umount <mount-point>"
echo " sudo losetup -d /dev/loopX"
exit 1
}
if [[ $# -lt 1 ]]; then
usage
fi
SEARCH_NAME="$1"
CUSTOM_MOUNT="${2:-}"
MANIFEST="$BACKUP_DIR/manifest.json"
if [[ ! -f "$MANIFEST" ]]; then
echo "Error: Manifest not found at $MANIFEST"
echo "Make sure you've run the backup script first."
exit 1
fi
find_volume() {
local search="$1"
local found=""
while IFS= read -r line; do
pvc_id=$(echo "$line" | grep -oP '"pvc_id":\s*"\K[^"]+')
friendly=$(echo "$line" | grep -oP '"friendly_name":\s*"\K[^"]+')
if [[ "$pvc_id" == "$search" ]] || [[ "$friendly" == "$search" ]]; then
echo "$pvc_id:$friendly"
return 0
fi
done < <(grep -A6 '"volumes"' "$MANIFEST" | grep -E '"pvc_id"|"friendly_name"')
return 1
}
VOLUME_INFO=$(find_volume "$SEARCH_NAME")
if [[ -z "$VOLUME_INFO" ]]; then
echo "Error: Volume '$SEARCH_NAME' not found in manifest."
echo ""
echo "Available volumes:"
grep -oP '"friendly_name":\s*"\K[^"]+' "$MANIFEST" | while read -r name; do
echo " - $name"
done
exit 1
fi
PVC_ID="${VOLUME_INFO%%:*}"
FRIENDLY_NAME="${VOLUME_INFO#*:}"
VOLUME_DIR="$BACKUP_DIR/volumes/$PVC_ID"
if [[ ! -d "$VOLUME_DIR" ]]; then
echo "Error: Volume directory not found: $VOLUME_DIR"
exit 1
fi
VOLUME_HEAD=$(find "$VOLUME_DIR" -name "volume-head-*.img" | head -1)
if [[ -z "$VOLUME_HEAD" ]]; then
echo "Error: No volume-head-*.img file found in $VOLUME_DIR"
echo "Contents:"
ls -la "$VOLUME_DIR"
exit 1
fi
if [[ -n "$CUSTOM_MOUNT" ]]; then
MOUNT_POINT="$CUSTOM_MOUNT"
else
MOUNT_POINT="$MOUNT_BASE/$FRIENDLY_NAME"
fi
echo "========================================"
echo " Mount Longhorn Volume"
echo "========================================"
echo ""
echo "PVC ID: $PVC_ID"
echo "Name: $FRIENDLY_NAME"
echo "Volume file: $(basename "$VOLUME_HEAD")"
echo "Mount point: $MOUNT_POINT"
echo ""
LOOP_DEV=$(sudo losetup -fP --show "$VOLUME_HEAD")
echo "Attached to: $LOOP_DEV"
sudo mkdir -p "$MOUNT_POINT"
echo ""
echo "Mounting..."
if sudo mount "$LOOP_DEV" "$MOUNT_POINT" 2>/dev/null; then
echo ""
echo "========================================"
echo " Mounted Successfully!"
echo "========================================"
echo ""
echo "Mount point: $MOUNT_POINT"
echo "Loop device: $LOOP_DEV"
echo ""
echo "Contents:"
ls -la "$MOUNT_POINT" 2>/dev/null | head -20
echo ""
echo "To unmount:"
echo " sudo umount $MOUNT_POINT"
echo " sudo losetup -d $LOOP_DEV"
else
echo "Mount failed. Trying with filesystem detection..."
FS_TYPE=$(sudo blkid -o value -s TYPE "$LOOP_DEV" 2>/dev/null || echo "")
if [[ -n "$FS_TYPE" ]]; then
echo "Detected filesystem: $FS_TYPE"
sudo mount -t "$FS_TYPE" "$LOOP_DEV" "$MOUNT_POINT"
echo ""
echo "Mounted successfully at $MOUNT_POINT"
else
echo "Could not detect filesystem. Volume may be empty or corrupted."
echo ""
echo "Loop device: $LOOP_DEV"
echo "Run 'sudo blkid $LOOP_DEV' to inspect."
echo ""
echo "To detach:"
echo " sudo losetup -d $LOOP_DEV"
fi
fi