Jelajahi Sumber

Working directory option to support source directories with relative paths (#431).

Reviewed-on: https://projects.torsion.org/borgmatic-collective/borgmatic/pulls/477
Dan Helfman 3 tahun lalu
induk
melakukan
0eb2634f9b
3 mengubah file dengan 60 tambahan dan 1 penghapusan
  1. 12 1
      borgmatic/borg/create.py
  2. 8 0
      borgmatic/config/schema.yaml
  3. 40 0
      tests/unit/borg/test_create.py

+ 12 - 1
borgmatic/borg/create.py

@@ -213,6 +213,10 @@ def create_archive(
         )
     )
 
+    try:
+        working_directory = os.path.expanduser(location_config.get('working_directory'))
+    except TypeError:
+        working_directory = None
     pattern_file = _write_pattern_file(location_config.get('patterns'))
     exclude_file = _write_pattern_file(
         _expand_home_directories(location_config.get('exclude_patterns'))
@@ -309,6 +313,13 @@ def create_archive(
             output_log_level,
             output_file,
             borg_local_path=local_path,
+            working_directory=working_directory,
         )
 
-    return execute_command(full_command, output_log_level, output_file, borg_local_path=local_path)
+    return execute_command(
+        full_command,
+        output_log_level,
+        output_file,
+        borg_local_path=local_path,
+        working_directory=working_directory,
+    )

+ 8 - 0
borgmatic/config/schema.yaml

@@ -42,6 +42,14 @@ properties:
                 example:
                     - user@backupserver:sourcehostname.borg
                     - "user@backupserver:{fqdn}"
+            working_directory:
+                type: string
+                description: |
+                    Working directory for the "borg create" command. Tildes are
+                    expanded. Useful for backing up using relative paths. See
+                    http://borgbackup.readthedocs.io/en/stable/usage/create.html
+                    for details. Defaults to not set.
+                example: /path/to/working/directory
             one_file_system:
                 type: boolean
                 description: |

+ 40 - 0
tests/unit/borg/test_create.py

@@ -277,6 +277,7 @@ def test_create_archive_calls_borg_with_parameters():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -310,6 +311,7 @@ def test_create_archive_with_patterns_calls_borg_with_patterns():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -343,6 +345,7 @@ def test_create_archive_with_exclude_patterns_calls_borg_with_excludes():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -373,6 +376,7 @@ def test_create_archive_with_log_info_calls_borg_with_info_parameter():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
     insert_logging_mock(logging.INFO)
 
@@ -404,6 +408,7 @@ def test_create_archive_with_log_info_and_json_suppresses_most_borg_output():
         output_log_level=None,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
     insert_logging_mock(logging.INFO)
 
@@ -436,6 +441,7 @@ def test_create_archive_with_log_debug_calls_borg_with_debug_parameter():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
     insert_logging_mock(logging.DEBUG)
 
@@ -467,6 +473,7 @@ def test_create_archive_with_log_debug_and_json_suppresses_most_borg_output():
         output_log_level=None,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
     insert_logging_mock(logging.DEBUG)
 
@@ -499,6 +506,7 @@ def test_create_archive_with_dry_run_calls_borg_with_dry_run_parameter():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -531,6 +539,7 @@ def test_create_archive_with_stats_and_dry_run_calls_borg_without_stats_paramete
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
     insert_logging_mock(logging.INFO)
 
@@ -563,6 +572,7 @@ def test_create_archive_with_checkpoint_interval_calls_borg_with_checkpoint_inte
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -593,6 +603,7 @@ def test_create_archive_with_chunker_params_calls_borg_with_chunker_params_param
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -623,6 +634,7 @@ def test_create_archive_with_compression_calls_borg_with_compression_parameters(
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -658,6 +670,7 @@ def test_create_archive_with_remote_rate_limit_calls_borg_with_upload_ratelimit_
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -688,6 +701,7 @@ def test_create_archive_with_one_file_system_calls_borg_with_one_file_system_par
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -724,6 +738,7 @@ def test_create_archive_with_numeric_owner_calls_borg_with_numeric_ids_parameter
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -755,6 +770,7 @@ def test_create_archive_with_read_special_calls_borg_with_read_special_parameter
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -835,6 +851,7 @@ def test_create_archive_with_atime_option_calls_borg_with_corresponding_paramete
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -877,6 +894,7 @@ def test_create_archive_with_bsd_flags_option_calls_borg_with_corresponding_para
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -908,6 +926,7 @@ def test_create_archive_with_files_cache_calls_borg_with_files_cache_parameters(
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -939,6 +958,7 @@ def test_create_archive_with_local_path_calls_borg_via_local_path():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg1',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -970,6 +990,7 @@ def test_create_archive_with_remote_path_calls_borg_with_remote_path_parameters(
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -1001,6 +1022,7 @@ def test_create_archive_with_umask_calls_borg_with_umask_parameters():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -1031,6 +1053,7 @@ def test_create_archive_with_lock_wait_calls_borg_with_lock_wait_parameters():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -1061,6 +1084,7 @@ def test_create_archive_with_stats_calls_borg_with_stats_parameter_and_warning_o
         output_log_level=logging.WARNING,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -1092,6 +1116,7 @@ def test_create_archive_with_stats_and_log_info_calls_borg_with_stats_parameter_
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
     insert_logging_mock(logging.INFO)
 
@@ -1124,6 +1149,7 @@ def test_create_archive_with_files_calls_borg_with_list_parameter_and_warning_ou
         output_log_level=logging.WARNING,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -1155,6 +1181,7 @@ def test_create_archive_with_files_and_log_info_calls_borg_with_list_parameter_a
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
     insert_logging_mock(logging.INFO)
 
@@ -1187,6 +1214,7 @@ def test_create_archive_with_progress_and_log_info_calls_borg_with_progress_para
         output_log_level=logging.INFO,
         output_file=module.DO_NOT_CAPTURE,
         borg_local_path='borg',
+        working_directory=None,
     )
     insert_logging_mock(logging.INFO)
 
@@ -1219,6 +1247,7 @@ def test_create_archive_with_progress_calls_borg_with_progress_parameter():
         output_log_level=logging.INFO,
         output_file=module.DO_NOT_CAPTURE,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -1253,6 +1282,7 @@ def test_create_archive_with_progress_and_stream_processes_calls_borg_with_progr
         output_log_level=logging.INFO,
         output_file=module.DO_NOT_CAPTURE,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -1285,6 +1315,7 @@ def test_create_archive_with_json_calls_borg_with_json_parameter():
         output_log_level=None,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     ).and_return('[]')
 
     json_output = module.create_archive(
@@ -1318,6 +1349,7 @@ def test_create_archive_with_stats_and_json_calls_borg_without_stats_parameter()
         output_log_level=None,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     ).and_return('[]')
 
     json_output = module.create_archive(
@@ -1352,6 +1384,7 @@ def test_create_archive_with_source_directories_glob_expands():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
     flexmock(module.glob).should_receive('glob').with_args('foo*').and_return(['foo', 'food'])
 
@@ -1383,6 +1416,7 @@ def test_create_archive_with_non_matching_source_directories_glob_passes_through
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
     flexmock(module.glob).should_receive('glob').with_args('foo*').and_return([])
 
@@ -1414,6 +1448,7 @@ def test_create_archive_with_glob_calls_borg_with_expanded_directories():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -1444,6 +1479,7 @@ def test_create_archive_with_archive_name_format_calls_borg_with_archive_name():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -1474,6 +1510,7 @@ def test_create_archive_with_archive_name_format_accepts_borg_placeholders():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -1504,6 +1541,7 @@ def test_create_archive_with_repository_accepts_borg_placeholders():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -1534,6 +1572,7 @@ def test_create_archive_with_extra_borg_options_calls_borg_with_extra_options():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(
@@ -1566,6 +1605,7 @@ def test_create_archive_with_stream_processes_calls_borg_with_processes():
         output_log_level=logging.INFO,
         output_file=None,
         borg_local_path='borg',
+        working_directory=None,
     )
 
     module.create_archive(