Save the last successful backup and add --last-backup

Write the completion time and backup directory to
$XDG_STATE_HOME/simple_backup/last_backup after each successful backup
(as the target user when run as root), for status bar reminders.
--last-backup prints it.
This commit is contained in:
Fuxino
2026-10-25 12:36:00 +01:00
parent 7547db1ea8
commit 6d54019a18
7 changed files with 306 additions and 5 deletions
+20 -1
View File
@@ -26,6 +26,8 @@ class FakeBackup:
instances: list['FakeBackup'] = []
check_code = 0
run_code = 0
destination = '/backups/simple_backup/2026-10-25_10-00-00'
def __init__(self, inputs: Any, output: Any, exclude: Any, keep: Any, options: str,
ssh_host: str | None = None, ssh_user: str | None = None,
@@ -56,7 +58,7 @@ class FakeBackup:
def run(self) -> int:
self.ran = True
return 0
return FakeBackup.run_code
def close(self) -> None:
self.closed = True
@@ -66,6 +68,7 @@ class FakeBackup:
def fake_backup(monkeypatch: pytest.MonkeyPatch) -> None:
FakeBackup.instances = []
FakeBackup.check_code = 0
FakeBackup.run_code = 0
monkeypatch.setattr(sb, 'Backup', FakeBackup)
@@ -83,6 +86,8 @@ def as_root(monkeypatch: pytest.MonkeyPatch) -> None:
"""Run as root, with no sudo/doas variables set"""
monkeypatch.setattr(os, 'geteuid', lambda: 0)
# Writing the state file as root would call seteuid() (covered in test_state.py)
monkeypatch.setattr(sb, '_write_state', lambda user, destination: None)
for var in ['SUDO_USER', 'SUDO_UID', 'DOAS_USER']:
monkeypatch.delenv(var, raising=False)
@@ -270,6 +275,20 @@ ssh_keyfile=/keys/id
assert not b.ran
assert b.closed
@pytest.mark.parametrize('check_code, run_code, saved', [(0, 0, True), (2, 0, False), (0, 4, False)])
def test_state_saved_only_on_success(self, run_cli: RunCli, config: Callable[[str], str], tmp_path: Path,
check_code: int, run_code: int, saved: bool) -> None:
FakeBackup.check_code = check_code
FakeBackup.run_code = run_code
assert run_cli('-c', config('backup_dir=/backups')) == (check_code or run_code)
state = tmp_path / 'state' / 'simple_backup' / 'last_backup'
assert state.exists() is saved
if saved:
assert state.read_text().splitlines()[1] == FakeBackup.destination
class TestUser:
@pytest.mark.usefixtures('as_user')