You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
75 lines
2.4 KiB
75 lines
2.4 KiB
#!/usr/bin/env python
|
|
import json
|
|
import tempfile
|
|
import subprocess
|
|
import datetime
|
|
from pathlib import Path
|
|
|
|
|
|
def get_last_boot():
|
|
with subprocess.Popen(
|
|
["journalctl", "--utc", "--list-boots"], stdout=subprocess.PIPE
|
|
) as proc:
|
|
for line in proc.stdout.read().decode().split("\n"):
|
|
info, end_time = line.split(chr(8212))
|
|
info = list(filter(bool, info.split(" ")))
|
|
bootnum = info[0]
|
|
if bootnum == "0":
|
|
start_date_string = " ".join(info[3:5])
|
|
return datetime.datetime.fromisoformat(start_date_string).replace(
|
|
tzinfo=datetime.timezone.utc
|
|
)
|
|
|
|
|
|
def get_snapshot_after_datetime(start: datetime.datetime):
|
|
with subprocess.Popen(
|
|
["snapper", "--utc", "--iso", "--jsonout", "list", "-t", "pre-post"],
|
|
stdout=subprocess.PIPE,
|
|
) as proc:
|
|
if proc.wait() != 0:
|
|
raise PermissionError("Snapper needs root privileges to read snapshots")
|
|
data = json.loads(proc.stdout.read().decode())
|
|
# ten years
|
|
td = 3153600000
|
|
ret = None
|
|
for snapshot in data["root"]:
|
|
snapshot_date = datetime.datetime.fromisoformat(snapshot["date"]).replace(
|
|
tzinfo=datetime.timezone.utc
|
|
)
|
|
d = (snapshot_date - start).total_seconds()
|
|
if 0 < d < td:
|
|
td = d
|
|
ret = snapshot
|
|
if ret is None:
|
|
print(f"No update since last boot on {start.astimezone()}")
|
|
exit(0)
|
|
return ret
|
|
|
|
|
|
def get_snapshot_path(snapshot):
|
|
return (
|
|
Path(snapshot["subvolume"])
|
|
/ ".snapshots"
|
|
/ Path(str(snapshot["number"]))
|
|
/ "snapshot"
|
|
)
|
|
|
|
|
|
def write_pacman_output(path):
|
|
out_file = tempfile.NamedTemporaryFile("wt")
|
|
proc = subprocess.Popen(["pacman", "-Q", "--dbpath", str(path)], stdout=out_file)
|
|
proc.wait()
|
|
return out_file
|
|
|
|
|
|
def diff_tempfiles(old, new):
|
|
subprocess.Popen(["diff", old.name, new.name, "--color=always", "--minimal"])
|
|
|
|
|
|
if __name__ == "__main__":
|
|
snapshot_data = get_snapshot_after_datetime(get_last_boot())
|
|
snapshot_root = get_snapshot_path(snapshot_data)
|
|
db_root = "var/lib/pacman"
|
|
old = write_pacman_output(snapshot_root / db_root)
|
|
new = write_pacman_output(Path(snapshot_data["subvolume"]) / db_root)
|
|
diff_tempfiles(old, new)
|