Merge branch '2017.7' into '2018.3'

Conflicts:
  - salt/modules/win_snmp.py
  - tests/integration/modules/test_saltutil.py
  - tests/integration/states/test_pkg.py
  - tests/support/helpers.py
  - tests/support/runtests.py
  - tests/unit/fileserver/test_gitfs.py
  - tests/whitelist.txt
This commit is contained in:
rallytime 2018-05-29 11:14:39 -04:00
commit dc32b67c03
No known key found for this signature in database
GPG Key ID: E8F1A4B90D0DEA19
27 changed files with 702 additions and 65 deletions

View File

@ -0,0 +1,17 @@
===========================
In Progress: Salt 2017.7.7 Release Notes
===========================
Version 2017.7.7 is an **unreleased** bugfix release for :ref:`2017.7.0 <release-2017-7-0>`.
This release is still in progress and has not been released yet.
New win_snmp behavior
---------------------
`win_snmp.get_community_names` now returns the SNMP settings actually in effect
on the box. If settings are managed via GroupPolicy, those settings will be
returned. Otherwise, normal settings are returned.
`win_snmp.set_community_names` now raises a CommandExecutionError when SNMP
settings are being managed by GroupPolicy

165
pkg/windows/sign.bat Normal file
View File

@ -0,0 +1,165 @@
:: ############################################################################
::
:: FILE: sign.bat
::
:: DESCRIPTION: Signing and Hashing script for Salt builds on Windows.
:: Requires an official Code Signing Certificate and drivers
:: installed to sign the files. Generates hashes in MD5 and
:: SHA256 in a file of the same name with a `.md5` or
:: `.sha256` extension.
::
:: NOTE: This script is used internally by SaltStack to sign and
:: hash Windows Installer builds and uses resources not
:: available to the community, such as SaltStack's Code
:: Signing Certificate. It is placed here for version
:: control.
::
:: COPYRIGHT: (c) 2012-2018 by the SaltStack Team
::
:: LICENSE: Apache 2.0
:: ORGANIZATION: SaltStack, Inc (saltstack.com)
:: CREATED: 2017
::
:: ############################################################################
::
:: USAGE: The script must be located in a directory that has the installer
:: files in a subfolder named with the major version, ie: `2018.3`.
:: Insert the key fob that contains the code signing certificate. Run
:: the script passing the full version: `.\sign.bat 2018.3.1`.
::
:: The script will sign the installers and generate the corresponding
:: hash files. These can then be uploaded to the salt repo.
::
:: The files must be in the following format:
:: <Series>\Salt-Minion-<Version>-<Python Version>-<System Architecture>-Setup.exe
:: So, for a Salt Minion installer for 2018.3.1 on AMD64 for Python 3
:: file would be placed in a subdirectory named `2018.3` and the file
:: would be named: `Salt-Minion-2018.3.1-Py3-AMD64-Setup.exe`. This
:: is how the file is created by the NSI Script anyway.
::
:: ############################################################################
@ echo off
if [%1]==[] (
echo You must pass a version
goto quit
) else (
set "Version=%~1"
)
for /F "tokens=1,2 delims=." %%a in ("%Version%") do (set Series=%%a.%%b)
:: Sign Installer Files
echo ===========================================================================
echo Signing...
echo ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
signtool.exe sign /t http://timestamp.digicert.com ^
"%Series%\Salt-Minion-%Version%-AMD64-Setup.exe" ^
"%Series%\Salt-Minion-%Version%-x86-Setup.exe" ^
"%Series%\Salt-%Version%-AMD64-Setup.exe" ^
"%Series%\Salt-%Version%-x86-Setup.exe" ^
"%Series%\Salt-%Version%-Py2-AMD64-Setup.exe" ^
"%Series%\Salt-%Version%-Py2-x86-Setup.exe" ^
"%Series%\Salt-%Version%-Py3-AMD64-Setup.exe" ^
"%Series%\Salt-%Version%-Py3-x86-Setup.exe" ^
"%Series%\Salt-Minion-%Version%-Py2-AMD64-Setup.exe" ^
"%Series%\Salt-Minion-%Version%-Py2-x86-Setup.exe" ^
"%Series%\Salt-Minion-%Version%-Py3-AMD64-Setup.exe" ^
"%Series%\Salt-Minion-%Version%-Py3-x86-Setup.exe"
echo ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
echo Signing Complete
echo ===========================================================================
:: Create Hash files
echo ===========================================================================
echo Creating Hashes...
echo ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
set "file_name=Salt-Minion-%Version%-AMD64-Setup.exe"
set "file=.\%Series%\%file_name%"
if exist "%file%" (
echo - %file_name%
powershell -c "$hash = (Get-FileHash -Algorithm MD5 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.md5\""
powershell -c "$hash = (Get-FileHash -Algorithm SHA256 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.sha256\"")
set "file_name=Salt-Minion-%Version%-x86-Setup.exe"
set "file=.\%Series%\%file_name%"
if exist "%file%" (
echo - %file_name%
powershell -c "$hash = (Get-FileHash -Algorithm MD5 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.md5\""
powershell -c "$hash = (Get-FileHash -Algorithm SHA256 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.sha256\"")
set "file_name=Salt-%Version%-AMD64-Setup.exe"
set "file=.\%Series%\%file_name%"
if exist "%file%" (
echo - %file_name%
powershell -c "$hash = (Get-FileHash -Algorithm MD5 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.md5\""
powershell -c "$hash = (Get-FileHash -Algorithm SHA256 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.sha256\"")
set "file_name=Salt-%Version%-x86-Setup.exe"
set "file=.\%Series%\%file_name%"
if exist "%file%" (
echo - %file_name%
powershell -c "$hash = (Get-FileHash -Algorithm MD5 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.md5\""
powershell -c "$hash = (Get-FileHash -Algorithm SHA256 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.sha256\"")
set "file_name=Salt-%Version%-Py2-AMD64-Setup.exe"
set "file=.\%Series%\%file_name%"
if exist "%file%" (
echo - %file_name%
powershell -c "$hash = (Get-FileHash -Algorithm MD5 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.md5\""
powershell -c "$hash = (Get-FileHash -Algorithm SHA256 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.sha256\"")
set "file_name=Salt-%Version%-Py2-x86-Setup.exe"
set "file=.\%Series%\%file_name%"
if exist "%file%" (
echo - %file_name%
powershell -c "$hash = (Get-FileHash -Algorithm MD5 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.md5\""
powershell -c "$hash = (Get-FileHash -Algorithm SHA256 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.sha256\"")
set "file_name=Salt-%Version%-Py3-AMD64-Setup.exe"
set "file=.\%Series%\%file_name%"
if exist "%file%" (
echo - %file_name%
powershell -c "$hash = (Get-FileHash -Algorithm MD5 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.md5\""
powershell -c "$hash = (Get-FileHash -Algorithm SHA256 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.sha256\"")
set "file_name=Salt-%Version%-Py3-x86-Setup.exe"
set "file=.\%Series%\%file_name%"
if exist "%file%" (
echo - %file_name%
powershell -c "$hash = (Get-FileHash -Algorithm MD5 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.md5\""
powershell -c "$hash = (Get-FileHash -Algorithm SHA256 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.sha256\"")
set "file_name=Salt-Minion-%Version%-Py2-AMD64-Setup.exe"
set "file=.\%Series%\%file_name%"
if exist "%file%" (
echo - %file_name%
powershell -c "$hash = (Get-FileHash -Algorithm MD5 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.md5\""
powershell -c "$hash = (Get-FileHash -Algorithm SHA256 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.sha256\"")
set "file_name=Salt-Minion-%Version%-Py2-x86-Setup.exe"
set "file=.\%Series%\%file_name%"
if exist "%file%" (
echo - %file_name%
powershell -c "$hash = (Get-FileHash -Algorithm MD5 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.md5\""
powershell -c "$hash = (Get-FileHash -Algorithm SHA256 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.sha256\"")
set "file_name=Salt-Minion-%Version%-Py3-AMD64-Setup.exe"
set "file=.\%Series%\%file_name%"
if exist "%file%" (
echo - %file_name%
powershell -c "$hash = (Get-FileHash -Algorithm MD5 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.md5\""
powershell -c "$hash = (Get-FileHash -Algorithm SHA256 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.sha256\"")
set "file_name=Salt-Minion-%Version%-Py3-x86-Setup.exe"
set "file=.\%Series%\%file_name%"
if exist "%file%" (
echo - %file_name%
powershell -c "$hash = (Get-FileHash -Algorithm MD5 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.md5\""
powershell -c "$hash = (Get-FileHash -Algorithm SHA256 \"%file%\").Hash; Out-File -InputObject $hash\" %file_name%\" -FilePath \"%file%.sha256\"")
echo ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
echo Hashing Complete
echo ===========================================================================
:quit

View File

@ -993,6 +993,59 @@ def get_password(vm_):
)
def _decode_linode_plan_label(label):
'''
Attempts to decode a user-supplied Linode plan label
into the format in Linode API output
label
The label, or name, of the plan to decode.
Example:
`Linode 2048` will decode to `Linode 2GB`
'''
sizes = avail_sizes()
if label not in sizes:
if 'GB' in label:
raise SaltCloudException(
'Invalid Linode plan ({}) specified - call avail_sizes() for all available options'.format(label)
)
else:
plan = label.split()
if len(plan) != 2:
raise SaltCloudException(
'Invalid Linode plan ({}) specified - call avail_sizes() for all available options'.format(label)
)
plan_type = plan[0]
try:
plan_size = int(plan[1])
except TypeError:
plan_size = 0
log.debug('Failed to decode Linode plan label in Cloud Profile: %s', label)
if plan_type == 'Linode' and plan_size == 1024:
plan_type = 'Nanode'
plan_size = plan_size/1024
new_label = "{} {}GB".format(plan_type, plan_size)
if new_label not in sizes:
raise SaltCloudException(
'Invalid Linode plan ({}) specified - call avail_sizes() for all available options'.format(new_label)
)
log.warning('An outdated Linode plan label was detected in your Cloud Profile ({}).'
' Please update the profile to use'
' the new label format ({}) for the requested Linode plan size.'.format(label, new_label))
label = new_label
return sizes[label]['PLANID']
def get_plan_id(kwargs=None, call=None):
'''
Returns the Linode Plan ID.
@ -1020,7 +1073,9 @@ def get_plan_id(kwargs=None, call=None):
'The get_plan_id function requires a \'label\'.'
)
return avail_sizes()[label]['PLANID']
label = _decode_linode_plan_label(label)
return label
def get_private_ip(vm_):

View File

@ -2305,9 +2305,9 @@ def _hw_data(osdata):
product_regexes = [
re.compile(r) for r in [
r'(?im)^\s*System\s+Configuration:\s*.*?sun\d\S+\s(.*)', # prtdiag
r'(?im)^\s*banner-name:\s*(.*)', # prtconf
r'(?im)^\s*product-name:\s*(.*)', # prtconf
r'(?im)^\s*System\s+Configuration:\s*.*?sun\d\S+[^\S\r\n]*(.*)', # prtdiag
r'(?im)^[^\S\r\n]*banner-name:[^\S\r\n]*(.*)', # prtconf
r'(?im)^[^\S\r\n]*product-name:[^\S\r\n]*(.*)', # prtconf
]
]
@ -2374,8 +2374,11 @@ def _hw_data(osdata):
for regex in product_regexes:
res = regex.search(data)
if res and len(res.groups()) >= 1:
grains['product'] = res.group(1).strip().replace("'", "")
break
t_productname = res.group(1).strip().replace("'", "")
if t_productname:
grains['product'] = t_productname
grains['productname'] = t_productname
break
return grains

View File

@ -9,16 +9,20 @@ import logging
# Import Salt libs
import salt.utils.platform
from salt.exceptions import SaltInvocationError
from salt.exceptions import SaltInvocationError, CommandExecutionError
# Import 3rd party libs
from salt.ext import six
_HKEY = 'HKLM'
_SNMP_KEY = r'SYSTEM\CurrentControlSet\Services\SNMP\Parameters'
_AGENT_KEY = r'{0}\RFC1156Agent'.format(_SNMP_KEY)
_COMMUNITIES_KEY = r'{0}\ValidCommunities'.format(_SNMP_KEY)
_SNMP_GPO_KEY = r'SOFTWARE\Policies\SNMP\Parameters'
_COMMUNITIES_GPO_KEY = r'{0}\ValidCommunities'.format(_SNMP_GPO_KEY)
_PERMISSION_TYPES = {'None': 1,
'Notify': 2,
'Read Only': 4,
@ -284,6 +288,21 @@ def get_community_names():
'''
Get the current accepted SNMP community names and their permissions.
If community names are being managed by Group Policy, those values will be
returned instead like this:
.. code-block:: bash
TestCommunity:
Managed by GPO
Community names managed normally will denote the permission instead:
.. code-block:: bash
TestCommunity:
Read Only
Returns:
dict: A dictionary of community names and permissions.
@ -294,25 +313,69 @@ def get_community_names():
salt '*' win_snmp.get_community_names
'''
ret = dict()
current_values = __salt__['reg.list_values'](
_HKEY, _COMMUNITIES_KEY, include_default=False)
# The communities are stored as the community name with a numeric permission
# value. Convert the numeric value to the text equivalent, as present in the
# Windows SNMP service GUI.
if isinstance(current_values, list):
for current_value in current_values:
# Look in GPO settings first
if __salt__['reg.key_exists'](_HKEY, _COMMUNITIES_GPO_KEY):
# Ignore error values
if not isinstance(current_value, dict):
continue
_LOG.debug('Loading communities from Group Policy settings')
permissions = six.text_type()
for permission_name in _PERMISSION_TYPES:
if current_value['vdata'] == _PERMISSION_TYPES[permission_name]:
permissions = permission_name
break
ret[current_value['vname']] = permissions
current_values = __salt__['reg.list_values'](
_HKEY, _COMMUNITIES_GPO_KEY, include_default=False)
# GPO settings are different in that they do not designate permissions
# They are a numbered list of communities like so:
#
# {1: "community 1",
# 2: "community 2"}
#
# Denote that it is being managed by Group Policy.
#
# community 1:
# Managed by GPO
# community 2:
# Managed by GPO
if isinstance(current_values, list):
for current_value in current_values:
# Ignore error values
if not isinstance(current_value, dict):
continue
ret[current_value['vdata']] = 'Managed by GPO'
if not ret:
_LOG.debug('Loading communities from SNMP settings')
current_values = __salt__['reg.list_values'](
_HKEY, _COMMUNITIES_KEY, include_default=False)
# The communities are stored as the community name with a numeric
# permission value. Like this (4 = Read Only):
#
# {"community 1": 4,
# "community 2": 4}
#
# Convert the numeric value to the text equivalent, as present in the
# Windows SNMP service GUI.
#
# community 1:
# Read Only
# community 2:
# Read Only
if isinstance(current_values, list):
for current_value in current_values:
# Ignore error values
if not isinstance(current_value, dict):
continue
permissions = six.text_type()
for permission_name in _PERMISSION_TYPES:
if current_value['vdata'] == _PERMISSION_TYPES[permission_name]:
permissions = permission_name
break
ret[current_value['vname']] = permissions
if not ret:
_LOG.debug('Unable to find existing communities.')
@ -323,6 +386,11 @@ def set_community_names(communities):
'''
Manage the SNMP accepted community names and their permissions.
.. note::
Settings managed by Group Policy will always take precedence over those
set using the SNMP interface. Therefore if this function finds Group
Policy settings it will raise a CommandExecutionError
Args:
communities (dict): A dictionary of SNMP community names and
permissions. The possible permissions can be found via
@ -331,6 +399,10 @@ def set_community_names(communities):
Returns:
bool: True if successful, otherwise False
Raises:
CommandExecutionError:
If SNMP settings are being managed by Group Policy
CLI Example:
.. code-block:: bash
@ -339,6 +411,11 @@ def set_community_names(communities):
'''
values = dict()
if __salt__['reg.key_exists'](_HKEY, _COMMUNITIES_GPO_KEY):
_LOG.debug('Communities on this system are managed by Group Policy')
raise CommandExecutionError(
'Communities on this system are managed by Group Policy')
current_communities = get_community_names()
if communities == current_communities:

View File

@ -1,6 +1,17 @@
# -*- coding: utf-8 -*-
'''
A convenience system to manage reactors
Beginning in the 2017.7 release, the reactor runner requires that the reactor
system is running. This is accomplished one of two ways, either
by having reactors configured or by including ``reactor`` in the
engine configuration for the Salt master.
.. code-block:: yaml
engines:
- reactor
'''
# Import python libs
from __future__ import absolute_import, print_function, unicode_literals

View File

@ -24,7 +24,7 @@ from tests.support import win_installer
INSTANCE_NAME = generate_random_name('CLOUD-TEST-')
PROVIDER_NAME = 'ec2'
HAS_WINRM = salt.utils.cloud.HAS_WINRM and salt.utils.cloud.HAS_SMB
TIMEOUT = 1000
TIMEOUT = 1200
class EC2Test(ShellCase):

View File

@ -1,12 +1,12 @@
ec2-test:
provider: ec2-config
image: ami-98aa1cf0
size: m1.small
size: m1.large
sh_username: ec2-user
script_args: '-P -Z'
ec2-win2012r2-test:
provider: ec2-config
size: m1.small
size: m1.large
image: ami-eb1ecd96
smb_port: 445
win_installer: ''
@ -19,7 +19,7 @@ ec2-win2012r2-test:
deploy: True
ec2-win2016-test:
provider: ec2-config
size: m1.small
size: m1.large
image: ami-ed14c790
smb_port: 445
win_installer: ''

View File

@ -0,0 +1,24 @@
{% set versions = {'18':['05', '03', '01'], '16':['04', '03', '02', '00'], '9':['20']} %}
Zzip:
{% for major, subversions in versions.items() %}
{% for minor in subversions %}
'{{major}}.{{minor}}.00.0':
{% if grains['cpuarch'] == 'AMD64' %}
full_name: '7-Zip {{major}}.{{minor}} (x64 edition)'
installer: 'http://d.7-zip.org/a/7z{{major}}{{minor}}-x64.msi'
uninstaller: 'http://d.7-zip.org/a/7z{{major}}{{minor}}-x64.msi'
arch: x64
{% else %}
full_name: '7-Zip {{major}}.{{minor}}'
installer: 'http://d.7-zip.org/a/7z{{major}}{{minor}}.msi'
uninstaller: 'http://d.7-zip.org/a/7z{{major}}{{minor}}.msi'
arch: x86
{% endif %}
install_flags: '/qn /norestart'
uninstall_flags: '/qn /norestart'
msiexec: True
locale: en_US
reboot: False
{% endfor %}
{% endfor %}

View File

@ -12,7 +12,8 @@ from tests.support.case import ModuleCase
from tests.support.helpers import (
destructiveTest,
skip_if_binaries_missing,
skip_if_not_root
skip_if_not_root,
this_user,
)
from tests.support.paths import TMP
from tests.support.unit import skipIf
@ -257,12 +258,7 @@ class CMDModuleTest(ModuleCase):
cmd = '''echo 'SELECT * FROM foo WHERE bar="baz"' '''
expected_result = 'SELECT * FROM foo WHERE bar="baz"'
try:
runas = os.getlogin()
except: # pylint: disable=W0702
# On some distros (notably Gentoo) os.getlogin() fails
import pwd
runas = pwd.getpwuid(os.getuid())[0]
runas = this_user()
result = self.run_function('cmd.run_stdout', [cmd],
runas=runas).strip()

View File

@ -194,7 +194,18 @@ class SaltUtilSyncPillarTest(ModuleCase):
'''))
self.run_function('saltutil.refresh_pillar')
self.run_function('test.sleep', [5])
pillar = False
timeout = time.time() + 30
while not pillar:
post_pillar = self.run_function('pillar.raw')
try:
self.assertIn(pillar_key, post_pillar.get(pillar_key, 'didnotwork'))
pillar = True
except AssertionError:
if time.time() > timeout:
self.assertIn(pillar_key, post_pillar.get(pillar_key, 'didnotwork'))
continue
post_pillar = self.run_function('pillar.raw')
self.assertIn(pillar_key, post_pillar.get(pillar_key, 'didnotwork'))

View File

@ -117,7 +117,7 @@ class ServiceModuleTest(ModuleCase):
systemd = salt.utils.systemd.booted()
# check service was not enabled
if systemd:
if systemd or salt.utils.is_windows():
self.assertIn('ERROR', enable)
else:
self.assertFalse(enable)

View File

@ -0,0 +1,37 @@
# -*- coding: utf-8 -*-
# Import Python libs
from __future__ import absolute_import
# Import Salt Testing libs
from tests.support.case import ModuleCase
from tests.support.unit import skipIf
from tests.support.helpers import destructiveTest
# Import Salt libs
import salt.utils
@skipIf(not salt.utils.is_windows(), 'windows test only')
class WinDNSTest(ModuleCase):
'''
Test for salt.modules.win_dns_client
'''
@destructiveTest
def test_add_remove_dns(self):
'''
Test add and removing a dns server
'''
dns = '8.8.8.8'
interface = 'Ethernet'
# add dns server
self.assertTrue(self.run_function('win_dns_client.add_dns', [dns, interface], index=42))
srvs = self.run_function('win_dns_client.get_dns_servers', interface=interface)
self.assertIn(dns, srvs)
# remove dns server
self.assertTrue(self.run_function('win_dns_client.rm_dns', [dns], interface=interface))
srvs = self.run_function('win_dns_client.get_dns_servers', interface=interface)
self.assertNotIn(dns, srvs)

View File

@ -0,0 +1,26 @@
# -*- coding: utf-8 -*-
# Import Python libs
from __future__ import absolute_import
# Import Salt Testing libs
from tests.support.case import ModuleCase
from tests.support.unit import skipIf
# Import Salt libs
import salt.utils
@skipIf(not salt.utils.is_windows(), 'windows test only')
class WinServermanagerTest(ModuleCase):
'''
Test for salt.modules.win_servermanager
'''
def test_list_available(self):
'''
Test list available features to install
'''
cmd = self.run_function('win_servermanager.list_available')
self.assertIn('DNS', cmd)
self.assertIn('NetworkController', cmd)
self.assertIn('RemoteAccess', cmd)

View File

@ -40,7 +40,7 @@ _PKG_TARGETS = {
'FreeBSD': ['aalib', 'pth'],
'Suse': ['aalib', 'rpm-python'],
'MacOS': ['libpng', 'jpeg'],
'Windows': ['firefox', '7zip'],
'Windows': ['putty', '7zip'],
}
_PKG_CAP_TARGETS = {
@ -167,7 +167,6 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
self.run_function('pkg.refresh_db')
__testcontext__['refresh'] = True
@skipIf(salt.utils.platform.is_windows(), 'minion is windows')
@requires_system_grains
def test_pkg_001_installed(self, grains=None):
'''
@ -198,7 +197,6 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
ret = self.run_state('pkg.removed', name=target)
self.assertSaltTrueReturn(ret)
@skipIf(salt.utils.platform.is_windows(), 'minion is windows')
@requires_system_grains
def test_pkg_002_installed_with_version(self, grains=None):
'''
@ -246,7 +244,6 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
ret = self.run_state('pkg.removed', name=target)
self.assertSaltTrueReturn(ret)
@skipIf(salt.utils.platform.is_windows(), 'minion is windows')
@requires_system_grains
def test_pkg_003_installed_multipkg(self, grains=None):
'''
@ -268,7 +265,10 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
# If this assert fails, we need to find new targets, this test needs to
# be able to test successful installation of packages, so these
# packages need to not be installed before we run the states below
self.assertFalse(any(version.values()))
try:
self.assertFalse(any(version.values()))
except AssertionError:
self.assertSaltTrueReturn(self.run_state('pkg.removed', name=None, pkgs=pkg_targets))
ret = self.run_state('pkg.installed',
name=None,
@ -278,7 +278,6 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
ret = self.run_state('pkg.removed', name=None, pkgs=pkg_targets)
self.assertSaltTrueReturn(ret)
@skipIf(salt.utils.platform.is_windows(), 'minion is windows')
@requires_system_grains
def test_pkg_004_installed_multipkg_with_version(self, grains=None):
'''
@ -327,7 +326,6 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
ret = self.run_state('pkg.removed', name=None, pkgs=pkg_targets)
self.assertSaltTrueReturn(ret)
@skipIf(salt.utils.platform.is_windows(), 'minion is windows')
@requires_system_grains
def test_pkg_005_installed_32bit(self, grains=None):
'''
@ -364,7 +362,6 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
ret = self.run_state('pkg.removed', name=target)
self.assertSaltTrueReturn(ret)
@skipIf(salt.utils.platform.is_windows(), 'minion is windows')
@requires_system_grains
def test_pkg_006_installed_32bit_with_version(self, grains=None):
'''
@ -412,7 +409,6 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
ret = self.run_state('pkg.removed', name=target)
self.assertSaltTrueReturn(ret)
@skipIf(salt.utils.platform.is_windows(), 'minion is windows')
@requires_system_grains
def test_pkg_007_with_dot_in_pkgname(self, grains=None):
'''
@ -443,7 +439,6 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
ret = self.run_state('pkg.removed', name=target)
self.assertSaltTrueReturn(ret)
@skipIf(salt.utils.platform.is_windows(), 'minion is windows')
@requires_system_grains
def test_pkg_008_epoch_in_version(self, grains=None):
'''
@ -494,7 +489,6 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
refresh=False)
self.assertSaltTrueReturn(ret)
@skipIf(salt.utils.platform.is_windows(), 'minion is windows')
@requires_salt_modules('pkg.info_installed')
def test_pkg_010_latest_with_epoch_and_info_installed(self):
'''
@ -514,7 +508,6 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
ret = self.run_function('pkg.info_installed', [package])
self.assertTrue(pkgquery in six.text_type(ret))
@skipIf(salt.utils.platform.is_windows(), 'minion is windows')
@requires_system_grains
def test_pkg_011_latest(self, grains=None):
'''
@ -546,7 +539,6 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
ret = self.run_state('pkg.removed', name=target)
self.assertSaltTrueReturn(ret)
@skipIf(salt.utils.platform.is_windows(), 'minion is windows')
@requires_system_grains
def test_pkg_012_latest_only_upgrade(self, grains=None):
'''

View File

@ -59,8 +59,12 @@ from tests.support.paths import FILES, TMP
import salt.utils.files
import salt.utils.platform
log = logging.getLogger(__name__)
if salt.utils.platform.is_windows():
import salt.utils.win_functions
else:
import pwd
log = logging.getLogger(__name__)
HAS_SYMLINKS = None
@ -1159,7 +1163,6 @@ def skip_if_not_root(func):
func.__unittest_skip__ = True
func.__unittest_skip_why__ = 'You must be logged in as root to run this test'
else:
import salt.utils.win_functions
current_user = salt.utils.win_functions.get_current_user()
if current_user != 'SYSTEM':
if not salt.utils.win_functions.is_admin(current_user):
@ -1592,3 +1595,12 @@ def win32_kill_process_tree(pid, sig=signal.SIGTERM, include_parent=True,
gone, alive = psutil.wait_procs(children, timeout=timeout,
callback=on_terminate)
return (gone, alive)
def this_user():
'''
Get the user associated with the current process.
'''
if salt.utils.is_windows():
return salt.utils.win_functions.get_current_user()
return pwd.getpwuid(os.getuid())[0]

View File

@ -49,7 +49,6 @@
# Import Python modules
from __future__ import absolute_import, print_function
import os
import sys
import shutil
import logging
import multiprocessing
@ -58,6 +57,7 @@ import salt.utils.json
# Import tests support libs
import tests.support.paths as paths
import tests.support.helpers
# Import 3rd-party libs
from salt.ext import six
@ -104,12 +104,9 @@ try:
except ImportError:
pass
if sys.platform.startswith('win'):
import win32api # pylint: disable=import-error
RUNNING_TESTS_USER = win32api.GetUserName()
else:
import pwd
RUNNING_TESTS_USER = pwd.getpwuid(os.getuid()).pw_name
RUNNING_TESTS_USER = tests.support.helpers.this_user()
log = logging.getLogger(__name__)

View File

@ -54,7 +54,8 @@ def latest_version(repo=REPO):
'''
Return the latest version found on the salt repository webpage.
'''
for name, md5 in iter_installers(requests.get(repo).content):
content = requests.get(repo).content.decode('utf-8')
for name, md5 in iter_installers(content):
pass
return split_installer(name)[0]

View File

@ -15,7 +15,7 @@ import tornado.ioloop
import logging
import stat
try:
import pwd
import pwd # pylint: disable=unused-import
except ImportError:
pass
@ -24,6 +24,7 @@ from tests.support.mixins import LoaderModuleMockMixin
from tests.support.unit import TestCase, skipIf
from tests.support.mock import NO_MOCK, NO_MOCK_REASON, patch
from tests.support.paths import TMP, FILES
from tests.support.helpers import this_user
# Import salt libs
import salt.fileserver.gitfs as gitfs

View File

@ -0,0 +1,3 @@
Oracle Solaris 11.3 SPARC
Copyright (c) 1983, 2017, Oracle and/or its affiliates. All rights reserved.
Assembled 05 October 2017

View File

@ -0,0 +1,24 @@
System Configuration: Oracle Corporation sun4v
Memory size: 16384 Megabytes
System Peripherals (PROM Nodes):
Node 0xfffffffff
scsi-initiator-id: 00000007
idprom: 00000000.00000000.00000000.00000000.00000000.00000000.00000000.00000000
pcie-ari-supported:
#priqs-per-pcibus: 00000010
#priqs-per-cpu: 00000010
priq-eq-sizes: 00000003
non-ios-perf-counters: 'ORCL,sn-non-ios-pr'
ios-perf-counters: 'ORCL,sn-ios-pr'
storage-variant: '8dbp'
product-name: 'SPARC S7-2'
banner-name: 'SPARC S7-2'
name: 'ORCL,SPARC-S7-2'
stick-frequency: 3b9aca00
hv-api-groups: 00000000.00000000.00000000.00000000.00000000.00000000.00000000.00000000.000000060.00000000.00000000
breakpoint-trap: 0000007f
device_type: 'sun4v'
compatible: 'sun4v'
#address-cells: 00000002
#size-cells: 00000002

View File

@ -0,0 +1,16 @@
System Configuration: Oracle Corporation sun4v
Memory size: 8192 Megabytes
System Peripherals (PROM Nodes):
Node 0xffffffff
idprom: 11111111.11111111.00000000.11111111.00000000.00000000.00000000.00000000
scsi-initiator-id: 00000007
banner-name: 'SPARC Enterprise T5220'
name: 'SUNW,SPARC-Enterprise-T5220'
stick-frequency: 5458c3a0
hv-api-groups: 00000000.00000000.00000000.00000000.00000000.00000000.00000000.00000000
breakpoint-trap: 0000007f
device_type: 'sun4v'
compatible: 'sun4v'
#address-cells: 00000002
#size-cells: 00000002

View File

@ -0,0 +1,24 @@
System Configuration: Oracle Corporation sun4v SPARC S7-2
Memory size: 16384 Megabytes
================================ Virtual CPUs ================================
CPU ID Frequency Implementation Status
------ --------- ---------------------- -------
0 4267 MHz SPARC-S7 on-line
1 4267 MHz SPARC-S7 on-line
2 4267 MHz SPARC-S7 on-line
3 4267 MHz SPARC-S7 on-line
4 4267 MHz SPARC-S7 on-line
5 4267 MHz SPARC-S7 on-line
6 4267 MHz SPARC-S7 on-line
7 4267 MHz SPARC-S7 on-line
8 4267 MHz SPARC-S7 on-line
9 4267 MHz SPARC-S7 on-line
10 4267 MHz SPARC-S7 on-line
11 4267 MHz SPARC-S7 on-line
12 4267 MHz SPARC-S7 on-line
13 4267 MHz SPARC-S7 on-line
14 4267 MHz SPARC-S7 on-line
15 4267 MHz SPARC-S7 on-line

View File

@ -0,0 +1,16 @@
System Configuration: Oracle Corporation sun4v SPARC Enterprise T5220
Memory size: 8192 Megabytes
================================ Virtual CPUs ================================
CPU ID Frequency Implementation Status
------ --------- ---------------------- -------
0 1415 MHz SUNW,UltraSPARC-T2 on-line
1 1415 MHz SUNW,UltraSPARC-T2 on-line
2 1415 MHz SUNW,UltraSPARC-T2 on-line
3 1415 MHz SUNW,UltraSPARC-T2 on-line
4 1415 MHz SUNW,UltraSPARC-T2 on-line
5 1415 MHz SUNW,UltraSPARC-T2 on-line
6 1415 MHz SUNW,UltraSPARC-T2 on-line
7 1415 MHz SUNW,UltraSPARC-T2 on-line

View File

@ -49,6 +49,7 @@ IP6_ADD1 = '2001:4860:4860::8844'
IP6_ADD2 = '2001:4860:4860::8888'
IP6_ADD_SCOPE = 'fe80::6238:e0ff:fe06:3f6b%enp2s0'
OS_RELEASE_DIR = os.path.join(os.path.dirname(__file__), "os-releases")
SOLARIS_DIR = os.path.join(os.path.dirname(__file__), 'solaris')
@skipIf(NO_MOCK, NO_MOCK_REASON)
@ -876,3 +877,100 @@ SwapTotal: 4789244 kB'''
osdata = {'kernel': 'test', }
ret = core._virtual(osdata)
self.assertEqual(ret['virtual'], virt)
def test_solaris_sparc_s7zone(self):
'''
verify productname grain for s7 zone
'''
expectation = {
'productname': 'SPARC S7-2',
'product': 'SPARC S7-2',
}
with salt.utils.fopen(os.path.join(SOLARIS_DIR, 'prtconf.s7-zone')) as sparc_return_data:
this_sparc_return_data = '\n'.join(sparc_return_data.readlines())
this_sparc_return_data += '\n'
self._check_solaris_sparc_productname_grains(this_sparc_return_data, expectation)
def test_solaris_sparc_s7(self):
'''
verify productname grain for s7
'''
expectation = {
'productname': 'SPARC S7-2',
'product': 'SPARC S7-2',
}
with salt.utils.fopen(os.path.join(SOLARIS_DIR, 'prtdiag.s7')) as sparc_return_data:
this_sparc_return_data = '\n'.join(sparc_return_data.readlines())
this_sparc_return_data += '\n'
self._check_solaris_sparc_productname_grains(this_sparc_return_data, expectation)
def test_solaris_sparc_t5220(self):
'''
verify productname grain for t5220
'''
expectation = {
'productname': 'SPARC Enterprise T5220',
'product': 'SPARC Enterprise T5220',
}
with salt.utils.fopen(os.path.join(SOLARIS_DIR, 'prtdiag.t5220')) as sparc_return_data:
this_sparc_return_data = '\n'.join(sparc_return_data.readlines())
this_sparc_return_data += '\n'
self._check_solaris_sparc_productname_grains(this_sparc_return_data, expectation)
def test_solaris_sparc_t5220zone(self):
'''
verify productname grain for t5220 zone
'''
expectation = {
'productname': 'SPARC Enterprise T5220',
'product': 'SPARC Enterprise T5220',
}
with salt.utils.fopen(os.path.join(SOLARIS_DIR, 'prtconf.t5220-zone')) as sparc_return_data:
this_sparc_return_data = '\n'.join(sparc_return_data.readlines())
this_sparc_return_data += '\n'
self._check_solaris_sparc_productname_grains(this_sparc_return_data, expectation)
def _check_solaris_sparc_productname_grains(self, prtdata, expectation):
'''
verify product grains on solaris sparc
'''
import platform
path_isfile_mock = MagicMock(side_effect=lambda x: x in ['/etc/release'])
with patch.object(platform, 'uname',
MagicMock(return_value=('SunOS', 'testsystem', '5.11', '11.3', 'sunv4', 'sparc'))):
with patch.object(salt.utils, 'is_proxy',
MagicMock(return_value=False)):
with patch.object(salt.utils, 'is_linux',
MagicMock(return_value=False)):
with patch.object(salt.utils, 'is_windows',
MagicMock(return_value=False)):
with patch.object(salt.utils, 'is_smartos',
MagicMock(return_value=False)):
with patch.object(salt.utils, 'which_bin',
MagicMock(return_value=None)):
with patch.object(os.path, 'isfile', path_isfile_mock):
with salt.utils.fopen(os.path.join(OS_RELEASE_DIR, "solaris-11.3")) as os_release_file:
os_release_content = os_release_file.readlines()
with patch("salt.utils.fopen", mock_open()) as os_release_file:
os_release_file.return_value.__iter__.return_value = os_release_content
with patch.object(core, '_sunos_cpudata',
MagicMock(return_value={'cpuarch': 'sparcv9',
'num_cpus': '1',
'cpu_model': 'MOCK_CPU_MODEL',
'cpu_flags': []})):
with patch.object(core, '_memdata',
MagicMock(return_value={'mem_total': 16384})):
with patch.object(core, '_zpool_data',
MagicMock(return_value={})):
with patch.object(core, '_virtual',
MagicMock(return_value={})):
with patch.object(core, '_ps',
MagicMock(return_value={})):
with patch.object(salt.utils, 'which',
MagicMock(return_value=True)):
sparc_return_mock = MagicMock(return_value=prtdata)
with patch.dict(core.__salt__, {'cmd.run': sparc_return_mock}):
os_grains = core.os_data()
grains = {k: v for k, v in os_grains.items()
if k in set(['product', 'productname'])}
self.assertEqual(grains, expectation)

View File

@ -11,6 +11,7 @@ from __future__ import absolute_import, unicode_literals, print_function
# Import Salt Libs
import salt.modules.win_snmp as win_snmp
from salt.exceptions import CommandExecutionError
# Import Salt Testing Libs
from tests.support.mixins import LoaderModuleMockMixin
@ -70,19 +71,47 @@ class WinSnmpTestCase(TestCase, LoaderModuleMockMixin):
'''
Test - Get the current accepted SNMP community names and their permissions.
'''
mock_value = MagicMock(return_value=[{'vdata': 16,
'vname': 'TestCommunity'}])
with patch.dict(win_snmp.__salt__, {'reg.list_values': mock_value}):
mock_ret = MagicMock(return_value=[{'vdata': 16,
'vname': 'TestCommunity'}])
mock_false = MagicMock(return_value=False)
with patch.dict(win_snmp.__salt__, {'reg.list_values': mock_ret,
'reg.key_exists': mock_false}):
self.assertEqual(win_snmp.get_community_names(),
COMMUNITY_NAMES)
def test_get_community_names_gpo(self):
'''
Test - Get the current accepted SNMP community names and their permissions.
'''
mock_ret = MagicMock(return_value=[{'vdata': 'TestCommunity',
'vname': 1}])
mock_false = MagicMock(return_value=True)
with patch.dict(win_snmp.__salt__, {'reg.list_values': mock_ret,
'reg.key_exists': mock_false}):
self.assertEqual(win_snmp.get_community_names(),
{'TestCommunity': 'Managed by GPO'})
def test_set_community_names(self):
'''
Test - Manage the SNMP accepted community names and their permissions.
'''
mock_value = MagicMock(return_value=True)
mock_true = MagicMock(return_value=True)
kwargs = {'communities': COMMUNITY_NAMES}
with patch.dict(win_snmp.__salt__, {'reg.set_value': mock_value}), \
mock_false = MagicMock(return_value=False)
with patch.dict(win_snmp.__salt__, {'reg.set_value': mock_true,
'reg.key_exists': mock_false}), \
patch('salt.modules.win_snmp.get_community_names',
MagicMock(return_value=COMMUNITY_NAMES)):
self.assertTrue(win_snmp.set_community_names(**kwargs))
def test_set_community_names_gpo(self):
'''
Test - Manage the SNMP accepted community names and their permissions.
'''
mock_true = MagicMock(return_value=True)
kwargs = {'communities': COMMUNITY_NAMES}
with patch.dict(win_snmp.__salt__, {'reg.set_value': mock_true,
'reg.key_exists': mock_true}), \
patch('salt.modules.win_snmp.get_community_names',
MagicMock(return_value=COMMUNITY_NAMES)):
self.assertRaises(CommandExecutionError, win_snmp.set_community_names, **kwargs)

View File

@ -29,6 +29,7 @@ integration.modules.test_sysmod
integration.modules.test_system
integration.modules.test_test
integration.modules.test_useradd
integration.modules.test_win_dns_client
integration.reactor.test_reactor
integration.renderers.test_pydsl
integration.returners.test_librato_return
@ -38,6 +39,7 @@ integration.runners.test_salt
integration.sdb.test_env
integration.states.test_host
integration.states.test_pip_state
integration.states.test_pkg
integration.states.test_reg
integration.states.test_renderers
integration.utils.testprogram