summaryrefslogtreecommitdiff
path: root/lib/ansible/executor/module_common.py
diff options
context:
space:
mode:
Diffstat (limited to 'lib/ansible/executor/module_common.py')
-rw-r--r--lib/ansible/executor/module_common.py85
1 files changed, 39 insertions, 46 deletions
diff --git a/lib/ansible/executor/module_common.py b/lib/ansible/executor/module_common.py
index 35175432..4d06acb2 100644
--- a/lib/ansible/executor/module_common.py
+++ b/lib/ansible/executor/module_common.py
@@ -26,7 +26,6 @@ import datetime
import json
import os
import shlex
-import time
import zipfile
import re
import pkgutil
@@ -167,7 +166,7 @@ def _ansiballz_main():
else:
PY3 = True
- ZIPDATA = %(zipdata)r
+ ZIPDATA = """%(zipdata)s"""
# Note: temp_path isn't needed once we switch to zipimport
def invoke_module(modlib_path, temp_path, json_params):
@@ -178,13 +177,13 @@ def _ansiballz_main():
z = zipfile.ZipFile(modlib_path, mode='a')
# py3: modlib_path will be text, py2: it's bytes. Need bytes at the end
- sitecustomize = u'import sys\\nsys.path.insert(0,"%%s")\\n' %% modlib_path
+ sitecustomize = u'import sys\\nsys.path.insert(0,"%%s")\\n' %% modlib_path
sitecustomize = sitecustomize.encode('utf-8')
# Use a ZipInfo to work around zipfile limitation on hosts with
# clocks set to a pre-1980 year (for instance, Raspberry Pi)
zinfo = zipfile.ZipInfo()
zinfo.filename = 'sitecustomize.py'
- zinfo.date_time = %(date_time)s
+ zinfo.date_time = ( %(year)i, %(month)i, %(day)i, %(hour)i, %(minute)i, %(second)i)
z.writestr(zinfo, sitecustomize)
z.close()
@@ -197,7 +196,7 @@ def _ansiballz_main():
basic._ANSIBLE_ARGS = json_params
%(coverage)s
# Run the module! By importing it as '__main__', it thinks it is executing as a script
- runpy.run_module(mod_name=%(module_fqn)r, init_globals=dict(_module_fqn=%(module_fqn)r, _modlib_path=modlib_path),
+ runpy.run_module(mod_name='%(module_fqn)s', init_globals=dict(_module_fqn='%(module_fqn)s', _modlib_path=modlib_path),
run_name='__main__', alter_sys=True)
# Ansible modules must exit themselves
@@ -288,7 +287,7 @@ def _ansiballz_main():
basic._ANSIBLE_ARGS = json_params
# Run the module! By importing it as '__main__', it thinks it is executing as a script
- runpy.run_module(mod_name=%(module_fqn)r, init_globals=None, run_name='__main__', alter_sys=True)
+ runpy.run_module(mod_name='%(module_fqn)s', init_globals=None, run_name='__main__', alter_sys=True)
# Ansible modules must exit themselves
print('{"msg": "New-style module did not handle its own exit", "failed": true}')
@@ -313,9 +312,9 @@ def _ansiballz_main():
# store this in remote_tmpdir (use system tempdir instead)
# Only need to use [ansible_module]_payload_ in the temp_path until we move to zipimport
# (this helps ansible-test produce coverage stats)
- temp_path = tempfile.mkdtemp(prefix='ansible_' + %(ansible_module)r + '_payload_')
+ temp_path = tempfile.mkdtemp(prefix='ansible_%(ansible_module)s_payload_')
- zipped_mod = os.path.join(temp_path, 'ansible_' + %(ansible_module)r + '_payload.zip')
+ zipped_mod = os.path.join(temp_path, 'ansible_%(ansible_module)s_payload.zip')
with open(zipped_mod, 'wb') as modlib:
modlib.write(base64.b64decode(ZIPDATA))
@@ -338,7 +337,7 @@ if __name__ == '__main__':
'''
ANSIBALLZ_COVERAGE_TEMPLATE = '''
- os.environ['COVERAGE_FILE'] = %(coverage_output)r + '=python-%%s=coverage' %% '.'.join(str(v) for v in sys.version_info[:2])
+ os.environ['COVERAGE_FILE'] = '%(coverage_output)s=python-%%s=coverage' %% '.'.join(str(v) for v in sys.version_info[:2])
import atexit
@@ -348,7 +347,7 @@ ANSIBALLZ_COVERAGE_TEMPLATE = '''
print('{"msg": "Could not import `coverage` module.", "failed": true}')
sys.exit(1)
- cov = coverage.Coverage(config_file=%(coverage_config)r)
+ cov = coverage.Coverage(config_file='%(coverage_config)s')
def atexit_coverage():
cov.stop()
@@ -871,17 +870,7 @@ class CollectionModuleUtilLocator(ModuleUtilLocatorBase):
return name_parts[5:] # eg, foo.bar for ansible_collections.ns.coll.plugins.module_utils.foo.bar
-def _make_zinfo(filename, date_time, zf=None):
- zinfo = zipfile.ZipInfo(
- filename=filename,
- date_time=date_time
- )
- if zf:
- zinfo.compress_type = zf.compression
- return zinfo
-
-
-def recursive_finder(name, module_fqn, module_data, zf, date_time=None):
+def recursive_finder(name, module_fqn, module_data, zf):
"""
Using ModuleDepFinder, make sure we have all of the module_utils files that
the module and its module_utils files needs. (no longer actually recursive)
@@ -891,8 +880,6 @@ def recursive_finder(name, module_fqn, module_data, zf, date_time=None):
:arg zf: An open :python:class:`zipfile.ZipFile` object that holds the Ansible module payload
which we're assembling
"""
- if date_time is None:
- date_time = time.gmtime()[:6]
# py_module_cache maps python module names to a tuple of the code in the module
# and the pathname to the module.
@@ -989,10 +976,7 @@ def recursive_finder(name, module_fqn, module_data, zf, date_time=None):
for py_module_name in py_module_cache:
py_module_file_name = py_module_cache[py_module_name][1]
- zf.writestr(
- _make_zinfo(py_module_file_name, date_time, zf=zf),
- py_module_cache[py_module_name][0]
- )
+ zf.writestr(py_module_file_name, py_module_cache[py_module_name][0])
mu_file = to_text(py_module_file_name, errors='surrogate_or_strict')
display.vvvvv("Including module_utils file %s" % mu_file)
@@ -1036,16 +1020,13 @@ def _get_ansible_module_fqn(module_path):
return remote_module_fqn
-def _add_module_to_zip(zf, date_time, remote_module_fqn, b_module_data):
+def _add_module_to_zip(zf, remote_module_fqn, b_module_data):
"""Add a module from ansible or from an ansible collection into the module zip"""
module_path_parts = remote_module_fqn.split('.')
# Write the module
module_path = '/'.join(module_path_parts) + '.py'
- zf.writestr(
- _make_zinfo(module_path, date_time, zf=zf),
- b_module_data
- )
+ zf.writestr(module_path, b_module_data)
# Write the __init__.py's necessary to get there
if module_path_parts[0] == 'ansible':
@@ -1064,10 +1045,7 @@ def _add_module_to_zip(zf, date_time, remote_module_fqn, b_module_data):
continue
# Note: We don't want to include more than one ansible module in a payload at this time
# so no need to fill the __init__.py with namespace code
- zf.writestr(
- _make_zinfo(package_path, date_time, zf=zf),
- b''
- )
+ zf.writestr(package_path, b'')
def _find_module_utils(module_name, b_module_data, module_path, module_args, task_vars, templar, module_compression, async_timeout, become,
@@ -1132,10 +1110,6 @@ def _find_module_utils(module_name, b_module_data, module_path, module_args, tas
remote_module_fqn = 'ansible.modules.%s' % module_name
if module_substyle == 'python':
- date_time = time.gmtime()[:6]
- if date_time[0] < 1980:
- date_string = datetime.datetime(*date_time, tzinfo=datetime.timezone.utc).strftime('%c')
- raise AnsibleError(f'Cannot create zipfile due to pre-1980 configured date: {date_string}')
params = dict(ANSIBLE_MODULE_ARGS=module_args,)
try:
python_repred_params = repr(json.dumps(params, cls=AnsibleJSONEncoder, vault_to_text=True))
@@ -1181,10 +1155,10 @@ def _find_module_utils(module_name, b_module_data, module_path, module_args, tas
zf = zipfile.ZipFile(zipoutput, mode='w', compression=compression_method)
# walk the module imports, looking for module_utils to send- they'll be added to the zipfile
- recursive_finder(module_name, remote_module_fqn, b_module_data, zf, date_time)
+ recursive_finder(module_name, remote_module_fqn, b_module_data, zf)
display.debug('ANSIBALLZ: Writing module into payload')
- _add_module_to_zip(zf, date_time, remote_module_fqn, b_module_data)
+ _add_module_to_zip(zf, remote_module_fqn, b_module_data)
zf.close()
zipdata = base64.b64encode(zipoutput.getvalue())
@@ -1267,6 +1241,7 @@ def _find_module_utils(module_name, b_module_data, module_path, module_args, tas
else:
coverage = ''
+ now = datetime.datetime.utcnow()
output.write(to_bytes(ACTIVE_ANSIBALLZ_TEMPLATE % dict(
zipdata=zipdata,
ansible_module=module_name,
@@ -1274,7 +1249,12 @@ def _find_module_utils(module_name, b_module_data, module_path, module_args, tas
params=python_repred_params,
shebang=shebang,
coding=ENCODING_STRING,
- date_time=date_time,
+ year=now.year,
+ month=now.month,
+ day=now.day,
+ hour=now.hour,
+ minute=now.minute,
+ second=now.second,
coverage=coverage,
rlimit=rlimit,
)))
@@ -1397,7 +1377,20 @@ def modify_module(module_name, module_path, module_args, templar, task_vars=None
return (b_module_data, module_style, shebang)
-def get_action_args_with_defaults(action, args, defaults, templar, action_groups=None):
+def get_action_args_with_defaults(action, args, defaults, templar, redirected_names=None, action_groups=None):
+ if redirected_names:
+ resolved_action_name = redirected_names[-1]
+ else:
+ resolved_action_name = action
+
+ if redirected_names is not None:
+ msg = (
+ "Finding module_defaults for the action %s. "
+ "The caller passed a list of redirected action names, which is deprecated. "
+ "The task's resolved action should be provided as the first argument instead."
+ )
+ display.deprecated(msg % resolved_action_name, version='2.16')
+
# Get the list of groups that contain this action
if action_groups is None:
msg = (
@@ -1408,7 +1401,7 @@ def get_action_args_with_defaults(action, args, defaults, templar, action_groups
display.warning(msg=msg)
group_names = []
else:
- group_names = action_groups.get(action, [])
+ group_names = action_groups.get(resolved_action_name, [])
tmp_args = {}
module_defaults = {}
@@ -1427,7 +1420,7 @@ def get_action_args_with_defaults(action, args, defaults, templar, action_groups
tmp_args.update((module_defaults.get('group/%s' % group_name) or {}).copy())
# handle specific action defaults
- tmp_args.update(module_defaults.get(action, {}).copy())
+ tmp_args.update(module_defaults.get(resolved_action_name, {}).copy())
# direct args override all
tmp_args.update(args)