Set up mocking

Move the code that sets up the group object, computer object and gets
existing members out of the individual functions so they can be mocked

Mock the GroupObj
Mock the ComputerObj
Mock existing members
Still need to fix info, getent, and members
This commit is contained in:
twangboy 2017-10-20 16:57:37 -06:00
parent c849f350ba
commit 6ab82394be
No known key found for this signature in database
GPG key ID: 93FF3BDEB278C9EB
2 changed files with 223 additions and 57 deletions

View file

@ -36,6 +36,12 @@ def __virtual__():
return (False, "Module win_groupadd: module only works on Windows systems")
def _get_computer_object():
pythoncom.CoInitialize()
nt = win32com.client.Dispatch('AdsNameSpaces')
return nt.GetObject('', 'WinNT://.,computer')
def add(name, **kwargs):
'''
Add the specified group
@ -60,10 +66,8 @@ def add(name, **kwargs):
'comment': ''}
if not info(name):
pythoncom.CoInitialize()
nt = win32com.client.Dispatch('AdsNameSpaces')
compObj = _get_computer_object()
try:
compObj = nt.GetObject('', 'WinNT://.,computer')
newGroup = compObj.Create('group', name)
newGroup.SetInfo()
ret['changes'].append('Successfully created group {0}'.format(name))
@ -104,10 +108,8 @@ def delete(name, **kwargs):
'comment': ''}
if info(name):
pythoncom.CoInitialize()
nt = win32com.client.Dispatch('AdsNameSpaces')
compObj = _get_computer_object()
try:
compObj = nt.GetObject('', 'WinNT://.,computer')
compObj.Delete('group', name)
ret['changes'].append(('Successfully removed group {0}').format(name))
except pywintypes.com_error as com_err:
@ -144,14 +146,12 @@ def info(name):
salt '*' group.info foo
'''
pythoncom.CoInitialize()
nt = win32com.client.Dispatch('AdsNameSpaces')
groupObj = _get_group_object(name)
existing_members = _get_group_members(groupObj)
try:
groupObj = nt.GetObject('', 'WinNT://./' + name + ',group')
gr_name = groupObj.Name
gr_mem = []
for member in groupObj.members():
for member in existing_members:
gr_mem.append(
member.ADSPath.replace('WinNT://', '').replace(
'/', '\\').encode('ascii', 'backslashreplace'))
@ -213,6 +213,21 @@ def getent(refresh=False):
return ret
def _get_group_object(name):
pythoncom.CoInitialize()
nt = win32com.client.Dispatch('AdsNameSpaces')
return nt.GetObject('', 'WinNT://./' + name + ',group')
def _get_group_members(groupObj):
existingMembers = []
for member in groupObj.members():
existingMembers.append(
member.ADSPath.replace('WinNT://', '').replace(
'/', '\\').encode('ascii', 'backslashreplace').lower())
return existingMembers
def adduser(name, username, **kwargs):
'''
Add a user to a group
@ -240,17 +255,11 @@ def adduser(name, username, **kwargs):
'changes': {'Users Added': []},
'comment': ''}
pythoncom.CoInitialize()
nt = win32com.client.Dispatch('AdsNameSpaces')
groupObj = nt.GetObject('', 'WinNT://./' + name + ',group')
existingMembers = []
for member in groupObj.members():
existingMembers.append(
member.ADSPath.replace('WinNT://', '').replace(
'/', '\\').encode('ascii', 'backslashreplace').lower())
groupObj = _get_group_object(name)
existingMembers = _get_group_members(groupObj)
try:
if salt.utils.win_functions.get_sam_name(username).lower() not in existingMembers:
if salt.utils.win_functions.get_sam_name(username) not in existingMembers:
if not __opts__['test']:
groupObj.Add('WinNT://' + username.replace('\\', '/'))
@ -299,17 +308,11 @@ def deluser(name, username, **kwargs):
'changes': {'Users Removed': []},
'comment': ''}
pythoncom.CoInitialize()
nt = win32com.client.Dispatch('AdsNameSpaces')
groupObj = nt.GetObject('', 'WinNT://./' + name + ',group')
existingMembers = []
for member in groupObj.members():
existingMembers.append(
member.ADSPath.replace('WinNT://', '').replace(
'/', '\\').encode('ascii', 'backslashreplace').lower())
groupObj = _get_group_object(name)
existingMembers = _get_group_members(groupObj)
try:
if salt.utils.win_functions.get_sam_name(username).lower() in existingMembers:
if salt.utils.win_functions.get_sam_name(username) in existingMembers:
if not __opts__['test']:
groupObj.Remove('WinNT://' + username.replace('\\', '/'))

View file

@ -10,6 +10,8 @@ from __future__ import absolute_import
from tests.support.mixins import LoaderModuleMockMixin
from tests.support.unit import TestCase, skipIf
from tests.support.mock import (
MagicMock,
Mock,
patch,
NO_MOCK,
NO_MOCK_REASON
@ -45,21 +47,103 @@ class WinGroupTestCase(TestCase, LoaderModuleMockMixin):
def test_add(self):
'''
Test if it add the specified group
Test adding a new group
'''
self.assertDictEqual(win_groupadd.add('foo'),
{'changes': [], 'name': 'foo', 'result': None,
'comment': 'The group foo already exists.'})
info = MagicMock(return_value=False)
with patch.object(win_groupadd, 'info', info),\
patch.object(win_groupadd, '_get_computer_object', Mock()):
self.assertDictEqual(win_groupadd.add('foo'),
{'changes': ['Successfully created group foo'],
'name': 'foo',
'result': True,
'comment': ''})
def test_add_group_exists(self):
'''
Test adding a new group if the group already exists
'''
info = MagicMock(return_value={'name': 'foo',
'passwd': None,
'gid': None,
'members': ['HOST\\spongebob']})
with patch.object(win_groupadd, 'info', info),\
patch.object(win_groupadd, '_get_computer_object', Mock()):
self.assertDictEqual(win_groupadd.add('foo'),
{'changes': [], 'name': 'foo', 'result': None,
'comment': 'The group foo already exists.'})
def test_add_error(self):
'''
Test adding a group and encountering an error
'''
class CompObj(object):
def Create(self, type, name):
raise pywintypes.com_error(-2147352567, 'Exception occurred.', (0, None, 'C', None, 0, -2146788248), None)
compobj_mock = MagicMock(return_value=CompObj())
info = MagicMock(return_value=False)
with patch.object(win_groupadd, 'info', info),\
patch.object(win_groupadd, '_get_computer_object', compobj_mock):
self.assertDictEqual(win_groupadd.add('foo'),
{'changes': [],
'name': 'foo',
'result': False,
'comment': 'Failed to create group foo. C'})
# 'delete' function tests: 1
def test_delete(self):
'''
Test if it remove the specified group
Test removing a group
'''
self.assertDictEqual(win_groupadd.delete('foo'),
{'changes': [], 'name': 'foo', 'result': None,
'comment': 'The group foo does not exists.'})
info = MagicMock(return_value={'name': 'foo',
'passwd': None,
'gid': None,
'members': ['HOST\\spongebob']})
with patch.object(win_groupadd, 'info', info), \
patch.object(win_groupadd, '_get_computer_object', Mock()):
self.assertDictEqual(
win_groupadd.delete('foo'),
{'changes': ['Successfully removed group foo'],
'name': 'foo',
'result': True,
'comment': ''})
def test_delete_no_group(self):
'''
Test removing a group that doesn't exists
'''
info = MagicMock(return_value=False)
with patch.object(win_groupadd, 'info', info), \
patch.object(win_groupadd, '_get_computer_object', Mock()):
self.assertDictEqual(win_groupadd.delete('foo'),
{'changes': [], 'name': 'foo', 'result': None,
'comment': 'The group foo does not exists.'})
def test_delete_error(self):
'''
Test removing a group and encountering an error
'''
class CompObj(object):
def Delete(self, type, name):
raise pywintypes.com_error(-2147352567, 'Exception occurred.', (0, None, 'C', None, 0, -2146788248), None)
compobj_mock = MagicMock(return_value=CompObj())
info = MagicMock(return_value={'name': 'foo',
'passwd': None,
'gid': None,
'members': ['HOST\\spongebob']})
with patch.object(win_groupadd, 'info', info),\
patch.object(win_groupadd, '_get_computer_object', compobj_mock):
self.assertDictEqual(
win_groupadd.delete('foo'),
{'changes': [],
'name': 'foo',
'result': False,
'comment': 'Failed to remove group foo. C'})
# 'info' function tests: 1
@ -67,12 +151,14 @@ class WinGroupTestCase(TestCase, LoaderModuleMockMixin):
'''
Test if it return information about a group.
'''
with patch(win_groupadd.win32.client, 'flag', None):
self.assertDictEqual(win_groupadd.info('dc=salt'),
members = MagicMock(return_value=['HOST\\steve'])
with patch.object(win_groupadd, '_get_group_object', Mock()), \
patch.object(win_groupadd, '_get_group_members', members):
self.assertDictEqual(win_groupadd.info('salt'),
{'gid': None,
'members': ['dc=\\user1'],
'members': ['user1'],
'passwd': None,
'name': 'WinNT://./dc=salt,group'})
'name': 'salt'})
with patch(win_groupadd.win32.client, 'flag', 1):
self.assertFalse(win_groupadd.info('dc=salt'))
@ -93,31 +179,108 @@ class WinGroupTestCase(TestCase, LoaderModuleMockMixin):
def test_adduser(self):
'''
Test if it add a user to a group
Test adding a user to a group
'''
with patch(win_groupadd.win32.client, 'flag', None):
self.assertDictEqual(win_groupadd.adduser('dc=foo', 'dc=\\username'),
{'changes': {'Users Added': ['dc=\\username']},
'comment': '', 'name': 'dc=foo', 'result': True})
members = MagicMock(return_value=['HOST\\steve'])
with patch.object(win_groupadd, '_get_group_object', Mock()),\
patch.object(win_groupadd, '_get_group_members', members),\
patch('salt.utils.win_functions.get_sam_name', return_value='HOST\\spongebob'):
self.assertDictEqual(
win_groupadd.adduser('foo', 'spongebob'),
{'changes': {'Users Added': ['spongebob']},
'comment': '',
'name': 'foo',
'result': True})
with patch(win_groupadd.win32.client, 'flag', 1):
comt = ('Failed to add dc=\\username to group dc=foo. C')
self.assertDictEqual(win_groupadd.adduser('dc=foo', 'dc=\\username'),
{'changes': {'Users Added': []}, 'name': 'dc=foo',
'comment': comt, 'result': False})
def test_add_user_already_exists(self):
'''
Test adding a user that already exists
'''
members = MagicMock(return_value=['HOST\\steve'])
with patch.object(win_groupadd, '_get_group_object', Mock()), \
patch.object(win_groupadd, '_get_group_members', members), \
patch('salt.utils.win_functions.get_sam_name', return_value='HOST\\spongebob'):
self.assertDictEqual(
win_groupadd.adduser('foo', 'spongebob'),
{'changes': {'Users Added': ['spongebob']},
'comment': '',
'name': 'foo',
'result': True})
def test_add_user_error(self):
'''
Test adding a user and encountering an error
'''
# Create mock group object
class GroupObj(object):
def Add(self, name):
raise pywintypes.com_error(-2147352567, 'Exception occurred.', (0, None, 'C', None, 0, -2146788248), None)
groupobj_mock = MagicMock(return_value=GroupObj())
members = MagicMock(return_value=['HOST\\steve'])
with patch.object(win_groupadd, '_get_group_object', groupobj_mock):
with patch.object(win_groupadd, '_get_group_members', members):
comt = ('Failed to add username to group foo. C')
self.assertDictEqual(
win_groupadd.adduser('foo', 'username'),
{'changes': {'Users Added': []},
'name': 'foo',
'comment': comt,
'result': False})
# 'deluser' function tests: 1
def test_deluser(self):
'''
Test if it remove a user to a group
Test removing a user from a group
'''
ret = {'changes': {'Users Removed': []},
'comment': 'User dc=\\username is not a member of dc=foo',
'name': 'dc=foo', 'result': None}
# Test removing a user
members = MagicMock(return_value=['HOST\\spongebob'])
with patch.object(win_groupadd, '_get_group_object', Mock()), \
patch.object(win_groupadd, '_get_group_members', members), \
patch('salt.utils.win_functions.get_sam_name', return_value='HOST\\spongebob'):
ret = {'changes': {'Users Removed': ['spongebob']},
'comment': '',
'name': 'foo', 'result': True}
self.assertDictEqual(win_groupadd.deluser('foo', 'spongebob'), ret)
self.assertDictEqual(win_groupadd.deluser('dc=foo', 'dc=\\username'),
ret)
def test_deluser_no_user(self):
'''
Test removing a user from a group and that user is not a member of the
group
'''
# Test removing a user that's not in the group
members = MagicMock(return_value=['HOST\\steve'])
with patch.object(win_groupadd, '_get_group_object', Mock()), \
patch.object(win_groupadd, '_get_group_members', members), \
patch('salt.utils.win_functions.get_sam_name', return_value='HOST\\spongebob'):
ret = {'changes': {'Users Removed': []},
'comment': 'User username is not a member of foo',
'name': 'foo', 'result': None}
self.assertDictEqual(win_groupadd.deluser('foo', 'username'), ret)
def test_deluser_error(self):
'''
Test removing a user and encountering an error
'''
class GroupObj(object):
def Remove(self, name):
raise pywintypes.com_error(-2147352567, 'Exception occurred.', (0, None, 'C', None, 0, -2146788248), None)
groupobj_mock = MagicMock(return_value=GroupObj())
members = MagicMock(return_value=['HOST\\spongebob'])
with patch.object(win_groupadd, '_get_group_object', groupobj_mock), \
patch.object(win_groupadd, '_get_group_members', members), \
patch('salt.utils.win_functions.get_sam_name', return_value='HOST\\spongebob'):
comt = ('Failed to remove spongebob from group foo. C')
self.assertDictEqual(
win_groupadd.deluser('foo', 'spongebob'),
{'changes': {'Users Removed': []},
'name': 'foo',
'comment': comt,
'result': False})
# 'members' function tests: 1