diff --git a/borgmatic/borg/create.py b/borgmatic/borg/create.py index 6ccf3cd1f..12c0b3b7d 100644 --- a/borgmatic/borg/create.py +++ b/borgmatic/borg/create.py @@ -208,7 +208,6 @@ def create_archive( # The progress output isn't compatible with captured and logged output, as progress messes with # the terminal directly. - # FIXME: "--progress" and stream_processes can't be used together. if progress: execute_command_without_capture(full_command, error_on_warnings=False) return diff --git a/borgmatic/hooks/mysql.py b/borgmatic/hooks/mysql.py index 82530d121..49e2ea040 100644 --- a/borgmatic/hooks/mysql.py +++ b/borgmatic/hooks/mysql.py @@ -126,7 +126,9 @@ def remove_database_dumps(databases, log_prefix, location_config, dry_run): # p ) -def make_database_dump_pattern(databases, log_prefix, location_config, name=None): +def make_database_dump_pattern( + databases, log_prefix, location_config, name=None +): # pragma: no cover ''' Given a sequence of configurations dicts, a prefix to log with, a location configuration dict, and a database name to match, return the corresponding glob patterns to match the database dump diff --git a/borgmatic/hooks/postgresql.py b/borgmatic/hooks/postgresql.py index 52037f1d7..d81374039 100644 --- a/borgmatic/hooks/postgresql.py +++ b/borgmatic/hooks/postgresql.py @@ -83,7 +83,9 @@ def remove_database_dumps(databases, log_prefix, location_config, dry_run): # p ) -def make_database_dump_pattern(databases, log_prefix, location_config, name=None): +def make_database_dump_pattern( + databases, log_prefix, location_config, name=None +): # pragma: no cover ''' Given a sequence of configurations dicts, a prefix to log with, a location configuration dict, and a database name to match, return the corresponding glob patterns to match the database dump diff --git a/tests/unit/borg/test_create.py b/tests/unit/borg/test_create.py index 68543718d..428df2d25 100644 --- a/tests/unit/borg/test_create.py +++ b/tests/unit/borg/test_create.py @@ -1179,3 +1179,31 @@ def test_create_archive_with_extra_borg_options_calls_borg_with_extra_options(): }, storage_config={'extra_borg_options': {'create': '--extra --options'}}, ) + + +def test_create_archive_with_stream_processes_calls_borg_with_processes(): + processes = flexmock() + flexmock(module).should_receive('borgmatic_source_directories').and_return([]) + flexmock(module).should_receive('_expand_directories').and_return(('foo', 'bar')) + flexmock(module).should_receive('_expand_home_directories').and_return(()) + flexmock(module).should_receive('_write_pattern_file').and_return(None) + flexmock(module).should_receive('_make_pattern_flags').and_return(()) + flexmock(module).should_receive('_make_exclude_flags').and_return(()) + flexmock(module).should_receive('execute_command_with_processes').with_args( + ('borg', 'create', '--read-special') + ARCHIVE_WITH_PATHS, + processes=processes, + output_log_level=logging.INFO, + error_on_warnings=False, + ) + + module.create_archive( + dry_run=False, + repository='repo', + location_config={ + 'source_directories': ['foo', 'bar'], + 'repositories': ['repo'], + 'exclude_patterns': None, + }, + storage_config={}, + stream_processes=processes, + ) diff --git a/tests/unit/borg/test_extract.py b/tests/unit/borg/test_extract.py index f6c904e3e..3723dc418 100644 --- a/tests/unit/borg/test_extract.py +++ b/tests/unit/borg/test_extract.py @@ -238,6 +238,31 @@ def test_extract_archive_calls_borg_with_progress_parameter(): ) +def test_extract_archive_calls_borg_with_stdout_parameter_and_returns_process(): + flexmock(module.os.path).should_receive('abspath').and_return('repo') + process = flexmock() + flexmock(module).should_receive('execute_command').with_args( + ('borg', 'extract', '--stdout', 'repo::archive'), + output_file=module.subprocess.PIPE, + working_directory=None, + error_on_warnings=True, + run_to_completion=False, + ).and_return(process).once() + + assert ( + module.extract_archive( + dry_run=False, + repository='repo', + archive='archive', + paths=None, + location_config={}, + storage_config={}, + extract_to_stdout=True, + ) + == process + ) + + def test_extract_archive_skips_abspath_for_remote_repository(): flexmock(module.os.path).should_receive('abspath').never() flexmock(module).should_receive('execute_command').with_args( diff --git a/tests/unit/hooks/test_dump.py b/tests/unit/hooks/test_dump.py index 9bcabc089..dd5efa78d 100644 --- a/tests/unit/hooks/test_dump.py +++ b/tests/unit/hooks/test_dump.py @@ -34,6 +34,14 @@ def test_make_database_dump_filename_with_invalid_name_raises(): module.make_database_dump_filename('databases', 'invalid/name') +def test_create_named_pipe_for_dump_does_not_raise(): + flexmock(module.os).should_receive('makedirs') + flexmock(module.os.path).should_receive('exists').and_return(False) + flexmock(module.os).should_receive('mkfifo') + + module.create_named_pipe_for_dump('/path/to/pipe') + + def test_remove_database_dumps_removes_dump_for_each_database(): databases = [{'name': 'foo'}, {'name': 'bar'}] flexmock(module).should_receive('make_database_dump_filename').with_args( diff --git a/tests/unit/hooks/test_mysql.py b/tests/unit/hooks/test_mysql.py index 53661fb71..abe837584 100644 --- a/tests/unit/hooks/test_mysql.py +++ b/tests/unit/hooks/test_mysql.py @@ -263,3 +263,13 @@ def test_restore_database_dump_runs_mysql_with_username_and_password(): module.restore_database_dump( database_config, 'test.yaml', {}, dry_run=False, extract_process=extract_process ) + + +def test_restore_database_dump_with_dry_run_skips_restore(): + database_config = [{'name': 'foo'}] + + flexmock(module).should_receive('execute_command_with_processes').never() + + module.restore_database_dump( + database_config, 'test.yaml', {}, dry_run=True, extract_process=flexmock() + ) diff --git a/tests/unit/hooks/test_postgresql.py b/tests/unit/hooks/test_postgresql.py index 144426750..1f9533289 100644 --- a/tests/unit/hooks/test_postgresql.py +++ b/tests/unit/hooks/test_postgresql.py @@ -336,3 +336,13 @@ def test_restore_database_dump_runs_psql_for_all_database_dump(): module.restore_database_dump( database_config, 'test.yaml', {}, dry_run=False, extract_process=extract_process ) + + +def test_restore_database_dump_with_dry_run_skips_restore(): + database_config = [{'name': 'foo'}] + + flexmock(module).should_receive('execute_command_with_processes').never() + + module.restore_database_dump( + database_config, 'test.yaml', {}, dry_run=True, extract_process=flexmock() + )