test_check.py 27 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722
  1. import logging
  2. import pytest
  3. from flexmock import flexmock
  4. from borgmatic.borg import check as module
  5. from ..test_verbosity import insert_logging_mock
  6. def insert_execute_command_mock(command):
  7. flexmock(module.environment).should_receive('make_environment')
  8. flexmock(module).should_receive('execute_command').with_args(
  9. command, extra_environment=None
  10. ).once()
  11. def insert_execute_command_never():
  12. flexmock(module).should_receive('execute_command').never()
  13. def test_parse_checks_returns_them_as_tuple():
  14. checks = module.parse_checks({'checks': [{'name': 'foo'}, {'name': 'bar'}]})
  15. assert checks == ('foo', 'bar')
  16. def test_parse_checks_with_missing_value_returns_defaults():
  17. checks = module.parse_checks({})
  18. assert checks == ('repository', 'archives')
  19. def test_parse_checks_with_empty_list_returns_defaults():
  20. checks = module.parse_checks({'checks': []})
  21. assert checks == ('repository', 'archives')
  22. def test_parse_checks_with_none_value_returns_defaults():
  23. checks = module.parse_checks({'checks': None})
  24. assert checks == ('repository', 'archives')
  25. def test_parse_checks_with_disabled_returns_no_checks():
  26. checks = module.parse_checks({'checks': [{'name': 'foo'}, {'name': 'disabled'}]})
  27. assert checks == ()
  28. def test_parse_checks_prefers_override_checks_to_configured_checks():
  29. checks = module.parse_checks(
  30. {'checks': [{'name': 'archives'}]}, only_checks=['repository', 'extract']
  31. )
  32. assert checks == ('repository', 'extract')
  33. @pytest.mark.parametrize(
  34. 'frequency,expected_result',
  35. (
  36. (None, None),
  37. ('always', None),
  38. ('1 hour', module.datetime.timedelta(hours=1)),
  39. ('2 hours', module.datetime.timedelta(hours=2)),
  40. ('1 day', module.datetime.timedelta(days=1)),
  41. ('2 days', module.datetime.timedelta(days=2)),
  42. ('1 week', module.datetime.timedelta(weeks=1)),
  43. ('2 weeks', module.datetime.timedelta(weeks=2)),
  44. ('1 month', module.datetime.timedelta(days=30)),
  45. ('2 months', module.datetime.timedelta(days=60)),
  46. ('1 year', module.datetime.timedelta(days=365)),
  47. ('2 years', module.datetime.timedelta(days=365 * 2)),
  48. ),
  49. )
  50. def test_parse_frequency_parses_into_timedeltas(frequency, expected_result):
  51. assert module.parse_frequency(frequency) == expected_result
  52. @pytest.mark.parametrize(
  53. 'frequency', ('sometime', 'x days', '3 decades',),
  54. )
  55. def test_parse_frequency_raises_on_parse_error(frequency):
  56. with pytest.raises(ValueError):
  57. module.parse_frequency(frequency)
  58. def test_filter_checks_on_frequency_without_config_uses_default_checks():
  59. flexmock(module).should_receive('parse_frequency').and_return(
  60. module.datetime.timedelta(weeks=4)
  61. )
  62. flexmock(module).should_receive('make_check_time_path')
  63. flexmock(module).should_receive('read_check_time').and_return(None)
  64. assert module.filter_checks_on_frequency(
  65. location_config={},
  66. consistency_config={},
  67. borg_repository_id='repo',
  68. checks=('repository', 'archives'),
  69. force=False,
  70. ) == ('repository', 'archives')
  71. def test_filter_checks_on_frequency_retains_unconfigured_check():
  72. assert module.filter_checks_on_frequency(
  73. location_config={},
  74. consistency_config={},
  75. borg_repository_id='repo',
  76. checks=('data',),
  77. force=False,
  78. ) == ('data',)
  79. def test_filter_checks_on_frequency_retains_check_without_frequency():
  80. flexmock(module).should_receive('parse_frequency').and_return(None)
  81. assert module.filter_checks_on_frequency(
  82. location_config={},
  83. consistency_config={'checks': [{'name': 'archives'}]},
  84. borg_repository_id='repo',
  85. checks=('archives',),
  86. force=False,
  87. ) == ('archives',)
  88. def test_filter_checks_on_frequency_retains_check_with_elapsed_frequency():
  89. flexmock(module).should_receive('parse_frequency').and_return(
  90. module.datetime.timedelta(hours=1)
  91. )
  92. flexmock(module).should_receive('make_check_time_path')
  93. flexmock(module).should_receive('read_check_time').and_return(
  94. module.datetime.datetime(year=module.datetime.MINYEAR, month=1, day=1)
  95. )
  96. assert module.filter_checks_on_frequency(
  97. location_config={},
  98. consistency_config={'checks': [{'name': 'archives', 'frequency': '1 hour'}]},
  99. borg_repository_id='repo',
  100. checks=('archives',),
  101. force=False,
  102. ) == ('archives',)
  103. def test_filter_checks_on_frequency_retains_check_with_missing_check_time_file():
  104. flexmock(module).should_receive('parse_frequency').and_return(
  105. module.datetime.timedelta(hours=1)
  106. )
  107. flexmock(module).should_receive('make_check_time_path')
  108. flexmock(module).should_receive('read_check_time').and_return(None)
  109. assert module.filter_checks_on_frequency(
  110. location_config={},
  111. consistency_config={'checks': [{'name': 'archives', 'frequency': '1 hour'}]},
  112. borg_repository_id='repo',
  113. checks=('archives',),
  114. force=False,
  115. ) == ('archives',)
  116. def test_filter_checks_on_frequency_skips_check_with_unelapsed_frequency():
  117. flexmock(module).should_receive('parse_frequency').and_return(
  118. module.datetime.timedelta(hours=1)
  119. )
  120. flexmock(module).should_receive('make_check_time_path')
  121. flexmock(module).should_receive('read_check_time').and_return(module.datetime.datetime.now())
  122. assert (
  123. module.filter_checks_on_frequency(
  124. location_config={},
  125. consistency_config={'checks': [{'name': 'archives', 'frequency': '1 hour'}]},
  126. borg_repository_id='repo',
  127. checks=('archives',),
  128. force=False,
  129. )
  130. == ()
  131. )
  132. def test_filter_checks_on_frequency_restains_check_with_unelapsed_frequency_and_force():
  133. assert module.filter_checks_on_frequency(
  134. location_config={},
  135. consistency_config={'checks': [{'name': 'archives', 'frequency': '1 hour'}]},
  136. borg_repository_id='repo',
  137. checks=('archives',),
  138. force=True,
  139. ) == ('archives',)
  140. def test_make_check_flags_with_repository_check_returns_flag():
  141. flexmock(module.feature).should_receive('available').and_return(True)
  142. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  143. flags = module.make_check_flags('1.2.3', {}, ('repository',))
  144. assert flags == ('--repository-only',)
  145. def test_make_check_flags_with_archives_check_returns_flag():
  146. flexmock(module.feature).should_receive('available').and_return(True)
  147. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  148. flags = module.make_check_flags('1.2.3', {}, ('archives',))
  149. assert flags == ('--archives-only',)
  150. def test_make_check_flags_with_data_check_returns_flag_and_implies_archives():
  151. flexmock(module.feature).should_receive('available').and_return(True)
  152. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  153. flags = module.make_check_flags('1.2.3', {}, ('data',))
  154. assert flags == ('--archives-only', '--verify-data',)
  155. def test_make_check_flags_with_extract_omits_extract_flag():
  156. flexmock(module.feature).should_receive('available').and_return(True)
  157. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  158. flags = module.make_check_flags('1.2.3', {}, ('extract',))
  159. assert flags == ()
  160. def test_make_check_flags_with_repository_and_data_checks_does_not_return_repository_only():
  161. flexmock(module.feature).should_receive('available').and_return(True)
  162. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  163. flags = module.make_check_flags('1.2.3', {}, ('repository', 'data',))
  164. assert flags == ('--verify-data',)
  165. def test_make_check_flags_with_default_checks_and_prefix_returns_default_flags():
  166. flexmock(module.feature).should_receive('available').and_return(True)
  167. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  168. flags = module.make_check_flags('1.2.3', {}, ('repository', 'archives'), prefix='foo',)
  169. assert flags == ('--match-archives', 'sh:foo*')
  170. def test_make_check_flags_with_all_checks_and_prefix_returns_default_flags():
  171. flexmock(module.feature).should_receive('available').and_return(True)
  172. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  173. flags = module.make_check_flags(
  174. '1.2.3', {}, ('repository', 'archives', 'extract'), prefix='foo',
  175. )
  176. assert flags == ('--match-archives', 'sh:foo*')
  177. def test_make_check_flags_with_all_checks_and_prefix_without_borg_features_returns_glob_archives_flags():
  178. flexmock(module.feature).should_receive('available').and_return(False)
  179. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  180. flags = module.make_check_flags(
  181. '1.2.3', {}, ('repository', 'archives', 'extract'), prefix='foo',
  182. )
  183. assert flags == ('--glob-archives', 'foo*')
  184. def test_make_check_flags_with_archives_check_and_last_includes_last_flag():
  185. flexmock(module.feature).should_receive('available').and_return(True)
  186. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  187. flags = module.make_check_flags('1.2.3', {}, ('archives',), check_last=3)
  188. assert flags == ('--archives-only', '--last', '3')
  189. def test_make_check_flags_with_data_check_and_last_includes_last_flag():
  190. flexmock(module.feature).should_receive('available').and_return(True)
  191. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  192. flags = module.make_check_flags('1.2.3', {}, ('data',), check_last=3)
  193. assert flags == ('--archives-only', '--last', '3', '--verify-data')
  194. def test_make_check_flags_with_repository_check_and_last_omits_last_flag():
  195. flexmock(module.feature).should_receive('available').and_return(True)
  196. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  197. flags = module.make_check_flags('1.2.3', {}, ('repository',), check_last=3)
  198. assert flags == ('--repository-only',)
  199. def test_make_check_flags_with_default_checks_and_last_includes_last_flag():
  200. flexmock(module.feature).should_receive('available').and_return(True)
  201. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  202. flags = module.make_check_flags('1.2.3', {}, ('repository', 'archives'), check_last=3)
  203. assert flags == ('--last', '3')
  204. def test_make_check_flags_with_archives_check_and_prefix_includes_match_archives_flag():
  205. flexmock(module.feature).should_receive('available').and_return(True)
  206. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  207. flags = module.make_check_flags('1.2.3', {}, ('archives',), prefix='foo-')
  208. assert flags == ('--archives-only', '--match-archives', 'sh:foo-*')
  209. def test_make_check_flags_with_data_check_and_prefix_includes_match_archives_flag():
  210. flexmock(module.feature).should_receive('available').and_return(True)
  211. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  212. flags = module.make_check_flags('1.2.3', {}, ('data',), prefix='foo-')
  213. assert flags == ('--archives-only', '--match-archives', 'sh:foo-*', '--verify-data')
  214. def test_make_check_flags_with_archives_check_and_empty_prefix_uses_archive_name_format_instead():
  215. flexmock(module.feature).should_receive('available').and_return(True)
  216. flexmock(module.flags).should_receive('make_match_archives_flags').with_args(
  217. None, 'bar-{now}', '1.2.3' # noqa: FS003
  218. ).and_return(('--match-archives', 'sh:bar-*'))
  219. flags = module.make_check_flags(
  220. '1.2.3', {'archive_name_format': 'bar-{now}'}, ('archives',), prefix='' # noqa: FS003
  221. )
  222. assert flags == ('--archives-only', '--match-archives', 'sh:bar-*')
  223. def test_make_check_flags_with_archives_check_and_none_prefix_omits_match_archives_flag():
  224. flexmock(module.feature).should_receive('available').and_return(True)
  225. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  226. flags = module.make_check_flags('1.2.3', {}, ('archives',), prefix=None)
  227. assert flags == ('--archives-only',)
  228. def test_make_check_flags_with_repository_check_and_prefix_omits_match_archives_flag():
  229. flexmock(module.feature).should_receive('available').and_return(True)
  230. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  231. flags = module.make_check_flags('1.2.3', {}, ('repository',), prefix='foo-')
  232. assert flags == ('--repository-only',)
  233. def test_make_check_flags_with_default_checks_and_prefix_includes_match_archives_flag():
  234. flexmock(module.feature).should_receive('available').and_return(True)
  235. flexmock(module.flags).should_receive('make_match_archives_flags').and_return(())
  236. flags = module.make_check_flags('1.2.3', {}, ('repository', 'archives'), prefix='foo-')
  237. assert flags == ('--match-archives', 'sh:foo-*')
  238. def test_read_check_time_does_not_raise():
  239. flexmock(module.os).should_receive('stat').and_return(flexmock(st_mtime=123))
  240. assert module.read_check_time('/path')
  241. def test_read_check_time_on_missing_file_does_not_raise():
  242. flexmock(module.os).should_receive('stat').and_raise(FileNotFoundError)
  243. assert module.read_check_time('/path') is None
  244. def test_check_archives_with_progress_calls_borg_with_progress_parameter():
  245. checks = ('repository',)
  246. consistency_config = {'check_last': None}
  247. flexmock(module).should_receive('parse_checks')
  248. flexmock(module).should_receive('filter_checks_on_frequency').and_return(checks)
  249. flexmock(module.rinfo).should_receive('display_repository_info').and_return(
  250. '{"repository": {"id": "repo"}}'
  251. )
  252. flexmock(module).should_receive('make_check_flags').and_return(())
  253. flexmock(module).should_receive('execute_command').never()
  254. flexmock(module.flags).should_receive('make_repository_flags').and_return(('repo',))
  255. flexmock(module.environment).should_receive('make_environment')
  256. flexmock(module).should_receive('execute_command').with_args(
  257. ('borg', 'check', '--progress', 'repo'),
  258. output_file=module.DO_NOT_CAPTURE,
  259. extra_environment=None,
  260. ).once()
  261. flexmock(module).should_receive('make_check_time_path')
  262. flexmock(module).should_receive('write_check_time')
  263. module.check_archives(
  264. repository_path='repo',
  265. location_config={},
  266. storage_config={},
  267. consistency_config=consistency_config,
  268. local_borg_version='1.2.3',
  269. progress=True,
  270. )
  271. def test_check_archives_with_repair_calls_borg_with_repair_parameter():
  272. checks = ('repository',)
  273. consistency_config = {'check_last': None}
  274. flexmock(module).should_receive('parse_checks')
  275. flexmock(module).should_receive('filter_checks_on_frequency').and_return(checks)
  276. flexmock(module.rinfo).should_receive('display_repository_info').and_return(
  277. '{"repository": {"id": "repo"}}'
  278. )
  279. flexmock(module).should_receive('make_check_flags').and_return(())
  280. flexmock(module).should_receive('execute_command').never()
  281. flexmock(module.flags).should_receive('make_repository_flags').and_return(('repo',))
  282. flexmock(module.environment).should_receive('make_environment')
  283. flexmock(module).should_receive('execute_command').with_args(
  284. ('borg', 'check', '--repair', 'repo'),
  285. output_file=module.DO_NOT_CAPTURE,
  286. extra_environment=None,
  287. ).once()
  288. flexmock(module).should_receive('make_check_time_path')
  289. flexmock(module).should_receive('write_check_time')
  290. module.check_archives(
  291. repository_path='repo',
  292. location_config={},
  293. storage_config={},
  294. consistency_config=consistency_config,
  295. local_borg_version='1.2.3',
  296. repair=True,
  297. )
  298. @pytest.mark.parametrize(
  299. 'checks',
  300. (
  301. ('repository',),
  302. ('archives',),
  303. ('repository', 'archives'),
  304. ('repository', 'archives', 'other'),
  305. ),
  306. )
  307. def test_check_archives_calls_borg_with_parameters(checks):
  308. check_last = flexmock()
  309. consistency_config = {'check_last': check_last}
  310. flexmock(module).should_receive('parse_checks')
  311. flexmock(module).should_receive('filter_checks_on_frequency').and_return(checks)
  312. flexmock(module.rinfo).should_receive('display_repository_info').and_return(
  313. '{"repository": {"id": "repo"}}'
  314. )
  315. flexmock(module).should_receive('make_check_flags').with_args(
  316. '1.2.3', {}, checks, check_last, prefix=None,
  317. ).and_return(())
  318. flexmock(module.flags).should_receive('make_repository_flags').and_return(('repo',))
  319. insert_execute_command_mock(('borg', 'check', 'repo'))
  320. flexmock(module).should_receive('make_check_time_path')
  321. flexmock(module).should_receive('write_check_time')
  322. module.check_archives(
  323. repository_path='repo',
  324. location_config={},
  325. storage_config={},
  326. consistency_config=consistency_config,
  327. local_borg_version='1.2.3',
  328. )
  329. def test_check_archives_with_json_error_raises():
  330. checks = ('archives',)
  331. check_last = flexmock()
  332. consistency_config = {'check_last': check_last}
  333. flexmock(module).should_receive('parse_checks')
  334. flexmock(module).should_receive('filter_checks_on_frequency').and_return(checks)
  335. flexmock(module.rinfo).should_receive('display_repository_info').and_return(
  336. '{"unexpected": {"id": "repo"}}'
  337. )
  338. with pytest.raises(ValueError):
  339. module.check_archives(
  340. repository_path='repo',
  341. location_config={},
  342. storage_config={},
  343. consistency_config=consistency_config,
  344. local_borg_version='1.2.3',
  345. )
  346. def test_check_archives_with_missing_json_keys_raises():
  347. checks = ('archives',)
  348. check_last = flexmock()
  349. consistency_config = {'check_last': check_last}
  350. flexmock(module).should_receive('parse_checks')
  351. flexmock(module).should_receive('filter_checks_on_frequency').and_return(checks)
  352. flexmock(module.rinfo).should_receive('display_repository_info').and_return('{invalid JSON')
  353. with pytest.raises(ValueError):
  354. module.check_archives(
  355. repository_path='repo',
  356. location_config={},
  357. storage_config={},
  358. consistency_config=consistency_config,
  359. local_borg_version='1.2.3',
  360. )
  361. def test_check_archives_with_extract_check_calls_extract_only():
  362. checks = ('extract',)
  363. check_last = flexmock()
  364. consistency_config = {'check_last': check_last}
  365. flexmock(module).should_receive('parse_checks')
  366. flexmock(module).should_receive('filter_checks_on_frequency').and_return(checks)
  367. flexmock(module.rinfo).should_receive('display_repository_info').and_return(
  368. '{"repository": {"id": "repo"}}'
  369. )
  370. flexmock(module).should_receive('make_check_flags').never()
  371. flexmock(module.flags).should_receive('make_repository_flags').and_return(('repo',))
  372. flexmock(module.extract).should_receive('extract_last_archive_dry_run').once()
  373. flexmock(module).should_receive('write_check_time')
  374. insert_execute_command_never()
  375. module.check_archives(
  376. repository_path='repo',
  377. location_config={},
  378. storage_config={},
  379. consistency_config=consistency_config,
  380. local_borg_version='1.2.3',
  381. )
  382. def test_check_archives_with_log_info_calls_borg_with_info_parameter():
  383. checks = ('repository',)
  384. consistency_config = {'check_last': None}
  385. flexmock(module).should_receive('parse_checks')
  386. flexmock(module).should_receive('filter_checks_on_frequency').and_return(checks)
  387. flexmock(module.rinfo).should_receive('display_repository_info').and_return(
  388. '{"repository": {"id": "repo"}}'
  389. )
  390. flexmock(module).should_receive('make_check_flags').and_return(())
  391. flexmock(module.flags).should_receive('make_repository_flags').and_return(('repo',))
  392. insert_logging_mock(logging.INFO)
  393. insert_execute_command_mock(('borg', 'check', '--info', 'repo'))
  394. flexmock(module).should_receive('make_check_time_path')
  395. flexmock(module).should_receive('write_check_time')
  396. module.check_archives(
  397. repository_path='repo',
  398. location_config={},
  399. storage_config={},
  400. consistency_config=consistency_config,
  401. local_borg_version='1.2.3',
  402. )
  403. def test_check_archives_with_log_debug_calls_borg_with_debug_parameter():
  404. checks = ('repository',)
  405. consistency_config = {'check_last': None}
  406. flexmock(module).should_receive('parse_checks')
  407. flexmock(module).should_receive('filter_checks_on_frequency').and_return(checks)
  408. flexmock(module.rinfo).should_receive('display_repository_info').and_return(
  409. '{"repository": {"id": "repo"}}'
  410. )
  411. flexmock(module).should_receive('make_check_flags').and_return(())
  412. flexmock(module.flags).should_receive('make_repository_flags').and_return(('repo',))
  413. insert_logging_mock(logging.DEBUG)
  414. insert_execute_command_mock(('borg', 'check', '--debug', '--show-rc', 'repo'))
  415. flexmock(module).should_receive('make_check_time_path')
  416. flexmock(module).should_receive('write_check_time')
  417. module.check_archives(
  418. repository_path='repo',
  419. location_config={},
  420. storage_config={},
  421. consistency_config=consistency_config,
  422. local_borg_version='1.2.3',
  423. )
  424. def test_check_archives_without_any_checks_bails():
  425. consistency_config = {'check_last': None}
  426. flexmock(module).should_receive('parse_checks')
  427. flexmock(module).should_receive('filter_checks_on_frequency').and_return(())
  428. flexmock(module.rinfo).should_receive('display_repository_info').and_return(
  429. '{"repository": {"id": "repo"}}'
  430. )
  431. insert_execute_command_never()
  432. module.check_archives(
  433. repository_path='repo',
  434. location_config={},
  435. storage_config={},
  436. consistency_config=consistency_config,
  437. local_borg_version='1.2.3',
  438. )
  439. def test_check_archives_with_local_path_calls_borg_via_local_path():
  440. checks = ('repository',)
  441. check_last = flexmock()
  442. consistency_config = {'check_last': check_last}
  443. flexmock(module).should_receive('parse_checks')
  444. flexmock(module).should_receive('filter_checks_on_frequency').and_return(checks)
  445. flexmock(module.rinfo).should_receive('display_repository_info').and_return(
  446. '{"repository": {"id": "repo"}}'
  447. )
  448. flexmock(module).should_receive('make_check_flags').with_args(
  449. '1.2.3', {}, checks, check_last, prefix=None,
  450. ).and_return(())
  451. flexmock(module.flags).should_receive('make_repository_flags').and_return(('repo',))
  452. insert_execute_command_mock(('borg1', 'check', 'repo'))
  453. flexmock(module).should_receive('make_check_time_path')
  454. flexmock(module).should_receive('write_check_time')
  455. module.check_archives(
  456. repository_path='repo',
  457. location_config={},
  458. storage_config={},
  459. consistency_config=consistency_config,
  460. local_borg_version='1.2.3',
  461. local_path='borg1',
  462. )
  463. def test_check_archives_with_remote_path_calls_borg_with_remote_path_parameters():
  464. checks = ('repository',)
  465. check_last = flexmock()
  466. consistency_config = {'check_last': check_last}
  467. flexmock(module).should_receive('parse_checks')
  468. flexmock(module).should_receive('filter_checks_on_frequency').and_return(checks)
  469. flexmock(module.rinfo).should_receive('display_repository_info').and_return(
  470. '{"repository": {"id": "repo"}}'
  471. )
  472. flexmock(module).should_receive('make_check_flags').with_args(
  473. '1.2.3', {}, checks, check_last, prefix=None,
  474. ).and_return(())
  475. flexmock(module.flags).should_receive('make_repository_flags').and_return(('repo',))
  476. insert_execute_command_mock(('borg', 'check', '--remote-path', 'borg1', 'repo'))
  477. flexmock(module).should_receive('make_check_time_path')
  478. flexmock(module).should_receive('write_check_time')
  479. module.check_archives(
  480. repository_path='repo',
  481. location_config={},
  482. storage_config={},
  483. consistency_config=consistency_config,
  484. local_borg_version='1.2.3',
  485. remote_path='borg1',
  486. )
  487. def test_check_archives_with_lock_wait_calls_borg_with_lock_wait_parameters():
  488. checks = ('repository',)
  489. check_last = flexmock()
  490. storage_config = {'lock_wait': 5}
  491. consistency_config = {'check_last': check_last}
  492. flexmock(module).should_receive('parse_checks')
  493. flexmock(module).should_receive('filter_checks_on_frequency').and_return(checks)
  494. flexmock(module.rinfo).should_receive('display_repository_info').and_return(
  495. '{"repository": {"id": "repo"}}'
  496. )
  497. flexmock(module).should_receive('make_check_flags').with_args(
  498. '1.2.3', storage_config, checks, check_last, None,
  499. ).and_return(())
  500. flexmock(module.flags).should_receive('make_repository_flags').and_return(('repo',))
  501. insert_execute_command_mock(('borg', 'check', '--lock-wait', '5', 'repo'))
  502. flexmock(module).should_receive('make_check_time_path')
  503. flexmock(module).should_receive('write_check_time')
  504. module.check_archives(
  505. repository_path='repo',
  506. location_config={},
  507. storage_config=storage_config,
  508. consistency_config=consistency_config,
  509. local_borg_version='1.2.3',
  510. )
  511. def test_check_archives_with_retention_prefix():
  512. checks = ('repository',)
  513. check_last = flexmock()
  514. prefix = 'foo-'
  515. consistency_config = {'check_last': check_last, 'prefix': prefix}
  516. flexmock(module).should_receive('parse_checks')
  517. flexmock(module).should_receive('filter_checks_on_frequency').and_return(checks)
  518. flexmock(module.rinfo).should_receive('display_repository_info').and_return(
  519. '{"repository": {"id": "repo"}}'
  520. )
  521. flexmock(module).should_receive('make_check_flags').with_args(
  522. '1.2.3', {}, checks, check_last, prefix
  523. ).and_return(())
  524. flexmock(module.flags).should_receive('make_repository_flags').and_return(('repo',))
  525. insert_execute_command_mock(('borg', 'check', 'repo'))
  526. flexmock(module).should_receive('make_check_time_path')
  527. flexmock(module).should_receive('write_check_time')
  528. module.check_archives(
  529. repository_path='repo',
  530. location_config={},
  531. storage_config={},
  532. consistency_config=consistency_config,
  533. local_borg_version='1.2.3',
  534. )
  535. def test_check_archives_with_extra_borg_options_calls_borg_with_extra_options():
  536. checks = ('repository',)
  537. consistency_config = {'check_last': None}
  538. flexmock(module).should_receive('parse_checks')
  539. flexmock(module).should_receive('filter_checks_on_frequency').and_return(checks)
  540. flexmock(module.rinfo).should_receive('display_repository_info').and_return(
  541. '{"repository": {"id": "repo"}}'
  542. )
  543. flexmock(module).should_receive('make_check_flags').and_return(())
  544. flexmock(module.flags).should_receive('make_repository_flags').and_return(('repo',))
  545. insert_execute_command_mock(('borg', 'check', '--extra', '--options', 'repo'))
  546. flexmock(module).should_receive('make_check_time_path')
  547. flexmock(module).should_receive('write_check_time')
  548. module.check_archives(
  549. repository_path='repo',
  550. location_config={},
  551. storage_config={'extra_borg_options': {'check': '--extra --options'}},
  552. consistency_config=consistency_config,
  553. local_borg_version='1.2.3',
  554. )