Merge branch '2017.7' into '2018.3'

Conflicts:
  - doc/man/salt-api.1
  - doc/man/salt-call.1
  - doc/man/salt-cloud.1
  - doc/man/salt-cp.1
  - doc/man/salt-key.1
  - doc/man/salt-master.1
  - doc/man/salt-minion.1
  - doc/man/salt-proxy.1
  - doc/man/salt-run.1
  - doc/man/salt-ssh.1
  - doc/man/salt-syndic.1
  - doc/man/salt-unity.1
  - doc/man/salt.1
  - doc/man/salt.7
  - doc/man/spm.1
  - salt/beacons/log.py
  - salt/client/ssh/__init__.py
  - salt/modules/cmdmod.py
  - salt/utils/win_functions.py
  - tests/integration/modules/test_cmdmod.py
  - tests/integration/netapi/rest_tornado/test_app.py
  - tests/integration/runners/test_state.py
This commit is contained in:
rallytime 2018-08-08 13:31:57 -04:00
commit 3e6445a9d6
No known key found for this signature in database
GPG Key ID: E8F1A4B90D0DEA19
39 changed files with 264 additions and 165 deletions

View File

@ -46,6 +46,8 @@ pipeline {
}
}}
archiveArtifacts artifacts: 'artifacts/xml-unittests-output/*.xml'
archiveArtifacts artifacts: 'artifacts/logs/minion'
archiveArtifacts artifacts: 'artifacts/logs/salt-runtests.log'
}
}
}

View File

@ -46,6 +46,8 @@ pipeline {
}
}}
archiveArtifacts artifacts: 'artifacts/xml-unittests-output/*.xml'
archiveArtifacts artifacts: 'artifacts/logs/minion'
archiveArtifacts artifacts: 'artifacts/logs/salt-runtests.log'
}
}
}

View File

@ -46,6 +46,8 @@ pipeline {
}
}}
archiveArtifacts artifacts: 'artifacts/xml-unittests-output/*.xml'
archiveArtifacts artifacts: 'artifacts/logs/minion'
archiveArtifacts artifacts: 'artifacts/logs/salt-runtests.log'
}
}
}

View File

@ -46,6 +46,8 @@ pipeline {
}
}}
archiveArtifacts artifacts: 'artifacts/xml-unittests-output/*.xml'
archiveArtifacts artifacts: 'artifacts/logs/minion'
archiveArtifacts artifacts: 'artifacts/logs/salt-runtests.log'
}
}
}

View File

@ -11,16 +11,11 @@ group :docker do
gem 'kitchen-docker', :git => 'https://github.com/test-kitchen/kitchen-docker.git'
end
group :opennebula do
gem 'kitchen-opennebula', '>=0.2.3'
gem 'xmlrpc'
end
group :windows do
gem 'vagrant-wrapper'
gem 'kitchen-vagrant'
gem 'winrm', '~>2.0'
gem 'winrm-fs', :git => 'https://github.com/WinRb/winrm-fs.git'
gem 'winrm-fs', '~>1.2.1'
end
group :ec2 do

View File

@ -103,9 +103,9 @@ Logfile logging log level. One of \fBall\fP, \fBgarbage\fP, \fBtrace\fP,
.UNINDENT
.SH SEE ALSO
.sp
\fBsalt\-api(7)\fP
\fBsalt(7)\fP
\fBsalt\-master(1)\fP
\fIsalt\-api(7)\fP
\fIsalt(7)\fP
\fIsalt\-master(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -265,9 +265,9 @@ output. Set to True or False. Default: none.
.UNINDENT
.SH SEE ALSO
.sp
\fBsalt(1)\fP
\fBsalt\-master(1)\fP
\fBsalt\-minion(1)\fP
\fIsalt(1)\fP
\fIsalt\-master(1)\fP
\fIsalt\-minion(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -387,10 +387,10 @@ salt\-cloud \-m /path/to/cloud.map \-Q
.UNINDENT
.SH SEE ALSO
.sp
\fBsalt\-cloud(7)\fP
\fBsalt(7)\fP
\fBsalt\-master(1)\fP
\fBsalt\-minion(1)\fP
\fIsalt\-cloud(7)\fP
\fIsalt(7)\fP
\fIsalt\-master(1)\fP
\fIsalt\-minion(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -201,9 +201,9 @@ New in version 2016.3.7,2016.11.6,2017.7.0.
.UNINDENT
.SH SEE ALSO
.sp
\fBsalt(1)\fP
\fBsalt\-master(1)\fP
\fBsalt\-minion(1)\fP
\fIsalt(1)\fP
\fIsalt\-master(1)\fP
\fIsalt\-minion(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -340,9 +340,9 @@ Auto\-create a signing key\-pair if it does not yet exist
.UNINDENT
.SH SEE ALSO
.sp
\fBsalt(7)\fP
\fBsalt\-master(1)\fP
\fBsalt\-minion(1)\fP
\fIsalt(7)\fP
\fIsalt\-master(1)\fP
\fIsalt\-minion(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -108,9 +108,9 @@ Logfile logging log level. One of \fBall\fP, \fBgarbage\fP, \fBtrace\fP,
.UNINDENT
.SH SEE ALSO
.sp
\fBsalt(1)\fP
\fBsalt(7)\fP
\fBsalt\-minion(1)\fP
\fIsalt(1)\fP
\fIsalt(7)\fP
\fIsalt\-minion(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -109,9 +109,9 @@ Logfile logging log level. One of \fBall\fP, \fBgarbage\fP, \fBtrace\fP,
.UNINDENT
.SH SEE ALSO
.sp
\fBsalt(1)\fP
\fBsalt(7)\fP
\fBsalt\-master(1)\fP
\fIsalt(1)\fP
\fIsalt(7)\fP
\fIsalt\-master(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -116,10 +116,10 @@ Logfile logging log level. One of \fBall\fP, \fBgarbage\fP, \fBtrace\fP,
.UNINDENT
.SH SEE ALSO
.sp
\fBsalt(1)\fP
\fBsalt(7)\fP
\fBsalt\-master(1)\fP
\fBsalt\-minion(1)\fP
\fIsalt(1)\fP
\fIsalt(7)\fP
\fIsalt\-master(1)\fP
\fIsalt\-minion(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -114,9 +114,9 @@ Logfile logging log level. One of \fBall\fP, \fBgarbage\fP, \fBtrace\fP,
.UNINDENT
.SH SEE ALSO
.sp
\fBsalt(1)\fP
\fBsalt\-master(1)\fP
\fBsalt\-minion(1)\fP
\fIsalt(1)\fP
\fIsalt\-master(1)\fP
\fIsalt\-minion(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -348,9 +348,9 @@ output. Set to True or False. Default: none.
.UNINDENT
.SH SEE ALSO
.sp
\fBsalt(7)\fP
\fBsalt\-master(1)\fP
\fBsalt\-minion(1)\fP
\fIsalt(7)\fP
\fIsalt\-master(1)\fP
\fIsalt\-minion(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -110,9 +110,9 @@ Logfile logging log level. One of \fBall\fP, \fBgarbage\fP, \fBtrace\fP,
.UNINDENT
.SH SEE ALSO
.sp
\fBsalt(1)\fP
\fBsalt\-master(1)\fP
\fBsalt\-minion(1)\fP
\fIsalt(1)\fP
\fIsalt\-master(1)\fP
\fIsalt\-minion(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -50,17 +50,17 @@ invokes that script.
.SH OPTIONS
.SH SEE ALSO
.sp
\fBsalt\-api(1)\fP
\fBsalt\-call(1)\fP
\fBsalt\-cloud(1)\fP
\fBsalt\-cp(1)\fP
\fBsalt\-key(1)\fP
\fBsalt\-main(1)\fP
\fBsalt\-master(1)\fP
\fBsalt\-minion(1)\fP
\fBsalt\-run(1)\fP
\fBsalt\-ssh(1)\fP
\fBsalt\-syndic(1)\fP
\fIsalt\-api(1)\fP
\fIsalt\-call(1)\fP
\fIsalt\-cloud(1)\fP
\fIsalt\-cp(1)\fP
\fIsalt\-key(1)\fP
\fIsalt\-main(1)\fP
\fIsalt\-master(1)\fP
\fIsalt\-minion(1)\fP
\fIsalt\-run(1)\fP
\fIsalt\-ssh(1)\fP
\fIsalt\-syndic(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -95,16 +95,6 @@ the started execution and complete.
.UNINDENT
.INDENT 0.0
.TP
.B \-\-state\-output=STATE_OUTPUT
New in version 0.17.
.sp
Override the configured \fBstate_output\fP value for minion output. One of
\fBfull\fP, \fBterse\fP, \fBmixed\fP, \fBchanges\fP or \fBfilter\fP\&. Default:
\fBfull\fP\&.
.UNINDENT
.INDENT 0.0
.TP
.B \-\-subset=SUBSET
Execute the routine on a random subset of the targeted minions. The
minions will be verified that they have the named function before
@ -344,9 +334,9 @@ output. Set to True or False. Default: none.
.UNINDENT
.SH SEE ALSO
.sp
\fBsalt(7)\fP
\fBsalt\-master(1)\fP
\fBsalt\-minion(1)\fP
\fIsalt(7)\fP
\fIsalt\-master(1)\fP
\fIsalt\-minion(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -132,9 +132,9 @@ in that directory which describes them.
.UNINDENT
.SH SEE ALSO
.sp
\fBsalt(1)\fP
\fBsalt\-master(1)\fP
\fBsalt\-minion(1)\fP
\fIsalt(1)\fP
\fIsalt\-master(1)\fP
\fIsalt\-minion(1)\fP
.SH AUTHOR
Thomas S. Hatch <thatch45@gmail.com> and many others, please see the Authors file
.\" Generated by docutils manpage writer.

View File

@ -21,7 +21,7 @@ management.
The default job cache is a temporary cache and jobs will be stored for 24
hours. If the default cache needs to store jobs for a different period the
time can be easily adjusted by changing the `keep_jobs` parameter in the
time can be easily adjusted by changing the ``keep_jobs`` parameter in the
Salt Master configuration file. The value passed in is measured via hours:
@ -47,7 +47,7 @@ checking for and preventing JID collisions.
The default location for the job cache is in the ``/var/cache/salt/master/jobs/``
directory.
Setting the :conf_master:`job_cache`` to ``False`` in addition to setting
Setting the :conf_master:`job_cache` to ``False`` in addition to setting
the :conf_master:`keep_jobs` option to a smaller value, such as ``1``, in the Salt
Master configuration file will reduce the size of the Default Job Cache, and thus
the burden on the Salt Master.

View File

@ -79,6 +79,12 @@ def beacon(config):
- tags:
<tag>:
regex: <pattern>
.. note::
regex matching is based on the `re`_ module
.. _re: https://docs.python.org/3.6/library/re.html#regular-expression-syntax
'''
_config = {}
list(map(_config.update, config))

View File

@ -440,12 +440,12 @@ class SSH(object):
'''
Deploy the SSH key if the minions don't auth
'''
if not isinstance(ret[host], dict) or self.opts.get('ssh_key_deploy'):
if not isinstance(ret[host], dict) or self.opts.get('ssh_key_deploy') is True:
target = self.targets[host]
if target.get('passwd', False) or self.opts['ssh_passwd']:
self._key_deploy_run(host, target, False)
return ret
if (ret[host].get('stderr') or '').count('Permission denied'):
if ret[host].get('stderr', '').count('Permission denied') and not self.opts.get('ssh_key_deploy') is False:
target = self.targets[host]
# permission denied, attempt to auto deploy ssh key
print(('Permission denied for host {0}, do you want to deploy '

View File

@ -2269,9 +2269,12 @@ def script(source,
os.chmod(path, 320)
os.chown(path, __salt__['file.user_to_uid'](runas), -1)
path = _cmd_quote(path)
if salt.utils.is_windows() and shell.lower() != 'powershell':
cmd_path = _cmd_quote(path, escape=False)
else:
cmd_path = _cmd_quote(path)
ret = _run(path + ' ' + six.text_type(args) if args else path,
ret = _run(cmd_path + ' ' + six.text_type(args) if args else cmd_path,
cwd=cwd,
stdin=stdin,
output_encoding=output_encoding,

View File

@ -677,6 +677,7 @@ def install(name=None,
reinstall_requires=False,
regex=False,
pcre=False,
batch=False,
**kwargs):
'''
Install package(s) from a repository
@ -800,7 +801,16 @@ def install(name=None,
.. code-block:: bash
salt '*' pkg.install <extended regular expression> pcre=True
batch
Use BATCH=true for pkg install, skipping all questions.
Be careful when using in production.
CLI Example:
.. code-block:: bash
salt '*' pkg.install <package name> batch=True
'''
try:
pkg_params, pkg_type = __salt__['pkg_resource.parse_targets'](
@ -812,6 +822,7 @@ def install(name=None,
if pkg_params is None or len(pkg_params) == 0:
return {}
env = {}
opts = 'y'
if salt.utils.data.is_true(orphan):
opts += 'A'
@ -831,6 +842,11 @@ def install(name=None,
opts += 'x'
if salt.utils.data.is_true(pcre):
opts += 'X'
if salt.utils.data.is_true(batch):
env = {
"BATCH": "true",
"ASSUME_ALWAYS_YES": "YES"
}
old = list_pkgs(jail=jail, chroot=chroot, root=root)
@ -867,7 +883,8 @@ def install(name=None,
out = __salt__['cmd.run_all'](
cmd,
output_loglevel='trace',
python_shell=False
python_shell=False,
env=env
)
if out['retcode'] != 0 and out['stderr']:

View File

@ -35,39 +35,24 @@ def __virtual__():
'Ubuntu',
'Debian',
'Devuan',
'Arch',
'Arch ARM',
'Manjaro',
'ALT',
'SUSE Enterprise Server',
'SUSE',
'OEL',
'Linaro',
'elementary OS',
'McAfee OS Server',
'Void',
'Mint',
'Raspbian',
'XenServer',
'Cumulus'
))
if __grains__.get('os', '') in disable:
if __grains__.get('os') in disable:
return (False, 'Your OS is on the disabled list')
# Disable on all non-Linux OSes as well
if __grains__['kernel'] != 'Linux':
return (False, 'Non Linux OSes are not supported')
# SUSE >=12.0 uses systemd
if __grains__.get('os_family', '') == 'Suse':
try:
# osrelease might be in decimal format (e.g. "12.1"), or for
# SLES might include service pack (e.g. "11 SP3"), so split on
# non-digit characters, and the zeroth element is the major
# number (it'd be so much simpler if it was always "X.Y"...)
import re
if int(re.split(r'\D+', __grains__.get('osrelease', ''))[0]) >= 12:
return (False, 'SUSE version greater than or equal to 12 is not supported')
except ValueError:
return (False, 'You are missing the os_family grain')
init_grain = __grains__.get('init')
if init_grain not in (None, 'sysvinit', 'unknown'):
return (False, 'Minion is running {0}'.format(init_grain))
elif __utils__['systemd.booted'](__context__):
# Should have been caught by init grain check, but check just in case
return (False, 'Minion is running systemd')
return 'service'

View File

@ -466,18 +466,13 @@ def _get_reg_software():
'{0}\\{1}'.format(key, reg_key),
'DisplayVersion',
use_32bit)
if (not d_vers_regdata['success'] or
d_vers_regdata['vtype'] not in ['REG_SZ', 'REG_EXPAND_SZ', 'REG_DWORD'] or
d_vers_regdata['vdata'] in [None, False]):
return
if isinstance(d_vers_regdata['vdata'], int):
d_vers = six.text_type(d_vers_regdata['vdata'])
else:
d_vers = d_vers_regdata['vdata']
if not d_vers or d_vers == '(value not set)':
d_vers = 'Not Found'
d_vers = 'Not Found'
if (d_vers_regdata['success'] and
d_vers_regdata['vtype'] in ['REG_SZ', 'REG_EXPAND_SZ', 'REG_DWORD']):
if isinstance(d_vers_regdata['vdata'], int):
d_vers = six.text_type(d_vers_regdata['vdata'])
elif d_vers_regdata['vdata'] and d_vers_regdata['vdata'] != '(value not set)': # Check for blank values
d_vers = d_vers_regdata['vdata']
check_ok = False
for check_reg in ['UninstallString', 'QuietUninstallString', 'ModifyPath']:

View File

@ -3064,12 +3064,21 @@ class SaltSSHOptionParser(six.with_metaclass(OptionParserMeta,
auth_group.add_option(
'--key-deploy',
dest='ssh_key_deploy',
default=False,
default=None,
action='store_true',
help='Set this flag to attempt to deploy the authorized ssh key '
'with all minions. This combined with --passwd can make '
'initial deployment of keys very fast and easy.'
)
auth_group.add_option(
'--no-key-deploy',
dest='ssh_key_deploy',
default=None,
action='store_false',
help='Set this flag to stop salt-ssh from attempting to deploy an authorized ssh key '
'with all minions. This is useful to skip the message about deploying to minions '
'that cannot be logged into.'
)
auth_group.add_option(
'--identities-only',
dest='ssh_identities_only',

View File

@ -175,7 +175,7 @@ def enable_ctrl_logoff_handler():
)
def escape_argument(arg):
def escape_argument(arg, escape=True):
'''
Escape the argument for the cmd.exe shell.
See http://blogs.msdn.com/b/twistylittlepassagesallalike/archive/2011/04/23/everyone-quotes-arguments-the-wrong-way.aspx
@ -186,12 +186,19 @@ def escape_argument(arg):
Args:
arg (str): a single command line argument to escape for the cmd.exe shell
Kwargs:
escape (bool): True will call the escape_for_cmd_exe() function
which escapes the characters '()%!^"<>&|'. False
will not call the function and only quotes the cmd
Returns:
str: an escaped string suitable to be passed as a program argument to the cmd.exe shell
'''
if not arg or re.search(r'(["\s])', arg):
arg = '"' + arg.replace('"', r'\"') + '"'
if not escape:
return arg
return escape_for_cmd_exe(arg)

View File

@ -21,6 +21,7 @@ import salt.utils.files
# Import Salt Testing Libs
from tests.support.case import ShellCase, SSHCase
from tests.support.helpers import flaky
class GrainsTargetingTest(ShellCase):
@ -52,6 +53,7 @@ class GrainsTargetingTest(ShellCase):
sub_minion = self.run_salt('-G \'id:sub_minion\' test.ping')
self.assertEqual(sorted(sub_minion), sorted(['sub_minion:', ' True']))
@flaky
def test_grains_targeting_disconnected(self):
'''
Tests return of minion using grains targeting on a disconnected minion.
@ -72,7 +74,7 @@ class GrainsTargetingTest(ShellCase):
for item in self.run_salt('-t 1 -G \'id:disconnected\' test.ping', timeout=40):
if item != 'disconnected:':
ret = item.strip()
self.assertEqual(ret, test_ret)
assert ret == test_ret
finally:
os.unlink(key_file)

View File

@ -9,6 +9,7 @@ import textwrap
# Import Salt Testing libs
from tests.support.case import ModuleCase
from tests.support.unit import skipIf
from tests.support.helpers import (
destructiveTest,
skip_if_binaries_missing,
@ -84,7 +85,7 @@ class CMDModuleTest(ModuleCase):
'''
self.assertEqual(self.run_function('cmd.run_stdout',
['echo "cheese"']).rstrip(),
'cheese')
'cheese' if not salt.utils.is_windows() else '"cheese"')
def test_stderr(self):
'''
@ -99,7 +100,7 @@ class CMDModuleTest(ModuleCase):
['echo "cheese" 1>&2',
'shell={0}'.format(shell)], python_shell=True
).rstrip(),
'cheese')
'cheese' if not salt.utils.is_windows() else '"cheese"')
def test_run_all(self):
'''
@ -120,7 +121,7 @@ class CMDModuleTest(ModuleCase):
self.assertTrue(isinstance(ret.get('retcode'), int))
self.assertTrue(isinstance(ret.get('stdout'), six.string_types))
self.assertTrue(isinstance(ret.get('stderr'), six.string_types))
self.assertEqual(ret.get('stderr').rstrip(), 'cheese')
self.assertEqual(ret.get('stderr').rstrip(), 'cheese' if not salt.utils.is_windows() else '"cheese"')
def test_retcode(self):
'''
@ -258,10 +259,13 @@ class CMDModuleTest(ModuleCase):
'''
cmd = '''echo 'SELECT * FROM foo WHERE bar="baz"' '''
expected_result = 'SELECT * FROM foo WHERE bar="baz"'
if salt.utils.is_windows():
expected_result = '\'SELECT * FROM foo WHERE bar="baz"\''
result = self.run_function('cmd.run_stdout', [cmd]).strip()
self.assertEqual(result, expected_result)
@skip_if_not_root
@skipIf(salt.utils.is_windows, 'skip windows, requires password')
def test_quotes_runas(self):
'''
cmd.run with quoted command
@ -289,6 +293,7 @@ class CMDModuleTest(ModuleCase):
out = self.run_function('cmd.run', ['env'], runas=self.runas_usr).splitlines()
self.assertIn('USER={0}'.format(self.runas_usr), out)
@skipIf(not salt.utils.which_bin('sleep'), 'sleep cmd not installed')
def test_timeout(self):
'''
cmd.run trigger timeout
@ -299,6 +304,7 @@ class CMDModuleTest(ModuleCase):
python_shell=True)
self.assertTrue('Timed out' in out)
@skipIf(not salt.utils.which_bin('sleep'), 'sleep cmd not installed')
def test_timeout_success(self):
'''
cmd.run sufficient timeout to succeed

View File

@ -126,6 +126,11 @@ class ServiceModuleTest(ModuleCase):
if tuple(self.run_function('grains.item', ['osrelease_info'])['osrelease_info']) == (14, 0o4) and not systemd:
# currently upstart does not have a mechanism to report if disabling a service fails if does not exist
self.assertTrue(self.run_function('service.disable', [srv_name]))
elif self.run_function('grains.item', ['osfullname'])['osfullname'] == 'Debian' and \
self.run_function('grains.item', ['osmajorrelease'])['osmajorrelease'] < 9 and systemd:
# currently disabling a service via systemd that does not exist
# on Debian 8 results in a True return code
self.assertTrue(self.run_function('service.disable', [srv_name]))
else:
try:
disable = self.run_function('service.disable', [srv_name])

View File

@ -80,6 +80,7 @@ class TestSaltAPIHandler(_SaltnadoIntegrationTestCase):
self.assertEqual(response.headers['Location'], '/login')
# Local client tests
@skipIf(True, 'to be re-enabled when #23623 is merged')
def test_simple_local_post(self):
'''
@ -121,6 +122,7 @@ class TestSaltAPIHandler(_SaltnadoIntegrationTestCase):
self.assertEqual(response_obj['return'], ["No minions matched the target. No command was sent, no jid was assigned."])
# local client request body test
@skipIf(True, 'Undetermined race condition in test. Temporarily disabled.')
def test_simple_local_post_only_dictionary_request(self):
'''

View File

@ -17,10 +17,10 @@ import threading
# Import Salt Testing Libs
from tests.support.case import ShellCase
from tests.support.unit import skipIf
from tests.support.paths import TMP
from tests.support.helpers import flaky, expensiveTest
from tests.support.mock import MagicMock, patch
from tests.support.paths import TMP
from tests.support.unit import skipIf
# Import Salt Libs
import salt.exceptions
@ -73,11 +73,11 @@ class StateRunnerTest(ShellCase):
# First, check that we don't have the "bad" output that was displaying in
# Issue #31330 where only the highstate outputter was listed
self.assertIsNot(bad_out, ret_output)
assert bad_out != ret_output
# Now test that some expected good sample output is present in the return.
for item in good_out:
self.assertIn(item, ret_output)
assert item in ret_output
def test_orchestrate_nested(self):
'''
@ -90,8 +90,8 @@ class StateRunnerTest(ShellCase):
'state.orchestrate nested-orch.outer',
with_retcode=True)
self.assertFalse(os.path.exists('/tmp/ewu-2016-12-13'))
self.assertNotEqual(code, 0)
assert os.path.exists('/tmp/ewu-2016-12-13') is False
assert code != 0
def test_orchestrate_state_and_function_failure(self):
'''
@ -168,7 +168,7 @@ class StateRunnerTest(ShellCase):
for out in ret_out:
for item in out:
self.assertIn(item, ret)
assert item in ret
def test_orchestrate_retcode(self):
'''
@ -199,7 +199,7 @@ class StateRunnerTest(ShellCase):
' Result: False'):
self.assertIn(result, ret)
def test_orchestrate_target_doesnt_exists(self):
def test_orchestrate_target_doesnt_exist(self):
'''
test orchestration when target doesn't exist
while using multiple states
@ -223,7 +223,7 @@ class StateRunnerTest(ShellCase):
for out in ret_out:
for item in out:
self.assertIn(item, ret)
assert item in ret
def test_state_event(self):
'''
@ -241,7 +241,7 @@ class StateRunnerTest(ShellCase):
while q.empty():
self.run_salt('minion test.ping --static')
out = q.get()
self.assertIn(expect, six.text_type(out))
assert expect in six.text_type(out)
server_thread.join()
@ -254,9 +254,9 @@ class StateRunnerTest(ShellCase):
def count(thing, listobj):
return sum([obj.strip() == thing for obj in listobj])
self.assertEqual(count('ID: test subset', ret), 1)
self.assertEqual(count('Succeeded: 1', ret), 1)
self.assertEqual(count('Failed: 0', ret), 1)
assert count('ID: test subset', ret) == 1
assert count('Succeeded: 1', ret) == 1
assert count('Failed: 0', ret) == 1
def test_orchestrate_salt_function_return_false_failure(self):
'''
@ -275,10 +275,7 @@ class StateRunnerTest(ShellCase):
state_result = ret['data']['master']['salt_|-deploy_check_|-test.false_|-function']['result']
func_ret = ret['data']['master']['salt_|-deploy_check_|-test.false_|-function']['changes']
self.assertEqual(
state_result,
False,
)
assert state_result is False
self.assertEqual(
func_ret,

View File

@ -22,7 +22,7 @@ from tests.support.case import ShellCase
from tests.support.unit import skipIf
from tests.support.paths import FILES, TMP
from tests.support.mixins import ShellCaseCommonTestsMixin
from tests.support.helpers import destructiveTest
from tests.support.helpers import destructiveTest, flaky
from tests.integration.utils import testprogram
# Import salt libs
@ -103,12 +103,10 @@ class CallTest(ShellCase, testprogram.TestProgramCase, ShellCaseCommonTestsMixin
log.debug('The pkg: {0} is already installed on the machine'.format(pkg))
@skipIf(sys.platform.startswith('win'), 'This test does not apply on Win')
@flaky
def test_user_delete_kw_output(self):
ret = self.run_call('-l quiet -d user.delete')
self.assertIn(
'salt \'*\' user.delete name remove=True force=True',
''.join(ret)
)
assert 'salt \'*\' user.delete name remove=True force=True' in ''.join(ret)
def test_salt_documentation_too_many_arguments(self):
'''

View File

@ -8,8 +8,9 @@ import time
# Import Salt Testing libs
from tests.support.case import ShellCase
from tests.support.paths import TMP
from tests.support.helpers import flaky
from tests.support.mixins import ShellCaseCommonTestsMixin
from tests.support.paths import TMP
# Import salt libs
import salt.utils.files
@ -91,11 +92,13 @@ class MatchTest(ShellCase, ShellCaseCommonTestsMixin):
assert minion_in_returns('minion', data) is True
assert minion_in_returns('sub_minion', data) is True
@flaky
def test_compound_pillar(self):
data = self.run_salt("-C 'I%@companions%three%sarah*' test.ping")
assert minion_in_returns('minion', data) is True
assert minion_in_returns('sub_minion', data) is True
@flaky
def test_coumpound_pillar_pcre(self):
data = self.run_salt("-C 'J%@knights%^(Lancelot|Galahad)$' test.ping")
assert minion_in_returns('minion', data) is True
@ -320,6 +323,7 @@ class MatchTest(ShellCase, ShellCaseCommonTestsMixin):
data = self.run_salt('-d "*" user')
self.assertIn('user.add:', data)
@flaky
def test_salt_documentation_arguments_not_assumed(self):
'''
Test to see if we're not auto-adding '*' and 'sys.doc' to the call
@ -331,16 +335,16 @@ class MatchTest(ShellCase, ShellCaseCommonTestsMixin):
'see https://github.com/saltstack/salt-jenkins/issues/324.')
data = self.run_salt('-d -t 20')
if data:
self.assertIn('user.add:', data)
assert 'user.add:' in data
data = self.run_salt('"*" -d -t 20')
if data:
self.assertIn('user.add:', data)
assert 'user.add:' in data
data = self.run_salt('"*" -d user -t 20')
self.assertIn('user.add:', data)
assert 'user.add:' in data
data = self.run_salt('"*" sys.doc -d user -t 20')
self.assertIn('user.add:', data)
assert 'user.add:' in data
data = self.run_salt('"*" sys.doc user -t 20')
self.assertIn('user.add:', data)
assert 'user.add:' in data
def test_salt_documentation_too_many_arguments(self):
'''

View File

@ -0,0 +1,49 @@
# -*- coding: utf-8 -*-
'''
:codeauthor: :email:`Daniel Wallace (daniel@saltstack.com)`
====================================
Test Case for --no-key-deploy
====================================
'''
from __future__ import unicode_literals, absolute_import
# Import Python Libs
import os
import json
# Import Tests Libs
from tests.support.case import SSHCase
from tests.support.runtests import RUNTIME_VARS
class SSHKeyDeployQuestionCase(SSHCase):
def _run_ssh(self, arg_str, with_retcode=False, timeout=25, catch_stderr=False):
arg_str = '-ldebug -c {0} -i --roster-file {1} --out=json localhost {2}'.format(
self.get_config_dir(),
os.path.join(RUNTIME_VARS.TMP_CONF_DIR, '_ssh', 'roster'),
arg_str,
)
return self.run_script('salt-ssh',
arg_str,
with_retcode=with_retcode,
catch_stderr=catch_stderr,
timeout=timeout,
raw=True)
def test_no_key_deploy(self):
exp = {
'localhost': {
'stdout': '',
'stderr': "Permission denied (publickey).\r\n",
'retcode': 255,
},
}
assert json.loads(self._run_ssh('--no-key-deploy localhost test.ping')) == exp
def test_key_deploy(self):
exp = ['Process took more than 5 seconds to complete. Process Killed!']
assert self._run_ssh('localhost test.ping', timeout=5) == exp

View File

@ -2515,8 +2515,8 @@ class BlockreplaceTest(ModuleCase, SaltReturnAssertsMixin):
Test blockreplace when prepend_if_not_found=True and block doesn't
exist in file.
'''
expected = self.marker_start + os.linesep + self.content + \
self.marker_end + os.linesep + self.without_block
expected = self.marker_start + '\n' + self.content + \
self.marker_end + '\n' + self.without_block
# Pass 1: content ends in newline
self._write(name, self.without_block)
@ -2569,8 +2569,8 @@ class BlockreplaceTest(ModuleCase, SaltReturnAssertsMixin):
exist in file. Test with append_newline explicitly set to True.
'''
# Pass 1: content ends in newline
expected = self.marker_start + os.linesep + self.content + \
os.linesep + self.marker_end + os.linesep + self.without_block
expected = self.marker_start + '\n' + self.content + \
'\n' + self.marker_end + '\n' + self.without_block
self._write(name, self.without_block)
ret = self.run_state('file.blockreplace',
name=name,
@ -2595,8 +2595,8 @@ class BlockreplaceTest(ModuleCase, SaltReturnAssertsMixin):
self.assertEqual(self._read(name), expected)
# Pass 2: content does not end in newline
expected = self.marker_start + os.linesep + self.content + \
self.marker_end + os.linesep + self.without_block
expected = self.marker_start + '\n' + self.content + \
self.marker_end + '\n' + self.without_block
self._write(name, self.without_block)
ret = self.run_state('file.blockreplace',
name=name,
@ -2627,8 +2627,8 @@ class BlockreplaceTest(ModuleCase, SaltReturnAssertsMixin):
exist in file. Test with append_newline explicitly set to False.
'''
# Pass 1: content ends in newline
expected = self.marker_start + os.linesep + self.content + \
self.marker_end + os.linesep + self.without_block
expected = self.marker_start + '\n' + self.content + \
self.marker_end + '\n' + self.without_block
self._write(name, self.without_block)
ret = self.run_state('file.blockreplace',
name=name,
@ -2653,8 +2653,8 @@ class BlockreplaceTest(ModuleCase, SaltReturnAssertsMixin):
self.assertEqual(self._read(name), expected)
# Pass 2: content does not end in newline
expected = self.marker_start + os.linesep + \
self.content.rstrip('\r\n') + self.marker_end + os.linesep + \
expected = self.marker_start + '\n' + \
self.content.rstrip('\r\n') + self.marker_end + '\n' + \
self.without_block
self._write(name, self.without_block)
ret = self.run_state('file.blockreplace',
@ -2685,8 +2685,8 @@ class BlockreplaceTest(ModuleCase, SaltReturnAssertsMixin):
Test blockreplace when append_if_not_found=True and block doesn't
exist in file.
'''
expected = self.without_block + self.marker_start + os.linesep + \
self.content + self.marker_end + os.linesep
expected = self.without_block + self.marker_start + '\n' + \
self.content + self.marker_end + '\n'
# Pass 1: content ends in newline
self._write(name, self.without_block)
@ -2739,8 +2739,8 @@ class BlockreplaceTest(ModuleCase, SaltReturnAssertsMixin):
exist in file. Test with append_newline explicitly set to True.
'''
# Pass 1: content ends in newline
expected = self.without_block + self.marker_start + os.linesep + \
self.content + os.linesep + self.marker_end + os.linesep
expected = self.without_block + self.marker_start + '\n' + \
self.content + '\n' + self.marker_end + '\n'
self._write(name, self.without_block)
ret = self.run_state('file.blockreplace',
name=name,
@ -2765,8 +2765,8 @@ class BlockreplaceTest(ModuleCase, SaltReturnAssertsMixin):
self.assertEqual(self._read(name), expected)
# Pass 2: content does not end in newline
expected = self.without_block + self.marker_start + os.linesep + \
self.content + self.marker_end + os.linesep
expected = self.without_block + self.marker_start + '\n' + \
self.content + self.marker_end + '\n'
self._write(name, self.without_block)
ret = self.run_state('file.blockreplace',
name=name,
@ -2797,8 +2797,8 @@ class BlockreplaceTest(ModuleCase, SaltReturnAssertsMixin):
exist in file. Test with append_newline explicitly set to False.
'''
# Pass 1: content ends in newline
expected = self.without_block + self.marker_start + os.linesep + \
self.content + self.marker_end + os.linesep
expected = self.without_block + self.marker_start + '\n' + \
self.content + self.marker_end + '\n'
self._write(name, self.without_block)
ret = self.run_state('file.blockreplace',
name=name,
@ -2823,8 +2823,8 @@ class BlockreplaceTest(ModuleCase, SaltReturnAssertsMixin):
self.assertEqual(self._read(name), expected)
# Pass 2: content does not end in newline
expected = self.without_block + self.marker_start + os.linesep + \
self.content.rstrip('\r\n') + self.marker_end + os.linesep
expected = self.without_block + self.marker_start + '\n' + \
self.content.rstrip('\r\n') + self.marker_end + '\n'
self._write(name, self.without_block)
ret = self.run_state('file.blockreplace',
name=name,

View File

@ -1065,6 +1065,16 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
pkg_targets = _PKG_TARGETS.get(os_family, [])
if os_family.lower() == 'redhat':
# If we're in the Red Hat family first we ensure that
# the yum-plugin-versionlock package is installed
ret = self.run_state(
'pkg.installed',
name='yum-plugin-versionlock',
refresh=False,
)
self.assertSaltTrueReturn(ret)
# Make sure that we have targets that match the os_family. If this
# fails then the _PKG_TARGETS dict above needs to have an entry added,
# with two packages that are not installed before these tests are run
@ -1088,15 +1098,25 @@ class PkgTest(ModuleCase, SaltReturnAssertsMixin):
refresh=False,
)
# changes from pkg.hold for Red Hat family are different
if os_family.lower() == 'redhat':
target_changes = {'new': 'hold', 'old': ''}
elif os_family.lower() == 'debian':
target_changes = {'new': 'hold', 'old': 'install'}
try:
tag = 'pkg_|-{0}_|-{0}_|-installed'.format(target)
self.assertSaltTrueReturn(ret)
self.assertIn(tag, ret)
self.assertIn('changes', ret[tag])
self.assertIn(target, ret[tag]['changes'])
self.assertEqual(ret[tag]['changes'][target], {'new': 'hold', 'old': 'install'})
self.assertEqual(ret[tag]['changes'][target], target_changes)
finally:
# Clean up, unhold package and remove
self.run_function('pkg.unhold', name=target)
ret = self.run_state('pkg.removed', name=target)
self.assertSaltTrueReturn(ret)
if os_family.lower() == 'redhat':
ret = self.run_state('pkg.removed',
name='yum-plugin-versionlock')
self.assertSaltTrueReturn(ret)

View File

@ -8,6 +8,7 @@ integration.modules.test_autoruns
integration.modules.test_beacons
integration.modules.test_config
integration.modules.test_cp
integration.modules.test_cmdmod
integration.modules.test_data
integration.modules.test_disk
integration.modules.test_firewall