btrfs_snapshot.py 2.0 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162
  1. #!/usr/bin/env python2
  2. # -*- coding:utf-8 -*-
  3. import sh
  4. import os
  5. from datetime import datetime
  6. from .hook import JobHook
  7. class BtrfsVolumeError(Exception):
  8. pass
  9. class BtrfsHook(JobHook):
  10. def __init__(self, service_dir, working_dir, gc_dir):
  11. self.service_dir = service_dir
  12. self.working_dir = working_dir
  13. self.gc_dir = gc_dir
  14. def before_job(self, ctx={}, *args, **kwargs):
  15. self._create_working_snapshot()
  16. ctx['current_dir'] = self.working_dir
  17. def after_job(self, status=None, ctx={}, *args, **kwargs):
  18. if status == "success":
  19. self._commit_changes()
  20. ctx['current_dir'] = self.service_dir
  21. def _ensure_subvolume(self):
  22. # print(self.service_dir)
  23. try:
  24. ret = sh.btrfs("subvolume", "show", self.service_dir)
  25. except Exception, e:
  26. print(e)
  27. raise BtrfsVolumeError("Invalid subvolume")
  28. if ret.stderr != '':
  29. raise BtrfsVolumeError("Invalid subvolume")
  30. def _create_working_snapshot(self):
  31. self._ensure_subvolume()
  32. if os.path.exists(self.working_dir):
  33. print("Warning: working dir existed, are you sure no rsync job is running?")
  34. else:
  35. # print("btrfs subvolume snapshot {} {}".format(self.service_dir, self.working_dir))
  36. sh.btrfs("subvolume", "snapshot", self.service_dir, self.working_dir)
  37. def _commit_changes(self):
  38. self._ensure_subvolume()
  39. self._ensure_subvolume()
  40. gc_dir = self.gc_dir.format(timestamp=datetime.now().strftime("%s"))
  41. out = sh.mv(self.service_dir, gc_dir)
  42. assert out.exit_code == 0 and out.stderr == ""
  43. out = sh.mv(self.working_dir, self.service_dir)
  44. assert out.exit_code == 0 and out.stderr == ""
  45. # print("btrfs subvolume delete {}".format(self.tmp_dir))
  46. # sh.sleep(3)
  47. # out = sh.btrfs("subvolume", "delete", self.tmp_dir)
  48. # assert out.exit_code == 0 and out.stderr == ""
  49. # vim: ts=4 sw=4 sts=4 expandtab