adding a test class for each supported mode and fixing some related bugs
authorEduardo Robles Elvira <edulix@wadobo.com>
Sat, 27 Jul 2013 08:17:15 +0000 (10:17 +0200)
committerEduardo Robles Elvira <edulix@wadobo.com>
Sat, 27 Jul 2013 08:17:15 +0000 (10:17 +0200)
deltatar/deltatar.py
runtests.py
testing/test_deltatar.py

index 4b3e667..297fe30 100644 (file)
@@ -53,9 +53,9 @@ class DeltaTar(object):
     # by default. The function receives a file path and must return a boolean.
     filter_func = None
 
-    # mode in which the delta will be created (when creating a backup ) or
-    # opened (when restoring). Accepts the same modes as the tarfile library.
-    mode = "r#gz"
+    # mode in which the delta will be created (when creating a backup) or
+    # opened (when restoring). Accepts modes analog to the tarfile library.
+    mode = ""
 
     # used together with aes modes to encrypt and decrypt backups.
     password = None
@@ -72,33 +72,22 @@ class DeltaTar(object):
 
     # valid tarfile modes and their corresponding default file extension
     __file_extensions_dict = {
-        'r:': 'tar',
-        'r:gz': 'tar.gz',
-        'r:bz2': 'tar.bz2',
-        'w': 'tar',
-        'w:gz': 'tar.gz',
-        'w:bz2': 'tar.bz2',
-
-        'r|': 'tar',
-        'r|gz': 'tar.gz',
-        'r|bz2': 'tar.bz2',
-        'w|': 'tar',
-        'w|gz': 'tar.gz',
-        'w|bz2': 'tar.bz2',
-
-        'r#gz': 'tar.gz',
-        'w#gz': 'tar.gz',
-
-        'r#gz.aes128': 'tar.gz.aes128',
-        'w#gz.aes128': 'tar.gz.aes128',
-        'r#gz.aes256': 'tar.gz.aes256',
-        'w#gz.aes256': 'tar.gz.aes256'
+        '': '',
+        ':': '',
+        ':gz': '.gz',
+        ':bz2': '.bz2',
+        '|': '',
+        '|gz': '.gz',
+        '|bz2': '.bz2',
+        '#gz': '.gz',
+        '#gz.aes128': '.gz.aes128',
+        '#gz.aes256': '.gz.aes256'
     }
 
     def __init__(self, excluded_files=[], included_files=[],
-                 filter_func=None, mode="r#gz", password=None,
+                 filter_func=None, mode="", password=None,
                  logger=None,
-                 index_encrypted=True, index_name_func=None,
+                 index_encrypted=False, index_name_func=None,
                  volume_name_func=None):
         '''
         Constructor. Configures the diff engine.
@@ -122,26 +111,16 @@ class DeltaTar(object):
           or opened (when restoring). Accepts the same modes as the tarfile
           library. Valid modes are:
 
-           'r:'         open for reading exclusively uncompressed
-           'r:gz'       open for reading with gzip compression
-           'r:bz2'      open for reading with bzip2 compression
-           'w:gz'       open for writing with gzip compression
-           'w:bz2'      open for writing with bzip2 compression
-
-           'r|'         open an uncompressed stream of tar blocks for reading
-           'r|gz'       open a gzip compressed stream of tar blocks
-           'r|bz2'      open a bzip2 compressed stream of tar blocks
-           'w|'         open an uncompressed stream for writing
-           'w|gz'       open a gzip compressed stream for writing
-           'w|bz2'      open a bzip2 compressed stream for writing
-
-           'r#gz'       open a stream of gzip compressed tar blocks for reading
-           'w#gz'       open a stream of gzip compressed tar blocks for writing
-
-           'r#gz.aes128'   open an aes128 encrypted stream of gzip compressed tar blocks for reading
-           'w#gz.aes128'   open an aes128 encrypted stream of gzip compressed tar blocks for writing
-           'r#gz.aes256'   open an aes256 encrypted stream of gzip compressed tar blocks for reading
-           'w#gz.aes256'   open an aes256 encrypted stream of gzip compressed tar blocks for writing
+           ''          open uncompressed
+           ':'         open uncompressed
+           ':gz'       open with gzip compression
+           ':bz2'      open with bzip2 compression
+           '|'         open an uncompressed stream of tar blocks
+           '|gz'       open a gzip compressed stream of tar blocks
+           '|bz2'      open a bzip2 compressed stream of tar blocks
+           '#gz'       open a stream of gzip compressed tar blocks
+           '#gz.aes128'   open an aes128 encrypted stream of gzip compressed tar blocks
+           '#gz.aes256'   open an aes256 encrypted stream of gzip compressed tar blocks
 
         - password: used together with aes modes to encrypt and decrypt backups.
 
@@ -161,7 +140,7 @@ class DeltaTar(object):
           DeltaTar has default names for tar volumes.
         '''
 
-        if self.mode not in self.__file_extensions_dict:
+        if mode not in self.__file_extensions_dict:
             raise Exception('Unrecognized extension')
 
         self.excluded_files = excluded_files
@@ -192,17 +171,10 @@ class DeltaTar(object):
         date_str = self.current_time.strftime("%y-%m-%d-%H%M")
         extension = ''
 
-        if 'gz' in self.mode:
-            extension += ".gz"
-        elif 'bz2' in self.mode:
-            extension += ".bz2"
-
-        if self.index_encrypted and 'aes128' in self.mode:
-            extension += ".aes128"
-        elif self.index_encrypted and 'aes256' in self.mode:
-            extension += ".aes256"
+        if self.index_encrypted and 'aes' in self.mode:
+            extension = self.__file_extensions_dict[self.mode]
 
-        return "%s-%s-index.%s" % (prefix, date_str, extension)
+        return "%s-%s.index%s" % (prefix, date_str, extension)
 
     def volume_name_func(self, backup_path, is_full, volume_number):
         '''
@@ -215,7 +187,7 @@ class DeltaTar(object):
         date_str = self.current_time.strftime("%y-%m-%d-%H%M")
         extension = self.__file_extensions_dict[self.mode]
 
-        return "%s-%s-%03d.%s" % (prefix, date_str, volume_number + 1, extension)
+        return "%s-%s-%03d.tar%s" % (prefix, date_str, volume_number + 1, extension)
 
     def _recursive_walk_dir(self, source_path):
         '''
@@ -356,7 +328,7 @@ class DeltaTar(object):
 
         # start creating the tarfile
         tarobj = tarfile.TarFile.open(tarfile_path,
-                              mode=self.mode,
+                              mode='w' + self.mode,
                               format=tarfile.GNU_FORMAT,
                               concat_compression='#gz' in self.mode,
                               password=self.password,
@@ -370,7 +342,7 @@ class DeltaTar(object):
             stat = self._stat_dict(path)
             stat['volume'] = vol_no
             stat['offset'] = tarobj.fileobj.tell() # TODO: check/fix this
-            index_fd.write(json.dumps(self._stat_dict(path)) + '\n')
+            index_fd.write(json.dumps(stat) + '\n')
 
             tarobj.add(path)
 
@@ -381,7 +353,6 @@ class DeltaTar(object):
         os.chdir(cwd)
         tarobj.close()
 
-
     def create_diff_backup(self, source_path, backup_path, previous_index_path,
                            max_volume_size=None):
         '''
@@ -442,7 +413,7 @@ class DeltaTar(object):
         new_volume_handler = partial(new_volume_handler, self)
 
         tarobj = tarfile.TarFile.open(backup_tar_path,
-                              mode=self.mode,
+                              mode='r' + self.mode,
                               format=tarfile.GNU_FORMAT,
                               concat_compression='#gz' in self.mode,
                               password=self.password,
index 19b3740..b9e6c03 100644 (file)
@@ -23,7 +23,7 @@ from testing.test_multivol import MultivolGnuFormatTest, MultivolPaxFormatTest
 from testing.test_concat_compress import ConcatCompressTest
 from testing.test_rescue_tar import RescueTarTest
 from testing.test_encryption import EncryptionTest
-from testing.test_deltatar import DeltaTarTest
+from testing.test_deltatar import *
 
 if __name__ == "__main__":
     unittest.main()
index fc1e21e..577b0c1 100644 (file)
@@ -31,6 +31,10 @@ class DeltaTarTest(BaseTest):
     """
     Test backups
     """
+    MODE = ''
+
+    PASSWORD = None
+
     def setUp(self):
         '''
         Create base test data
@@ -55,7 +59,8 @@ class DeltaTarTest(BaseTest):
         '''
         Creates a full backup without any filtering and restores it.
         '''
-        deltatar = DeltaTar(mode="w", logger=self.consoleLogger)
+        deltatar = DeltaTar(mode=self.MODE, password=self.PASSWORD,
+                            logger=self.consoleLogger)
 
         # create first backup
         deltatar.create_full_backup(
@@ -68,7 +73,6 @@ class DeltaTarTest(BaseTest):
         tar_filename = deltatar.volume_name_func('backup_dir', True, 0)
         tar_path = os.path.join("backup_dir", tar_filename)
 
-        deltatar.mode = 'r'
         deltatar.restore_backup(target_path="source_dir",
                                 backup_tar_path=tar_path)
 
@@ -76,3 +80,75 @@ class DeltaTarTest(BaseTest):
             assert os.path.exists(key)
             if value:
                 assert value == self.md5sum(key)
+
+
+class DeltaTar2Test(DeltaTarTest):
+    '''
+    Same as DeltaTar but with specific ":" mode
+    '''
+    MODE = ':'
+
+
+class DeltaTarStreamTest(DeltaTarTest):
+    '''
+    Same as DeltaTar but with specific uncompressed stream mode
+    '''
+    MODE = '|'
+
+
+class DeltaTarGzipTest(DeltaTarTest):
+    '''
+    Same as DeltaTar but with specific gzip mode
+    '''
+    MODE = ':gz'
+
+
+class DeltaTarBz2Test(DeltaTarTest):
+    '''
+    Same as DeltaTar but with specific bz2 mode
+    '''
+    MODE = ':bz2'
+
+
+class DeltaTarGzipStreamTest(DeltaTarTest):
+    '''
+    Same as DeltaTar but with specific gzip stream mode
+    '''
+    MODE = '|gz'
+
+
+class DeltaTarBz2StreamTest(DeltaTarTest):
+    '''
+    Same as DeltaTar but with specific bz2 stream mode
+    '''
+    MODE = '|bz2'
+
+
+class DeltaTarGzipConcatTest(DeltaTarTest):
+    '''
+    Same as DeltaTar but with specific gzip concat stream mode
+    '''
+    MODE = '#gz'
+
+
+class DeltaTarBz2ConcatTest(DeltaTarTest):
+    '''
+    Same as DeltaTar but with specific bz2 concat stream mode
+    '''
+    MODE = '#bz2'
+
+
+class DeltaTarGzipAes128ConcatTest(DeltaTarTest):
+    '''
+    Same as DeltaTar but with specific gzip aes128 concat stream mode
+    '''
+    MODE = '#gz.aes128'
+    PASSWORD = 'some magic key'
+
+
+class DeltaTarGzipAes256ConcatTest(DeltaTarTest):
+    '''
+    Same as DeltaTar but with specific gzip aes256 concat stream mode
+    '''
+    MODE = '#gz.aes256'
+    PASSWORD = 'some magic key'