Add restore option to restic-batch

This commit is contained in:
Wojciech Kozlowski 2023-02-13 00:12:30 +01:00
parent c64427f4c8
commit 486a1e9809
8 changed files with 50 additions and 14 deletions

View File

@ -44,6 +44,10 @@ class Volume(abc.ABC):
def _backup_path(self):
raise NotImplementedError
@abc.abstractproperty
def _restore_path(self):
raise NotImplementedError
def backup(self):
print(f"Backing up {self._bucket_name}", flush=True)
@ -68,9 +72,10 @@ class Volume(abc.ABC):
# --------------------------------------------------------------------------------------
# Perform the backup.
# --------------------------------------------------------------------------------------
subprocess.run(self._restic_cmd_base + ["backup", "."], cwd=self._backup_path,
env=self._environ, check=True,
stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
ps = subprocess.run(self._restic_cmd_base + ["backup", "."], cwd=self._backup_path,
env=self._environ, check=True,
stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
print(ps.stdout.decode("ascii"), flush=True)
# --------------------------------------------------------------------------------------
# Forget and prune old snapshots.
@ -94,6 +99,19 @@ class Volume(abc.ABC):
print(err.stdout.decode("ascii"), flush=True)
raise
def restore(self):
print(f"Restoring {self._bucket_name}", flush=True)
try:
subprocess.run(self._restic_cmd_base + ["restore", "latest", "--target", "."],
cwd=self._restore_path,
env=self._environ, check=True,
stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
except subprocess.CalledProcessError as err:
print(err.stdout.decode("ascii"), flush=True)
raise
class DirectoryVolume(Volume):
@ -105,6 +123,10 @@ class DirectoryVolume(Volume):
def _backup_path(self):
return self.__directory
@property
def _restore_path(self):
return self.__directory
class DatasetMount:
@ -142,8 +164,9 @@ class DatasetVolume(Volume):
super().__init__(name, repo_config)
self.__dataset = dataset
self.__snapshot = self.__get_last_daily_snapshot()
self.__mountpoint = mountpoint
self.__backup_path = os.path.normpath(
os.path.join("/", "mnt", os.path.relpath(mountpoint, "/"))
os.path.join("/", "mnt", os.path.relpath(self.__mountpoint, "/"))
)
def __get_last_daily_snapshot(self):
@ -160,6 +183,10 @@ class DatasetVolume(Volume):
def _backup_path(self):
return self.__backup_path
@property
def _restore_path(self):
return self.__mountpoint
def backup(self):
with DatasetMount(self.__snapshot, self._backup_path):
super().backup()

View File

@ -40,6 +40,10 @@
state: "directory"
mode: 0755
- name: "install restic-batch dependencies"
ansible.builtin.apt:
name: "python3-yaml"
- name: "install the restic-batch script"
ansible.builtin.copy:
src: "./restic-batch"

View File

@ -1,7 +0,0 @@
---
argument_specs:
main:
options:
services_data_dataset:
type: "str"
required: true

View File

@ -0,0 +1,4 @@
---
services_backups_user_data_dataset: "{{ services_data_dataset }}/{{ services_service_user_name }}"
services_backups_user_data_directory: "\
{{ services_data_directory }}/{{ services_service_user_name }}"

View File

@ -1,2 +0,0 @@
---
services_backups_user_data_dataset: "{{ services_data_dataset }}/{{ services_service_user_name }}"

View File

@ -8,6 +8,12 @@ argument_specs:
services_service_name:
type: "str"
required: true
services_data_dataset:
type: "str"
required: false
services_data_directory:
type: "str"
required: false
services_backups_restic_services:
type: "dict"
elem: "dict"

View File

@ -7,7 +7,7 @@
- name: "{{ services_service_name }} : tasks:vars"
ansible.builtin.import_role:
name: "services/backups/include"
vars_from: "main"
vars_from: "datasets"
- name: "{{ services_service_name }} : create restic password file"
ansible.builtin.template:

View File

@ -1,4 +1,8 @@
{% if services_data_dataset is defined %}
dataset: {{ services_backups_user_data_dataset }}
{% else %}
directory: {{ services_backups_user_data_directory }}
{% endif %}
aws_bucket_keys_file: {{ services_backups_restic_services[services_service_name].aws_keys_file }}
aws_bucket_endpoint: {{ services_backups_restic_services[services_service_name].aws_bucket_endpoint }}
aws_bucket_prefix: {{ services_backups_restic_services[services_service_name].aws_bucket_prefix }}