mirror of
https://github.com/saltstack/salt.git
synced 2025-04-17 10:10:20 +00:00
Merge pull request #52040 from garethgreenaway/52036_rsync_state_no_changes_when_error
[2019.2] Fix to rsync state
This commit is contained in:
commit
a00245eb6a
2 changed files with 129 additions and 1 deletions
|
@ -28,10 +28,13 @@ State to synchronize files and directories with rsync.
|
|||
'''
|
||||
|
||||
from __future__ import absolute_import, print_function, unicode_literals
|
||||
import logging
|
||||
import os
|
||||
|
||||
import salt.utils.path
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
|
||||
def __virtual__():
|
||||
'''
|
||||
|
@ -155,7 +158,6 @@ def synchronized(name, source,
|
|||
if result.get('retcode'):
|
||||
ret['result'] = False
|
||||
ret['comment'] = result['stderr']
|
||||
ret['changes'] = result['stdout']
|
||||
# Changed
|
||||
elif _get_changes(result['stdout'])['changed']:
|
||||
ret['comment'] = _get_summary(result['stdout'])
|
||||
|
|
126
tests/unit/states/test_rsync.py
Normal file
126
tests/unit/states/test_rsync.py
Normal file
|
@ -0,0 +1,126 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
'''
|
||||
:codeauthor: Gareth J. Greenaway <gareth@saltstack.com>
|
||||
'''
|
||||
# Import Python libs
|
||||
from __future__ import absolute_import, print_function, unicode_literals
|
||||
|
||||
# Import Salt Libs
|
||||
import salt.states.rsync as rsync
|
||||
|
||||
# Import Salt Testing Libs
|
||||
from tests.support.mixins import LoaderModuleMockMixin
|
||||
from tests.support.unit import skipIf, TestCase
|
||||
from tests.support.mock import (
|
||||
NO_MOCK,
|
||||
NO_MOCK_REASON,
|
||||
MagicMock,
|
||||
patch
|
||||
)
|
||||
|
||||
|
||||
@skipIf(NO_MOCK, NO_MOCK_REASON)
|
||||
class RsyncTestCase(TestCase, LoaderModuleMockMixin):
|
||||
'''
|
||||
Validate the Rsync state
|
||||
'''
|
||||
def setup_loader_modules(self):
|
||||
return {rsync: {}}
|
||||
|
||||
def test_syncronized_failed(self):
|
||||
'''
|
||||
Test to perform an rsync.synchorized call that fails
|
||||
'''
|
||||
ret = {'pid': 100, 'retcode': 23, 'stderr': '', 'stdout': ''}
|
||||
_expected = {'changes': {},
|
||||
'comment': 'Destination directory name was not found.',
|
||||
'name': u'name',
|
||||
'result': False}
|
||||
|
||||
with patch.dict(rsync.__opts__, {'test': True}):
|
||||
mock = MagicMock(return_value=ret)
|
||||
with patch.dict(rsync.__salt__, {'rsync.rsync': mock}):
|
||||
self.assertDictEqual(rsync.synchronized("name", "source"),
|
||||
_expected)
|
||||
|
||||
# Run again mocking os.path.exists as True
|
||||
ret = {'pid': 100,
|
||||
'retcode': 23,
|
||||
'stderr': 'Something went wrong',
|
||||
'stdout': ''}
|
||||
_expected = {'changes': {},
|
||||
'comment': 'Something went wrong',
|
||||
'name': u'name',
|
||||
'result': False}
|
||||
|
||||
with patch('os.path.exists', MagicMock(return_value=True)):
|
||||
with patch.dict(rsync.__opts__, {'test': False}):
|
||||
mock = MagicMock(return_value=ret)
|
||||
with patch.dict(rsync.__salt__, {'rsync.rsync': mock}):
|
||||
self.assertDictEqual(rsync.synchronized("name", "source"),
|
||||
_expected)
|
||||
|
||||
def test_syncronized(self):
|
||||
'''
|
||||
Test to perform an rsync.synchorized call that succeeds
|
||||
'''
|
||||
ret = {'pid': 100,
|
||||
'retcode': 0,
|
||||
'stderr': '',
|
||||
'stdout': ('sending incremental file list\nsnapshot.jar\n\n'
|
||||
'sent 106 bytes received 35 bytes 282.00 bytes/sec\n'
|
||||
'total size is 0 speedup is 0.00')}
|
||||
_expected = {'changes': {'copied': 'snapshot.jar', 'deleted': u'N/A'},
|
||||
'comment': ('- sent 106 bytes\n- received 35 bytes\n- '
|
||||
'282.00 bytes/sec\n- total size is 0\n- speedup is 0.00'),
|
||||
'name': 'name',
|
||||
'result': True}
|
||||
|
||||
with patch('os.path.exists', MagicMock(return_value=True)):
|
||||
with patch.dict(rsync.__opts__, {'test': False}):
|
||||
mock = MagicMock(return_value=ret)
|
||||
with patch.dict(rsync.__salt__, {'rsync.rsync': mock}):
|
||||
self.assertDictEqual(rsync.synchronized("name", "source"),
|
||||
_expected)
|
||||
|
||||
# Second pass simulating the file being in place
|
||||
ret = {'pid': 100,
|
||||
'retcode': 0,
|
||||
'stderr': '',
|
||||
'stdout': ('sending incremental file list\n\n'
|
||||
'sent 106 bytes received 35 bytes '
|
||||
'282.00 bytes/sec\ntotal size is 0 '
|
||||
'speedup is 0.00')}
|
||||
_expected = {'changes': {},
|
||||
'comment': ('- sent 106 bytes\n- received '
|
||||
'35 bytes\n- 282.00 bytes/sec\n- total '
|
||||
'size is 0\n- speedup is 0.00'),
|
||||
'name': 'name',
|
||||
'result': True}
|
||||
|
||||
with patch('os.path.exists', MagicMock(return_value=True)):
|
||||
with patch.dict(rsync.__opts__, {'test': False}):
|
||||
mock = MagicMock(return_value=ret)
|
||||
with patch.dict(rsync.__salt__, {'rsync.rsync': mock}):
|
||||
self.assertDictEqual(rsync.synchronized("name", "source"),
|
||||
_expected)
|
||||
|
||||
def test_syncronized_test_true(self):
|
||||
'''
|
||||
Test to perform an rsync.synchorized call that fails
|
||||
'''
|
||||
ret = {'pid': 100,
|
||||
'retcode': 23,
|
||||
'stderr': 'Something went wrong',
|
||||
'stdout': ''}
|
||||
_expected = {'changes': {},
|
||||
'comment': '- ',
|
||||
'name': u'name',
|
||||
'result': None}
|
||||
|
||||
with patch('os.path.exists', MagicMock(return_value=True)):
|
||||
with patch.dict(rsync.__opts__, {'test': True}):
|
||||
mock = MagicMock(return_value=ret)
|
||||
with patch.dict(rsync.__salt__, {'rsync.rsync': mock}):
|
||||
self.assertDictEqual(rsync.synchronized("name", "source"),
|
||||
_expected)
|
Loading…
Add table
Reference in a new issue