ansible-core 2.18.2__py3-none-any.whl → 2.18.3__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of ansible-core might be problematic. Click here for more details.

@@ -17,6 +17,6 @@
17
17
 
18
18
  from __future__ import annotations
19
19
 
20
- __version__ = '2.18.2'
20
+ __version__ = '2.18.3'
21
21
  __author__ = 'Ansible, Inc.'
22
22
  __codename__ = "Fool in the Rain"
ansible/modules/meta.py CHANGED
@@ -22,8 +22,13 @@ options:
22
22
  points to implicitly trigger handler runs (after pre/post tasks, the final role execution, and the main tasks section of your plays).
23
23
  - V(refresh_inventory) (added in Ansible 2.0) forces the reload of the inventory, which in the case of dynamic inventory scripts means they will be
24
24
  re-executed. If the dynamic inventory script is using a cache, Ansible cannot know this and has no way of refreshing it (you can disable the cache
25
- or, if available for your specific inventory datasource (e.g. aws), you can use the an inventory plugin instead of an inventory script).
26
- This is mainly useful when additional hosts are created and users wish to use them instead of using the M(ansible.builtin.add_host) module.
25
+ or, if available for your specific inventory datasource (for example P(amazon.aws.aws_ec2#inventory)), you can use the an inventory plugin instead
26
+ of an inventory script). This is mainly useful when additional hosts are created and users wish to use them instead of using the
27
+ M(ansible.builtin.add_host) module.
28
+ - Note that neither V(refresh_inventory) nor the M(ansible.builtin.add_host) add hosts to the hosts the current play iterates over.
29
+ However, if needed, you can explicitly delegate tasks to new hosts with C(delegate_to). Generally,
30
+ C(delegate_to) can be used against hosts regardless of whether they are in the inventory or not, as long as
31
+ the value supplied is sufficient for the connection plugin to access the host.
27
32
  - V(noop) (added in Ansible 2.0) This literally does 'nothing'. It is mainly used internally and not recommended for general use.
28
33
  - V(clear_facts) (added in Ansible 2.1) causes the gathered facts for the hosts specified in the play's list of hosts to be cleared,
29
34
  including the fact cache.
@@ -162,7 +162,7 @@ class StrategyModule(StrategyBase):
162
162
  # for the linear strategy, we run meta tasks just once and for
163
163
  # all hosts currently being iterated over rather than one host
164
164
  results.extend(self._execute_meta(task, play_context, iterator, host))
165
- if task.args.get('_raw_params', None) not in ('noop', 'reset_connection', 'end_host', 'role_complete', 'flush_handlers'):
165
+ if task.args.get('_raw_params', None) not in ('noop', 'reset_connection', 'end_host', 'role_complete', 'flush_handlers', 'end_role'):
166
166
  run_once = True
167
167
  if (task.any_errors_fatal or run_once) and not task.ignore_errors:
168
168
  any_errors_fatal = True
ansible/release.py CHANGED
@@ -17,6 +17,6 @@
17
17
 
18
18
  from __future__ import annotations
19
19
 
20
- __version__ = '2.18.2'
20
+ __version__ = '2.18.3'
21
21
  __author__ = 'Ansible, Inc.'
22
22
  __codename__ = "Fool in the Rain"
ansible/vars/manager.py CHANGED
@@ -599,7 +599,7 @@ class VariableManager:
599
599
  Sets a value in the vars_cache for a host.
600
600
  """
601
601
 
602
- warn_if_reserved(varname)
602
+ warn_if_reserved([varname])
603
603
  if host not in self._vars_cache:
604
604
  self._vars_cache[host] = dict()
605
605
  if varname in self._vars_cache[host] and isinstance(self._vars_cache[host][varname], MutableMapping) and isinstance(value, MutableMapping):
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.2
2
2
  Name: ansible-core
3
- Version: 2.18.2
3
+ Version: 2.18.3
4
4
  Summary: Radically simple IT automation
5
5
  Author: Ansible Project
6
6
  Project-URL: Homepage, https://ansible.com/
@@ -3,7 +3,7 @@ ansible/__main__.py,sha256=24j-7-YT4lZ2fmV80JD-VRoYBnxR7YoP_VP-orJtDt0,796
3
3
  ansible/constants.py,sha256=dSgbrzNsmhYc4GQOWZvRm4XKgf--_MUWcMa_9_7l5Pc,9757
4
4
  ansible/context.py,sha256=oKYyfjfWpy8vDeProtqfnqSmuij_t75_5e5t0U_hQ1g,1933
5
5
  ansible/keyword_desc.yml,sha256=xD-MRMB8mSRaj2ADwRnjIEbOwJKbc6BYadouGPfS0mI,7462
6
- ansible/release.py,sha256=U-5xX-4Rd1AukTzNrukHD-Qk_UrpbV4_Z-oIFaTMD0A,836
6
+ ansible/release.py,sha256=8JDdr3xoPP96cBtrknWA5s62nQX34KZNwTlkFf994GA,836
7
7
  ansible/_vendor/__init__.py,sha256=2QBeBwT7uG7M3Aw-pIdCpt6XPtHMCpbEKfACYKA7xIg,2033
8
8
  ansible/cli/__init__.py,sha256=e0KjeLfG1Ketbwl-uOmQ-zXoq3_El80LnHTGu80d1gs,28111
9
9
  ansible/cli/adhoc.py,sha256=quJ9WzRzf3dz_dtDGmahNMffqyNVy1jzQCMo21YL5Qg,8194
@@ -141,7 +141,7 @@ ansible/inventory/host.py,sha256=PDb5OTplhfpUIvdHiP2BckUOB1gUl302N-3sW0_sTyg,503
141
141
  ansible/inventory/manager.py,sha256=45mHgZTAkQ3IjAtrgsNzJXvynC-HIEor-JJE-V3xXN4,29454
142
142
  ansible/module_utils/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
143
143
  ansible/module_utils/_text.py,sha256=VkWgAnSNVCbTQqZgllUObBFsH3uM4EUW5srl1UR9t1g,544
144
- ansible/module_utils/ansible_release.py,sha256=U-5xX-4Rd1AukTzNrukHD-Qk_UrpbV4_Z-oIFaTMD0A,836
144
+ ansible/module_utils/ansible_release.py,sha256=8JDdr3xoPP96cBtrknWA5s62nQX34KZNwTlkFf994GA,836
145
145
  ansible/module_utils/api.py,sha256=r4wd6XZGhUnxMF416Ry6ebgq8BIhjCPSPOvO2ZtrYxE,5785
146
146
  ansible/module_utils/basic.py,sha256=fogfpo_l7JtS34WvgwwOebmPfMhFjQaJN5CwjKgUJVE,86291
147
147
  ansible/module_utils/connection.py,sha256=8TviwCucQ7d_JILwaUHE4tCuNfR3U1WFkmxLMxWa8Rw,7671
@@ -319,7 +319,7 @@ ansible/modules/include_vars.py,sha256=IyLjhjIpwCPes9ytQ7bzGsLgJRQuiOFqt8nzTUhcn
319
319
  ansible/modules/iptables.py,sha256=8An92NU65l8Lswj5Ptf4FYqmE7ZC4bFkTPIPmGDWCTk,34708
320
320
  ansible/modules/known_hosts.py,sha256=QPDEQgoVHSLAZrfv4zrvTUa65w5DIvwSGaOcw9SPTG8,14439
321
321
  ansible/modules/lineinfile.py,sha256=ZAUoZQJYJe4HMItmeLmrGTWKOoT_Q0kuOPGEU9Yr2Yk,23734
322
- ansible/modules/meta.py,sha256=91yQY-KOsuWVoV_DMAv7aj4Q_iZGIgxmKTe8Yjxut2g,6620
322
+ ansible/modules/meta.py,sha256=DQlvH4rQGBvRI3zvF3rHJ7lSXPEjwJyDrlqITrhfrOE,7121
323
323
  ansible/modules/mount_facts.py,sha256=TbRFvz55BU473OI5SFt8cSQRVXfu6-MJ5ka7on46EkY,25997
324
324
  ansible/modules/package.py,sha256=oJRsLK4U9oxsW4WNALMeGmPhWpZW9NsMgswwz3ad8xM,3748
325
325
  ansible/modules/package_facts.py,sha256=3u_DOU57hyp7y1qcsTfBf-oWG1kqU29T-G9OQxdiwqo,16806
@@ -587,7 +587,7 @@ ansible/plugins/strategy/__init__.py,sha256=rkfyXtvBqvQIXgL8T4XChQTRMaiLnliTZj5c
587
587
  ansible/plugins/strategy/debug.py,sha256=yMmfT-lQHfR2y9bQcqrSPzqHuWZMo7V9y4ZWOXoboRE,1205
588
588
  ansible/plugins/strategy/free.py,sha256=WNrpfg2B8fVcYC5qvBhn4uEH0Cc1-UmFzBH6Hhs3u_I,16728
589
589
  ansible/plugins/strategy/host_pinned.py,sha256=GrDDQCtohmmJn3t9VOPb0lUZK_nUWy0s__z5Tq_rHfI,1875
590
- ansible/plugins/strategy/linear.py,sha256=syZPVmCr2hlHBAzdpUtoajIz4Zs3ycXzcvlUGyQl5_0,17997
590
+ ansible/plugins/strategy/linear.py,sha256=WPn8KKNZLnjRAftgoe6EWTistiip94cSretMklINwck,18009
591
591
  ansible/plugins/terminal/__init__.py,sha256=EqeJpMokRzuUMO66yYErPSyninjqNX0_5r55CEkTc4o,4420
592
592
  ansible/plugins/test/__init__.py,sha256=m-XTUgWU-qSLJoZvHN3A85igElMjhaBJrzCTDrU7zhs,418
593
593
  ansible/plugins/test/abs.yml,sha256=lZA0XP1oBNg___Du6SqNOkDeQC9xIcZpROYV5XJG9bg,764
@@ -684,7 +684,7 @@ ansible/vars/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
684
684
  ansible/vars/clean.py,sha256=X2WMksJMWITQ9FsM-Fb_YxT_hAGDqJ3urSTJzYBEdAk,5999
685
685
  ansible/vars/fact_cache.py,sha256=M57vMhkQ2DrzvNaZkfaCmKQJUqP1Rn_A31_X-5YBfzQ,1903
686
686
  ansible/vars/hostvars.py,sha256=o11xrzDVYn23renGbb3lx3R-nH9qOjLFju5IYJanDxg,5324
687
- ansible/vars/manager.py,sha256=yksGRuDjOQnbTV1B0ot3gLSMtjCazIEmNjY5H_z1iw8,31258
687
+ ansible/vars/manager.py,sha256=JF2KTL4iYSbcdnFNjhQPktwH05YhWJhTWtjSlF0qg9E,31260
688
688
  ansible/vars/plugins.py,sha256=PocWZPMqFl1LoNgWlGFNxwg9nZnUzhQmlXO4g7bcP2A,4503
689
689
  ansible/vars/reserved.py,sha256=Tsc4m2UwVce3dOvSWrjT2wB3lpNJtUyNZn45zNhsW0I,2869
690
690
  ansible_test/__init__.py,sha256=20VPOj11c6Ut1Av9RaurgwJvFhMqkWG3vAvcCbecNKw,66
@@ -757,7 +757,7 @@ ansible_test/_internal/executor.py,sha256=KW5yI-f-giErQ077MTj707fTtFkf_Kr8IV_Nr3
757
757
  ansible_test/_internal/git.py,sha256=njtciWq2DlzZ1DAkQi08HRRP-TgH0mgeGZsWcsJGctI,4366
758
758
  ansible_test/_internal/host_configs.py,sha256=ElAo2t3kSyb7bShqBENiHH0oEe-8Am8JXG9xY5l7HY4,18634
759
759
  ansible_test/_internal/host_profiles.py,sha256=Y2_LM5nH_J0Yb0Cq9CX8D0VSM2JHJWY6Xs-ZUFX-opU,65629
760
- ansible_test/_internal/http.py,sha256=27EGOIWupvFXPo8abJ-3DScE2V2fyMMwAJ_3g0eL7O4,4123
760
+ ansible_test/_internal/http.py,sha256=ENuIPnBXIuvgDSxC-r5eOxfGzscxB6MOVJzT4OQXQSA,3864
761
761
  ansible_test/_internal/init.py,sha256=f2ZN7F-FyjMgN73SUgxwbVtWNhkJv7BIlZ-q4ALHyjM,505
762
762
  ansible_test/_internal/inventory.py,sha256=c79s-xc1uv2nD7rPISv0JKkKspY-X2-kHoozF2R4e1Q,5408
763
763
  ansible_test/_internal/io.py,sha256=e7ccixoPL5lrAPLUx50vOGYpcELWHhs0R3a5Sh6b5hs,2807
@@ -980,13 +980,13 @@ ansible_test/config/cloud-config-vultr.ini.template,sha256=XLKHk3lg_8ReQMdWfZzhh
980
980
  ansible_test/config/config.yml,sha256=1zdGucnIl6nIecZA7ISIANvqXiHWqq6Dthsk_6MUwNc,2642
981
981
  ansible_test/config/inventory.networking.template,sha256=bFNSk8zNQOaZ_twaflrY0XZ9mLwUbRLuNT0BdIFwvn4,1335
982
982
  ansible_test/config/inventory.winrm.template,sha256=1QU8W-GFLnYEw8yY9bVIvUAVvJYPM3hyoijf6-M7T00,1098
983
- ansible_core-2.18.2.dist-info/Apache-License.txt,sha256=y16Ofl9KOYjhBjwULGDcLfdWBfTEZRXnduOspt-XbhQ,11325
984
- ansible_core-2.18.2.dist-info/COPYING,sha256=OXLcl0T2SZ8Pmy2_dmlvKuetivmyPd5m1q-Gyd-zaYY,35149
985
- ansible_core-2.18.2.dist-info/METADATA,sha256=Cg9WFxRolEkSO_EFlMIPEHI68issQS76-gOeSyoVxIo,7668
986
- ansible_core-2.18.2.dist-info/MIT-license.txt,sha256=jLXp2XurnyZKbye40g9tfmLGtVlxh3pPD4n8xNqX8xc,1023
987
- ansible_core-2.18.2.dist-info/PSF-license.txt,sha256=g7BC_H1qyg8Q1o5F76Vrm8ChSWYI5-dyj-CdGlNKBUo,2484
988
- ansible_core-2.18.2.dist-info/WHEEL,sha256=In9FTNxeP60KnTkGw7wk6mJPYd_dQSjEZmXdBdMCI-8,91
989
- ansible_core-2.18.2.dist-info/entry_points.txt,sha256=S9yJij5Im6FgRQxzkqSCnPQokC7PcWrDW_NSygZczJU,451
990
- ansible_core-2.18.2.dist-info/simplified_bsd.txt,sha256=8R5R7R7sOa0h1Fi6RNgFgHowHBfun-OVOMzJ4rKAk2w,1237
991
- ansible_core-2.18.2.dist-info/top_level.txt,sha256=IFbRLjAvih1DYzJWg3_F6t4sCzEMxRO7TOMNs6GkYHo,21
992
- ansible_core-2.18.2.dist-info/RECORD,,
983
+ ansible_core-2.18.3.dist-info/Apache-License.txt,sha256=y16Ofl9KOYjhBjwULGDcLfdWBfTEZRXnduOspt-XbhQ,11325
984
+ ansible_core-2.18.3.dist-info/COPYING,sha256=OXLcl0T2SZ8Pmy2_dmlvKuetivmyPd5m1q-Gyd-zaYY,35149
985
+ ansible_core-2.18.3.dist-info/METADATA,sha256=jYnYoxfqbNuXTlbWtLaiB_7R8TZ7jgenorDCyhQR9dg,7668
986
+ ansible_core-2.18.3.dist-info/MIT-license.txt,sha256=jLXp2XurnyZKbye40g9tfmLGtVlxh3pPD4n8xNqX8xc,1023
987
+ ansible_core-2.18.3.dist-info/PSF-license.txt,sha256=g7BC_H1qyg8Q1o5F76Vrm8ChSWYI5-dyj-CdGlNKBUo,2484
988
+ ansible_core-2.18.3.dist-info/WHEEL,sha256=In9FTNxeP60KnTkGw7wk6mJPYd_dQSjEZmXdBdMCI-8,91
989
+ ansible_core-2.18.3.dist-info/entry_points.txt,sha256=S9yJij5Im6FgRQxzkqSCnPQokC7PcWrDW_NSygZczJU,451
990
+ ansible_core-2.18.3.dist-info/simplified_bsd.txt,sha256=8R5R7R7sOa0h1Fi6RNgFgHowHBfun-OVOMzJ4rKAk2w,1237
991
+ ansible_core-2.18.3.dist-info/top_level.txt,sha256=IFbRLjAvih1DYzJWg3_F6t4sCzEMxRO7TOMNs6GkYHo,21
992
+ ansible_core-2.18.3.dist-info/RECORD,,
@@ -1,36 +1,29 @@
1
- """
2
- Primitive replacement for requests to avoid extra dependency.
3
- Avoids use of urllib2 due to lack of SNI support.
4
- """
1
+ """A simple HTTP client."""
5
2
  from __future__ import annotations
6
3
 
4
+ import http.client
7
5
  import json
8
6
  import time
9
7
  import typing as t
8
+ import urllib.error
9
+ import urllib.request
10
10
 
11
11
  from .util import (
12
12
  ApplicationError,
13
- SubprocessError,
14
13
  display,
15
14
  )
16
15
 
17
16
  from .util_common import (
18
17
  CommonConfig,
19
- run_command,
20
18
  )
21
19
 
22
20
 
23
21
  class HttpClient:
24
- """Make HTTP requests via curl."""
22
+ """Make HTTP requests."""
25
23
 
26
- def __init__(self, args: CommonConfig, always: bool = False, insecure: bool = False, proxy: t.Optional[str] = None) -> None:
24
+ def __init__(self, args: CommonConfig, always: bool = False) -> None:
27
25
  self.args = args
28
26
  self.always = always
29
- self.insecure = insecure
30
- self.proxy = proxy
31
-
32
- self.username = None
33
- self.password = None
34
27
 
35
28
  def get(self, url: str) -> HttpResponse:
36
29
  """Perform an HTTP GET and return the response."""
@@ -46,74 +39,65 @@ class HttpClient:
46
39
 
47
40
  def request(self, method: str, url: str, data: t.Optional[str] = None, headers: t.Optional[dict[str, str]] = None) -> HttpResponse:
48
41
  """Perform an HTTP request and return the response."""
49
- cmd = ['curl', '-s', '-S', '-i', '-X', method]
50
-
51
- if self.insecure:
52
- cmd += ['--insecure']
53
-
54
42
  if headers is None:
55
43
  headers = {}
56
44
 
57
- headers['Expect'] = '' # don't send expect continue header
58
-
59
- if self.username:
60
- if self.password:
61
- display.sensitive.add(self.password)
62
- cmd += ['-u', '%s:%s' % (self.username, self.password)]
63
- else:
64
- cmd += ['-u', self.username]
65
-
66
- for header in headers.keys():
67
- cmd += ['-H', '%s: %s' % (header, headers[header])]
68
-
69
- if data is not None:
70
- cmd += ['-d', data]
45
+ data_bytes = data.encode() if data else None
71
46
 
72
- if self.proxy:
73
- cmd += ['-x', self.proxy]
47
+ request = urllib.request.Request(method=method, url=url, data=data_bytes, headers=headers)
48
+ response: http.client.HTTPResponse
74
49
 
75
- cmd += [url]
50
+ display.info(f'HTTP {method} {url}', verbosity=2)
76
51
 
77
52
  attempts = 0
78
53
  max_attempts = 3
79
54
  sleep_seconds = 3
80
55
 
81
- # curl error codes which are safe to retry (request never sent to server)
82
- retry_on_status = (
83
- 6, # CURLE_COULDNT_RESOLVE_HOST
84
- )
85
-
86
- stdout = ''
56
+ status_code = 200
57
+ reason = 'OK'
58
+ body_bytes = b''
87
59
 
88
60
  while True:
89
61
  attempts += 1
90
62
 
91
- try:
92
- stdout = run_command(self.args, cmd, capture=True, always=self.always, cmd_verbosity=2)[0]
63
+ start = time.monotonic()
64
+
65
+ if self.args.explain and not self.always:
93
66
  break
94
- except SubprocessError as ex:
95
- if ex.status in retry_on_status and attempts < max_attempts:
96
- display.warning('%s' % ex)
97
- time.sleep(sleep_seconds)
98
- continue
99
67
 
100
- raise
68
+ try:
69
+ try:
70
+ with urllib.request.urlopen(request) as response:
71
+ status_code = response.status
72
+ reason = response.reason
73
+ body_bytes = response.read()
74
+ except urllib.error.HTTPError as ex:
75
+ status_code = ex.status
76
+ reason = ex.reason
77
+ body_bytes = ex.read()
78
+ except Exception as ex: # pylint: disable=broad-exception-caught
79
+ if attempts >= max_attempts:
80
+ raise
81
+
82
+ # all currently implemented methods are idempotent, so retries are unconditionally supported
83
+ duration = time.monotonic() - start
84
+ display.warning(f'{type(ex).__module__}.{type(ex).__name__}: {ex} [{duration:.2f} seconds]')
85
+ time.sleep(sleep_seconds)
86
+
87
+ continue
101
88
 
102
- if self.args.explain and not self.always:
103
- return HttpResponse(method, url, 200, '')
89
+ break
104
90
 
105
- header, body = stdout.split('\r\n\r\n', 1)
91
+ duration = time.monotonic() - start
92
+ display.info(f'HTTP {method} {url} -> HTTP {status_code} ({reason}) [{len(body_bytes)} bytes, {duration:.2f} seconds]', verbosity=3)
106
93
 
107
- response_headers = header.split('\r\n')
108
- first_line = response_headers[0]
109
- http_response = first_line.split(' ')
110
- status_code = int(http_response[1])
94
+ body = body_bytes.decode()
111
95
 
112
96
  return HttpResponse(method, url, status_code, body)
113
97
 
114
98
 
115
99
  class HttpResponse:
116
- """HTTP response from curl."""
100
+ """HTTP response."""
117
101
 
118
102
  def __init__(self, method: str, url: str, status_code: int, response: str) -> None:
119
103
  self.method = method