mirror of
https://github.com/saltstack/salt.git
synced 2025-04-17 10:10:20 +00:00
Merge branch '2016.3' into 'develop'
Conflicts: - salt/grains/core.py - salt/modules/aptpkg.py - salt/pillar/stack.py - salt/returners/local_cache.py - salt/runners/manage.py
This commit is contained in:
commit
e6bbc82b58
15 changed files with 151 additions and 37 deletions
|
@ -230,6 +230,20 @@ other salt modules which needed to import :mod:`sys<python2:sys>` would have to
|
|||
also import :mod:`absolute_import<python2:__future__>`, which should be
|
||||
avoided.
|
||||
|
||||
.. note::
|
||||
|
||||
An exception to this rule is the ``absolute_import`` from ``__future__`` at
|
||||
the top of each file within the Salt project. This import is necessary for
|
||||
Py3 compatibility. This particular import looks like this:
|
||||
|
||||
.. code-block:: python
|
||||
|
||||
from __future__ import absolute_import
|
||||
|
||||
This import is required for all new Salt files and is a good idea to add to
|
||||
any custom states or modules. However, the practice of avoiding absolute
|
||||
imports still applies to all other cases as to avoid a name conflict.
|
||||
|
||||
.. _`absolute imports`: http://legacy.python.org/dev/peps/pep-0328/#rationale-for-absolute-imports
|
||||
|
||||
|
||||
|
|
|
@ -10,12 +10,38 @@ Changes for v2015.5.10..v2015.5.11
|
|||
|
||||
Extended changelog courtesy of Todd Stansell (https://github.com/tjstansell/salt-changelogs):
|
||||
|
||||
*Generated at: 2016-05-13T14:26:40Z*
|
||||
*Generated at: 2016-05-20T21:02:38Z*
|
||||
|
||||
Total Merges: **99**
|
||||
Total Merges: **101**
|
||||
|
||||
Changes:
|
||||
|
||||
* dc8ce2d Fix traceback in logging for config validation (`#33386`_) (`#33405`_)
|
||||
|
||||
- **PR** `#33383`_: (*thatch45*) maintain the fallabck because I am totally sick of this crap
|
||||
|
||||
* 755acfb Improve doc clarity for disable_modules documentation (`#33379`_)
|
||||
|
||||
* 2b5ad12 Better YAML syntax error handling (`#33375`_)
|
||||
|
||||
- **PR** `#33372`_: (*jacobhammons*) revved 2015.8 branch to .9 in version selector
|
||||
|
||||
* 55be0ab Expanded documentation for boto_elb state and module (`#33341`_)
|
||||
|
||||
* 9b42a05 Added some more docs for master and minion config settings (`#33292`_)
|
||||
|
||||
* 8acee5e Fix iptables --match-set (`#23643`_) (`#33301`_)
|
||||
|
||||
* 757ef20 fix "loose" typo (`#33290`_)
|
||||
|
||||
* b7d98da Add auth_tries config option to minion.rst docs (`#33287`_)
|
||||
|
||||
* 061851b Document minion_id_caching config value (`#33282`_)
|
||||
|
||||
* 8fa72f6 Clarify file.replace MULTILINE flag interaction with regex anchors (`#33137`_)
|
||||
|
||||
* 4b1f460 update 2015.5.11 release notes (`#33236`_)
|
||||
|
||||
- **PR** `#33211`_: (*cachedout*) Don't try to kill a parent proc if we can't
|
||||
|
||||
* f868329 Resolve issue with pkg module on Mint Linux (`#33205`_)
|
||||
|
@ -404,6 +430,7 @@ Changes:
|
|||
.. _`#33078`: https://github.com/saltstack/salt/pull/33078
|
||||
.. _`#33080`: https://github.com/saltstack/salt/pull/33080
|
||||
.. _`#33132`: https://github.com/saltstack/salt/pull/33132
|
||||
.. _`#33137`: https://github.com/saltstack/salt/pull/33137
|
||||
.. _`#33141`: https://github.com/saltstack/salt/pull/33141
|
||||
.. _`#33155`: https://github.com/saltstack/salt/pull/33155
|
||||
.. _`#33160`: https://github.com/saltstack/salt/pull/33160
|
||||
|
@ -414,3 +441,17 @@ Changes:
|
|||
.. _`#33197`: https://github.com/saltstack/salt/pull/33197
|
||||
.. _`#33205`: https://github.com/saltstack/salt/pull/33205
|
||||
.. _`#33211`: https://github.com/saltstack/salt/pull/33211
|
||||
.. _`#33236`: https://github.com/saltstack/salt/pull/33236
|
||||
.. _`#33282`: https://github.com/saltstack/salt/pull/33282
|
||||
.. _`#33286`: https://github.com/saltstack/salt/pull/33286
|
||||
.. _`#33287`: https://github.com/saltstack/salt/pull/33287
|
||||
.. _`#33290`: https://github.com/saltstack/salt/pull/33290
|
||||
.. _`#33292`: https://github.com/saltstack/salt/pull/33292
|
||||
.. _`#33301`: https://github.com/saltstack/salt/pull/33301
|
||||
.. _`#33341`: https://github.com/saltstack/salt/pull/33341
|
||||
.. _`#33372`: https://github.com/saltstack/salt/pull/33372
|
||||
.. _`#33375`: https://github.com/saltstack/salt/pull/33375
|
||||
.. _`#33379`: https://github.com/saltstack/salt/pull/33379
|
||||
.. _`#33383`: https://github.com/saltstack/salt/pull/33383
|
||||
.. _`#33386`: https://github.com/saltstack/salt/pull/33386
|
||||
.. _`#33405`: https://github.com/saltstack/salt/pull/33405
|
||||
|
|
|
@ -107,8 +107,6 @@ VALID_RESPONSE_CODES = [
|
|||
http_client.NO_CONTENT
|
||||
]
|
||||
|
||||
DEFAULT_NETWORKS = ['Joyent-SDC-Public']
|
||||
|
||||
|
||||
# Only load in this module if the Joyent configurations are in place
|
||||
def __virtual__():
|
||||
|
@ -284,12 +282,14 @@ def create(vm_):
|
|||
salt.utils.cloud.check_name(vm_['name'], 'a-zA-Z0-9-.')
|
||||
kwargs = {
|
||||
'name': vm_['name'],
|
||||
'networks': vm_.get('networks', DEFAULT_NETWORKS),
|
||||
'image': get_image(vm_),
|
||||
'size': get_size(vm_),
|
||||
'location': vm_.get('location', DEFAULT_LOCATION)
|
||||
|
||||
}
|
||||
# Let's not assign a default here; only assign a network value if
|
||||
# one is explicitly configured
|
||||
if 'networks' in vm_:
|
||||
kwargs['networks'] = vm_.get('networks')
|
||||
|
||||
salt.utils.cloud.fire_event(
|
||||
'event',
|
||||
|
@ -344,14 +344,16 @@ def create_node(**kwargs):
|
|||
size = kwargs['size']
|
||||
image = kwargs['image']
|
||||
location = kwargs['location']
|
||||
networks = kwargs['networks']
|
||||
networks = kwargs.get('networks')
|
||||
|
||||
data = json.dumps({
|
||||
create_data = {
|
||||
'name': name,
|
||||
'package': size['name'],
|
||||
'image': image['name'],
|
||||
'networks': networks
|
||||
})
|
||||
}
|
||||
if networks is not None:
|
||||
create_data['networks'] = networks
|
||||
data = json.dumps(create_data)
|
||||
|
||||
try:
|
||||
ret = query(command='/my/machines', data=data, method='POST',
|
||||
|
|
|
@ -73,6 +73,8 @@ class SudoExecutor(ModuleExecutorBase):
|
|||
'-c', salt.syspaths.CONFIG_DIR,
|
||||
'--',
|
||||
data.get('fun')]
|
||||
if data['fun'] == 'state.sls':
|
||||
kwargs['concurrent'] = True
|
||||
for arg in args:
|
||||
self.cmd.append(_cmd_quote(str(arg)))
|
||||
for key in kwargs:
|
||||
|
|
|
@ -216,9 +216,11 @@ def pvcreate(devices, override=True, **kwargs):
|
|||
'''
|
||||
if not devices:
|
||||
return 'Error: at least one device is required'
|
||||
if isinstance(devices, six.string_types):
|
||||
devices = devices.split(',')
|
||||
|
||||
cmd = ['pvcreate']
|
||||
for device in devices.split(','):
|
||||
for device in devices:
|
||||
if not os.path.exists(device):
|
||||
raise CommandExecutionError('{0} does not exist'.format(device))
|
||||
# Verify pvcreate was successful
|
||||
|
@ -244,7 +246,7 @@ def pvcreate(devices, override=True, **kwargs):
|
|||
raise CommandExecutionError(out.get('stderr'))
|
||||
|
||||
# Verify pvcreate was successful
|
||||
for device in devices.split(','):
|
||||
for device in devices:
|
||||
if not pvdisplay(device):
|
||||
raise CommandExecutionError('Device "{0}" was not affected.'.format(device))
|
||||
|
||||
|
@ -264,8 +266,11 @@ def pvremove(devices, override=True):
|
|||
|
||||
salt mymachine lvm.pvremove /dev/sdb1,/dev/sdb2
|
||||
'''
|
||||
if isinstance(devices, six.string_types):
|
||||
devices = devices.split(',')
|
||||
|
||||
cmd = ['pvremove', '-y']
|
||||
for device in devices.split(','):
|
||||
for device in devices:
|
||||
if pvdisplay(device):
|
||||
cmd.append(device)
|
||||
elif not override:
|
||||
|
@ -280,7 +285,7 @@ def pvremove(devices, override=True):
|
|||
raise CommandExecutionError(out.get('stderr'))
|
||||
|
||||
# Verify pvcremove was successful
|
||||
for device in devices.split(','):
|
||||
for device in devices:
|
||||
if pvdisplay(device):
|
||||
raise CommandExecutionError('Device "{0}" was not affected.'.format(device))
|
||||
|
||||
|
@ -300,9 +305,11 @@ def vgcreate(vgname, devices, **kwargs):
|
|||
'''
|
||||
if not vgname or not devices:
|
||||
return 'Error: vgname and device(s) are both required'
|
||||
if isinstance(devices, six.string_types):
|
||||
devices = devices.split(',')
|
||||
|
||||
cmd = ['vgcreate', vgname]
|
||||
for device in devices.split(','):
|
||||
for device in devices:
|
||||
cmd.append(device)
|
||||
valid = ('clustered', 'maxlogicalvolumes', 'maxphysicalvolumes',
|
||||
'vgmetadatacopies', 'metadatacopies', 'physicalextentsize')
|
||||
|
@ -329,9 +336,11 @@ def vgextend(vgname, devices):
|
|||
'''
|
||||
if not vgname or not devices:
|
||||
return 'Error: vgname and device(s) are both required'
|
||||
if isinstance(devices, six.string_types):
|
||||
devices = devices.split(',')
|
||||
|
||||
cmd = ['vgextend', vgname]
|
||||
for device in devices.split(','):
|
||||
for device in devices:
|
||||
cmd.append(device)
|
||||
out = __salt__['cmd.run'](cmd, python_shell=False).splitlines()
|
||||
vgdata = {'Output from vgextend': out[0].strip()}
|
||||
|
|
|
@ -810,16 +810,23 @@ def install(name=None, refresh=False, pkgs=None, saltenv='base', **kwargs):
|
|||
cmd.append(cached_pkg)
|
||||
cmd.extend(salt.utils.shlex_split(install_flags))
|
||||
# Launch the command
|
||||
result = __salt__['cmd.run_stdout'](cmd,
|
||||
cache_path,
|
||||
output_loglevel='trace',
|
||||
python_shell=False)
|
||||
if result:
|
||||
log.error('Failed to install {0}'.format(pkg_name))
|
||||
log.error('error message: {0}'.format(result))
|
||||
ret[pkg_name] = {'failed': result}
|
||||
else:
|
||||
result = __salt__['cmd.run_all'](cmd,
|
||||
cache_path,
|
||||
output_loglevel='quiet',
|
||||
python_shell=False,
|
||||
redirect_stderr=True)
|
||||
if not result['retcode']:
|
||||
ret[pkg_name] = {'install status': 'success'}
|
||||
changed.append(pkg_name)
|
||||
elif result['retcode'] == 3010:
|
||||
# 3010 is ERROR_SUCCESS_REBOOT_REQUIRED
|
||||
ret[pkg_name] = {'install status': 'success, reboot required'}
|
||||
changed.append(pkg_name)
|
||||
else:
|
||||
log.error('Failed to install {0}'.format(pkg_name))
|
||||
log.error('retcode {0}'.format(result['retcode']))
|
||||
log.error('installer output: {0}'.format(result['stdout']))
|
||||
ret[pkg_name] = {'install status': 'failed'}
|
||||
|
||||
# Get a new list of installed software
|
||||
new = list_pkgs(saltenv=saltenv)
|
||||
|
@ -1044,15 +1051,18 @@ def remove(name=None, pkgs=None, version=None, saltenv='base', **kwargs):
|
|||
cmd.append(expanded_cached_pkg)
|
||||
cmd.extend(salt.utils.shlex_split(uninstall_flags))
|
||||
# Launch the command
|
||||
result = __salt__['cmd.run_stdout'](cmd,
|
||||
output_loglevel='trace',
|
||||
python_shell=False)
|
||||
if result:
|
||||
log.error('Failed to install {0}'.format(target))
|
||||
log.error('error message: {0}'.format(result))
|
||||
ret[target] = {'failed': result}
|
||||
else:
|
||||
result = __salt__['cmd.run_all'](cmd,
|
||||
output_loglevel='trace',
|
||||
python_shell=False,
|
||||
redirect_stderr=True)
|
||||
if not result['retcode']:
|
||||
ret[target] = {'uninstall status': 'success'}
|
||||
changed.append(target)
|
||||
else:
|
||||
log.error('Failed to remove {0}'.format(target))
|
||||
log.error('retcode {0}'.format(result['retcode']))
|
||||
log.error('uninstaller output: {0}'.format(result['stdout']))
|
||||
ret[target] = {'uninstall status': 'failed'}
|
||||
|
||||
# Get a new list of installed software
|
||||
new = list_pkgs(saltenv=saltenv)
|
||||
|
|
|
@ -510,3 +510,4 @@ def _parse_stack_cfg(content):
|
|||
except Exception as e:
|
||||
pass
|
||||
return content.splitlines()
|
||||
|
||||
|
|
|
@ -395,6 +395,9 @@ def clean_old_jobs():
|
|||
for top in os.listdir(jid_root):
|
||||
t_path = os.path.join(jid_root, top)
|
||||
|
||||
if not os.path.exists(t_path):
|
||||
continue
|
||||
|
||||
# Check if there are any stray/empty JID t_path dirs
|
||||
t_path_dirs = os.listdir(t_path)
|
||||
if not t_path_dirs and t_path not in dirs_to_remove:
|
||||
|
|
|
@ -766,7 +766,7 @@ def bootstrap(version='develop',
|
|||
('root@' if root_user else '') + host,
|
||||
'python -c \'import urllib; '
|
||||
'print urllib.urlopen('
|
||||
'\'' + script + '\''
|
||||
'"' + script + '"'
|
||||
').read()\' | sh -s -- git ' + version
|
||||
])
|
||||
return ret
|
||||
|
|
|
@ -16,6 +16,15 @@ aliases:
|
|||
thomas:
|
||||
alias.present:
|
||||
- target: thomas@example.com
|
||||
|
||||
The default alias file is set to ``/etc/aliases``, as defined in Salt's
|
||||
:mod:`config execution module <salt.modules.config>`. To change the alias
|
||||
file from the default location, set the following in your minion config:
|
||||
|
||||
.. code-block:: yaml
|
||||
|
||||
aliases.file: /my/alias/file
|
||||
|
||||
'''
|
||||
|
||||
|
||||
|
|
|
@ -154,6 +154,8 @@ def extracted(name,
|
|||
Set this to ``True`` if archive should be extracted if source_hash has
|
||||
changed. This would extract regardless of the ``if_missing`` parameter.
|
||||
|
||||
.. versionadded:: 2016.3.0
|
||||
|
||||
archive_format
|
||||
``tar``, ``zip`` or ``rar``
|
||||
|
||||
|
@ -207,6 +209,8 @@ def extracted(name,
|
|||
trim_output
|
||||
The number of files we should output on success before the rest are
|
||||
trimmed, if this is set to True then it will default to 100
|
||||
|
||||
.. versionadded:: 2016.3.0
|
||||
'''
|
||||
ret = {'name': name, 'result': None, 'changes': {}, 'comment': ''}
|
||||
valid_archives = ('tar', 'rar', 'zip')
|
||||
|
|
|
@ -19,7 +19,7 @@ def __virtual__():
|
|||
'''
|
||||
Only load if the bigip exec module is available in __salt__
|
||||
'''
|
||||
return 'bigip' if 'bigip.exec_action' in __salt__ else False
|
||||
return 'bigip' if 'bigip.list_transaction' in __salt__ else False
|
||||
|
||||
|
||||
def _load_result(response, ret):
|
||||
|
|
|
@ -4783,7 +4783,7 @@ def serialize(name,
|
|||
template can result in YAML formatting issues due to the newlines
|
||||
causing indentation mismatches.
|
||||
|
||||
.. versionadded:: FIXME
|
||||
.. versionadded:: 2015.8.0
|
||||
|
||||
formatter
|
||||
Write the data as this format. Supported output formats:
|
||||
|
|
|
@ -28,6 +28,7 @@ import os
|
|||
|
||||
# Import salt libs
|
||||
import salt.utils
|
||||
import salt.ext.six as six
|
||||
|
||||
|
||||
def __virtual__():
|
||||
|
@ -121,10 +122,12 @@ def vg_present(name, devices=None, **kwargs):
|
|||
'comment': '',
|
||||
'name': name,
|
||||
'result': True}
|
||||
if isinstance(devices, six.string_types):
|
||||
devices = devices.split(',')
|
||||
|
||||
if __salt__['lvm.vgdisplay'](name):
|
||||
ret['comment'] = 'Volume Group {0} already present'.format(name)
|
||||
for device in devices.split(','):
|
||||
for device in devices:
|
||||
realdev = os.path.realpath(device)
|
||||
pvs = __salt__['lvm.pvdisplay'](realdev, real=True)
|
||||
if pvs and pvs.get(realdev, None):
|
||||
|
|
|
@ -1062,6 +1062,22 @@ def installed(
|
|||
A dictionary containing the state of the software installation
|
||||
:rtype dict:
|
||||
|
||||
.. note::
|
||||
|
||||
The ``pkg.installed`` state supports the usage of ``reload_modules``.
|
||||
This functionality allows you to force Salt to reload all modules. In
|
||||
many cases, Salt is clever enough to transparently reload the modules.
|
||||
For example, if you install a package, Salt reloads modules because some
|
||||
other module or state might require the package which was installed.
|
||||
However, there are some edge cases where this may not be the case, which
|
||||
is what ``reload_modules`` is meant to resolve.
|
||||
|
||||
You should only use ``reload_modules`` if your ``pkg.installed`` does some
|
||||
sort of installation where if you do not reload the modules future items
|
||||
in your state which rely on the software being installed will fail. Please
|
||||
see the :ref:`Reloading Modules <reloading-modules>` documentation for more
|
||||
information.
|
||||
|
||||
'''
|
||||
if isinstance(pkgs, list) and len(pkgs) == 0:
|
||||
return {'name': name,
|
||||
|
|
Loading…
Add table
Reference in a new issue