ansible-core 2.18.7rc1__py3-none-any.whl → 2.19.0__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.

Files changed (757) hide show
  1. ansible/_internal/__init__.py +53 -0
  2. ansible/_internal/_ansiballz/__init__.py +0 -0
  3. ansible/_internal/_ansiballz/_builder.py +101 -0
  4. ansible/_internal/_ansiballz/_wrapper.py +262 -0
  5. ansible/_internal/_collection_proxy.py +47 -0
  6. ansible/_internal/_datatag/__init__.py +0 -0
  7. ansible/_internal/_datatag/_tags.py +130 -0
  8. ansible/_internal/_datatag/_utils.py +19 -0
  9. ansible/_internal/_datatag/_wrappers.py +33 -0
  10. ansible/_internal/_errors/__init__.py +0 -0
  11. ansible/_internal/_errors/_alarm_timeout.py +66 -0
  12. ansible/_internal/_errors/_captured.py +123 -0
  13. ansible/_internal/_errors/_error_factory.py +89 -0
  14. ansible/_internal/_errors/_error_utils.py +240 -0
  15. ansible/_internal/_errors/_handler.py +91 -0
  16. ansible/_internal/_errors/_task_timeout.py +28 -0
  17. ansible/_internal/_event_formatting.py +127 -0
  18. ansible/_internal/_json/__init__.py +214 -0
  19. ansible/_internal/_json/_legacy_encoder.py +34 -0
  20. ansible/_internal/_json/_profiles/__init__.py +0 -0
  21. ansible/_internal/_json/_profiles/_cache_persistence.py +57 -0
  22. ansible/_internal/_json/_profiles/_inventory_legacy.py +40 -0
  23. ansible/_internal/_json/_profiles/_legacy.py +189 -0
  24. ansible/_internal/_locking.py +21 -0
  25. ansible/_internal/_plugins/__init__.py +0 -0
  26. ansible/_internal/_plugins/_cache.py +57 -0
  27. ansible/_internal/_ssh/__init__.py +0 -0
  28. ansible/_internal/_ssh/_agent_launch.py +91 -0
  29. ansible/_internal/_ssh/_ssh_agent.py +619 -0
  30. ansible/_internal/_task.py +78 -0
  31. ansible/_internal/_templating/__init__.py +12 -0
  32. ansible/_internal/_templating/_access.py +86 -0
  33. ansible/_internal/_templating/_chain_templar.py +63 -0
  34. ansible/_internal/_templating/_datatag.py +95 -0
  35. ansible/_internal/_templating/_engine.py +592 -0
  36. ansible/_internal/_templating/_errors.py +28 -0
  37. ansible/_internal/_templating/_jinja_bits.py +1106 -0
  38. ansible/_internal/_templating/_jinja_common.py +323 -0
  39. ansible/_internal/_templating/_jinja_patches.py +44 -0
  40. ansible/_internal/_templating/_jinja_plugins.py +375 -0
  41. ansible/_internal/_templating/_lazy_containers.py +633 -0
  42. ansible/_internal/_templating/_marker_behaviors.py +103 -0
  43. ansible/_internal/_templating/_template_vars.py +72 -0
  44. ansible/_internal/_templating/_transform.py +70 -0
  45. ansible/_internal/_templating/_utils.py +108 -0
  46. ansible/_internal/_testing.py +26 -0
  47. ansible/_internal/_wrapt.py +1052 -0
  48. ansible/_internal/_yaml/__init__.py +0 -0
  49. ansible/_internal/_yaml/_constructor.py +240 -0
  50. ansible/_internal/_yaml/_dumper.py +70 -0
  51. ansible/_internal/_yaml/_errors.py +166 -0
  52. ansible/_internal/_yaml/_loader.py +66 -0
  53. ansible/_internal/ansible_collections/ansible/_protomatter/README.md +11 -0
  54. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/action/debug.py +36 -0
  55. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/filter/apply_trust.py +19 -0
  56. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/filter/dump_object.py +27 -0
  57. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/filter/finalize.py +16 -0
  58. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/filter/origin.py +18 -0
  59. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/filter/python_literal_eval.py +24 -0
  60. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/filter/python_literal_eval.yml +33 -0
  61. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/filter/tag_names.py +16 -0
  62. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/filter/true_type.py +17 -0
  63. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/filter/unmask.py +49 -0
  64. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/lookup/config.py +21 -0
  65. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/lookup/config.yml +2 -0
  66. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/test/tagged.py +15 -0
  67. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/test/tagged.yml +19 -0
  68. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/test/tagged_with.py +18 -0
  69. ansible/_internal/ansible_collections/ansible/_protomatter/plugins/test/tagged_with.yml +19 -0
  70. ansible/cli/__init__.py +93 -104
  71. ansible/cli/_ssh_askpass.py +54 -0
  72. ansible/cli/adhoc.py +20 -10
  73. ansible/cli/arguments/option_helpers.py +163 -10
  74. ansible/cli/config.py +43 -68
  75. ansible/cli/console.py +13 -11
  76. ansible/cli/doc.py +134 -77
  77. ansible/cli/galaxy.py +27 -20
  78. ansible/cli/inventory.py +28 -28
  79. ansible/cli/playbook.py +4 -12
  80. ansible/cli/pull.py +6 -3
  81. ansible/cli/scripts/ansible_connection_cli_stub.py +7 -7
  82. ansible/cli/vault.py +12 -11
  83. ansible/compat/__init__.py +2 -2
  84. ansible/compat/importlib_resources.py +9 -12
  85. ansible/config/base.yml +218 -133
  86. ansible/config/manager.py +220 -159
  87. ansible/constants.py +2 -65
  88. ansible/errors/__init__.py +350 -256
  89. ansible/executor/interpreter_discovery.py +28 -149
  90. ansible/executor/module_common.py +480 -514
  91. ansible/executor/play_iterator.py +22 -27
  92. ansible/executor/playbook_executor.py +11 -11
  93. ansible/executor/powershell/async_watchdog.ps1 +97 -102
  94. ansible/executor/powershell/async_wrapper.ps1 +204 -153
  95. ansible/executor/powershell/become_wrapper.ps1 +107 -144
  96. ansible/executor/powershell/bootstrap_wrapper.ps1 +46 -9
  97. ansible/executor/powershell/coverage_wrapper.ps1 +91 -135
  98. ansible/executor/powershell/exec_wrapper.ps1 +675 -196
  99. ansible/executor/powershell/module_manifest.py +469 -265
  100. ansible/executor/powershell/module_wrapper.ps1 +195 -186
  101. ansible/executor/powershell/powershell_expand_user.ps1 +20 -0
  102. ansible/executor/powershell/powershell_mkdtemp.ps1 +17 -0
  103. ansible/executor/powershell/psrp_fetch_file.ps1 +41 -0
  104. ansible/executor/powershell/psrp_put_file.ps1 +122 -0
  105. ansible/executor/powershell/winrm_fetch_file.ps1 +46 -0
  106. ansible/executor/powershell/winrm_put_file.ps1 +36 -0
  107. ansible/executor/process/worker.py +139 -149
  108. ansible/executor/stats.py +5 -5
  109. ansible/executor/task_executor.py +270 -297
  110. ansible/executor/task_queue_manager.py +135 -137
  111. ansible/executor/task_result.py +182 -79
  112. ansible/galaxy/__init__.py +2 -2
  113. ansible/galaxy/api.py +26 -25
  114. ansible/galaxy/collection/__init__.py +6 -14
  115. ansible/galaxy/collection/concrete_artifact_manager.py +12 -21
  116. ansible/galaxy/dependency_resolution/dataclasses.py +14 -4
  117. ansible/galaxy/dependency_resolution/providers.py +4 -4
  118. ansible/galaxy/dependency_resolution/reporters.py +81 -0
  119. ansible/galaxy/role.py +6 -10
  120. ansible/galaxy/token.py +28 -21
  121. ansible/inventory/data.py +47 -57
  122. ansible/inventory/group.py +50 -73
  123. ansible/inventory/helpers.py +9 -0
  124. ansible/inventory/host.py +37 -54
  125. ansible/inventory/manager.py +79 -34
  126. ansible/keyword_desc.yml +1 -1
  127. ansible/module_utils/_internal/__init__.py +55 -0
  128. ansible/module_utils/_internal/_ambient_context.py +58 -0
  129. ansible/module_utils/_internal/_ansiballz/__init__.py +0 -0
  130. ansible/module_utils/_internal/_ansiballz/_extensions/__init__.py +0 -0
  131. ansible/module_utils/_internal/_ansiballz/_extensions/_coverage.py +45 -0
  132. ansible/module_utils/_internal/_ansiballz/_extensions/_pydevd.py +62 -0
  133. ansible/module_utils/_internal/_ansiballz/_loader.py +81 -0
  134. ansible/module_utils/_internal/_ansiballz/_respawn.py +32 -0
  135. ansible/module_utils/_internal/_ansiballz/_respawn_wrapper.py +23 -0
  136. ansible/module_utils/_internal/_concurrent/_daemon_threading.py +1 -0
  137. ansible/module_utils/_internal/_dataclass_validation.py +217 -0
  138. ansible/module_utils/_internal/_datatag/__init__.py +961 -0
  139. ansible/module_utils/_internal/_datatag/_tags.py +16 -0
  140. ansible/module_utils/_internal/_debugging.py +31 -0
  141. ansible/module_utils/_internal/_deprecator.py +157 -0
  142. ansible/module_utils/_internal/_errors.py +101 -0
  143. ansible/module_utils/_internal/_event_utils.py +61 -0
  144. ansible/module_utils/_internal/_json/__init__.py +63 -0
  145. ansible/module_utils/_internal/_json/_legacy_encoder.py +26 -0
  146. ansible/module_utils/_internal/_json/_profiles/__init__.py +428 -0
  147. ansible/module_utils/_internal/_json/_profiles/_fallback_to_str.py +73 -0
  148. ansible/module_utils/_internal/_json/_profiles/_module_legacy_c2m.py +33 -0
  149. ansible/module_utils/_internal/_json/_profiles/_module_legacy_m2c.py +37 -0
  150. ansible/module_utils/_internal/_json/_profiles/_module_modern_c2m.py +35 -0
  151. ansible/module_utils/_internal/_json/_profiles/_module_modern_m2c.py +33 -0
  152. ansible/module_utils/_internal/_json/_profiles/_tagless.py +52 -0
  153. ansible/module_utils/_internal/_messages.py +130 -0
  154. ansible/module_utils/_internal/_patches/__init__.py +66 -0
  155. ansible/module_utils/_internal/_patches/_dataclass_annotation_patch.py +53 -0
  156. ansible/module_utils/_internal/_patches/_socket_patch.py +34 -0
  157. ansible/module_utils/_internal/_patches/_sys_intern_patch.py +34 -0
  158. ansible/module_utils/_internal/_plugin_info.py +38 -0
  159. ansible/module_utils/_internal/_stack.py +22 -0
  160. ansible/module_utils/_internal/_testing.py +0 -0
  161. ansible/module_utils/_internal/_text_utils.py +6 -0
  162. ansible/module_utils/_internal/_traceback.py +92 -0
  163. ansible/module_utils/_internal/_validation.py +14 -0
  164. ansible/module_utils/ansible_release.py +2 -2
  165. ansible/module_utils/api.py +1 -2
  166. ansible/module_utils/basic.py +303 -202
  167. ansible/module_utils/common/_utils.py +24 -28
  168. ansible/module_utils/common/arg_spec.py +8 -3
  169. ansible/module_utils/common/collections.py +7 -2
  170. ansible/module_utils/common/dict_transformations.py +2 -2
  171. ansible/module_utils/common/file.py +2 -2
  172. ansible/module_utils/common/json.py +90 -84
  173. ansible/module_utils/common/locale.py +2 -2
  174. ansible/module_utils/common/parameters.py +27 -24
  175. ansible/module_utils/common/process.py +2 -3
  176. ansible/module_utils/common/respawn.py +11 -33
  177. ansible/module_utils/common/sentinel.py +66 -0
  178. ansible/module_utils/common/sys_info.py +8 -8
  179. ansible/module_utils/common/text/converters.py +16 -37
  180. ansible/module_utils/common/validation.py +35 -24
  181. ansible/module_utils/common/warnings.py +143 -25
  182. ansible/module_utils/common/yaml.py +29 -3
  183. ansible/module_utils/compat/datetime.py +33 -21
  184. ansible/module_utils/compat/paramiko.py +21 -10
  185. ansible/module_utils/compat/typing.py +6 -5
  186. ansible/module_utils/connection.py +10 -13
  187. ansible/module_utils/csharp/Ansible.Basic.cs +15 -12
  188. ansible/module_utils/csharp/Ansible.Become.cs +1 -0
  189. ansible/module_utils/csharp/Ansible.Privilege.cs +2 -2
  190. ansible/module_utils/csharp/Ansible._Async.cs +517 -0
  191. ansible/module_utils/datatag.py +49 -0
  192. ansible/module_utils/distro/__init__.py +2 -2
  193. ansible/module_utils/facts/ansible_collector.py +4 -5
  194. ansible/module_utils/facts/collector.py +13 -14
  195. ansible/module_utils/facts/compat.py +4 -4
  196. ansible/module_utils/facts/default_collectors.py +1 -1
  197. ansible/module_utils/facts/hardware/aix.py +34 -0
  198. ansible/module_utils/facts/hardware/base.py +2 -2
  199. ansible/module_utils/facts/hardware/darwin.py +1 -3
  200. ansible/module_utils/facts/hardware/freebsd.py +2 -2
  201. ansible/module_utils/facts/hardware/linux.py +5 -5
  202. ansible/module_utils/facts/namespace.py +1 -1
  203. ansible/module_utils/facts/network/base.py +1 -1
  204. ansible/module_utils/facts/network/fc_wwn.py +1 -2
  205. ansible/module_utils/facts/network/iscsi.py +1 -2
  206. ansible/module_utils/facts/network/nvme.py +1 -2
  207. ansible/module_utils/facts/other/facter.py +2 -3
  208. ansible/module_utils/facts/other/ohai.py +2 -3
  209. ansible/module_utils/facts/sysctl.py +4 -6
  210. ansible/module_utils/facts/system/apparmor.py +1 -2
  211. ansible/module_utils/facts/system/caps.py +3 -3
  212. ansible/module_utils/facts/system/chroot.py +1 -2
  213. ansible/module_utils/facts/system/cmdline.py +1 -2
  214. ansible/module_utils/facts/system/date_time.py +5 -3
  215. ansible/module_utils/facts/system/distribution.py +27 -13
  216. ansible/module_utils/facts/system/dns.py +1 -1
  217. ansible/module_utils/facts/system/env.py +1 -2
  218. ansible/module_utils/facts/system/fips.py +7 -20
  219. ansible/module_utils/facts/system/loadavg.py +1 -2
  220. ansible/module_utils/facts/system/local.py +2 -3
  221. ansible/module_utils/facts/system/lsb.py +1 -2
  222. ansible/module_utils/facts/system/pkg_mgr.py +1 -2
  223. ansible/module_utils/facts/system/platform.py +1 -2
  224. ansible/module_utils/facts/system/python.py +1 -2
  225. ansible/module_utils/facts/system/selinux.py +1 -1
  226. ansible/module_utils/facts/system/service_mgr.py +1 -2
  227. ansible/module_utils/facts/system/ssh_pub_keys.py +1 -1
  228. ansible/module_utils/facts/system/systemd.py +1 -1
  229. ansible/module_utils/facts/system/user.py +1 -2
  230. ansible/module_utils/facts/utils.py +3 -3
  231. ansible/module_utils/facts/virtual/base.py +1 -1
  232. ansible/module_utils/facts/virtual/linux.py +3 -3
  233. ansible/module_utils/facts/virtual/sunos.py +3 -15
  234. ansible/module_utils/facts/virtual/sysctl.py +3 -16
  235. ansible/module_utils/json_utils.py +2 -2
  236. ansible/module_utils/parsing/convert_bool.py +7 -1
  237. ansible/module_utils/powershell/Ansible.ModuleUtils.AddType.psm1 +1 -1
  238. ansible/module_utils/powershell/Ansible.ModuleUtils.CamelConversion.psm1 +1 -1
  239. ansible/module_utils/powershell/Ansible.ModuleUtils.CommandUtil.psm1 +1 -1
  240. ansible/module_utils/powershell/Ansible.ModuleUtils.WebRequest.psm1 +1 -1
  241. ansible/module_utils/service.py +21 -31
  242. ansible/module_utils/splitter.py +7 -7
  243. ansible/module_utils/testing.py +31 -0
  244. ansible/module_utils/urls.py +64 -35
  245. ansible/modules/add_host.py +4 -4
  246. ansible/modules/apt.py +69 -49
  247. ansible/modules/apt_key.py +19 -12
  248. ansible/modules/apt_repository.py +32 -51
  249. ansible/modules/assemble.py +16 -14
  250. ansible/modules/assert.py +4 -4
  251. ansible/modules/async_status.py +24 -24
  252. ansible/modules/async_wrapper.py +20 -25
  253. ansible/modules/blockinfile.py +6 -7
  254. ansible/modules/command.py +13 -20
  255. ansible/modules/copy.py +60 -147
  256. ansible/modules/cron.py +24 -21
  257. ansible/modules/deb822_repository.py +8 -9
  258. ansible/modules/debconf.py +5 -5
  259. ansible/modules/debug.py +4 -4
  260. ansible/modules/dnf.py +8 -8
  261. ansible/modules/dnf5.py +39 -13
  262. ansible/modules/dpkg_selections.py +4 -4
  263. ansible/modules/expect.py +13 -15
  264. ansible/modules/fail.py +4 -4
  265. ansible/modules/fetch.py +4 -4
  266. ansible/modules/file.py +184 -144
  267. ansible/modules/find.py +22 -20
  268. ansible/modules/gather_facts.py +3 -3
  269. ansible/modules/get_url.py +77 -54
  270. ansible/modules/getent.py +7 -9
  271. ansible/modules/git.py +38 -38
  272. ansible/modules/group.py +6 -6
  273. ansible/modules/group_by.py +4 -4
  274. ansible/modules/hostname.py +15 -32
  275. ansible/modules/import_playbook.py +6 -6
  276. ansible/modules/import_role.py +6 -6
  277. ansible/modules/import_tasks.py +6 -6
  278. ansible/modules/include_role.py +6 -6
  279. ansible/modules/include_tasks.py +6 -6
  280. ansible/modules/include_vars.py +6 -6
  281. ansible/modules/iptables.py +86 -73
  282. ansible/modules/known_hosts.py +22 -24
  283. ansible/modules/lineinfile.py +5 -5
  284. ansible/modules/meta.py +4 -4
  285. ansible/modules/mount_facts.py +2 -2
  286. ansible/modules/package.py +10 -4
  287. ansible/modules/package_facts.py +22 -10
  288. ansible/modules/pause.py +6 -6
  289. ansible/modules/ping.py +6 -6
  290. ansible/modules/pip.py +21 -26
  291. ansible/modules/raw.py +6 -6
  292. ansible/modules/reboot.py +6 -6
  293. ansible/modules/replace.py +10 -14
  294. ansible/modules/rpm_key.py +7 -8
  295. ansible/modules/script.py +4 -4
  296. ansible/modules/service.py +10 -17
  297. ansible/modules/service_facts.py +87 -10
  298. ansible/modules/set_fact.py +5 -5
  299. ansible/modules/set_stats.py +4 -4
  300. ansible/modules/setup.py +2 -2
  301. ansible/modules/shell.py +6 -6
  302. ansible/modules/slurp.py +16 -19
  303. ansible/modules/stat.py +15 -31
  304. ansible/modules/subversion.py +15 -15
  305. ansible/modules/systemd.py +7 -7
  306. ansible/modules/systemd_service.py +7 -7
  307. ansible/modules/sysvinit.py +9 -9
  308. ansible/modules/tempfile.py +5 -6
  309. ansible/modules/template.py +6 -6
  310. ansible/modules/unarchive.py +38 -17
  311. ansible/modules/uri.py +33 -26
  312. ansible/modules/user.py +45 -32
  313. ansible/modules/validate_argument_spec.py +10 -7
  314. ansible/modules/wait_for.py +70 -60
  315. ansible/modules/wait_for_connection.py +6 -6
  316. ansible/modules/yum_repository.py +10 -9
  317. ansible/parsing/ajson.py +17 -37
  318. ansible/parsing/dataloader.py +99 -54
  319. ansible/parsing/mod_args.py +62 -60
  320. ansible/parsing/plugin_docs.py +21 -86
  321. ansible/parsing/quoting.py +1 -1
  322. ansible/parsing/splitter.py +27 -12
  323. ansible/parsing/utils/addresses.py +24 -24
  324. ansible/parsing/utils/jsonify.py +5 -1
  325. ansible/parsing/utils/yaml.py +32 -61
  326. ansible/parsing/vault/__init__.py +327 -99
  327. ansible/parsing/yaml/__init__.py +0 -18
  328. ansible/parsing/yaml/dumper.py +6 -120
  329. ansible/parsing/yaml/loader.py +6 -39
  330. ansible/parsing/yaml/objects.py +43 -335
  331. ansible/playbook/__init__.py +1 -1
  332. ansible/playbook/attribute.py +8 -3
  333. ansible/playbook/base.py +187 -134
  334. ansible/playbook/block.py +26 -24
  335. ansible/playbook/collectionsearch.py +1 -15
  336. ansible/playbook/conditional.py +3 -77
  337. ansible/playbook/handler.py +8 -2
  338. ansible/playbook/helpers.py +41 -53
  339. ansible/playbook/included_file.py +32 -26
  340. ansible/playbook/loop_control.py +2 -2
  341. ansible/playbook/play.py +85 -44
  342. ansible/playbook/play_context.py +14 -17
  343. ansible/playbook/playbook_include.py +27 -62
  344. ansible/playbook/role/__init__.py +64 -49
  345. ansible/playbook/role/definition.py +15 -17
  346. ansible/playbook/role/include.py +2 -4
  347. ansible/playbook/role/metadata.py +10 -11
  348. ansible/playbook/role_include.py +3 -3
  349. ansible/playbook/taggable.py +28 -12
  350. ansible/playbook/task.py +192 -121
  351. ansible/playbook/task_include.py +5 -5
  352. ansible/plugins/__init__.py +58 -26
  353. ansible/plugins/action/__init__.py +188 -186
  354. ansible/plugins/action/add_host.py +2 -2
  355. ansible/plugins/action/assemble.py +11 -18
  356. ansible/plugins/action/assert.py +55 -67
  357. ansible/plugins/action/async_status.py +7 -2
  358. ansible/plugins/action/copy.py +14 -17
  359. ansible/plugins/action/debug.py +37 -31
  360. ansible/plugins/action/dnf.py +3 -4
  361. ansible/plugins/action/fail.py +1 -1
  362. ansible/plugins/action/fetch.py +7 -8
  363. ansible/plugins/action/gather_facts.py +13 -14
  364. ansible/plugins/action/group_by.py +1 -1
  365. ansible/plugins/action/include_vars.py +10 -11
  366. ansible/plugins/action/package.py +8 -14
  367. ansible/plugins/action/pause.py +2 -2
  368. ansible/plugins/action/script.py +27 -38
  369. ansible/plugins/action/service.py +9 -18
  370. ansible/plugins/action/set_fact.py +3 -12
  371. ansible/plugins/action/set_stats.py +3 -8
  372. ansible/plugins/action/template.py +47 -67
  373. ansible/plugins/action/unarchive.py +6 -16
  374. ansible/plugins/action/uri.py +9 -20
  375. ansible/plugins/action/validate_argument_spec.py +5 -5
  376. ansible/plugins/action/wait_for_connection.py +1 -1
  377. ansible/plugins/become/__init__.py +31 -8
  378. ansible/plugins/become/runas.py +71 -0
  379. ansible/plugins/become/su.py +13 -8
  380. ansible/plugins/become/sudo.py +19 -0
  381. ansible/plugins/cache/__init__.py +52 -63
  382. ansible/plugins/cache/base.py +8 -0
  383. ansible/plugins/cache/jsonfile.py +10 -16
  384. ansible/plugins/cache/memory.py +6 -12
  385. ansible/plugins/callback/__init__.py +294 -201
  386. ansible/plugins/callback/default.py +99 -95
  387. ansible/plugins/callback/junit.py +44 -43
  388. ansible/plugins/callback/minimal.py +28 -25
  389. ansible/plugins/callback/oneline.py +34 -21
  390. ansible/plugins/callback/tree.py +27 -16
  391. ansible/plugins/connection/__init__.py +47 -34
  392. ansible/plugins/connection/local.py +156 -60
  393. ansible/plugins/connection/paramiko_ssh.py +34 -24
  394. ansible/plugins/connection/psrp.py +76 -165
  395. ansible/plugins/connection/ssh.py +326 -86
  396. ansible/plugins/connection/winrm.py +62 -141
  397. ansible/plugins/doc_fragments/action_common_attributes.py +14 -14
  398. ansible/plugins/doc_fragments/action_core.py +6 -6
  399. ansible/plugins/doc_fragments/backup.py +2 -2
  400. ansible/plugins/doc_fragments/checksum_common.py +27 -0
  401. ansible/plugins/doc_fragments/constructed.py +8 -4
  402. ansible/plugins/doc_fragments/decrypt.py +2 -2
  403. ansible/plugins/doc_fragments/default_callback.py +2 -2
  404. ansible/plugins/doc_fragments/files.py +2 -2
  405. ansible/plugins/doc_fragments/inventory_cache.py +2 -2
  406. ansible/plugins/doc_fragments/result_format_callback.py +2 -2
  407. ansible/plugins/doc_fragments/return_common.py +2 -2
  408. ansible/plugins/doc_fragments/template_common.py +4 -4
  409. ansible/plugins/doc_fragments/url.py +17 -1
  410. ansible/plugins/doc_fragments/url_windows.py +2 -2
  411. ansible/plugins/doc_fragments/validate.py +2 -2
  412. ansible/plugins/doc_fragments/vars_plugin_staging.py +2 -2
  413. ansible/plugins/filter/__init__.py +6 -2
  414. ansible/plugins/filter/b64decode.yml +22 -0
  415. ansible/plugins/filter/b64encode.yml +22 -0
  416. ansible/plugins/filter/bool.yml +11 -4
  417. ansible/plugins/filter/core.py +245 -120
  418. ansible/plugins/filter/encryption.py +42 -34
  419. ansible/plugins/filter/flatten.yml +3 -2
  420. ansible/plugins/filter/human_to_bytes.yml +1 -1
  421. ansible/plugins/filter/mathstuff.py +30 -37
  422. ansible/plugins/filter/password_hash.yml +8 -0
  423. ansible/plugins/filter/pow.yml +1 -1
  424. ansible/plugins/filter/regex_search.yml +1 -4
  425. ansible/plugins/filter/root.yml +1 -1
  426. ansible/plugins/filter/split.yml +1 -1
  427. ansible/plugins/filter/strftime.yml +3 -3
  428. ansible/plugins/filter/to_nice_yaml.yml +0 -4
  429. ansible/plugins/filter/to_uuid.yml +1 -1
  430. ansible/plugins/filter/to_yaml.yml +0 -4
  431. ansible/plugins/filter/unvault.yml +1 -1
  432. ansible/plugins/filter/urls.py +1 -1
  433. ansible/plugins/filter/urlsplit.py +8 -9
  434. ansible/plugins/filter/vault.yml +14 -9
  435. ansible/plugins/filter/win_basename.yml +6 -1
  436. ansible/plugins/filter/win_dirname.yml +5 -0
  437. ansible/plugins/inventory/__init__.py +107 -86
  438. ansible/plugins/inventory/advanced_host_list.py +7 -5
  439. ansible/plugins/inventory/auto.py +11 -4
  440. ansible/plugins/inventory/constructed.py +21 -24
  441. ansible/plugins/inventory/generator.py +16 -11
  442. ansible/plugins/inventory/host_list.py +7 -5
  443. ansible/plugins/inventory/ini.py +78 -44
  444. ansible/plugins/inventory/script.py +190 -120
  445. ansible/plugins/inventory/toml.py +16 -126
  446. ansible/plugins/inventory/yaml.py +10 -8
  447. ansible/plugins/list.py +72 -19
  448. ansible/plugins/loader.py +383 -198
  449. ansible/plugins/lookup/__init__.py +21 -4
  450. ansible/plugins/lookup/config.py +21 -35
  451. ansible/plugins/lookup/csvfile.py +19 -73
  452. ansible/plugins/lookup/dict.py +1 -6
  453. ansible/plugins/lookup/env.py +12 -9
  454. ansible/plugins/lookup/file.py +5 -8
  455. ansible/plugins/lookup/first_found.py +87 -55
  456. ansible/plugins/lookup/indexed_items.py +1 -10
  457. ansible/plugins/lookup/ini.py +14 -13
  458. ansible/plugins/lookup/items.py +1 -1
  459. ansible/plugins/lookup/lines.py +8 -1
  460. ansible/plugins/lookup/list.py +1 -1
  461. ansible/plugins/lookup/nested.py +2 -18
  462. ansible/plugins/lookup/password.py +5 -5
  463. ansible/plugins/lookup/pipe.py +5 -7
  464. ansible/plugins/lookup/sequence.py +18 -8
  465. ansible/plugins/lookup/subelements.py +1 -4
  466. ansible/plugins/lookup/template.py +47 -36
  467. ansible/plugins/lookup/together.py +0 -12
  468. ansible/plugins/lookup/unvault.py +1 -5
  469. ansible/plugins/lookup/url.py +4 -10
  470. ansible/plugins/lookup/vars.py +16 -24
  471. ansible/plugins/shell/__init__.py +58 -4
  472. ansible/plugins/shell/cmd.py +2 -2
  473. ansible/plugins/shell/powershell.py +106 -31
  474. ansible/plugins/shell/sh.py +13 -7
  475. ansible/plugins/strategy/__init__.py +168 -193
  476. ansible/plugins/strategy/debug.py +2 -2
  477. ansible/plugins/strategy/free.py +16 -31
  478. ansible/plugins/strategy/host_pinned.py +2 -2
  479. ansible/plugins/strategy/linear.py +41 -41
  480. ansible/plugins/terminal/__init__.py +4 -4
  481. ansible/plugins/test/__init__.py +7 -2
  482. ansible/plugins/test/core.py +75 -35
  483. ansible/plugins/test/files.py +1 -1
  484. ansible/plugins/test/finished.yml +1 -1
  485. ansible/plugins/test/mathstuff.py +3 -3
  486. ansible/plugins/test/uri.py +5 -8
  487. ansible/plugins/vars/host_group_vars.py +7 -14
  488. ansible/release.py +2 -2
  489. ansible/template/__init__.py +353 -943
  490. ansible/utils/__init__.py +0 -18
  491. ansible/utils/collection_loader/__init__.py +54 -5
  492. ansible/utils/collection_loader/_collection_config.py +5 -6
  493. ansible/utils/collection_loader/_collection_finder.py +82 -96
  494. ansible/utils/collection_loader/_collection_meta.py +15 -8
  495. ansible/utils/display.py +485 -73
  496. ansible/utils/encrypt.py +27 -19
  497. ansible/utils/fqcn.py +2 -2
  498. ansible/utils/galaxy.py +2 -2
  499. ansible/utils/hashing.py +8 -10
  500. ansible/utils/helpers.py +2 -2
  501. ansible/utils/listify.py +10 -8
  502. ansible/utils/lock.py +2 -2
  503. ansible/utils/path.py +10 -12
  504. ansible/utils/plugin_docs.py +16 -14
  505. ansible/utils/py3compat.py +2 -7
  506. ansible/utils/sentinel.py +4 -62
  507. ansible/utils/singleton.py +2 -0
  508. ansible/utils/ssh_functions.py +6 -2
  509. ansible/utils/unsafe_proxy.py +23 -332
  510. ansible/utils/vars.py +55 -8
  511. ansible/utils/version.py +2 -2
  512. ansible/vars/clean.py +5 -5
  513. ansible/vars/hostvars.py +60 -90
  514. ansible/vars/manager.py +220 -285
  515. ansible/vars/plugins.py +4 -4
  516. ansible/vars/reserved.py +13 -12
  517. {ansible_core-2.18.7rc1.dist-info → ansible_core-2.19.0.dist-info}/METADATA +4 -3
  518. ansible_core-2.19.0.dist-info/RECORD +1097 -0
  519. ansible_core-2.19.0.dist-info/licenses/licenses/BSD-3-Clause.txt +28 -0
  520. ansible_test/_data/completion/docker.txt +7 -7
  521. ansible_test/_data/completion/remote.txt +6 -6
  522. ansible_test/_data/completion/windows.txt +1 -0
  523. ansible_test/_data/requirements/ansible.txt +2 -2
  524. ansible_test/_data/requirements/sanity.ansible-doc.txt +3 -3
  525. ansible_test/_data/requirements/sanity.changelog.txt +2 -2
  526. ansible_test/_data/requirements/sanity.import.plugin.txt +2 -2
  527. ansible_test/_data/requirements/sanity.pep8.txt +1 -1
  528. ansible_test/_data/requirements/sanity.pylint.txt +5 -5
  529. ansible_test/_data/requirements/sanity.validate-modules.txt +2 -2
  530. ansible_test/_data/requirements/sanity.yamllint.txt +1 -1
  531. ansible_test/_data/requirements/units.txt +1 -0
  532. ansible_test/_internal/__init__.py +6 -0
  533. ansible_test/_internal/ansible_util.py +3 -1
  534. ansible_test/_internal/become.py +1 -0
  535. ansible_test/_internal/bootstrap.py +1 -0
  536. ansible_test/_internal/cache.py +1 -0
  537. ansible_test/_internal/cgroup.py +1 -0
  538. ansible_test/_internal/ci/__init__.py +1 -0
  539. ansible_test/_internal/ci/azp.py +1 -0
  540. ansible_test/_internal/ci/local.py +1 -0
  541. ansible_test/_internal/classification/__init__.py +1 -0
  542. ansible_test/_internal/classification/common.py +1 -0
  543. ansible_test/_internal/classification/csharp.py +1 -0
  544. ansible_test/_internal/classification/powershell.py +1 -0
  545. ansible_test/_internal/classification/python.py +1 -0
  546. ansible_test/_internal/cli/__init__.py +1 -0
  547. ansible_test/_internal/cli/actions.py +1 -0
  548. ansible_test/_internal/cli/argparsing/__init__.py +1 -0
  549. ansible_test/_internal/cli/argparsing/actions.py +1 -0
  550. ansible_test/_internal/cli/argparsing/argcompletion.py +1 -0
  551. ansible_test/_internal/cli/argparsing/parsers.py +1 -0
  552. ansible_test/_internal/cli/commands/__init__.py +11 -5
  553. ansible_test/_internal/cli/commands/coverage/__init__.py +1 -0
  554. ansible_test/_internal/cli/commands/coverage/analyze/__init__.py +1 -0
  555. ansible_test/_internal/cli/commands/coverage/analyze/targets/__init__.py +1 -0
  556. ansible_test/_internal/cli/commands/coverage/analyze/targets/combine.py +1 -0
  557. ansible_test/_internal/cli/commands/coverage/analyze/targets/expand.py +1 -0
  558. ansible_test/_internal/cli/commands/coverage/analyze/targets/filter.py +1 -0
  559. ansible_test/_internal/cli/commands/coverage/analyze/targets/generate.py +1 -0
  560. ansible_test/_internal/cli/commands/coverage/analyze/targets/missing.py +1 -0
  561. ansible_test/_internal/cli/commands/coverage/combine.py +1 -0
  562. ansible_test/_internal/cli/commands/coverage/erase.py +1 -0
  563. ansible_test/_internal/cli/commands/coverage/html.py +1 -0
  564. ansible_test/_internal/cli/commands/coverage/report.py +1 -0
  565. ansible_test/_internal/cli/commands/coverage/xml.py +1 -0
  566. ansible_test/_internal/cli/commands/env.py +1 -0
  567. ansible_test/_internal/cli/commands/integration/__init__.py +1 -0
  568. ansible_test/_internal/cli/commands/integration/network.py +1 -0
  569. ansible_test/_internal/cli/commands/integration/posix.py +1 -0
  570. ansible_test/_internal/cli/commands/integration/windows.py +1 -0
  571. ansible_test/_internal/cli/commands/sanity.py +9 -0
  572. ansible_test/_internal/cli/commands/shell.py +1 -0
  573. ansible_test/_internal/cli/commands/units.py +1 -0
  574. ansible_test/_internal/cli/compat.py +1 -0
  575. ansible_test/_internal/cli/completers.py +1 -0
  576. ansible_test/_internal/cli/converters.py +1 -0
  577. ansible_test/_internal/cli/environments.py +52 -5
  578. ansible_test/_internal/cli/epilog.py +1 -0
  579. ansible_test/_internal/cli/parsers/__init__.py +1 -0
  580. ansible_test/_internal/cli/parsers/base_argument_parsers.py +1 -0
  581. ansible_test/_internal/cli/parsers/helpers.py +1 -0
  582. ansible_test/_internal/cli/parsers/host_config_parsers.py +1 -0
  583. ansible_test/_internal/cli/parsers/key_value_parsers.py +1 -0
  584. ansible_test/_internal/cli/parsers/value_parsers.py +1 -0
  585. ansible_test/_internal/commands/__init__.py +1 -0
  586. ansible_test/_internal/commands/coverage/__init__.py +3 -2
  587. ansible_test/_internal/commands/coverage/analyze/__init__.py +1 -0
  588. ansible_test/_internal/commands/coverage/analyze/targets/__init__.py +1 -0
  589. ansible_test/_internal/commands/coverage/analyze/targets/combine.py +1 -0
  590. ansible_test/_internal/commands/coverage/analyze/targets/expand.py +1 -0
  591. ansible_test/_internal/commands/coverage/analyze/targets/filter.py +1 -0
  592. ansible_test/_internal/commands/coverage/analyze/targets/generate.py +1 -0
  593. ansible_test/_internal/commands/coverage/analyze/targets/missing.py +1 -0
  594. ansible_test/_internal/commands/coverage/combine.py +2 -1
  595. ansible_test/_internal/commands/coverage/erase.py +1 -0
  596. ansible_test/_internal/commands/coverage/html.py +1 -0
  597. ansible_test/_internal/commands/coverage/report.py +1 -0
  598. ansible_test/_internal/commands/coverage/xml.py +1 -0
  599. ansible_test/_internal/commands/env/__init__.py +2 -0
  600. ansible_test/_internal/commands/integration/__init__.py +22 -5
  601. ansible_test/_internal/commands/integration/cloud/__init__.py +1 -0
  602. ansible_test/_internal/commands/integration/cloud/acme.py +2 -1
  603. ansible_test/_internal/commands/integration/cloud/aws.py +1 -0
  604. ansible_test/_internal/commands/integration/cloud/azure.py +1 -0
  605. ansible_test/_internal/commands/integration/cloud/cs.py +1 -0
  606. ansible_test/_internal/commands/integration/cloud/digitalocean.py +1 -0
  607. ansible_test/_internal/commands/integration/cloud/galaxy.py +3 -2
  608. ansible_test/_internal/commands/integration/cloud/hcloud.py +1 -0
  609. ansible_test/_internal/commands/integration/cloud/httptester.py +3 -2
  610. ansible_test/_internal/commands/integration/cloud/nios.py +2 -1
  611. ansible_test/_internal/commands/integration/cloud/opennebula.py +1 -0
  612. ansible_test/_internal/commands/integration/cloud/openshift.py +1 -0
  613. ansible_test/_internal/commands/integration/cloud/scaleway.py +1 -0
  614. ansible_test/_internal/commands/integration/cloud/vcenter.py +1 -0
  615. ansible_test/_internal/commands/integration/cloud/vultr.py +1 -0
  616. ansible_test/_internal/commands/integration/coverage.py +8 -2
  617. ansible_test/_internal/commands/integration/filters.py +1 -0
  618. ansible_test/_internal/commands/integration/network.py +1 -0
  619. ansible_test/_internal/commands/integration/posix.py +1 -0
  620. ansible_test/_internal/commands/integration/windows.py +1 -0
  621. ansible_test/_internal/commands/sanity/__init__.py +19 -2
  622. ansible_test/_internal/commands/sanity/ansible_doc.py +1 -0
  623. ansible_test/_internal/commands/sanity/bin_symlinks.py +1 -0
  624. ansible_test/_internal/commands/sanity/compile.py +1 -0
  625. ansible_test/_internal/commands/sanity/ignores.py +1 -0
  626. ansible_test/_internal/commands/sanity/import.py +1 -0
  627. ansible_test/_internal/commands/sanity/integration_aliases.py +12 -0
  628. ansible_test/_internal/commands/sanity/pep8.py +1 -0
  629. ansible_test/_internal/commands/sanity/pslint.py +1 -0
  630. ansible_test/_internal/commands/sanity/pylint.py +25 -26
  631. ansible_test/_internal/commands/sanity/shellcheck.py +1 -0
  632. ansible_test/_internal/commands/sanity/validate_modules.py +1 -0
  633. ansible_test/_internal/commands/sanity/yamllint.py +1 -0
  634. ansible_test/_internal/commands/shell/__init__.py +44 -4
  635. ansible_test/_internal/commands/units/__init__.py +5 -1
  636. ansible_test/_internal/compat/__init__.py +1 -0
  637. ansible_test/_internal/compat/packaging.py +1 -0
  638. ansible_test/_internal/compat/yaml.py +1 -0
  639. ansible_test/_internal/completion.py +1 -0
  640. ansible_test/_internal/config.py +23 -13
  641. ansible_test/_internal/connections.py +1 -0
  642. ansible_test/_internal/constants.py +1 -0
  643. ansible_test/_internal/containers.py +1 -0
  644. ansible_test/_internal/content_config.py +1 -0
  645. ansible_test/_internal/core_ci.py +1 -0
  646. ansible_test/_internal/coverage_util.py +11 -10
  647. ansible_test/_internal/data.py +1 -0
  648. ansible_test/_internal/debugging.py +166 -0
  649. ansible_test/_internal/delegation.py +22 -13
  650. ansible_test/_internal/dev/__init__.py +1 -0
  651. ansible_test/_internal/dev/container_probe.py +1 -0
  652. ansible_test/_internal/diff.py +3 -2
  653. ansible_test/_internal/docker_util.py +2 -1
  654. ansible_test/_internal/encoding.py +1 -0
  655. ansible_test/_internal/executor.py +1 -0
  656. ansible_test/_internal/git.py +1 -0
  657. ansible_test/_internal/host_configs.py +1 -0
  658. ansible_test/_internal/host_profiles.py +260 -16
  659. ansible_test/_internal/http.py +1 -0
  660. ansible_test/_internal/init.py +1 -0
  661. ansible_test/_internal/inventory.py +39 -3
  662. ansible_test/_internal/io.py +1 -0
  663. ansible_test/_internal/metadata.py +95 -4
  664. ansible_test/_internal/payload.py +1 -0
  665. ansible_test/_internal/processes.py +80 -0
  666. ansible_test/_internal/provider/__init__.py +1 -0
  667. ansible_test/_internal/provider/layout/__init__.py +1 -0
  668. ansible_test/_internal/provider/layout/ansible.py +1 -0
  669. ansible_test/_internal/provider/layout/collection.py +1 -0
  670. ansible_test/_internal/provider/layout/unsupported.py +1 -0
  671. ansible_test/_internal/provider/source/__init__.py +1 -0
  672. ansible_test/_internal/provider/source/git.py +1 -0
  673. ansible_test/_internal/provider/source/installed.py +1 -0
  674. ansible_test/_internal/provider/source/unsupported.py +1 -0
  675. ansible_test/_internal/provider/source/unversioned.py +1 -0
  676. ansible_test/_internal/provisioning.py +11 -4
  677. ansible_test/_internal/pypi_proxy.py +6 -5
  678. ansible_test/_internal/python_requirements.py +28 -0
  679. ansible_test/_internal/ssh.py +2 -5
  680. ansible_test/_internal/target.py +9 -0
  681. ansible_test/_internal/test.py +3 -2
  682. ansible_test/_internal/thread.py +3 -1
  683. ansible_test/_internal/timeout.py +2 -1
  684. ansible_test/_internal/util.py +41 -12
  685. ansible_test/_internal/util_common.py +18 -5
  686. ansible_test/_internal/venv.py +1 -0
  687. ansible_test/_util/controller/sanity/code-smell/action-plugin-docs.py +1 -0
  688. ansible_test/_util/controller/sanity/code-smell/changelog/sphinx.py +1 -0
  689. ansible_test/_util/controller/sanity/code-smell/changelog.py +1 -0
  690. ansible_test/_util/controller/sanity/code-smell/empty-init.py +1 -0
  691. ansible_test/_util/controller/sanity/code-smell/line-endings.py +1 -0
  692. ansible_test/_util/controller/sanity/code-smell/no-assert.py +1 -0
  693. ansible_test/_util/controller/sanity/code-smell/no-get-exception.py +1 -0
  694. ansible_test/_util/controller/sanity/code-smell/no-illegal-filenames.py +1 -0
  695. ansible_test/_util/controller/sanity/code-smell/no-smart-quotes.py +1 -0
  696. ansible_test/_util/controller/sanity/code-smell/replace-urlopen.py +1 -0
  697. ansible_test/_util/controller/sanity/code-smell/runtime-metadata.py +28 -1
  698. ansible_test/_util/controller/sanity/code-smell/shebang.py +1 -0
  699. ansible_test/_util/controller/sanity/code-smell/symlinks.py +1 -0
  700. ansible_test/_util/controller/sanity/code-smell/use-argspec-type-path.py +1 -0
  701. ansible_test/_util/controller/sanity/code-smell/use-compat-six.py +1 -0
  702. ansible_test/_util/controller/sanity/integration-aliases/yaml_to_json.py +2 -1
  703. ansible_test/_util/controller/sanity/pep8/current-ignore.txt +4 -0
  704. ansible_test/_util/controller/sanity/pylint/config/ansible-test-target.cfg +8 -5
  705. ansible_test/_util/controller/sanity/pylint/config/ansible-test.cfg +8 -5
  706. ansible_test/_util/controller/sanity/pylint/config/code-smell.cfg +8 -5
  707. ansible_test/_util/controller/sanity/pylint/config/collection.cfg +4 -5
  708. ansible_test/_util/controller/sanity/pylint/config/default.cfg +8 -7
  709. ansible_test/_util/controller/sanity/pylint/plugins/deprecated_calls.py +541 -0
  710. ansible_test/_util/controller/sanity/pylint/plugins/deprecated_comment.py +137 -0
  711. ansible_test/_util/controller/sanity/pylint/plugins/hide_unraisable.py +1 -0
  712. ansible_test/_util/controller/sanity/pylint/plugins/string_format.py +1 -8
  713. ansible_test/_util/controller/sanity/pylint/plugins/unwanted.py +1 -8
  714. ansible_test/_util/controller/sanity/validate-modules/validate_modules/main.py +55 -28
  715. ansible_test/_util/controller/sanity/validate-modules/validate_modules/module_args.py +12 -5
  716. ansible_test/_util/controller/sanity/validate-modules/validate_modules/schema.py +13 -2
  717. ansible_test/_util/controller/sanity/validate-modules/validate_modules/utils.py +1 -0
  718. ansible_test/_util/controller/sanity/yamllint/yamllinter.py +35 -17
  719. ansible_test/_util/controller/tools/collection_detail.py +1 -0
  720. ansible_test/_util/controller/tools/yaml_to_json.py +2 -1
  721. ansible_test/_util/target/injector/python.py +8 -0
  722. ansible_test/_util/target/pytest/plugins/ansible_forked.py +6 -1
  723. ansible_test/_util/target/pytest/plugins/ansible_pytest_collections.py +2 -1
  724. ansible_test/_util/target/pytest/plugins/ansible_pytest_coverage.py +1 -0
  725. ansible_test/_util/target/sanity/compile/compile.py +1 -0
  726. ansible_test/_util/target/sanity/import/importer.py +15 -16
  727. ansible_test/_util/target/setup/bootstrap.sh +9 -20
  728. ansible_test/_util/target/setup/probe_cgroups.py +1 -0
  729. ansible_test/_util/target/setup/quiet_pip.py +1 -0
  730. ansible_test/_util/target/setup/requirements.py +38 -36
  731. ansible_test/_util/target/tools/virtualenvcheck.py +2 -1
  732. ansible_test/_util/target/tools/yamlcheck.py +2 -1
  733. ansible/compat/selectors.py +0 -32
  734. ansible/errors/yaml_strings.py +0 -138
  735. ansible/executor/action_write_locks.py +0 -44
  736. ansible/executor/discovery/python_target.py +0 -47
  737. ansible/executor/powershell/module_powershell_wrapper.ps1 +0 -86
  738. ansible/executor/powershell/module_script_wrapper.ps1 +0 -22
  739. ansible/module_utils/compat/importlib.py +0 -26
  740. ansible/module_utils/compat/selectors.py +0 -32
  741. ansible/module_utils/pycompat24.py +0 -73
  742. ansible/parsing/yaml/constructor.py +0 -178
  743. ansible/template/native_helpers.py +0 -251
  744. ansible/template/template.py +0 -43
  745. ansible/template/vars.py +0 -77
  746. ansible/utils/native_jinja.py +0 -11
  747. ansible/vars/fact_cache.py +0 -71
  748. ansible_core-2.18.7rc1.dist-info/RECORD +0 -992
  749. ansible_test/_util/controller/sanity/pylint/plugins/deprecated.py +0 -411
  750. {ansible_core-2.18.7rc1.dist-info → ansible_core-2.19.0.dist-info}/WHEEL +0 -0
  751. {ansible_core-2.18.7rc1.dist-info → ansible_core-2.19.0.dist-info}/entry_points.txt +0 -0
  752. {ansible_core-2.18.7rc1.dist-info → ansible_core-2.19.0.dist-info}/licenses/COPYING +0 -0
  753. {ansible_core-2.18.7rc1.dist-info → ansible_core-2.19.0.dist-info}/licenses/licenses/Apache-License.txt +0 -0
  754. {ansible_core-2.18.7rc1.dist-info → ansible_core-2.19.0.dist-info}/licenses/licenses/MIT-license.txt +0 -0
  755. {ansible_core-2.18.7rc1.dist-info → ansible_core-2.19.0.dist-info}/licenses/licenses/PSF-license.txt +0 -0
  756. {ansible_core-2.18.7rc1.dist-info → ansible_core-2.19.0.dist-info}/licenses/licenses/simplified_bsd.txt +0 -0
  757. {ansible_core-2.18.7rc1.dist-info → ansible_core-2.19.0.dist-info}/top_level.txt +0 -0
@@ -14,7 +14,7 @@ __all__ = ('get_distribution', 'get_distribution_version', 'get_platform_subclas
14
14
 
15
15
 
16
16
  def get_distribution():
17
- '''
17
+ """
18
18
  Return the name of the distribution the module is running on.
19
19
 
20
20
  :rtype: NativeString or None
@@ -23,7 +23,7 @@ def get_distribution():
23
23
  This function attempts to determine what distribution the code is running
24
24
  on and return a string representing that value. If the platform is Linux
25
25
  and the distribution cannot be determined, it returns ``OtherLinux``.
26
- '''
26
+ """
27
27
  distribution = distro.id().capitalize()
28
28
 
29
29
  if platform.system() == 'Linux':
@@ -38,14 +38,14 @@ def get_distribution():
38
38
 
39
39
 
40
40
  def get_distribution_version():
41
- '''
41
+ """
42
42
  Get the version of the distribution the code is running on
43
43
 
44
44
  :rtype: NativeString or None
45
45
  :returns: A string representation of the version of the distribution. If it
46
46
  cannot determine the version, it returns an empty string. If this is not run on
47
47
  a Linux machine it returns None.
48
- '''
48
+ """
49
49
  version = None
50
50
 
51
51
  needs_best_version = frozenset((
@@ -79,12 +79,12 @@ def get_distribution_version():
79
79
 
80
80
 
81
81
  def get_distribution_codename():
82
- '''
82
+ """
83
83
  Return the code name for this Linux Distribution
84
84
 
85
85
  :rtype: NativeString or None
86
86
  :returns: A string representation of the distribution's codename or None if not a Linux distro
87
- '''
87
+ """
88
88
  codename = None
89
89
  if platform.system() == 'Linux':
90
90
  # Until this gets merged and we update our bundled copy of distro:
@@ -109,7 +109,7 @@ def get_distribution_codename():
109
109
 
110
110
 
111
111
  def get_platform_subclass(cls):
112
- '''
112
+ """
113
113
  Finds a subclass implementing desired functionality on the platform the code is running on
114
114
 
115
115
  :arg cls: Class to find an appropriate subclass for
@@ -135,7 +135,7 @@ def get_platform_subclass(cls):
135
135
  def __new__(cls, *args, **kwargs):
136
136
  new_cls = get_platform_subclass(User)
137
137
  return super(cls, new_cls).__new__(new_cls)
138
- '''
138
+ """
139
139
  this_platform = platform.system()
140
140
  distribution = get_distribution()
141
141
 
@@ -6,12 +6,9 @@
6
6
  from __future__ import annotations
7
7
 
8
8
  import codecs
9
- import datetime
10
9
  import json
11
10
 
12
- from ansible.module_utils.six.moves.collections_abc import Set
13
11
  from ansible.module_utils.six import (
14
- PY3,
15
12
  binary_type,
16
13
  iteritems,
17
14
  text_type,
@@ -237,49 +234,30 @@ def to_text(obj, encoding='utf-8', errors=None, nonstring='simplerepr'):
237
234
  return to_text(value, encoding, errors)
238
235
 
239
236
 
240
- #: :py:func:`to_native`
241
- #: Transform a variable into the native str type for the python version
242
- #:
243
- #: On Python2, this is an alias for
244
- #: :func:`~ansible.module_utils.to_bytes`. On Python3 it is an alias for
245
- #: :func:`~ansible.module_utils.to_text`. It makes it easier to
246
- #: transform a variable into the native str type for the python version
247
- #: the code is running on. Use this when constructing the message to
248
- #: send to exceptions or when dealing with an API that needs to take
249
- #: a native string. Example::
250
- #:
251
- #: try:
252
- #: 1//0
253
- #: except ZeroDivisionError as e:
254
- #: raise MyException('Encountered and error: %s' % to_native(e))
255
- if PY3:
256
- to_native = to_text
257
- else:
258
- to_native = to_bytes
259
-
260
-
261
- def _json_encode_fallback(obj):
262
- if isinstance(obj, Set):
263
- return list(obj)
264
- elif isinstance(obj, datetime.datetime):
265
- return obj.isoformat()
266
- raise TypeError("Cannot json serialize %s" % to_native(obj))
237
+ to_native = to_text
267
238
 
268
239
 
269
240
  def jsonify(data, **kwargs):
270
- try:
271
- new_data = container_to_text(data, encoding='utf-8')
272
- except UnicodeDecodeError:
273
- raise UnicodeError('Invalid unicode encoding encountered')
274
- return json.dumps(new_data, default=_json_encode_fallback, **kwargs)
241
+ from ansible.module_utils.common import json as _common_json
242
+ # from ansible.module_utils.common.warnings import deprecate
243
+
244
+ # deprecated: description='deprecate jsonify()' core_version='2.23'
245
+ # deprecate(
246
+ # msg="The `jsonify` function is deprecated.",
247
+ # version="2.27",
248
+ # # help_text="", # DTFIX-FUTURE: fill in this help text
249
+ # )
250
+
251
+ return json.dumps(data, cls=_common_json._get_legacy_encoder(), _decode_bytes=True, **kwargs)
275
252
 
276
253
 
277
254
  def container_to_bytes(d, encoding='utf-8', errors='surrogate_or_strict'):
278
- ''' Recursively convert dict keys and values to byte str
255
+ """ Recursively convert dict keys and values to byte str
279
256
 
280
257
  Specialized for json return because this only handles, lists, tuples,
281
258
  and dict container types (the containers that the json module returns)
282
- '''
259
+ """
260
+ # DTFIX-FUTURE: deprecate
283
261
 
284
262
  if isinstance(d, text_type):
285
263
  return to_bytes(d, encoding=encoding, errors=errors)
@@ -299,6 +277,7 @@ def container_to_text(d, encoding='utf-8', errors='surrogate_or_strict'):
299
277
  Specialized for json return because this only handles, lists, tuples,
300
278
  and dict container types (the containers that the json module returns)
301
279
  """
280
+ # DTFIX-FUTURE: deprecate
302
281
 
303
282
  if isinstance(d, binary_type):
304
283
  # Warning, can traceback
@@ -10,16 +10,14 @@ import os
10
10
  import re
11
11
 
12
12
  from ast import literal_eval
13
+ from ansible.module_utils.common import json as _common_json
13
14
  from ansible.module_utils.common.text.converters import to_native
14
15
  from ansible.module_utils.common.collections import is_iterable
15
- from ansible.module_utils.common.text.converters import jsonify
16
16
  from ansible.module_utils.common.text.formatters import human_to_bytes
17
17
  from ansible.module_utils.common.warnings import deprecate
18
18
  from ansible.module_utils.parsing.convert_bool import boolean
19
19
  from ansible.module_utils.six import (
20
- binary_type,
21
20
  string_types,
22
- text_type,
23
21
  )
24
22
 
25
23
 
@@ -185,7 +183,7 @@ def check_required_by(requirements, parameters, options_context=None):
185
183
  :kwarg options_context: List of strings of parent key names if ``requirements`` are
186
184
  in a sub spec.
187
185
 
188
- :returns: Empty dictionary or raises :class:`TypeError` if the
186
+ :returns: Empty dictionary or raises :class:`TypeError` if the check fails.
189
187
  """
190
188
 
191
189
  result = {}
@@ -195,22 +193,15 @@ def check_required_by(requirements, parameters, options_context=None):
195
193
  for (key, value) in requirements.items():
196
194
  if key not in parameters or parameters[key] is None:
197
195
  continue
198
- result[key] = []
199
196
  # Support strings (single-item lists)
200
197
  if isinstance(value, string_types):
201
198
  value = [value]
202
- for required in value:
203
- if required not in parameters or parameters[required] is None:
204
- result[key].append(required)
205
-
206
- if result:
207
- for key, missing in result.items():
208
- if len(missing) > 0:
209
- msg = "missing parameter(s) required by '%s': %s" % (key, ', '.join(missing))
210
- if options_context:
211
- msg = "{0} found in {1}".format(msg, " -> ".join(options_context))
212
- raise TypeError(to_native(msg))
213
199
 
200
+ if missing := [required for required in value if required not in parameters or parameters[required] is None]:
201
+ msg = f"missing parameter(s) required by '{key}': {', '.join(missing)}"
202
+ if options_context:
203
+ msg = f"{msg} found in {' -> '.join(options_context)}"
204
+ raise TypeError(to_native(msg))
214
205
  return result
215
206
 
216
207
 
@@ -392,6 +383,10 @@ def check_type_str(value, allow_conversion=True, param=None, prefix=''):
392
383
  raise TypeError(to_native(msg))
393
384
 
394
385
 
386
+ def _check_type_str_no_conversion(value) -> str:
387
+ return check_type_str(value, allow_conversion=False)
388
+
389
+
395
390
  def check_type_list(value):
396
391
  """Verify that the value is a list or convert to a list
397
392
 
@@ -407,6 +402,7 @@ def check_type_list(value):
407
402
  if isinstance(value, list):
408
403
  return value
409
404
 
405
+ # DTFIX-FUTURE: deprecate legacy comma split functionality, eventually replace with `_check_type_list_strict`
410
406
  if isinstance(value, string_types):
411
407
  return value.split(",")
412
408
  elif isinstance(value, int) or isinstance(value, float):
@@ -415,6 +411,14 @@ def check_type_list(value):
415
411
  raise TypeError('%s cannot be converted to a list' % type(value))
416
412
 
417
413
 
414
+ def _check_type_list_strict(value):
415
+ # FUTURE: this impl should replace `check_type_list`
416
+ if isinstance(value, list):
417
+ return value
418
+
419
+ return [value]
420
+
421
+
418
422
  def check_type_dict(value):
419
423
  """Verify that value is a dict or convert it to a dict and return it.
420
424
 
@@ -572,14 +576,21 @@ def check_type_bits(value):
572
576
 
573
577
 
574
578
  def check_type_jsonarg(value):
575
- """Return a jsonified string. Sometimes the controller turns a json string
576
- into a dict/list so transform it back into json here
577
-
578
- Raises :class:`TypeError` if unable to convert the value
579
-
580
579
  """
581
- if isinstance(value, (text_type, binary_type)):
580
+ JSON serialize dict/list/tuple, strip str and bytes.
581
+ Previously required for cases where Ansible/Jinja classic-mode literal eval pass could inadvertently deserialize objects.
582
+ """
583
+ # deprecated: description='deprecate jsonarg type support' core_version='2.23'
584
+ # deprecate(
585
+ # msg="The `jsonarg` type is deprecated.",
586
+ # version="2.27",
587
+ # help_text="JSON string arguments should use `str`; structures can be explicitly serialized as JSON with the `to_json` filter.",
588
+ # )
589
+
590
+ if isinstance(value, (str, bytes)):
582
591
  return value.strip()
583
- elif isinstance(value, (list, tuple, dict)):
584
- return jsonify(value)
592
+
593
+ if isinstance(value, (list, tuple, dict)):
594
+ return json.dumps(value, cls=_common_json._get_legacy_encoder(), _decode_bytes=True)
595
+
585
596
  raise TypeError('%s cannot be converted to a json string' % type(value))
@@ -2,38 +2,156 @@
2
2
  # Copyright (c) 2019 Ansible Project
3
3
  # Simplified BSD License (see licenses/simplified_bsd.txt or https://opensource.org/licenses/BSD-2-Clause)
4
4
 
5
- from __future__ import annotations
5
+ from __future__ import annotations as _annotations
6
6
 
7
- from ansible.module_utils.six import string_types
7
+ import typing as _t
8
8
 
9
- _global_warnings = []
10
- _global_deprecations = []
9
+ from ansible.module_utils._internal import _traceback, _deprecator, _event_utils, _messages, _errors
10
+ from ansible.module_utils import _internal
11
11
 
12
12
 
13
- def warn(warning):
14
- if isinstance(warning, string_types):
15
- _global_warnings.append(warning)
16
- else:
17
- raise TypeError("warn requires a string not a %s" % type(warning))
13
+ def warn(
14
+ warning: str,
15
+ *,
16
+ help_text: str | None = None,
17
+ obj: object | None = None,
18
+ ) -> None:
19
+ """Record a warning to be returned with the module result."""
20
+ _skip_stackwalk = True
18
21
 
22
+ if _internal.is_controller:
23
+ _display = _internal.import_controller_module('ansible.utils.display').Display()
24
+ _display.warning(
25
+ msg=warning,
26
+ help_text=help_text,
27
+ obj=obj,
28
+ )
19
29
 
20
- def deprecate(msg, version=None, date=None, collection_name=None):
21
- if isinstance(msg, string_types):
22
- # For compatibility, we accept that neither version nor date is set,
23
- # and treat that the same as if version would haven been set
24
- if date is not None:
25
- _global_deprecations.append({'msg': msg, 'date': date, 'collection_name': collection_name})
26
- else:
27
- _global_deprecations.append({'msg': msg, 'version': version, 'collection_name': collection_name})
28
- else:
29
- raise TypeError("deprecate requires a string not a %s" % type(msg))
30
+ return
30
31
 
32
+ warning = _messages.WarningSummary(
33
+ event=_messages.Event(
34
+ msg=warning,
35
+ help_text=help_text,
36
+ formatted_traceback=_traceback.maybe_capture_traceback(warning, _traceback.TracebackEvent.WARNING),
37
+ ),
38
+ )
31
39
 
32
- def get_warning_messages():
33
- """Return a tuple of warning messages accumulated over this run"""
34
- return tuple(_global_warnings)
40
+ _global_warnings[warning] = None
35
41
 
36
42
 
37
- def get_deprecation_messages():
38
- """Return a tuple of deprecations accumulated over this run"""
39
- return tuple(_global_deprecations)
43
+ def error_as_warning(
44
+ msg: str | None,
45
+ exception: BaseException,
46
+ *,
47
+ help_text: str | None = None,
48
+ obj: object = None,
49
+ ) -> None:
50
+ """Display an exception as a warning."""
51
+ _skip_stackwalk = True
52
+
53
+ if _internal.is_controller:
54
+ _display = _internal.import_controller_module('ansible.utils.display').Display()
55
+ _display.error_as_warning(
56
+ msg=msg,
57
+ exception=exception,
58
+ help_text=help_text,
59
+ obj=obj,
60
+ )
61
+
62
+ return
63
+
64
+ event = _errors.EventFactory.from_exception(exception, _traceback.is_traceback_enabled(_traceback.TracebackEvent.WARNING))
65
+
66
+ warning = _messages.WarningSummary(
67
+ event=_messages.Event(
68
+ msg=msg,
69
+ help_text=help_text,
70
+ formatted_traceback=_traceback.maybe_capture_traceback(msg, _traceback.TracebackEvent.WARNING),
71
+ chain=_messages.EventChain(
72
+ msg_reason=_errors.MSG_REASON_DIRECT_CAUSE,
73
+ traceback_reason=_errors.TRACEBACK_REASON_EXCEPTION_DIRECT_WARNING,
74
+ event=event,
75
+ ),
76
+ ),
77
+ )
78
+
79
+ _global_warnings[warning] = None
80
+
81
+
82
+ def deprecate(
83
+ msg: str,
84
+ version: str | None = None,
85
+ date: str | None = None,
86
+ collection_name: str | None = None,
87
+ *,
88
+ deprecator: _messages.PluginInfo | None = None,
89
+ help_text: str | None = None,
90
+ obj: object | None = None,
91
+ ) -> None:
92
+ """
93
+ Record a deprecation warning.
94
+ The `obj` argument is only useful in a controller context; it is ignored for target-side callers.
95
+ Most callers do not need to provide `collection_name` or `deprecator` -- but provide only one if needed.
96
+ Specify `version` or `date`, but not both.
97
+ If `date` is a string, it must be in the form `YYYY-MM-DD`.
98
+ """
99
+ _skip_stackwalk = True
100
+
101
+ deprecator = _deprecator.get_best_deprecator(deprecator=deprecator, collection_name=collection_name)
102
+
103
+ if _internal.is_controller:
104
+ _display = _internal.import_controller_module('ansible.utils.display').Display()
105
+ _display.deprecated(
106
+ msg=msg,
107
+ version=version,
108
+ date=date,
109
+ help_text=help_text,
110
+ obj=obj,
111
+ # skip passing collection_name; get_best_deprecator already accounted for it when present
112
+ deprecator=deprecator,
113
+ )
114
+
115
+ return
116
+
117
+ warning = _messages.DeprecationSummary(
118
+ event=_messages.Event(
119
+ msg=msg,
120
+ help_text=help_text,
121
+ formatted_traceback=_traceback.maybe_capture_traceback(msg, _traceback.TracebackEvent.DEPRECATED),
122
+ ),
123
+ version=version,
124
+ date=date,
125
+ deprecator=deprecator,
126
+ )
127
+
128
+ _global_deprecations[warning] = None
129
+
130
+
131
+ def get_warning_messages() -> tuple[str, ...]:
132
+ """Return a tuple of warning messages accumulated over this run."""
133
+ # DTFIX7: add future deprecation comment
134
+ return tuple(_event_utils.format_event_brief_message(item.event) for item in _global_warnings)
135
+
136
+
137
+ def get_deprecation_messages() -> tuple[dict[str, _t.Any], ...]:
138
+ """Return a tuple of deprecation warning messages accumulated over this run."""
139
+ # DTFIX7: add future deprecation comment
140
+ return tuple(_event_utils.deprecation_as_dict(item) for item in _global_deprecations)
141
+
142
+
143
+ def get_warnings() -> list[_messages.WarningSummary]:
144
+ """Return a list of warning messages accumulated over this run."""
145
+ return list(_global_warnings)
146
+
147
+
148
+ def get_deprecations() -> list[_messages.DeprecationSummary]:
149
+ """Return a list of deprecations accumulated over this run."""
150
+ return list(_global_deprecations)
151
+
152
+
153
+ _global_warnings: dict[_messages.WarningSummary, object] = {}
154
+ """Global, ordered, de-duplicated storage of accumulated warnings for the current module run."""
155
+
156
+ _global_deprecations: dict[_messages.DeprecationSummary, object] = {}
157
+ """Global, ordered, de-duplicated storage of accumulated deprecations for the current module run."""
@@ -6,10 +6,15 @@ This file provides ease of use shortcuts for loading and dumping YAML,
6
6
  preferring the YAML compiled C extensions to reduce duplicated code.
7
7
  """
8
8
 
9
- from __future__ import annotations
9
+ from __future__ import annotations as _annotations
10
+
11
+ import collections.abc as _c
12
+ import typing as _t
10
13
 
11
14
  from functools import partial as _partial
12
15
 
16
+ from .._internal import _datatag
17
+
13
18
  HAS_LIBYAML = False
14
19
 
15
20
  try:
@@ -19,23 +24,44 @@ except ImportError:
19
24
  else:
20
25
  HAS_YAML = True
21
26
 
27
+ # DTFIX-FUTURE: refactor this to share the implementation with the controller version
28
+ # use an abstract base class, with __init_subclass__ for representer registration, and instance methods for overridable representers
29
+ # then tests can be consolidated instead of having two nearly identical copies
30
+
22
31
  if HAS_YAML:
23
32
  try:
24
33
  from yaml import CSafeLoader as SafeLoader
25
34
  from yaml import CSafeDumper as SafeDumper
35
+ from yaml.representer import SafeRepresenter
26
36
  from yaml.cyaml import CParser as Parser # type: ignore[attr-defined] # pylint: disable=unused-import
27
37
 
28
38
  HAS_LIBYAML = True
29
39
  except (ImportError, AttributeError):
30
40
  from yaml import SafeLoader # type: ignore[assignment]
31
41
  from yaml import SafeDumper # type: ignore[assignment]
42
+ from yaml.representer import SafeRepresenter # type: ignore[assignment]
32
43
  from yaml.parser import Parser # type: ignore[assignment] # pylint: disable=unused-import
33
44
 
45
+ class _AnsibleDumper(SafeDumper):
46
+ pass
47
+
48
+ def _represent_ansible_tagged_object(self, data: _datatag.AnsibleTaggedObject) -> _t.Any:
49
+ return self.represent_data(_datatag.AnsibleTagHelper.as_native_type(data))
50
+
51
+ def _represent_tripwire(self, data: _datatag.Tripwire) -> _t.NoReturn:
52
+ data.trip()
53
+
54
+ _AnsibleDumper.add_multi_representer(_datatag.AnsibleTaggedObject, _represent_ansible_tagged_object)
55
+
56
+ _AnsibleDumper.add_multi_representer(_datatag.Tripwire, _represent_tripwire)
57
+ _AnsibleDumper.add_multi_representer(_c.Mapping, SafeRepresenter.represent_dict)
58
+ _AnsibleDumper.add_multi_representer(_c.Sequence, SafeRepresenter.represent_list)
59
+
34
60
  yaml_load = _partial(_yaml.load, Loader=SafeLoader)
35
61
  yaml_load_all = _partial(_yaml.load_all, Loader=SafeLoader)
36
62
 
37
- yaml_dump = _partial(_yaml.dump, Dumper=SafeDumper)
38
- yaml_dump_all = _partial(_yaml.dump_all, Dumper=SafeDumper)
63
+ yaml_dump = _partial(_yaml.dump, Dumper=_AnsibleDumper)
64
+ yaml_dump_all = _partial(_yaml.dump_all, Dumper=_AnsibleDumper)
39
65
  else:
40
66
  SafeLoader = object # type: ignore[assignment,misc]
41
67
  SafeDumper = object # type: ignore[assignment,misc]
@@ -3,36 +3,48 @@
3
3
 
4
4
  from __future__ import annotations
5
5
 
6
- from ansible.module_utils.six import PY3
6
+ import datetime as _datetime
7
+ import typing as t
7
8
 
8
- import datetime
9
+ from ansible.module_utils.common.warnings import deprecate
9
10
 
10
11
 
11
- if PY3:
12
- UTC = datetime.timezone.utc
13
- else:
14
- _ZERO = datetime.timedelta(0)
12
+ _UTC = _datetime.timezone.utc
15
13
 
16
- class _UTC(datetime.tzinfo):
17
- __slots__ = ()
18
14
 
19
- def utcoffset(self, dt):
20
- return _ZERO
15
+ def _utcfromtimestamp(timestamp: float) -> _datetime.datetime:
16
+ """Construct an aware UTC datetime from a POSIX timestamp."""
17
+ return _datetime.datetime.fromtimestamp(timestamp, _UTC)
21
18
 
22
- def dst(self, dt):
23
- return _ZERO
24
19
 
25
- def tzname(self, dt):
26
- return "UTC"
20
+ def _utcnow() -> _datetime.datetime:
21
+ """Construct an aware UTC datetime from time.time()."""
22
+ return _datetime.datetime.now(_UTC)
27
23
 
28
- UTC = _UTC()
29
24
 
25
+ _deprecated_shims_map: dict[str, t.Callable[..., object] | _datetime.timezone] = {
26
+ 'UTC': _UTC,
27
+ 'utcfromtimestamp': _utcfromtimestamp,
28
+ 'utcnow': _utcnow,
29
+ }
30
30
 
31
- def utcfromtimestamp(timestamp): # type: (float) -> datetime.datetime
32
- """Construct an aware UTC datetime from a POSIX timestamp."""
33
- return datetime.datetime.fromtimestamp(timestamp, UTC)
31
+ __all__ = tuple(_deprecated_shims_map)
34
32
 
35
33
 
36
- def utcnow(): # type: () -> datetime.datetime
37
- """Construct an aware UTC datetime from time.time()."""
38
- return datetime.datetime.now(UTC)
34
+ def __getattr__(importable_name: str) -> t.Callable[..., object] | _datetime.timezone:
35
+ """Inject import-time deprecation warnings.
36
+
37
+ Specifically, for ``UTC``, ``utcfromtimestamp()`` and ``utcnow()``.
38
+ """
39
+ try:
40
+ importable = _deprecated_shims_map[importable_name]
41
+ except KeyError as key_err:
42
+ raise AttributeError(f"module {__name__!r} has no attribute {key_err}") from None
43
+
44
+ deprecate(
45
+ msg=f'The `ansible.module_utils.compat.datetime.{importable_name}` '
46
+ 'function is deprecated.',
47
+ version='2.21',
48
+ )
49
+
50
+ return importable
@@ -2,25 +2,36 @@
2
2
  # Copyright (c) 2019 Ansible Project
3
3
  # Simplified BSD License (see licenses/simplified_bsd.txt or https://opensource.org/licenses/BSD-2-Clause)
4
4
 
5
- from __future__ import annotations
5
+ from __future__ import annotations as _annotations
6
6
 
7
- import types # pylint: disable=unused-import
8
- import warnings
7
+ import warnings as _warnings
9
8
 
10
- PARAMIKO_IMPORT_ERR = None
9
+ from ansible.module_utils.common.warnings import deprecate as _deprecate
10
+
11
+ _PARAMIKO_IMPORT_ERR = None
11
12
 
12
13
  try:
13
- with warnings.catch_warnings():
14
+ with _warnings.catch_warnings():
14
15
  # Blowfish has been moved, but the deprecated import is used by paramiko versions older than 2.9.5.
15
16
  # See: https://github.com/paramiko/paramiko/pull/2039
16
- warnings.filterwarnings('ignore', message='Blowfish has been ', category=UserWarning)
17
+ _warnings.filterwarnings('ignore', message='Blowfish has been ', category=UserWarning)
17
18
  # TripleDES has been moved, but the deprecated import is used by paramiko versions older than 3.3.2 and 3.4.1.
18
19
  # See: https://github.com/paramiko/paramiko/pull/2421
19
- warnings.filterwarnings('ignore', message='TripleDES has been ', category=UserWarning)
20
- import paramiko # pylint: disable=unused-import
20
+ _warnings.filterwarnings('ignore', message='TripleDES has been ', category=UserWarning)
21
+ import paramiko as _paramiko
21
22
  # paramiko and gssapi are incompatible and raise AttributeError not ImportError
22
23
  # When running in FIPS mode, cryptography raises InternalError
23
24
  # https://bugzilla.redhat.com/show_bug.cgi?id=1778939
24
25
  except Exception as err:
25
- paramiko = None # type: types.ModuleType | None # type: ignore[no-redef]
26
- PARAMIKO_IMPORT_ERR = err
26
+ _paramiko = None # type: ignore[no-redef]
27
+ _PARAMIKO_IMPORT_ERR = err
28
+
29
+
30
+ def __getattr__(name: str) -> object:
31
+ """Dynamic lookup to issue deprecation warnings for external import of deprecated items."""
32
+ if (res := globals().get(f'_{name}', ...)) is not ...:
33
+ _deprecate(f'The {name!r} compat import is deprecated.', version='2.21')
34
+
35
+ return res
36
+
37
+ raise AttributeError(name)
@@ -6,6 +6,8 @@ from __future__ import annotations
6
6
  # catch *all* exceptions to prevent type annotation support module bugs causing runtime failures
7
7
  # (eg, https://github.com/ansible/ansible/issues/77857)
8
8
 
9
+ TYPE_CHECKING = False
10
+
9
11
  try:
10
12
  from typing_extensions import *
11
13
  except Exception: # pylint: disable=broad-except
@@ -17,8 +19,7 @@ except Exception: # pylint: disable=broad-except
17
19
  pass
18
20
 
19
21
 
20
- try:
21
- cast # type: ignore[used-before-def]
22
- except NameError:
23
- def cast(typ, val): # type: ignore[no-redef]
24
- return val
22
+ # this import and patch occur after typing_extensions/typing imports since the presence of those modules affects dataclasses behavior
23
+ from .._internal._patches import _dataclass_annotation_patch
24
+
25
+ _dataclass_annotation_patch.DataclassesIsTypePatch.patch()