def test_change_flag(self): # Flags are set in a second run of parted(). # Between the two runs, the partition dict is updated. # use checkmode here allow us to continue even if the dictionary is # not updated. set_module_args({ 'device': '/dev/sdb', 'number': 3, 'state': 'present', 'flags': ['lvm', 'boot'], '_ansible_check_mode': True, }) with patch('ansible.modules.system.parted.get_device_info', return_value=parted_dict1): self.parted.reset_mock() self.execute_module(changed=True) # When using multiple flags: # order of execution is non deterministic, because set() operations are used in # the current implementation. expected_calls_order1 = [ call('unit KiB set 3 lvm on set 3 boot on ', '/dev/sdb', 'optimal') ] expected_calls_order2 = [ call('unit KiB set 3 boot on set 3 lvm on ', '/dev/sdb', 'optimal') ] self.assertTrue(self.parted.mock_calls == expected_calls_order1 or self.parted.mock_calls == expected_calls_order2)
def test__save_data__write_failure(self, fetch, write): # Setup mod_cls = create_autospec(AnsibleModule) mod = mod_cls.return_value mod.params = dict( url="https://www.google.com", dest="/tmp/firstmod.txt" ) write.side_effect = firstmod.WriteError # Exercise firstmod.save_data(mod) # Verify self.assertEqual(1, mod.fail_json.call_count) self.assertEqual(1, fetch.call_count) expected = call(mod.params["url"]) self.assertEqual(expected, fetch.call_args) self.assertEqual(1, write.call_count) expected = call(fetch.return_value, mod.params["dest"]) self.assertEqual(expected, write.call_args)
def run_parse_common(self, galaxycli_obj, action): with patch.object(ansible.cli.SortedOptParser, "set_usage") as mocked_usage: galaxycli_obj.parse() # checking that the common results of parse() for all possible actions have been created/called self.assertIsInstance(galaxycli_obj.parser, ansible.cli.SortedOptParser) self.assertIsInstance(galaxycli_obj.galaxy, ansible.galaxy.Galaxy) formatted_call = { 'import': 'usage: %prog import [options] github_user github_repo', 'delete': 'usage: %prog delete [options] github_user github_repo', 'info': 'usage: %prog info [options] role_name[,version]', 'init': 'usage: %prog init [options] role_name', 'install': 'usage: %prog install [options] [-r FILE | role_name(s)[,version] | scm+role_repo_url[,version] | tar_file(s)]', 'list': 'usage: %prog list [role_name]', 'login': '******', 'remove': 'usage: %prog remove role1 role2 ...', 'search': ('usage: %prog search [searchterm1 searchterm2] [--galaxy-tags galaxy_tag1,galaxy_tag2] [--platforms platform1,platform2] ' '[--author username]'), 'setup': 'usage: %prog setup [options] source github_user github_repo secret', } first_call = 'usage: %prog [delete|import|info|init|install|list|login|remove|search|setup] [--help] [options] ...' second_call = formatted_call[action] calls = [call(first_call), call(second_call)] mocked_usage.assert_has_calls(calls)
def test__save_data__happy_path(self, fetch, write): # Setup mod_cls = create_autospec(AnsibleModule) mod = mod_cls.return_value mod.params = dict( url="https://www.google.com", dest="/tmp/firstmod.txt" ) # Exercise firstmod.save_data(mod) # Verify self.assertEqual(1, mod.exit_json.call_count) expected = call(msg="Data saved", changed=True) self.assertEqual(expected, mod.exit_json.call_args) self.assertEqual(1, fetch.call_count) expected = call(mod.params["url"]) self.assertEqual(expected, fetch.call_args) self.assertEqual(1, write.call_count) expected = call(fetch.return_value, mod.params["dest"]) self.assertEqual(expected, write.call_args)
def test_change_flag(self): # Flags are set in a second run of parted(). # Between the two runs, the partition dict is updated. # use checkmode here allow us to continue even if the dictionary is # not updated. set_module_args({ 'device': '/dev/sdb', 'number': 3, 'state': 'present', 'flags': ['lvm', 'boot'], '_ansible_check_mode': True, }) with patch('ansible.modules.system.parted.get_device_info', return_value=parted_dict1): self.parted.reset_mock() self.execute_module(changed=True) # When using multiple flags: # order of execution is non deterministic, because set() operations are used in # the current implementation. expected_calls_order1 = [call('unit KiB set 3 lvm on set 3 boot on ', '/dev/sdb', 'optimal')] expected_calls_order2 = [call('unit KiB set 3 boot on set 3 lvm on ', '/dev/sdb', 'optimal')] self.assertTrue(self.parted.mock_calls == expected_calls_order1 or self.parted.mock_calls == expected_calls_order2)
def test_cwd_relative_path(self): self.os.getcwd.return_value = '/old' self.module.run_command('/bin/ls', cwd='sub-dir') self.assertEqual(self.os.chdir.mock_calls, [ call('/old/sub-dir'), call('/old'), ])
def test_edit_upserted_object(self, _set_default_mock, copy_properties_mock, edit_object_mock, get_operation_mock): model_operations = mock.MagicMock() existing_object = mock.MagicMock() params = { 'path_params': {}, 'data': {} } result = self._resource._edit_upserted_object(model_operations, existing_object, params) assert result == edit_object_mock.return_value _set_default_mock.assert_has_calls([ mock.call(params, 'path_params', {}), mock.call(params, 'data', {}) ]) get_operation_mock.assert_called_once_with( self._resource._operation_checker.is_edit_operation, model_operations ) copy_properties_mock.assert_called_once_with( existing_object, params['data'] ) edit_object_mock.assert_called_once_with( get_operation_mock.return_value, params )
def test_iterate_over_pageable_resource_should_pass_with_string_offset_and_limit( self): resource_func = mock.Mock(side_effect=[ { 'items': ['foo'] }, { 'items': [] }, ]) items = iterate_over_pageable_resource( resource_func, {'query_params': { 'offset': '1', 'limit': '1' }}) assert ['foo'] == list(items) resource_func.assert_has_calls([ call(params={'query_params': { 'offset': '1', 'limit': '1' }}), call(params={'query_params': { 'offset': 2, 'limit': '1' }}) ])
def run_parse_common(self, galaxycli_obj, action): with patch.object(ansible.cli.SortedOptParser, "set_usage") as mocked_usage: galaxycli_obj.parse() # checking that the common results of parse() for all possible actions have been created/called self.assertIsInstance(galaxycli_obj.parser, ansible.cli.SortedOptParser) self.assertIsInstance(galaxycli_obj.galaxy, ansible.galaxy.Galaxy) if action in ['import', 'delete']: formatted_call = 'usage: %prog ' + action + ' [options] github_user github_repo' elif action == 'info': formatted_call = 'usage: %prog ' + action + ' [options] role_name[,version]' elif action == 'init': formatted_call = 'usage: %prog ' + action + ' [options] role_name' elif action == 'install': formatted_call = 'usage: %prog ' + action + ' [options] [-r FILE | role_name(s)[,version] | scm+role_repo_url[,version] | tar_file(s)]' elif action == 'list': formatted_call = 'usage: %prog ' + action + ' [role_name]' elif action == 'login': formatted_call = 'usage: %prog ' + action + ' [options]' elif action == 'remove': formatted_call = 'usage: %prog ' + action + ' role1 role2 ...' elif action == 'search': formatted_call = 'usage: %prog ' + action + ' [searchterm1 searchterm2] [--galaxy-tags galaxy_tag1,galaxy_tag2] [--platforms platform1,platform2] [--author username]' elif action == 'setup': formatted_call = 'usage: %prog ' + action + ' [options] source github_user github_repo secret' calls = [ call( 'usage: %prog [delete|import|info|init|install|list|login|remove|search|setup] [--help] [options] ...' ), call(formatted_call) ] mocked_usage.assert_has_calls(calls)
def test_cwd(self): self.os.getcwd.return_value = '/old' self.module.run_command('/bin/ls', cwd='/new') self.assertEqual(self.os.chdir.mock_calls, [ call('/new'), call('/old'), ])
def test_module_can_use_template_and_scheme_repos(self, mock_run_command): set_module_args({ 'scheme': 'tomorrow-night', 'template': 'i3', }) with self.assertRaises(AnsibleExitJson) as result: base16_builder.main() set_module_args({ 'scheme': 'tomorrow-night', 'template': 'i3', 'schemes_source': 'https://github.com/mnussbaum/base16-schemes-source', 'templates_source': 'https://github.com/mnussbaum/base16-templates-source', 'cache_dir': self.test_cache_dir, }) with self.assertRaises(AnsibleExitJson) as result: base16_builder.main() result_args = result.exception.args[0] self.assertEqual(result_args['changed'], True) schemes_source = os.path.join( self.test_cache_dir, 'base16-builder-ansible', 'sources', 'schemes', ) self.assertTrue(os.path.exists(schemes_source)) self.assertTrue( call([ ANY, 'clone', 'https://github.com/mnussbaum/base16-schemes-source', ANY, ], check_rc=True) in mock_run_command.mock_calls) templates_source = os.path.join( self.test_cache_dir, 'base16-builder-ansible', 'sources', 'templates', ) self.assertTrue(os.path.exists(templates_source)) self.assertTrue( call([ ANY, 'clone', 'https://github.com/mnussbaum/base16-templates-source', ANY, ], check_rc=True) in mock_run_command.mock_calls)
def test_get_objects_by_filter_with_multiple_responses(self, send_request_mock, connection_mock): send_request_mock.side_effect = [ {'items': [ {'name': 'obj1', 'type': 'foo'}, {'name': 'obj2', 'type': 'bar'} ]}, {'items': [ {'name': 'obj3', 'type': 'foo'} ]}, {'items': []} ] connection_mock.get_operation_spec.return_value = { 'method': HTTPMethod.GET, 'url': '/object/' } resource = BaseConfigurationResource(connection_mock, False) assert [{'name': 'obj1', 'type': 'foo'}] == list(resource.get_objects_by_filter( 'test', {ParamName.FILTERS: {'type': 'foo'}})) send_request_mock.assert_has_calls( [ mock.call('/object/', 'get', {}, {}, {QueryParams.FILTER: "type:foo", 'limit': 10, 'offset': 0}) ] ) send_request_mock.reset_mock() send_request_mock.side_effect = [ {'items': [ {'name': 'obj1', 'type': 'foo'}, {'name': 'obj2', 'type': 'bar'} ]}, {'items': [ {'name': 'obj3', 'type': 'foo'} ]}, {'items': []} ] resp = list(resource.get_objects_by_filter( 'test', { ParamName.FILTERS: {'type': 'foo'}, ParamName.QUERY_PARAMS: {'limit': 2} })) assert [{'name': 'obj1', 'type': 'foo'}, {'name': 'obj3', 'type': 'foo'}] == resp send_request_mock.assert_has_calls( [ mock.call('/object/', 'get', {}, {}, {QueryParams.FILTER: "type:foo", 'limit': 2, 'offset': 0}), mock.call('/object/', 'get', {}, {}, {QueryParams.FILTER: "type:foo", 'limit': 2, 'offset': 2}) ] )
def test_iterate_over_pageable_resource_raises_exception_when_server_returned_more_items_than_requested( self): resource_func = mock.Mock(side_effect=[ { 'items': ['foo', 'redundant_bar'] }, { 'items': [] }, ]) with pytest.raises(FtdUnexpectedResponse): list( iterate_over_pageable_resource( resource_func, {'query_params': { 'offset': '1', 'limit': '1' }})) resource_func.assert_has_calls( [call(params={'query_params': { 'offset': '1', 'limit': '1' }})])
def test_write(self): # setup data = "Somedata" dest = "/tmp/testAnsible.txt" # exercise obj_open = "fetch_resources.open" mok_open = mock_open() with patch(obj_open, mok_open, create=True): fetch_resources.write(data=data, dest=dest) # verify expected = call(dest, "w") self.assertEqual(expected, mok_open.mock_calls[0]) expected = call().write(data) self.assertEqual(expected, mok_open.mock_calls[2])
def test_cwd_not_a_dir(self): self.os.getcwd.return_value = '/old' self.os.path.isdir.side_effect = lambda d: d != '/not-a-dir' self.module.run_command('/bin/ls', cwd='/not-a-dir') self.assertEqual(self.os.chdir.mock_calls, [ call('/old'), ])
def test_get_objects_by_filter_with_multiple_filters(self, send_request_mock, connection_mock): objects = [ {'name': 'obj1', 'type': 1, 'foo': {'bar': 'buzz'}}, {'name': 'obj2', 'type': 1, 'foo': {'bar': 'buz'}}, {'name': 'obj3', 'type': 2, 'foo': {'bar': 'buzz'}} ] connection_mock.get_operation_spec.return_value = { 'method': HTTPMethod.GET, 'url': '/object/' } resource = BaseConfigurationResource(connection_mock, False) send_request_mock.side_effect = [{'items': objects}, {'items': []}] # resource.get_objects_by_filter returns generator so to be able compare generated list with expected list # we need evaluate it. assert objects == list(resource.get_objects_by_filter('test', {})) send_request_mock.assert_has_calls( [ mock.call('/object/', 'get', {}, {}, {'limit': 10, 'offset': 0}) ] ) send_request_mock.reset_mock() send_request_mock.side_effect = [{'items': objects}, {'items': []}] # resource.get_objects_by_filter returns generator so to be able compare generated list with expected list # we need evaluate it. assert [objects[0]] == list(resource.get_objects_by_filter('test', {ParamName.FILTERS: {'name': 'obj1'}})) send_request_mock.assert_has_calls( [ mock.call('/object/', 'get', {}, {}, {QueryParams.FILTER: 'name:obj1', 'limit': 10, 'offset': 0}) ] ) send_request_mock.reset_mock() send_request_mock.side_effect = [{'items': objects}, {'items': []}] # resource.get_objects_by_filter returns generator so to be able compare generated list with expected list # we need evaluate it. assert [objects[1]] == list(resource.get_objects_by_filter( 'test', {ParamName.FILTERS: {'type': 1, 'foo': {'bar': 'buz'}}})) send_request_mock.assert_has_calls( [ mock.call('/object/', 'get', {}, {}, {QueryParams.FILTER: "foo:{'bar': 'buz'};type:1", 'limit': 10, 'offset': 0}) ] )
def test__write__happy_path(self): # Setup data = "Somedata here" dest = "/path/to/file.txt" # Exercise o_open = "ansible.modules.extras.cloud.somebodyscomputer.firstmod.open" m_open = mock_open() with patch(o_open, m_open, create=True): firstmod.write(data, dest) # Verify expected = call(dest, "w") self.assertEqual(expected, m_open.mock_calls[0]) expected = call().write(data) self.assertEqual(expected, m_open.mock_calls[2])
def test_module_can_use_template_and_scheme_local_paths( self, mock_run_command): set_module_args({ 'scheme': 'local-scheme', 'template': 'local-template', 'schemes_source': os.path.join( os.path.dirname(__file__), 'fixtures', 'sources', 'schemes', ), 'templates_source': os.path.join( os.path.dirname(__file__), 'fixtures', 'sources', 'templates', ), 'cache_dir': self.test_cache_dir, }) with self.assertRaises(AnsibleExitJson) as result: base16_builder.main() result_args = result.exception.args[0] self.assertEqual(result_args['changed'], False) self.assertFalse( call([ ANY, 'clone', ANY, ANY, ], check_rc=True) in mock_run_command.mock_calls) self.assertEqual( result_args['schemes'], { 'local-scheme-night': { 'local-template': { 'themes': { 'base16-local-scheme-night.test': "000000\n" }, } }, 'local-scheme': { 'local-template': { 'themes': { 'base16-local-scheme.test': "111111\n" }, } }, }, )
def test__save_data__happy_path(self, fetch, write): # Setup mod_cls = create_autospec(AnsibleModule) mod = mod_cls.return_value mod.params = dict(url='www.google.com', dest='/tmp/firstmod.txt') # Exercise wyfm.save_data(mod) # Verify self.assertEqual(1, fetch.call_count) expected = call(mod.params['url']) self.assertEqual(expected, fetch.call_args) self.assertEqual(1, write.call_count) expected = call(fetch.return_value, mod.params['dest']) self.assertEqual(expected, write.call_args) self.assertEqual(1, mod.exit_json.call_count) expected = call(msg='Data saved', changed=True) self.assertEqual(expected, mod.exit_json.call_args)
def test_iterate_over_pageable_resource_with_one_page(self): resource_func = mock.Mock(side_effect=[ {'items': ['foo', 'bar']}, {'items': []}, ]) items = iterate_over_pageable_resource(resource_func, {'query_params': {}}) assert ['foo', 'bar'] == list(items) resource_func.assert_has_calls([ call(params={'query_params': {'offset': 0, 'limit': 10}}) ])
def test_iterate_over_pageable_resource_should_preserve_offset(self): resource_func = mock.Mock(side_effect=[ {'items': ['foo']}, {'items': []}, ]) items = iterate_over_pageable_resource(resource_func, {'query_params': {'offset': 3}}) assert ['foo'] == list(items) resource_func.assert_has_calls([ call(params={'query_params': {'offset': 3, 'limit': 10}}), ])
def test_should_update_server_when_task_include_network_personalization(self): self.mock_connection.get.side_effect = [self.get_as_rest_collection([DEFAULT_BUILD_PLAN]), self.get_as_rest_collection([DEFAULT_SERVER])] self.mock_server_service.get_server.side_effect = [DEFAULT_SERVER, DEFAULT_SERVER_UPDATED] self.mock_icsp.common.monitor_execution.return_value = {} self.mock_icsp_jobs.add_job.return_value = {"job mock return"} task_with_network_personalization = deepcopy(TASK_OS_DEPLOYMENT) network_config = {"network_config": {"hostname": "test-web.io.fc.hpe.com", "domain": "demo.com"}} task_with_network_personalization['personality_data'] = network_config self.mock_ansible_instance.params = task_with_network_personalization hpe_icsp_os_deployment.main() server_data = {"serverUri": DEFAULT_SERVER['uri'], "personalityData": None} network_config = {"serverData": [server_data]} build_plan_body = {"osbpUris": [DEFAULT_BUILD_PLAN['uri']], "serverData": [server_data], "stepNo": 1} monitor_build_plan = mock.call(self.mock_icsp_jobs.add_job(build_plan_body), self.mock_icsp_jobs) monitor_update_server = mock.call(self.mock_icsp_jobs.add_job(network_config), self.mock_icsp_jobs) calls = [monitor_build_plan, monitor_update_server] self.mock_icsp.common.monitor_execution.assert_has_calls(calls)
def test_ensure_feature_is_enabled_called(self): self.set_module_state('present') from ansible.modules.network.netscaler import netscaler_cs_policy client_mock = Mock() ensure_feature_is_enabled_mock = Mock() with patch.multiple( 'ansible.modules.network.netscaler.netscaler_cs_policy', get_nitro_client=Mock(return_value=client_mock), policy_exists=Mock(side_effect=[True, True]), nitro_exception=self.MockException, ensure_feature_is_enabled=ensure_feature_is_enabled_mock, ): self.module = netscaler_cs_policy result = self.exited() ensure_feature_is_enabled_mock.assert_has_calls([call(client_mock, 'CS')])
def test__fetch__happy_path(self, open_url): # Setup url = 'https://www.google.com' # Mock the return value of open_url stream = open_url.return_value stream.read.return_value = "<html><head></head><body>Hello</body></html>" stream.getcode.return_value = 200 open_url.return_value = stream # Exercise data = wyfm.fetch(url) # Verify self.assertEqual(stream.read.return_value, data) self.assertEqual(1, open_url.call_count) expected = call(url) self.assertEqual(expected, open_url.call_args)
def test_fetch(self, open_url): # setup url = "https://www.google.com" # mock the return value of open_url stream = open_url.return_value stream.read.return_value = "<html><head></head><body>Hello</body></html>" stream.getcode.return_value = 200 open_url.return_value = stream # exercise data = fetch_resources.fetch(url) # verify self.assertEqual(stream.read.return_value, data) self.assertEqual(1, open_url.call_count) expected = call(url) self.assertEqual(expected, open_url.call_args)
def test__write__write_error(self): # Setup data = "Somedata here" dest = "/path/to/file.txt" o_open = "ansible.modules.extras.cloud.somebodyscomputer.firstmod.open" m_open = mock_open() m_open.side_effect = IOError # Exercise with self.assertRaises(firstmod.WriteError): with patch(o_open, m_open, create=True): firstmod.write(data, dest) # Verify self.assertEqual(1, m_open.call_count) expected = call(dest, "w") self.assertEqual(expected, m_open.mock_calls[0])
def test_module_utils_basic_ansible_module_atomic_move( self, _os_path_exists, _os_stat, _os_chmod, _os_chown, _os_getlogin, _os_environ, _os_getuid, _pwd_getpwuid, _os_rename, _shutil_copy2, _shutil_move, _shutil_copyfileobj, _os_umask, _tempfile_NamedTemporaryFile, ): from ansible.module_utils import basic basic.MODULE_COMPLEX_ARGS = '{}' am = basic.AnsibleModule(argument_spec=dict(), ) environ = dict() _os_environ.__getitem__ = environ.__getitem__ _os_environ.__setitem__ = environ.__setitem__ am.selinux_enabled = MagicMock() am.selinux_context = MagicMock() am.selinux_default_context = MagicMock() am.set_context_if_different = MagicMock() # test destination does not exist, no selinux, login name = 'root', # no environment, os.rename() succeeds _os_path_exists.side_effect = [False, False] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_rename.return_value = None _os_umask.side_effect = [18, 0] am.selinux_enabled.return_value = False _os_chmod.reset_mock() _os_chown.reset_mock() am.set_context_if_different.reset_mock() am.atomic_move('/path/to/src', '/path/to/dest') _os_rename.assert_called_with('/path/to/src', '/path/to/dest') self.assertEqual(_os_chmod.call_args_list, [call('/path/to/dest', basic.DEFAULT_PERM & ~18)]) # same as above, except selinux_enabled _os_path_exists.side_effect = [False, False] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_rename.return_value = None _os_umask.side_effect = [18, 0] mock_context = MagicMock() am.selinux_default_context.return_value = mock_context am.selinux_enabled.return_value = True _os_chmod.reset_mock() _os_chown.reset_mock() am.set_context_if_different.reset_mock() am.selinux_default_context.reset_mock() am.atomic_move('/path/to/src', '/path/to/dest') _os_rename.assert_called_with('/path/to/src', '/path/to/dest') self.assertEqual(_os_chmod.call_args_list, [call('/path/to/dest', basic.DEFAULT_PERM & ~18)]) self.assertEqual(am.selinux_default_context.call_args_list, [call('/path/to/dest')]) self.assertEqual(am.set_context_if_different.call_args_list, [call('/path/to/dest', mock_context, False)]) # now with dest present, no selinux, also raise OSError when using # os.getlogin() to test corner case with no tty _os_path_exists.side_effect = [True, True] _os_getlogin.side_effect = OSError() _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_rename.return_value = None _os_umask.side_effect = [18, 0] environ['LOGNAME'] = 'root' stat1 = MagicMock() stat1.st_mode = 0o0644 stat1.st_uid = 0 stat1.st_gid = 0 _os_stat.side_effect = [ stat1, ] am.selinux_enabled.return_value = False _os_chmod.reset_mock() _os_chown.reset_mock() am.set_context_if_different.reset_mock() am.atomic_move('/path/to/src', '/path/to/dest') _os_rename.assert_called_with('/path/to/src', '/path/to/dest') # dest missing, selinux enabled _os_path_exists.side_effect = [True, True] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_rename.return_value = None _os_umask.side_effect = [18, 0] stat1 = MagicMock() stat1.st_mode = 0o0644 stat1.st_uid = 0 stat1.st_gid = 0 _os_stat.side_effect = [ stat1, ] mock_context = MagicMock() am.selinux_context.return_value = mock_context am.selinux_enabled.return_value = True _os_chmod.reset_mock() _os_chown.reset_mock() am.set_context_if_different.reset_mock() am.selinux_default_context.reset_mock() am.atomic_move('/path/to/src', '/path/to/dest') _os_rename.assert_called_with('/path/to/src', '/path/to/dest') self.assertEqual(am.selinux_context.call_args_list, [call('/path/to/dest')]) self.assertEqual(am.set_context_if_different.call_args_list, [call('/path/to/dest', mock_context, False)]) # now testing with exceptions raised # have os.stat raise OSError which is not EPERM _os_stat.side_effect = OSError() _os_path_exists.side_effect = [True, True] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_rename.return_value = None _os_umask.side_effect = [18, 0] self.assertRaises(OSError, am.atomic_move, '/path/to/src', '/path/to/dest') # and now have os.stat return EPERM, which should not fail _os_stat.side_effect = OSError(errno.EPERM, 'testing os stat with EPERM') _os_path_exists.side_effect = [True, True] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_rename.return_value = None _os_umask.side_effect = [18, 0] # FIXME: we don't assert anything here yet am.atomic_move('/path/to/src', '/path/to/dest') # now we test os.rename() raising errors... # first we test with a bad errno to verify it bombs out _os_path_exists.side_effect = [False, False] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_umask.side_effect = [18, 0] _os_rename.side_effect = OSError(errno.EIO, 'failing with EIO') self.assertRaises(SystemExit, am.atomic_move, '/path/to/src', '/path/to/dest') # next we test with EPERM so it continues to the alternate code for moving # test with NamedTemporaryFile raising an error first _os_path_exists.side_effect = [False, False] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_umask.side_effect = [18, 0] _os_rename.side_effect = [ OSError(errno.EPERM, 'failing with EPERM'), None ] _tempfile_NamedTemporaryFile.return_value = None _tempfile_NamedTemporaryFile.side_effect = OSError() am.selinux_enabled.return_value = False self.assertRaises(SystemExit, am.atomic_move, '/path/to/src', '/path/to/dest') # then test with it creating a temp file _os_path_exists.side_effect = [False, False] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_umask.side_effect = [18, 0] _os_rename.side_effect = [ OSError(errno.EPERM, 'failing with EPERM'), None ] mock_stat1 = MagicMock() mock_stat2 = MagicMock() mock_stat3 = MagicMock() _os_stat.return_value = [mock_stat1, mock_stat2, mock_stat3] _os_stat.side_effect = None mock_tempfile = MagicMock() mock_tempfile.name = '/path/to/tempfile' _tempfile_NamedTemporaryFile.return_value = mock_tempfile _tempfile_NamedTemporaryFile.side_effect = None am.selinux_enabled.return_value = False # FIXME: we don't assert anything here yet am.atomic_move('/path/to/src', '/path/to/dest') # same as above, but with selinux enabled _os_path_exists.side_effect = [False, False] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_umask.side_effect = [18, 0] _os_rename.side_effect = [ OSError(errno.EPERM, 'failing with EPERM'), None ] mock_tempfile = MagicMock() _tempfile_NamedTemporaryFile.return_value = mock_tempfile mock_context = MagicMock() am.selinux_default_context.return_value = mock_context am.selinux_enabled.return_value = True am.atomic_move('/path/to/src', '/path/to/dest')
def test_cwd_relative_path(self): self.os.getcwd.return_value = '/old' self.module.run_command('/bin/ls', cwd='sub-dir') self.assertEqual(self.os.chdir.mock_calls, [call('/old/sub-dir'), call('/old'), ])
def test_cwd_not_a_dir(self): self.os.getcwd.return_value = '/old' self.os.path.isdir.side_effect = lambda d: d != '/not-a-dir' self.module.run_command('/bin/ls', cwd='/not-a-dir') self.assertEqual(self.os.chdir.mock_calls, [call('/old'), ])
def test_cwd(self): self.os.getcwd.return_value = '/old' self.module.run_command('/bin/ls', cwd='/new') self.assertEqual(self.os.chdir.mock_calls, [call('/new'), call('/old'), ])
def test_module_utils_basic_ansible_module_atomic_move( self, _os_path_exists, _os_stat, _os_chmod, _os_chown, _os_getlogin, _os_environ, _os_getuid, _pwd_getpwuid, _os_rename, _shutil_copy2, _shutil_move, _shutil_copyfileobj, _os_umask, _tempfile_NamedTemporaryFile, ): from ansible.module_utils import basic reload(basic) am = basic.AnsibleModule( argument_spec = dict(), ) environ = dict() _os_environ.__getitem__ = environ.__getitem__ _os_environ.__setitem__ = environ.__setitem__ am.selinux_enabled = MagicMock() am.selinux_context = MagicMock() am.selinux_default_context = MagicMock() am.set_context_if_different = MagicMock() # test destination does not exist, no selinux, login name = 'root', # no environment, os.rename() succeeds _os_path_exists.side_effect = [False, False] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_rename.return_value = None _os_umask.side_effect = [18, 0] am.selinux_enabled.return_value = False _os_chmod.reset_mock() _os_chown.reset_mock() am.set_context_if_different.reset_mock() am.atomic_move('/path/to/src', '/path/to/dest') _os_rename.assert_called_with('/path/to/src', '/path/to/dest') self.assertEqual(_os_chmod.call_args_list, [call('/path/to/dest', basic.DEFAULT_PERM & ~18)]) # same as above, except selinux_enabled _os_path_exists.side_effect = [False, False] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_rename.return_value = None _os_umask.side_effect = [18, 0] mock_context = MagicMock() am.selinux_default_context.return_value = mock_context am.selinux_enabled.return_value = True _os_chmod.reset_mock() _os_chown.reset_mock() am.set_context_if_different.reset_mock() am.selinux_default_context.reset_mock() am.atomic_move('/path/to/src', '/path/to/dest') _os_rename.assert_called_with('/path/to/src', '/path/to/dest') self.assertEqual(_os_chmod.call_args_list, [call('/path/to/dest', basic.DEFAULT_PERM & ~18)]) self.assertEqual(am.selinux_default_context.call_args_list, [call('/path/to/dest')]) self.assertEqual(am.set_context_if_different.call_args_list, [call('/path/to/dest', mock_context, False)]) # now with dest present, no selinux, also raise OSError when using # os.getlogin() to test corner case with no tty _os_path_exists.side_effect = [True, True] _os_getlogin.side_effect = OSError() _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_rename.return_value = None _os_umask.side_effect = [18, 0] environ['LOGNAME'] = 'root' stat1 = MagicMock() stat1.st_mode = 0o0644 stat1.st_uid = 0 stat1.st_gid = 0 _os_stat.side_effect = [stat1,] am.selinux_enabled.return_value = False _os_chmod.reset_mock() _os_chown.reset_mock() am.set_context_if_different.reset_mock() am.atomic_move('/path/to/src', '/path/to/dest') _os_rename.assert_called_with('/path/to/src', '/path/to/dest') # dest missing, selinux enabled _os_path_exists.side_effect = [True, True] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_rename.return_value = None _os_umask.side_effect = [18, 0] stat1 = MagicMock() stat1.st_mode = 0o0644 stat1.st_uid = 0 stat1.st_gid = 0 _os_stat.side_effect = [stat1,] mock_context = MagicMock() am.selinux_context.return_value = mock_context am.selinux_enabled.return_value = True _os_chmod.reset_mock() _os_chown.reset_mock() am.set_context_if_different.reset_mock() am.selinux_default_context.reset_mock() am.atomic_move('/path/to/src', '/path/to/dest') _os_rename.assert_called_with('/path/to/src', '/path/to/dest') self.assertEqual(am.selinux_context.call_args_list, [call('/path/to/dest')]) self.assertEqual(am.set_context_if_different.call_args_list, [call('/path/to/dest', mock_context, False)]) # now testing with exceptions raised # have os.stat raise OSError which is not EPERM _os_stat.side_effect = OSError() _os_path_exists.side_effect = [True, True] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_rename.return_value = None _os_umask.side_effect = [18, 0] self.assertRaises(OSError, am.atomic_move, '/path/to/src', '/path/to/dest') # and now have os.stat return EPERM, which should not fail _os_stat.side_effect = OSError(errno.EPERM, 'testing os stat with EPERM') _os_path_exists.side_effect = [True, True] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_rename.return_value = None _os_umask.side_effect = [18, 0] # FIXME: we don't assert anything here yet am.atomic_move('/path/to/src', '/path/to/dest') # now we test os.rename() raising errors... # first we test with a bad errno to verify it bombs out _os_path_exists.side_effect = [False, False] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_umask.side_effect = [18, 0] _os_rename.side_effect = OSError(errno.EIO, 'failing with EIO') self.assertRaises(SystemExit, am.atomic_move, '/path/to/src', '/path/to/dest') # next we test with EPERM so it continues to the alternate code for moving # test with NamedTemporaryFile raising an error first _os_path_exists.side_effect = [False, False] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_umask.side_effect = [18, 0] _os_rename.side_effect = [OSError(errno.EPERM, 'failing with EPERM'), None] _tempfile_NamedTemporaryFile.return_value = None _tempfile_NamedTemporaryFile.side_effect = OSError() am.selinux_enabled.return_value = False self.assertRaises(SystemExit, am.atomic_move, '/path/to/src', '/path/to/dest') # then test with it creating a temp file _os_path_exists.side_effect = [False, False] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_umask.side_effect = [18, 0] _os_rename.side_effect = [OSError(errno.EPERM, 'failing with EPERM'), None] mock_stat1 = MagicMock() mock_stat2 = MagicMock() mock_stat3 = MagicMock() _os_stat.return_value = [mock_stat1, mock_stat2, mock_stat3] _os_stat.side_effect = None mock_tempfile = MagicMock() mock_tempfile.name = '/path/to/tempfile' _tempfile_NamedTemporaryFile.return_value = mock_tempfile _tempfile_NamedTemporaryFile.side_effect = None am.selinux_enabled.return_value = False # FIXME: we don't assert anything here yet am.atomic_move('/path/to/src', '/path/to/dest') # same as above, but with selinux enabled _os_path_exists.side_effect = [False, False] _os_getlogin.return_value = 'root' _os_getuid.return_value = 0 _pwd_getpwuid.return_value = ('root', '', 0, 0, '', '', '') _os_umask.side_effect = [18, 0] _os_rename.side_effect = [OSError(errno.EPERM, 'failing with EPERM'), None] mock_tempfile = MagicMock() _tempfile_NamedTemporaryFile.return_value = mock_tempfile mock_context = MagicMock() am.selinux_default_context.return_value = mock_context am.selinux_enabled.return_value = True am.atomic_move('/path/to/src', '/path/to/dest')