Hi everybody,

enclosed is a puny patch I wrote against the script
tools/backup/hot-backup.py.in.

When creating a backup archive of a live repository, the "legacy"
behaviour of the script is simply to call tar.add() on a hotdump copy.
This has, however, an inconvenience when the original repository is on
a POSIX filesystem and the hotcopy dump is written e.g. on a CIFS
filesystem, thus leading to a possible "permission leakage".

My patch changes this behaviour by letting the script build up the
archive file by file, and paying special care in copying the
permissions for each file from the repository itself rather than from
the hotcopy dump.

Do you think it would be useful?

Regards,
Roberto
[[[

* tools/backup/hot-backup.py.in: Always save correct file
  permissions in tar archives.

]]]


Index: tools/backup/hot-backup.py.in
===================================================================
--- tools/backup/hot-backup.py.in       (revision 1706408)
+++ tools/backup/hot-backup.py.in       (working copy)
@@ -292,7 +292,26 @@ if archive_type:
     try:
       import tarfile
       tar = tarfile.open(archive_path, 'w:' + archive_type)
-      tar.add(backup_subdir, os.path.basename(backup_subdir))
+      # Build up the archive file by file, paying special care
+      # in replicating the permissions for each file from
+      # the repository itself rather than from the hotcopy dump.
+      # This can be useful in such cases when the original
+      # repository is on a POSIX filesystem and the hotcopy
+      # dump is written e.g. on a CIFS filesystem, thus leading
+      # to a possible "permission leakage" were the archive
+      # built directly from hotcopy dump via tar.add().
+      for dirpath, dirnames, filenames in os.walk(backup_subdir, 
followlinks=True):
+        for leafname in dirnames + filenames:
+          backup_based_path = os.path.join(dirpath, leafname)
+          relpath = os.path.relpath(backup_based_path, backup_subdir)
+          repo_based_path = os.path.join(repo_dir, relpath)
+          tarinfo = tar.gettarinfo(backup_based_path, os.path.join(repo, 
relpath))
+          tarinfo.mode = os.stat(repo_based_path).st_mode
+          if tarinfo.isreg():
+            with open(backup_based_path, "rb") as f:
+              tar.addfile(tarinfo, f)
+          else:
+            tar.addfile(tarinfo)
       tar.close()
     except ImportError, e:
       err_msg = "Import failed: " + str(e)

Reply via email to