Етапи 1, 2 і 4 є відносно простими і можуть бути виконані за допомогою launchd
(або cron
) для виклику сценарію.
Моє рішення передбачає деякі налаштування, взяті з цієї публікації в блозі :
Відкрийте Keychain Access
( ⌘Space Keychain Access
), натисніть Password
, а потім +створити новий пароль. Користувач restic
для Keychain Item Name
і для Account Name
. Введіть пароль у Password
полі (тобто введіть той самий пароль, який ви використовували, коли ви бігли restic init
). Нарешті, натисніть, Add
щоб завершити процес налаштування.
launchd
(або cron
) робота працює кожні 24 години і просто викликає сценарій оболонкиrestic-backup.sh
restic-backup.sh
перевіряє, якщо /Volumes/usb-storage-name
він встановлений, і зупиняє, чи ні. Якщо диск встановлений, він перевіряє наявність /Users/user/data
каталогу і зупиняється, якщо каталог не існує (він не може створити резервну копію неіснуючого каталогу!) Якщо том резервного копіювання встановлено, а вихідний каталог його існує, переходимо до кроку 3 ...
Якщо встановлена змінна середовище RESTIC_PASSWORD
, Restic використовуватиме її значення замість запиту пароля . restic-backup.sh
встановимо RESTIC_PASSWORD
за допомогою security
команди та деякої ruby
магії:
RESTIC_PASSWORD=$(security 2>&1 >/dev/null find-generic-password -ga restic |ruby -e 'print $1 if STDIN.gets =~ /^password: "(.*)"$/')
З RESTIC_PASSWORD
набором сценарію тепер можна виконати резервну копію:
restic -r /Volumes/usb-storage-name/restic-backups backup /Users/user/data
launchd
/ Завдання cron
з кроку 1 має виконуватися кожні 24 години, охоплюючи також етап 4.
restic-backup.sh
:
#!/bin/bash
# USER CONFIGURATION:
resticuser=restic
srcdir=/Users/user/data
backupvolume=/Volumes/usb-storage-name
backupdir=${backupvolume}/restic-backups
# Script vars:
longname=$0
shortname=$(/usr/bin/basename "${longname}")
printf '%s %s (%s) running...\n' "$(date -u "+%Y-%m-%d %H:%M:%S")" "${shortname}" "${longname}"
if [[ ! -d "${srcdir}" ]]; then
printf '%s %s does NOT exist.' "$(date -u "+%Y-%m-%d %H:%M:%S")" "${srcdir}" >&2
exit 1
else
if [[ $(mount | grep "${backupvolume}") ]]; then
# See: http://blog.macromates.com/2006/keychain-access-from-shell/
# Parse output of 'security' and set RESTIC_PASSWORD:
export RESTIC_PASSWORD=$(security 2>&1 >/dev/null find-generic-password -ga ${resticuser} |ruby -e 'print $1 if STDIN.gets =~ /^password: "(.*)"$/')
# Run backup, capturing output in case of error:
output=$(restic -r ${backupdir} backup "${srcdir}")
error=$?
if [[ "${error}" == "0" ]]; then
printf '%s Restic backup completed successfully.\n' "$(date -u "+%Y-%m-%d %H:%M:%S")"
else
printf '%s Restic backup failed: error code: %s, error: %s\n' \
"$(date -u "+%Y-%m-%d %H:%M:%S")" "${error}" "${output}" >&2
fi
else
printf '%s %s is NOT mounted.' "$(date -u "+%Y-%m-%d %H:%M:%S")" "${backupvolume}" >&2
exit 1
fi
fi
printf '%s %s ended.\n' "$(date -u "+%Y-%m-%d %H:%M:%S")" "${shortname}"
launchd
але міг би досить швидко зібрати разом,launchd plist
якщо він вам потрібен.