Merge pull request #39379 from terminalmage/issue34821

win_pkg: remove all installed versions when no explicit version passed
This commit is contained in:
Mike Place 2017-02-14 11:41:28 -07:00 committed by GitHub
commit 878946d0f8

View file

@ -1296,152 +1296,161 @@ def remove(name=None, pkgs=None, version=None, **kwargs):
pkg_params = __salt__['pkg_resource.parse_targets'](name, pkgs, **kwargs)[0]
# Get a list of currently installed software for comparison at the end
old = list_pkgs(saltenv=saltenv, refresh=refresh)
old = list_pkgs(saltenv=saltenv, refresh=refresh, versions_as_list=True)
# Loop through each package
changed = []
for target in pkg_params:
for pkgname, version_num in six.iteritems(pkg_params):
# Load package information for the package
pkginfo = _get_package_info(target, saltenv=saltenv)
pkginfo = _get_package_info(pkgname, saltenv=saltenv)
# Make sure pkginfo was found
if not pkginfo:
log.error('Unable to locate package {0}'.format(name))
ret[target] = 'Unable to locate package {0}'.format(target)
msg = 'Unable to locate package {0}'.format(pkgname)
log.error(msg)
ret[pkgname] = msg
continue
# Get latest version if no version passed, else use passed version
if not version:
version_num = _get_latest_pkg_version(pkginfo)
else:
version_num = version
if 'latest' in pkginfo and version_num not in pkginfo:
if version_num is not None \
and version_num not in pkginfo \
and 'latest' in pkginfo:
version_num = 'latest'
# Check to see if package is installed on the system
if target not in old:
log.error('{0} {1} not installed'.format(target, version))
ret[target] = {'current': 'not installed'}
removal_targets = []
if pkgname not in old:
log.error('%s %s not installed', pkgname, version)
ret[pkgname] = {'current': 'not installed'}
continue
else:
if version_num not in old.get(target, '').split(',') \
and not old.get(target) == "Not Found" \
if version_num is None:
removal_targets.extend(old[pkgname])
elif version_num not in old[pkgname] \
and 'Not Found' not in old['pkgname'] \
and version_num != 'latest':
log.error('{0} {1} not installed'.format(target, version))
ret[target] = {
log.error('%s %s not installed', pkgname, version)
ret[pkgname] = {
'current': '{0} not installed'.format(version_num)
}
continue
else:
removal_targets.append(version_num)
# Get the uninstaller
uninstaller = pkginfo[version_num].get('uninstaller')
for target in removal_targets:
# Get the uninstaller
uninstaller = pkginfo[target].get('uninstaller')
# If no uninstaller found, use the installer
if not uninstaller:
uninstaller = pkginfo[version_num].get('installer')
# If no uninstaller found, use the installer
if not uninstaller:
uninstaller = pkginfo[target].get('installer')
# If still no uninstaller found, fail
if not uninstaller:
log.error('Error: No installer or uninstaller configured '
'for package {0}'.format(name))
ret[target] = {'no uninstaller': version_num}
continue
# If still no uninstaller found, fail
if not uninstaller:
log.error(
'No installer or uninstaller configured for package %s',
pkgname,
)
ret[pkgname] = {'no uninstaller': target}
continue
# Where is the uninstaller
if uninstaller.startswith(('salt:', 'http:', 'https:', 'ftp:')):
# Where is the uninstaller
if uninstaller.startswith(('salt:', 'http:', 'https:', 'ftp:')):
# Check to see if the uninstaller is cached
cached_pkg = __salt__['cp.is_cached'](uninstaller)
if not cached_pkg:
# It's not cached. Cache it, mate.
cached_pkg = __salt__['cp.cache_file'](uninstaller)
# Check if the uninstaller was cached successfully
# Check to see if the uninstaller is cached
cached_pkg = __salt__['cp.is_cached'](uninstaller)
if not cached_pkg:
log.error('Unable to cache {0}'.format(uninstaller))
ret[target] = {'unable to cache': uninstaller}
continue
else:
# Run the uninstaller directly (not hosted on salt:, https:, etc.)
cached_pkg = uninstaller
# It's not cached. Cache it, mate.
cached_pkg = __salt__['cp.cache_file'](uninstaller)
# Fix non-windows slashes
cached_pkg = cached_pkg.replace('/', '\\')
cache_path, _ = os.path.split(cached_pkg)
# Check if the uninstaller was cached successfully
if not cached_pkg:
log.error('Unable to cache %s', uninstaller)
ret[pkgname] = {'unable to cache': uninstaller}
continue
else:
# Run the uninstaller directly (not hosted on salt:, https:, etc.)
cached_pkg = uninstaller
# Get parameters for cmd
expanded_cached_pkg = str(os.path.expandvars(cached_pkg))
# Fix non-windows slashes
cached_pkg = cached_pkg.replace('/', '\\')
cache_path, _ = os.path.split(cached_pkg)
# Get uninstall flags
uninstall_flags = '{0}'.format(
pkginfo[version_num].get('uninstall_flags', '')
)
if kwargs.get('extra_uninstall_flags'):
uninstall_flags = '{0} {1}'.format(
uninstall_flags,
kwargs.get('extra_uninstall_flags', "")
# Get parameters for cmd
expanded_cached_pkg = str(os.path.expandvars(cached_pkg))
# Get uninstall flags
uninstall_flags = '{0}'.format(
pkginfo[target].get('uninstall_flags', '')
)
if kwargs.get('extra_uninstall_flags'):
uninstall_flags = '{0} {1}'.format(
uninstall_flags,
kwargs.get('extra_uninstall_flags', "")
)
# Uninstall the software
# Check Use Scheduler Option
if pkginfo[version_num].get('use_scheduler', False):
# Uninstall the software
# Check Use Scheduler Option
if pkginfo[target].get('use_scheduler', False):
# Build Scheduled Task Parameters
if pkginfo[version_num].get('msiexec'):
cmd = 'msiexec.exe'
arguments = ['/x']
arguments.extend(salt.utils.shlex_split(uninstall_flags))
else:
cmd = expanded_cached_pkg
arguments = salt.utils.shlex_split(uninstall_flags)
# Build Scheduled Task Parameters
if pkginfo[target].get('msiexec'):
cmd = 'msiexec.exe'
arguments = ['/x']
arguments.extend(salt.utils.shlex_split(uninstall_flags))
else:
cmd = expanded_cached_pkg
arguments = salt.utils.shlex_split(uninstall_flags)
# Create Scheduled Task
__salt__['task.create_task'](name='update-salt-software',
user_name='System',
force=True,
action_type='Execute',
cmd=cmd,
arguments=' '.join(arguments),
start_in=cache_path,
trigger_type='Once',
start_date='1975-01-01',
start_time='01:00',
ac_only=False,
stop_if_on_batteries=False)
# Run Scheduled Task
if not __salt__['task.run_wait'](name='update-salt-software'):
log.error('Failed to remove {0}'.format(target))
log.error('Scheduled Task failed to run')
ret[target] = {'uninstall status': 'failed'}
else:
# Build the install command
cmd = []
if pkginfo[version_num].get('msiexec'):
cmd.extend(['msiexec', '/x', expanded_cached_pkg])
# Create Scheduled Task
__salt__['task.create_task'](name='update-salt-software',
user_name='System',
force=True,
action_type='Execute',
cmd=cmd,
arguments=' '.join(arguments),
start_in=cache_path,
trigger_type='Once',
start_date='1975-01-01',
start_time='01:00',
ac_only=False,
stop_if_on_batteries=False)
# Run Scheduled Task
if not __salt__['task.run_wait'](name='update-salt-software'):
log.error('Failed to remove %s', pkgname)
log.error('Scheduled Task failed to run')
ret[pkgname] = {'uninstall status': 'failed'}
else:
cmd.append(expanded_cached_pkg)
cmd.extend(salt.utils.shlex_split(uninstall_flags))
# Launch the command
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'}
# Build the install command
cmd = []
if pkginfo[target].get('msiexec'):
cmd.extend(['msiexec', '/x', expanded_cached_pkg])
else:
cmd.append(expanded_cached_pkg)
cmd.extend(salt.utils.shlex_split(uninstall_flags))
# Launch the command
result = __salt__['cmd.run_all'](cmd,
output_loglevel='trace',
python_shell=False,
redirect_stderr=True)
if not result['retcode']:
ret[pkgname] = {'uninstall status': 'success'}
changed.append(pkgname)
else:
log.error('Failed to remove %s', pkgname)
log.error('retcode %s', result['retcode'])
log.error('uninstaller output: %s', result['stdout'])
ret[pkgname] = {'uninstall status': 'failed'}
# Get a new list of installed software
new = list_pkgs(saltenv=saltenv)
tries = 0
difference = salt.utils.compare_dicts(old, new)
# Take the "old" package list and convert the values to strings in
# preparation for the comparison below.
__salt__['pkg_resource.stringify'](old)
difference = salt.utils.compare_dicts(old, new)
tries = 0
while not all(name in difference for name in changed) and tries <= 1000:
new = list_pkgs(saltenv=saltenv)
difference = salt.utils.compare_dicts(old, new)