mirror of
https://github.com/Xevion/dotfiles.git
synced 2026-01-31 06:24:13 -06:00
viofo_backup: fixed indentation, always unmount after mounting properly
This commit is contained in:
@@ -6,45 +6,49 @@ use std/log
|
|||||||
# It is intended to be ran semi-rarely (every month or two), and is also a limited test of the Fish shell/scripting language.
|
# It is intended to be ran semi-rarely (every month or two), and is also a limited test of the Fish shell/scripting language.
|
||||||
# It is intended to be cross-platform, but targets Ubuntu 22.04 LTS (with WSL2 support).
|
# It is intended to be cross-platform, but targets Ubuntu 22.04 LTS (with WSL2 support).
|
||||||
|
|
||||||
try {
|
# Configuration details
|
||||||
# Configuration details
|
|
||||||
let host = "roman" # The host to backup to. This is defined in the ~/.ssh/config file.
|
let host = "roman" # The host to backup to. This is defined in the ~/.ssh/config file.
|
||||||
let host_path = "/mnt/user/media/backup/dashcam" # The path on the remote host to backup to.
|
let host_path = "/mnt/user/media/backup/dashcam" # The path on the remote host to backup to.
|
||||||
|
|
||||||
# Check for required commands
|
# Global state tracking
|
||||||
let required_commands = ["rsync", "sudo", "mount", "umount", "cmd.exe", "ssh"]
|
mut mounted = false # Track if we've mounted a drive
|
||||||
for cmd in $required_commands {
|
mut letter = "" # Track the drive letter we're using
|
||||||
|
|
||||||
|
try {
|
||||||
|
# Check for required commands
|
||||||
|
let required_commands = ["rsync", "sudo", "mount", "umount", "cmd.exe", "ssh"]
|
||||||
|
for cmd in $required_commands {
|
||||||
if (which $cmd | length) == 0 {
|
if (which $cmd | length) == 0 {
|
||||||
log error $"Error: Required command ($cmd) not found."
|
log error $"Error: Required command ($cmd) not found."
|
||||||
exit 1
|
exit 1
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
# Acquire the actual hostname of the defined host
|
# Acquire the actual hostname of the defined host
|
||||||
let host_name: string = (ssh -G $host | lines | find -r "^hostname\\s+" | str trim | split column " " | get column2).0
|
let host_name: string = (ssh -G $host | lines | find -r "^hostname\\s+" | str trim | split column " " | get column2).0
|
||||||
|
|
||||||
# Check network connectivity to backup target
|
# Check network connectivity to backup target
|
||||||
log debug "Checking network connectivity to backup server..."
|
log debug "Checking network connectivity to backup server..."
|
||||||
let ping_check = ping -c 1 $host_name | complete
|
let ping_check = ping -c 1 $host_name | complete
|
||||||
if $ping_check.exit_code != 0 {
|
if $ping_check.exit_code != 0 {
|
||||||
log error $"Error: Could not verify network connectivity to '($host_name)'"
|
log error $"Error: Could not verify network connectivity to '($host_name)'"
|
||||||
log error $ping_check.stderr
|
log error $ping_check.stderr
|
||||||
exit 1
|
exit 1
|
||||||
}
|
}
|
||||||
|
|
||||||
# Check if backup destination exists and is writable
|
# Check if backup destination exists and is writable
|
||||||
log debug "Checking backup destination..."
|
log debug "Checking backup destination..."
|
||||||
try {
|
try {
|
||||||
ssh $host "test -d $host_path && test -w $host_path"
|
ssh $host "test -d $host_path && test -w $host_path"
|
||||||
} catch {
|
} catch {
|
||||||
log error "Error: Backup destination is not accessible or writable"
|
log error "Error: Backup destination is not accessible or writable"
|
||||||
exit 1
|
exit 1
|
||||||
}
|
}
|
||||||
|
|
||||||
# Check available space on backup destination
|
# Check available space on backup destination
|
||||||
log debug "Checking available space on backup destination..."
|
log debug "Checking available space on backup destination..."
|
||||||
let required_space = 10GB # 10GB in bytes
|
let required_space = 10GB # 10GB in bytes
|
||||||
try {
|
try {
|
||||||
let available_space = ssh $host $"df --output=avail /mnt/user" | lines | skip 1 | str trim | get 0 | append "KB" | str join " " | into filesize
|
let available_space = ssh $host $"df --output=avail /mnt/user" | lines | skip 1 | str trim | get 0 | append "KB" | str join " " | into filesize
|
||||||
if $available_space < $required_space {
|
if $available_space < $required_space {
|
||||||
log error $"Error: Insufficient space on backup destination"
|
log error $"Error: Insufficient space on backup destination"
|
||||||
@@ -53,31 +57,32 @@ try {
|
|||||||
}
|
}
|
||||||
|
|
||||||
log debug $"Available space: ($available_space)"
|
log debug $"Available space: ($available_space)"
|
||||||
} catch { |err|
|
} catch { |err|
|
||||||
log error $"Error: Could not check available space on backup destination: ($err.msg)"
|
log error $"Error: Could not check available space on backup destination: ($err.msg)"
|
||||||
exit 1
|
exit 1
|
||||||
}
|
}
|
||||||
|
|
||||||
# Acquire a list of potential mountable drive letters
|
# Acquire a list of potential mountable drive letters
|
||||||
let mountable = (cd /mnt/c; cmd.exe /C "wmic logicaldisk where DriveType=2 get DeviceID,Name /format:csv" | from csv)
|
let mountable = (cd /mnt/c; cmd.exe /C "wmic logicaldisk where DriveType=2 get DeviceID,Name /format:csv" | from csv)
|
||||||
log info "Pick a USB device to mount for Viofo backup:"
|
log info "Pick a USB device to mount for Viofo backup:"
|
||||||
|
|
||||||
# Check that at least one drive is available
|
# Check that at least one drive is available
|
||||||
if ($mountable | length) == 0 {
|
if ($mountable | length) == 0 {
|
||||||
log error "No USB drives found"
|
log error "No USB drives found"
|
||||||
exit 1
|
exit 1
|
||||||
}
|
}
|
||||||
|
|
||||||
# Have the user choose a drive
|
# Have the user choose a drive
|
||||||
let selected_drive = $mountable | input list -d "DeviceID" "Select a drive to mount for backup"
|
let selected_drive = $mountable | input list -d "DeviceID" "Select a drive to mount for backup"
|
||||||
let letter = $selected_drive.DeviceId | str replace --regex ":$" "" | str downcase
|
$letter = $selected_drive.DeviceId | str replace --regex ":$" "" | str downcase
|
||||||
let win_drive_path = $"($letter | str upcase):"
|
let win_drive_path = $"($letter | str upcase):"
|
||||||
|
|
||||||
# Check if already mounted
|
# Check if already mounted
|
||||||
log info "Checking if drive is already mounted..."
|
log info "Checking if drive is already mounted..."
|
||||||
let findmnt_check = findmnt -J --mountpoint /mnt/($letter) | complete
|
let findmnt_check = findmnt -J --mountpoint /mnt/($letter) | complete
|
||||||
if $findmnt_check.exit_code == 0 {
|
if $findmnt_check.exit_code == 0 {
|
||||||
log debug "Drive is already mounted"
|
log debug "Drive is already mounted"
|
||||||
|
$mounted = true
|
||||||
|
|
||||||
# Check was successful, meaning something must be mounted there
|
# Check was successful, meaning something must be mounted there
|
||||||
let mounts = $findmnt_check.stdout | from json
|
let mounts = $findmnt_check.stdout | from json
|
||||||
@@ -106,7 +111,7 @@ if $findmnt_check.exit_code == 0 {
|
|||||||
|
|
||||||
log info $"Mount Details: ($current_mount.options)"
|
log info $"Mount Details: ($current_mount.options)"
|
||||||
while true {
|
while true {
|
||||||
let continue = input "Continue anyways? (y/n)"
|
let continue = input "Continue anyways? [y/n]"
|
||||||
if $continue == "y" {
|
if $continue == "y" {
|
||||||
break
|
break
|
||||||
} else if $continue == "n" {
|
} else if $continue == "n" {
|
||||||
@@ -114,7 +119,7 @@ if $findmnt_check.exit_code == 0 {
|
|||||||
exit 1
|
exit 1
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
# Mount the drive
|
# Mount the drive
|
||||||
@@ -131,6 +136,7 @@ if $findmnt_check.exit_code == 0 {
|
|||||||
try {
|
try {
|
||||||
log debug "Mounting drive..."
|
log debug "Mounting drive..."
|
||||||
sudo mount -t drvfs ($win_drive_path) /mnt/($letter) -o uid=(id -u $env.USER),gid=(id -g $env.USER),metadata
|
sudo mount -t drvfs ($win_drive_path) /mnt/($letter) -o uid=(id -u $env.USER),gid=(id -g $env.USER),metadata
|
||||||
|
$mounted = true
|
||||||
} catch { |err|
|
} catch { |err|
|
||||||
log error $"Error: Could not mount drive: ($err.msg)"
|
log error $"Error: Could not mount drive: ($err.msg)"
|
||||||
exit 1
|
exit 1
|
||||||
@@ -146,6 +152,7 @@ if $findmnt_check.exit_code == 0 {
|
|||||||
error "Failed to mount drive"
|
error "Failed to mount drive"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
# Test permissions & folder structure
|
# Test permissions & folder structure
|
||||||
let expected_folders = [
|
let expected_folders = [
|
||||||
"DCIM",
|
"DCIM",
|
||||||
@@ -162,7 +169,6 @@ if $findmnt_check.exit_code == 0 {
|
|||||||
let status = test -d ($path) | complete
|
let status = test -d ($path) | complete
|
||||||
if $status.exit_code != 0 {
|
if $status.exit_code != 0 {
|
||||||
error $"Expected folder "($path)" does not exist."
|
error $"Expected folder "($path)" does not exist."
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
log debug $"Folder "($path)" exists"
|
log debug $"Folder "($path)" exists"
|
||||||
}
|
}
|
||||||
@@ -200,28 +206,32 @@ if $findmnt_check.exit_code == 0 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
log info "Sync complete."
|
log info "Sync complete."
|
||||||
|
} catch {|err|
|
||||||
|
log error $"Failed after mounting: ($err.msg)"
|
||||||
|
}
|
||||||
|
|
||||||
# Unmount the drive
|
# Unmount the drive
|
||||||
log info "Unmounting drive..."
|
log info "Unmounting drive..."
|
||||||
|
try {
|
||||||
sudo umount /mnt/($letter)
|
sudo umount /mnt/($letter)
|
||||||
sudo rmdir /mnt/($letter)
|
sudo rmdir /mnt/($letter)
|
||||||
|
$mounted = false
|
||||||
# TODO: Check if duplicate mounts exist
|
} catch { |err|
|
||||||
log info "All backed up."
|
log error $"Could not unmount drive: ($err.msg)"
|
||||||
} catch { |err|
|
exit 999
|
||||||
|
}
|
||||||
|
} catch { |err|
|
||||||
log error $"Error: Could not unmount drive: ($err.msg)"
|
log error $"Error: Could not unmount drive: ($err.msg)"
|
||||||
exit 1
|
exit 1
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# TODO: Statistical analysis of file duration
|
||||||
|
# On average, how far back do my recordings go? 2 months?
|
||||||
# TODO: Statistical analysis of file duration
|
# While the oldest video file could give an idea of how back I currently go, it would be better to use p99 average bitrate.
|
||||||
# On average, how far back do my recordings go? 2 months?
|
# If you know the average bitrate, you can use the current space occupied by all files to estimate the total duration you could store on the drive.
|
||||||
# While the oldest video file could give an idea of how back I currently go, it would be better to use p99 average bitrate.
|
# Then, if you can estimate the daily recording duration on average, you can estimate how many days back you can record on average.
|
||||||
# If you know the average bitrate, you can use the current space occupied by all files to estimate the total duration you could store on the drive.
|
# Additionally, since this script removes files, it might be better to use the 'full size' of the disk to estimate maximum duration capacity (minus 1GB).
|
||||||
# Then, if you can estimate the daily recording duration on average, you can estimate how many days back you can record on average.
|
} catch {|err|
|
||||||
# Additionally, since this script removes files, it might be better to use the 'full size' of the disk to estimate maximum duration capacity (minus 1GB).
|
|
||||||
} catch {|err|
|
|
||||||
log error $"Uncaught error: ($err.msg)"
|
log error $"Uncaught error: ($err.msg)"
|
||||||
exit 1
|
exit 1
|
||||||
}
|
}
|
||||||
Reference in New Issue
Block a user