ansible-core 2.15.4rc1__py3-none-any.whl → 2.16.0b2__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 (427) hide show
  1. ansible/cli/__init__.py +3 -3
  2. ansible/cli/adhoc.py +1 -1
  3. ansible/cli/arguments/option_helpers.py +15 -5
  4. ansible/cli/config.py +2 -2
  5. ansible/cli/console.py +21 -17
  6. ansible/cli/doc.py +8 -9
  7. ansible/cli/galaxy.py +60 -27
  8. ansible/cli/inventory.py +1 -1
  9. ansible/cli/playbook.py +1 -1
  10. ansible/cli/pull.py +2 -2
  11. ansible/cli/scripts/ansible_connection_cli_stub.py +1 -1
  12. ansible/cli/vault.py +11 -6
  13. ansible/collections/__init__.py +0 -29
  14. ansible/collections/list.py +23 -44
  15. ansible/config/ansible_builtin_runtime.yml +8 -4
  16. ansible/config/base.yml +34 -22
  17. ansible/config/manager.py +1 -1
  18. ansible/constants.py +3 -5
  19. ansible/errors/__init__.py +1 -1
  20. ansible/executor/interpreter_discovery.py +1 -1
  21. ansible/executor/module_common.py +39 -32
  22. ansible/executor/play_iterator.py +0 -15
  23. ansible/executor/playbook_executor.py +3 -3
  24. ansible/executor/powershell/module_manifest.py +1 -1
  25. ansible/executor/powershell/module_wrapper.ps1 +4 -1
  26. ansible/executor/process/worker.py +22 -7
  27. ansible/executor/task_executor.py +39 -40
  28. ansible/executor/task_queue_manager.py +8 -11
  29. ansible/galaxy/__init__.py +1 -1
  30. ansible/galaxy/api.py +8 -11
  31. ansible/galaxy/collection/__init__.py +17 -4
  32. ansible/galaxy/collection/concrete_artifact_manager.py +7 -2
  33. ansible/galaxy/collection/galaxy_api_proxy.py +1 -1
  34. ansible/galaxy/data/container/README.md +3 -5
  35. ansible/galaxy/dependency_resolution/__init__.py +1 -6
  36. ansible/galaxy/dependency_resolution/dataclasses.py +22 -1
  37. ansible/galaxy/dependency_resolution/providers.py +61 -69
  38. ansible/galaxy/role.py +31 -13
  39. ansible/galaxy/token.py +2 -2
  40. ansible/inventory/group.py +1 -1
  41. ansible/inventory/manager.py +1 -1
  42. ansible/module_utils/ansible_release.py +2 -2
  43. ansible/module_utils/basic.py +11 -41
  44. ansible/module_utils/common/file.py +0 -100
  45. ansible/module_utils/common/json.py +1 -1
  46. ansible/module_utils/common/locale.py +1 -1
  47. ansible/module_utils/common/text/converters.py +2 -2
  48. ansible/module_utils/common/validation.py +1 -1
  49. ansible/module_utils/compat/_selectors2.py +4 -4
  50. ansible/module_utils/compat/datetime.py +40 -0
  51. ansible/module_utils/compat/selinux.py +1 -1
  52. ansible/module_utils/compat/typing.py +1 -1
  53. ansible/module_utils/connection.py +1 -1
  54. ansible/module_utils/facts/hardware/linux.py +2 -2
  55. ansible/module_utils/facts/hardware/openbsd.py +1 -1
  56. ansible/module_utils/facts/network/linux.py +3 -3
  57. ansible/module_utils/facts/other/facter.py +8 -15
  58. ansible/module_utils/facts/sysctl.py +1 -1
  59. ansible/module_utils/facts/system/date_time.py +2 -2
  60. ansible/module_utils/facts/system/distribution.py +1 -1
  61. ansible/module_utils/facts/system/local.py +6 -2
  62. ansible/module_utils/facts/system/pkg_mgr.py +6 -1
  63. ansible/module_utils/facts/system/service_mgr.py +4 -2
  64. ansible/module_utils/parsing/convert_bool.py +1 -1
  65. ansible/module_utils/service.py +9 -6
  66. ansible/module_utils/urls.py +40 -22
  67. ansible/modules/add_host.py +2 -2
  68. ansible/modules/apt.py +48 -31
  69. ansible/modules/apt_key.py +4 -4
  70. ansible/modules/apt_repository.py +5 -5
  71. ansible/modules/assemble.py +7 -7
  72. ansible/modules/assert.py +1 -1
  73. ansible/modules/async_status.py +11 -7
  74. ansible/modules/async_wrapper.py +1 -1
  75. ansible/modules/blockinfile.py +60 -17
  76. ansible/modules/command.py +37 -15
  77. ansible/modules/copy.py +35 -30
  78. ansible/modules/cron.py +14 -14
  79. ansible/modules/deb822_repository.py +4 -3
  80. ansible/modules/debconf.py +35 -14
  81. ansible/modules/debug.py +1 -1
  82. ansible/modules/dnf.py +29 -27
  83. ansible/modules/dnf5.py +22 -22
  84. ansible/modules/dpkg_selections.py +9 -2
  85. ansible/modules/expect.py +4 -4
  86. ansible/modules/fetch.py +7 -7
  87. ansible/modules/file.py +30 -30
  88. ansible/modules/find.py +82 -22
  89. ansible/modules/gather_facts.py +6 -2
  90. ansible/modules/get_url.py +29 -29
  91. ansible/modules/getent.py +4 -4
  92. ansible/modules/git.py +27 -27
  93. ansible/modules/group.py +5 -12
  94. ansible/modules/hostname.py +21 -2
  95. ansible/modules/include_role.py +5 -5
  96. ansible/modules/include_tasks.py +2 -2
  97. ansible/modules/include_vars.py +5 -5
  98. ansible/modules/iptables.py +70 -65
  99. ansible/modules/known_hosts.py +7 -7
  100. ansible/modules/lineinfile.py +33 -33
  101. ansible/modules/meta.py +13 -13
  102. ansible/modules/package.py +8 -8
  103. ansible/modules/package_facts.py +3 -3
  104. ansible/modules/pause.py +2 -2
  105. ansible/modules/ping.py +5 -5
  106. ansible/modules/pip.py +80 -46
  107. ansible/modules/reboot.py +8 -4
  108. ansible/modules/replace.py +20 -15
  109. ansible/modules/rpm_key.py +2 -2
  110. ansible/modules/script.py +16 -10
  111. ansible/modules/service.py +26 -98
  112. ansible/modules/service_facts.py +36 -12
  113. ansible/modules/set_fact.py +2 -2
  114. ansible/modules/set_stats.py +2 -2
  115. ansible/modules/setup.py +18 -18
  116. ansible/modules/shell.py +3 -3
  117. ansible/modules/stat.py +9 -30
  118. ansible/modules/subversion.py +9 -9
  119. ansible/modules/systemd.py +20 -19
  120. ansible/modules/systemd_service.py +20 -19
  121. ansible/modules/sysvinit.py +26 -21
  122. ansible/modules/tempfile.py +5 -4
  123. ansible/modules/template.py +60 -6
  124. ansible/modules/unarchive.py +21 -18
  125. ansible/modules/uri.py +39 -39
  126. ansible/modules/user.py +81 -53
  127. ansible/modules/wait_for.py +22 -21
  128. ansible/modules/wait_for_connection.py +4 -4
  129. ansible/modules/yum.py +38 -38
  130. ansible/modules/yum_repository.py +58 -80
  131. ansible/parsing/dataloader.py +27 -27
  132. ansible/parsing/mod_args.py +1 -1
  133. ansible/parsing/plugin_docs.py +3 -3
  134. ansible/parsing/splitter.py +14 -16
  135. ansible/parsing/utils/yaml.py +1 -1
  136. ansible/parsing/vault/__init__.py +8 -6
  137. ansible/parsing/yaml/constructor.py +1 -1
  138. ansible/parsing/yaml/objects.py +1 -1
  139. ansible/playbook/__init__.py +1 -1
  140. ansible/playbook/base.py +2 -2
  141. ansible/playbook/block.py +0 -1
  142. ansible/playbook/conditional.py +40 -114
  143. ansible/playbook/helpers.py +5 -28
  144. ansible/playbook/included_file.py +8 -7
  145. ansible/playbook/play.py +1 -1
  146. ansible/playbook/play_context.py +2 -2
  147. ansible/playbook/playbook_include.py +2 -2
  148. ansible/playbook/role/__init__.py +1 -1
  149. ansible/playbook/role/include.py +1 -1
  150. ansible/playbook/role/metadata.py +1 -1
  151. ansible/playbook/role_include.py +1 -1
  152. ansible/playbook/task.py +2 -2
  153. ansible/playbook/task_include.py +1 -24
  154. ansible/plugins/__init__.py +13 -5
  155. ansible/plugins/action/__init__.py +17 -43
  156. ansible/plugins/action/add_host.py +2 -3
  157. ansible/plugins/action/assemble.py +1 -1
  158. ansible/plugins/action/assert.py +2 -1
  159. ansible/plugins/action/copy.py +2 -2
  160. ansible/plugins/action/debug.py +2 -1
  161. ansible/plugins/action/fail.py +1 -0
  162. ansible/plugins/action/fetch.py +3 -1
  163. ansible/plugins/action/gather_facts.py +37 -13
  164. ansible/plugins/action/group_by.py +1 -0
  165. ansible/plugins/action/include_vars.py +3 -2
  166. ansible/plugins/action/normal.py +3 -3
  167. ansible/plugins/action/pause.py +1 -1
  168. ansible/plugins/action/reboot.py +21 -16
  169. ansible/plugins/action/script.py +23 -8
  170. ansible/plugins/action/set_fact.py +1 -0
  171. ansible/plugins/action/set_stats.py +1 -0
  172. ansible/plugins/action/shell.py +6 -0
  173. ansible/plugins/action/template.py +1 -1
  174. ansible/plugins/action/unarchive.py +1 -1
  175. ansible/plugins/action/uri.py +1 -1
  176. ansible/plugins/action/validate_argument_spec.py +1 -0
  177. ansible/plugins/action/wait_for_connection.py +4 -4
  178. ansible/plugins/become/__init__.py +1 -1
  179. ansible/plugins/become/su.py +1 -1
  180. ansible/plugins/cache/__init__.py +1 -1
  181. ansible/plugins/callback/junit.py +1 -1
  182. ansible/plugins/callback/oneline.py +1 -1
  183. ansible/plugins/callback/tree.py +1 -1
  184. ansible/plugins/cliconf/__init__.py +2 -2
  185. ansible/plugins/connection/__init__.py +65 -37
  186. ansible/plugins/connection/local.py +9 -8
  187. ansible/plugins/connection/paramiko_ssh.py +34 -28
  188. ansible/plugins/connection/psrp.py +56 -43
  189. ansible/plugins/connection/ssh.py +67 -43
  190. ansible/plugins/connection/winrm.py +77 -30
  191. ansible/plugins/doc_fragments/constructed.py +4 -4
  192. ansible/plugins/doc_fragments/files.py +12 -12
  193. ansible/plugins/doc_fragments/inventory_cache.py +0 -6
  194. ansible/plugins/doc_fragments/result_format_callback.py +5 -5
  195. ansible/plugins/doc_fragments/shell_common.py +2 -2
  196. ansible/plugins/doc_fragments/shell_windows.py +1 -1
  197. ansible/plugins/doc_fragments/template_common.py +6 -6
  198. ansible/plugins/doc_fragments/url.py +10 -10
  199. ansible/plugins/doc_fragments/url_windows.py +15 -15
  200. ansible/plugins/doc_fragments/vars_plugin_staging.py +4 -4
  201. ansible/plugins/filter/b64decode.yml +1 -1
  202. ansible/plugins/filter/b64encode.yml +2 -2
  203. ansible/plugins/filter/bool.yml +5 -5
  204. ansible/plugins/filter/combine.yml +1 -1
  205. ansible/plugins/filter/commonpath.yml +2 -1
  206. ansible/plugins/filter/core.py +6 -8
  207. ansible/plugins/filter/dict2items.yml +11 -1
  208. ansible/plugins/filter/difference.yml +1 -0
  209. ansible/plugins/filter/encryption.py +1 -1
  210. ansible/plugins/filter/extract.yml +1 -1
  211. ansible/plugins/filter/flatten.yml +1 -1
  212. ansible/plugins/filter/from_yaml.yml +1 -1
  213. ansible/plugins/filter/from_yaml_all.yml +2 -2
  214. ansible/plugins/filter/hash.yml +1 -1
  215. ansible/plugins/filter/human_readable.yml +1 -1
  216. ansible/plugins/filter/human_to_bytes.yml +2 -2
  217. ansible/plugins/filter/intersect.yml +1 -0
  218. ansible/plugins/filter/mandatory.yml +7 -0
  219. ansible/plugins/filter/mathstuff.py +15 -17
  220. ansible/plugins/filter/normpath.yml +1 -1
  221. ansible/plugins/filter/path_join.yml +8 -1
  222. ansible/plugins/filter/realpath.yml +3 -2
  223. ansible/plugins/filter/regex_findall.yml +8 -2
  224. ansible/plugins/filter/regex_replace.yml +9 -3
  225. ansible/plugins/filter/regex_search.yml +8 -2
  226. ansible/plugins/filter/relpath.yml +2 -2
  227. ansible/plugins/filter/root.yml +1 -1
  228. ansible/plugins/filter/splitext.yml +1 -1
  229. ansible/plugins/filter/subelements.yml +2 -2
  230. ansible/plugins/filter/symmetric_difference.yml +1 -0
  231. ansible/plugins/filter/ternary.yml +5 -5
  232. ansible/plugins/filter/to_json.yml +7 -7
  233. ansible/plugins/filter/to_nice_json.yml +5 -5
  234. ansible/plugins/filter/to_yaml.yml +2 -2
  235. ansible/plugins/filter/type_debug.yml +1 -1
  236. ansible/plugins/filter/union.yml +1 -0
  237. ansible/plugins/filter/unvault.yml +2 -2
  238. ansible/plugins/filter/urldecode.yml +13 -32
  239. ansible/plugins/filter/urlsplit.py +1 -1
  240. ansible/plugins/filter/vault.yml +1 -1
  241. ansible/plugins/filter/zip.yml +1 -1
  242. ansible/plugins/filter/zip_longest.yml +1 -1
  243. ansible/plugins/inventory/__init__.py +1 -1
  244. ansible/plugins/inventory/advanced_host_list.py +1 -1
  245. ansible/plugins/inventory/constructed.py +2 -2
  246. ansible/plugins/inventory/host_list.py +1 -1
  247. ansible/plugins/inventory/ini.py +6 -3
  248. ansible/plugins/inventory/script.py +8 -2
  249. ansible/plugins/inventory/toml.py +1 -1
  250. ansible/plugins/inventory/yaml.py +1 -1
  251. ansible/plugins/list.py +21 -17
  252. ansible/plugins/loader.py +66 -88
  253. ansible/plugins/lookup/__init__.py +1 -1
  254. ansible/plugins/lookup/config.py +16 -6
  255. ansible/plugins/lookup/csvfile.py +7 -4
  256. ansible/plugins/lookup/env.py +1 -1
  257. ansible/plugins/lookup/file.py +5 -2
  258. ansible/plugins/lookup/fileglob.py +5 -2
  259. ansible/plugins/lookup/first_found.py +20 -14
  260. ansible/plugins/lookup/ini.py +6 -3
  261. ansible/plugins/lookup/lines.py +2 -1
  262. ansible/plugins/lookup/password.py +7 -7
  263. ansible/plugins/lookup/pipe.py +1 -0
  264. ansible/plugins/lookup/random_choice.py +2 -2
  265. ansible/plugins/lookup/sequence.py +1 -1
  266. ansible/plugins/lookup/subelements.py +2 -2
  267. ansible/plugins/lookup/template.py +4 -1
  268. ansible/plugins/lookup/unvault.py +4 -1
  269. ansible/plugins/lookup/url.py +6 -6
  270. ansible/plugins/lookup/varnames.py +1 -1
  271. ansible/plugins/netconf/__init__.py +3 -3
  272. ansible/plugins/shell/__init__.py +1 -1
  273. ansible/plugins/shell/cmd.py +7 -7
  274. ansible/plugins/shell/powershell.py +1 -1
  275. ansible/plugins/strategy/__init__.py +8 -10
  276. ansible/plugins/strategy/free.py +1 -1
  277. ansible/plugins/strategy/linear.py +3 -3
  278. ansible/plugins/terminal/__init__.py +2 -2
  279. ansible/plugins/test/abs.yml +1 -1
  280. ansible/plugins/test/all.yml +1 -1
  281. ansible/plugins/test/any.yml +1 -1
  282. ansible/plugins/test/change.yml +2 -2
  283. ansible/plugins/test/changed.yml +2 -2
  284. ansible/plugins/test/contains.yml +1 -1
  285. ansible/plugins/test/core.py +1 -1
  286. ansible/plugins/test/directory.yml +1 -1
  287. ansible/plugins/test/exists.yml +3 -2
  288. ansible/plugins/test/failed.yml +2 -2
  289. ansible/plugins/test/failure.yml +2 -2
  290. ansible/plugins/test/falsy.yml +2 -2
  291. ansible/plugins/test/file.yml +1 -1
  292. ansible/plugins/test/finished.yml +2 -2
  293. ansible/plugins/test/is_abs.yml +1 -1
  294. ansible/plugins/test/is_dir.yml +1 -1
  295. ansible/plugins/test/is_file.yml +1 -1
  296. ansible/plugins/test/is_link.yml +1 -1
  297. ansible/plugins/test/is_mount.yml +1 -1
  298. ansible/plugins/test/is_same_file.yml +1 -1
  299. ansible/plugins/test/isnan.yml +1 -1
  300. ansible/plugins/test/issubset.yml +1 -2
  301. ansible/plugins/test/issuperset.yml +1 -2
  302. ansible/plugins/test/link.yml +1 -1
  303. ansible/plugins/test/link_exists.yml +1 -1
  304. ansible/plugins/test/match.yml +2 -2
  305. ansible/plugins/test/mount.yml +1 -1
  306. ansible/plugins/test/nan.yml +1 -1
  307. ansible/plugins/test/reachable.yml +2 -2
  308. ansible/plugins/test/regex.yml +1 -1
  309. ansible/plugins/test/same_file.yml +1 -1
  310. ansible/plugins/test/search.yml +2 -2
  311. ansible/plugins/test/skip.yml +3 -3
  312. ansible/plugins/test/skipped.yml +3 -3
  313. ansible/plugins/test/started.yml +2 -2
  314. ansible/plugins/test/subset.yml +1 -2
  315. ansible/plugins/test/succeeded.yml +2 -2
  316. ansible/plugins/test/success.yml +2 -2
  317. ansible/plugins/test/successful.yml +2 -2
  318. ansible/plugins/test/superset.yml +1 -2
  319. ansible/plugins/test/truthy.yml +3 -3
  320. ansible/plugins/test/unreachable.yml +2 -2
  321. ansible/plugins/test/uri.yml +1 -1
  322. ansible/plugins/test/url.yml +1 -1
  323. ansible/plugins/test/urn.yml +1 -1
  324. ansible/plugins/test/vault_encrypted.yml +1 -1
  325. ansible/plugins/test/version.yml +7 -7
  326. ansible/plugins/test/version_compare.yml +7 -7
  327. ansible/plugins/vars/host_group_vars.py +1 -1
  328. ansible/release.py +2 -2
  329. ansible/template/__init__.py +24 -26
  330. ansible/template/native_helpers.py +1 -1
  331. ansible/template/vars.py +1 -1
  332. ansible/utils/_junit_xml.py +1 -1
  333. ansible/utils/cmd_functions.py +1 -1
  334. ansible/utils/collection_loader/_collection_finder.py +12 -1
  335. ansible/utils/display.py +113 -62
  336. ansible/utils/encrypt.py +11 -14
  337. ansible/utils/hashing.py +1 -1
  338. ansible/utils/jsonrpc.py +1 -1
  339. ansible/utils/path.py +1 -1
  340. ansible/utils/plugin_docs.py +1 -1
  341. ansible/utils/py3compat.py +1 -1
  342. ansible/utils/shlex.py +2 -10
  343. ansible/utils/ssh_functions.py +5 -4
  344. ansible/utils/unicode.py +1 -1
  345. ansible/utils/unsafe_proxy.py +1 -1
  346. ansible/utils/vars.py +4 -29
  347. ansible/vars/hostvars.py +1 -2
  348. ansible/vars/manager.py +13 -9
  349. ansible/vars/plugins.py +2 -2
  350. {ansible_core-2.15.4rc1.dist-info → ansible_core-2.16.0b2.dist-info}/COPYING +4 -5
  351. {ansible_core-2.15.4rc1.dist-info → ansible_core-2.16.0b2.dist-info}/METADATA +2 -4
  352. {ansible_core-2.15.4rc1.dist-info → ansible_core-2.16.0b2.dist-info}/RECORD +424 -425
  353. ansible_test/_data/completion/docker.txt +9 -9
  354. ansible_test/_data/completion/remote.txt +4 -7
  355. ansible_test/_data/completion/windows.txt +0 -2
  356. ansible_test/_data/requirements/ansible-test.txt +2 -1
  357. ansible_test/_data/requirements/ansible.txt +0 -3
  358. ansible_test/_data/requirements/constraints.txt +0 -2
  359. ansible_test/_data/requirements/sanity.ansible-doc.txt +3 -5
  360. ansible_test/_data/requirements/sanity.changelog.in +1 -2
  361. ansible_test/_data/requirements/sanity.changelog.txt +4 -6
  362. ansible_test/_data/requirements/sanity.import.plugin.txt +2 -4
  363. ansible_test/_data/requirements/sanity.import.txt +1 -3
  364. ansible_test/_data/requirements/sanity.integration-aliases.txt +1 -3
  365. ansible_test/_data/requirements/sanity.mypy.txt +12 -12
  366. ansible_test/_data/requirements/sanity.pep8.txt +1 -1
  367. ansible_test/_data/requirements/sanity.pylint.txt +6 -12
  368. ansible_test/_data/requirements/sanity.runtime-metadata.txt +1 -3
  369. ansible_test/_data/requirements/sanity.validate-modules.in +1 -1
  370. ansible_test/_data/requirements/sanity.validate-modules.txt +3 -5
  371. ansible_test/_data/requirements/sanity.yamllint.txt +3 -5
  372. ansible_test/_data/requirements/units.txt +0 -1
  373. ansible_test/_internal/ci/azp.py +4 -4
  374. ansible_test/_internal/cli/environments.py +0 -13
  375. ansible_test/_internal/commands/coverage/analyze/targets/__init__.py +4 -4
  376. ansible_test/_internal/commands/coverage/combine.py +1 -1
  377. ansible_test/_internal/commands/integration/cloud/acme.py +6 -8
  378. ansible_test/_internal/commands/integration/cloud/cs.py +4 -9
  379. ansible_test/_internal/commands/integration/cloud/galaxy.py +103 -96
  380. ansible_test/_internal/commands/integration/cloud/httptester.py +0 -3
  381. ansible_test/_internal/commands/integration/cloud/nios.py +7 -9
  382. ansible_test/_internal/commands/integration/cloud/openshift.py +2 -7
  383. ansible_test/_internal/commands/integration/cloud/vcenter.py +11 -95
  384. ansible_test/_internal/commands/sanity/__init__.py +10 -0
  385. ansible_test/_internal/commands/sanity/import.py +8 -2
  386. ansible_test/_internal/commands/sanity/pylint.py +27 -1
  387. ansible_test/_internal/commands/units/__init__.py +2 -1
  388. ansible_test/_internal/config.py +0 -7
  389. ansible_test/_internal/containers.py +11 -56
  390. ansible_test/_internal/core_ci.py +0 -7
  391. ansible_test/_internal/coverage_util.py +8 -3
  392. ansible_test/_internal/delegation.py +0 -1
  393. ansible_test/_internal/diff.py +1 -1
  394. ansible_test/_internal/docker_util.py +9 -2
  395. ansible_test/_internal/host_profiles.py +6 -6
  396. ansible_test/_internal/http.py +1 -1
  397. ansible_test/_internal/junit_xml.py +1 -1
  398. ansible_test/_internal/pypi_proxy.py +1 -1
  399. ansible_test/_internal/python_requirements.py +3 -8
  400. ansible_test/_internal/util.py +1 -6
  401. ansible_test/_util/controller/sanity/code-smell/no-get-exception.json +4 -0
  402. ansible_test/_util/controller/sanity/code-smell/replace-urlopen.json +4 -0
  403. ansible_test/_util/controller/sanity/code-smell/use-compat-six.json +4 -0
  404. ansible_test/_util/controller/sanity/mypy/ansible-core.ini +3 -0
  405. ansible_test/_util/controller/sanity/pylint/config/ansible-test-target.cfg +2 -0
  406. ansible_test/_util/controller/sanity/pylint/config/ansible-test.cfg +0 -1
  407. ansible_test/_util/controller/sanity/pylint/config/collection.cfg +1 -0
  408. ansible_test/_util/controller/sanity/pylint/plugins/deprecated.py +172 -10
  409. ansible_test/_util/controller/sanity/pylint/plugins/string_format.py +13 -2
  410. ansible_test/_util/controller/sanity/pylint/plugins/unwanted.py +7 -1
  411. ansible_test/_util/controller/sanity/validate-modules/validate_modules/main.py +6 -6
  412. ansible_test/_util/controller/sanity/validate-modules/validate_modules/module_args.py +1 -1
  413. ansible_test/_util/controller/sanity/validate-modules/validate_modules/utils.py +1 -1
  414. ansible_test/_util/controller/sanity/yamllint/yamllinter.py +3 -3
  415. ansible_test/_util/controller/tools/collection_detail.py +2 -2
  416. ansible_test/_util/target/common/constants.py +2 -2
  417. ansible_test/_util/target/pytest/plugins/ansible_forked.py +103 -0
  418. ansible_test/_util/target/sanity/import/importer.py +0 -8
  419. ansible_test/_util/target/setup/bootstrap.sh +36 -16
  420. ansible_test/_util/target/setup/quiet_pip.py +0 -4
  421. ansible/modules/_include.py +0 -80
  422. ansible_test/_internal/commands/integration/cloud/foreman.py +0 -102
  423. ansible_test/_util/target/setup/ConfigureRemotingForAnsible.ps1 +0 -435
  424. {ansible_core-2.15.4rc1.data → ansible_core-2.16.0b2.data}/scripts/ansible-test +0 -0
  425. {ansible_core-2.15.4rc1.dist-info → ansible_core-2.16.0b2.dist-info}/WHEEL +0 -0
  426. {ansible_core-2.15.4rc1.dist-info → ansible_core-2.16.0b2.dist-info}/entry_points.txt +0 -0
  427. {ansible_core-2.15.4rc1.dist-info → ansible_core-2.16.0b2.dist-info}/top_level.txt +0 -0
@@ -15,7 +15,7 @@ from xml.dom import minidom
15
15
  from xml.etree import ElementTree as ET
16
16
 
17
17
 
18
- @dataclasses.dataclass # type: ignore[misc] # https://github.com/python/mypy/issues/5374
18
+ @dataclasses.dataclass
19
19
  class TestResult(metaclass=abc.ABCMeta):
20
20
  """Base class for the result of a test case."""
21
21
 
@@ -24,7 +24,7 @@ import shlex
24
24
  import subprocess
25
25
  import sys
26
26
 
27
- from ansible.module_utils._text import to_bytes
27
+ from ansible.module_utils.common.text.converters import to_bytes
28
28
 
29
29
 
30
30
  def run_cmd(cmd, live=False, readsize=10):
@@ -40,8 +40,19 @@ except ImportError:
40
40
  reload_module = reload # type: ignore[name-defined] # pylint:disable=undefined-variable
41
41
 
42
42
  try:
43
- from importlib.abc import TraversableResources
43
+ try:
44
+ # Available on Python >= 3.11
45
+ # We ignore the import error that will trigger when running mypy with
46
+ # older Python versions.
47
+ from importlib.resources.abc import TraversableResources # type: ignore[import]
48
+ except ImportError:
49
+ # Used with Python 3.9 and 3.10 only
50
+ # This member is still available as an alias up until Python 3.14 but
51
+ # is deprecated as of Python 3.12.
52
+ from importlib.abc import TraversableResources # deprecated: description='TraversableResources move' python_version='3.10'
44
53
  except ImportError:
54
+ # Python < 3.9
55
+ # deprecated: description='TraversableResources fallback' python_version='3.8'
45
56
  TraversableResources = object # type: ignore[assignment,misc]
46
57
 
47
58
  try:
ansible/utils/display.py CHANGED
@@ -15,8 +15,7 @@
15
15
  # You should have received a copy of the GNU General Public License
16
16
  # along with Ansible. If not, see <http://www.gnu.org/licenses/>.
17
17
 
18
- from __future__ import (absolute_import, division, print_function)
19
- __metaclass__ = type
18
+ from __future__ import annotations
20
19
 
21
20
  try:
22
21
  import curses
@@ -26,6 +25,7 @@ else:
26
25
  # this will be set to False if curses.setupterm() fails
27
26
  HAS_CURSES = True
28
27
 
28
+ import collections.abc as c
29
29
  import codecs
30
30
  import ctypes.util
31
31
  import fcntl
@@ -48,13 +48,17 @@ from struct import unpack, pack
48
48
 
49
49
  from ansible import constants as C
50
50
  from ansible.errors import AnsibleError, AnsibleAssertionError, AnsiblePromptInterrupt, AnsiblePromptNoninteractive
51
- from ansible.module_utils._text import to_bytes, to_text
51
+ from ansible.module_utils.common.text.converters import to_bytes, to_text
52
52
  from ansible.module_utils.six import text_type
53
53
  from ansible.utils.color import stringc
54
54
  from ansible.utils.multiprocessing import context as multiprocessing_context
55
55
  from ansible.utils.singleton import Singleton
56
56
  from ansible.utils.unsafe_proxy import wrap_var
57
57
 
58
+ if t.TYPE_CHECKING:
59
+ # avoid circular import at runtime
60
+ from ansible.executor.task_queue_manager import FinalQueue
61
+
58
62
  _LIBC = ctypes.cdll.LoadLibrary(ctypes.util.find_library('c'))
59
63
  # Set argtypes, to avoid segfault if the wrong type is provided,
60
64
  # restype is assumed to be c_int
@@ -67,7 +71,7 @@ MOVE_TO_BOL = b'\r'
67
71
  CLEAR_TO_EOL = b'\x1b[K'
68
72
 
69
73
 
70
- def get_text_width(text):
74
+ def get_text_width(text: str) -> int:
71
75
  """Function that utilizes ``wcswidth`` or ``wcwidth`` to determine the
72
76
  number of columns used to display a text string.
73
77
 
@@ -118,6 +122,20 @@ def get_text_width(text):
118
122
  return width if width >= 0 else 0
119
123
 
120
124
 
125
+ def proxy_display(method):
126
+
127
+ def proxyit(self, *args, **kwargs):
128
+ if self._final_q:
129
+ # If _final_q is set, that means we are in a WorkerProcess
130
+ # and instead of displaying messages directly from the fork
131
+ # we will proxy them through the queue
132
+ return self._final_q.send_display(method.__name__, *args, **kwargs)
133
+ else:
134
+ return method(self, *args, **kwargs)
135
+
136
+ return proxyit
137
+
138
+
121
139
  class FilterBlackList(logging.Filter):
122
140
  def __init__(self, blacklist):
123
141
  self.blacklist = [logging.Filter(name) for name in blacklist]
@@ -178,7 +196,7 @@ b_COW_PATHS = (
178
196
  )
179
197
 
180
198
 
181
- def _synchronize_textiowrapper(tio, lock):
199
+ def _synchronize_textiowrapper(tio: t.TextIO, lock: threading.RLock):
182
200
  # Ensure that a background thread can't hold the internal buffer lock on a file object
183
201
  # during a fork, which causes forked children to hang. We're using display's existing lock for
184
202
  # convenience (and entering the lock before a fork).
@@ -193,11 +211,11 @@ def _synchronize_textiowrapper(tio, lock):
193
211
  buffer = tio.buffer
194
212
 
195
213
  # monkeypatching the underlying file-like object isn't great, but likely safer than subclassing
196
- buffer.write = _wrap_with_lock(buffer.write, lock)
197
- buffer.flush = _wrap_with_lock(buffer.flush, lock)
214
+ buffer.write = _wrap_with_lock(buffer.write, lock) # type: ignore[method-assign]
215
+ buffer.flush = _wrap_with_lock(buffer.flush, lock) # type: ignore[method-assign]
198
216
 
199
217
 
200
- def setraw(fd, when=termios.TCSAFLUSH):
218
+ def setraw(fd: int, when: int = termios.TCSAFLUSH) -> None:
201
219
  """Put terminal into a raw mode.
202
220
 
203
221
  Copied from ``tty`` from CPython 3.11.0, and modified to not remove OPOST from OFLAG
@@ -218,13 +236,12 @@ def setraw(fd, when=termios.TCSAFLUSH):
218
236
  termios.tcsetattr(fd, when, mode)
219
237
 
220
238
 
221
- def clear_line(stdout):
239
+ def clear_line(stdout: t.BinaryIO) -> None:
222
240
  stdout.write(b'\x1b[%s' % MOVE_TO_BOL)
223
241
  stdout.write(b'\x1b[%s' % CLEAR_TO_EOL)
224
242
 
225
243
 
226
- def setup_prompt(stdin_fd, stdout_fd, seconds, echo):
227
- # type: (int, int, int, bool) -> None
244
+ def setup_prompt(stdin_fd: int, stdout_fd: int, seconds: int, echo: bool) -> None:
228
245
  setraw(stdin_fd)
229
246
 
230
247
  # Only set stdout to raw mode if it is a TTY. This is needed when redirecting
@@ -238,7 +255,7 @@ def setup_prompt(stdin_fd, stdout_fd, seconds, echo):
238
255
  termios.tcsetattr(stdin_fd, termios.TCSANOW, new_settings)
239
256
 
240
257
 
241
- def setupterm():
258
+ def setupterm() -> None:
242
259
  # Nest the try except since curses.error is not available if curses did not import
243
260
  try:
244
261
  curses.setupterm()
@@ -255,9 +272,9 @@ def setupterm():
255
272
 
256
273
  class Display(metaclass=Singleton):
257
274
 
258
- def __init__(self, verbosity=0):
275
+ def __init__(self, verbosity: int = 0) -> None:
259
276
 
260
- self._final_q = None
277
+ self._final_q: FinalQueue | None = None
261
278
 
262
279
  # NB: this lock is used to both prevent intermingled output between threads and to block writes during forks.
263
280
  # Do not change the type of this lock or upgrade to a shared lock (eg multiprocessing.RLock).
@@ -267,11 +284,11 @@ class Display(metaclass=Singleton):
267
284
  self.verbosity = verbosity
268
285
 
269
286
  # list of all deprecation messages to prevent duplicate display
270
- self._deprecations = {}
271
- self._warns = {}
272
- self._errors = {}
287
+ self._deprecations: dict[str, int] = {}
288
+ self._warns: dict[str, int] = {}
289
+ self._errors: dict[str, int] = {}
273
290
 
274
- self.b_cowsay = None
291
+ self.b_cowsay: bytes | None = None
275
292
  self.noncow = C.ANSIBLE_COW_SELECTION
276
293
 
277
294
  self.set_cowsay_info()
@@ -282,12 +299,12 @@ class Display(metaclass=Singleton):
282
299
  (out, err) = cmd.communicate()
283
300
  if cmd.returncode:
284
301
  raise Exception
285
- self.cows_available = {to_text(c) for c in out.split()} # set comprehension
302
+ self.cows_available: set[str] = {to_text(c) for c in out.split()}
286
303
  if C.ANSIBLE_COW_ACCEPTLIST and any(C.ANSIBLE_COW_ACCEPTLIST):
287
304
  self.cows_available = set(C.ANSIBLE_COW_ACCEPTLIST).intersection(self.cows_available)
288
305
  except Exception:
289
306
  # could not execute cowsay for some reason
290
- self.b_cowsay = False
307
+ self.b_cowsay = None
291
308
 
292
309
  self._set_column_width()
293
310
 
@@ -307,7 +324,7 @@ class Display(metaclass=Singleton):
307
324
 
308
325
  self.setup_curses = False
309
326
 
310
- def _replacing_warning_handler(self, exception):
327
+ def _replacing_warning_handler(self, exception: UnicodeError) -> tuple[str | bytes, int]:
311
328
  # TODO: This should probably be deferred until after the current display is completed
312
329
  # this will require some amount of new functionality
313
330
  self.deprecated(
@@ -316,7 +333,7 @@ class Display(metaclass=Singleton):
316
333
  )
317
334
  return '?', exception.end
318
335
 
319
- def set_queue(self, queue):
336
+ def set_queue(self, queue: FinalQueue) -> None:
320
337
  """Set the _final_q on Display, so that we know to proxy display over the queue
321
338
  instead of directly writing to stdout/stderr from forks
322
339
 
@@ -326,7 +343,7 @@ class Display(metaclass=Singleton):
326
343
  raise RuntimeError('queue cannot be set in parent process')
327
344
  self._final_q = queue
328
345
 
329
- def set_cowsay_info(self):
346
+ def set_cowsay_info(self) -> None:
330
347
  if C.ANSIBLE_NOCOWS:
331
348
  return
332
349
 
@@ -337,7 +354,16 @@ class Display(metaclass=Singleton):
337
354
  if os.path.exists(b_cow_path):
338
355
  self.b_cowsay = b_cow_path
339
356
 
340
- def display(self, msg, color=None, stderr=False, screen_only=False, log_only=False, newline=True):
357
+ @proxy_display
358
+ def display(
359
+ self,
360
+ msg: str,
361
+ color: str | None = None,
362
+ stderr: bool = False,
363
+ screen_only: bool = False,
364
+ log_only: bool = False,
365
+ newline: bool = True,
366
+ ) -> None:
341
367
  """ Display a message to the user
342
368
 
343
369
  Note: msg *must* be a unicode string to prevent UnicodeError tracebacks.
@@ -346,13 +372,6 @@ class Display(metaclass=Singleton):
346
372
  if not isinstance(msg, str):
347
373
  raise TypeError(f'Display message must be str, not: {msg.__class__.__name__}')
348
374
 
349
- if self._final_q:
350
- # If _final_q is set, that means we are in a WorkerProcess
351
- # and instead of displaying messages directly from the fork
352
- # we will proxy them through the queue
353
- return self._final_q.send_display(msg, color=color, stderr=stderr,
354
- screen_only=screen_only, log_only=log_only, newline=newline)
355
-
356
375
  nocolor = msg
357
376
 
358
377
  if not log_only:
@@ -406,32 +425,32 @@ class Display(metaclass=Singleton):
406
425
  # actually log
407
426
  logger.log(lvl, msg2)
408
427
 
409
- def v(self, msg, host=None):
428
+ def v(self, msg: str, host: str | None = None) -> None:
410
429
  return self.verbose(msg, host=host, caplevel=0)
411
430
 
412
- def vv(self, msg, host=None):
431
+ def vv(self, msg: str, host: str | None = None) -> None:
413
432
  return self.verbose(msg, host=host, caplevel=1)
414
433
 
415
- def vvv(self, msg, host=None):
434
+ def vvv(self, msg: str, host: str | None = None) -> None:
416
435
  return self.verbose(msg, host=host, caplevel=2)
417
436
 
418
- def vvvv(self, msg, host=None):
437
+ def vvvv(self, msg: str, host: str | None = None) -> None:
419
438
  return self.verbose(msg, host=host, caplevel=3)
420
439
 
421
- def vvvvv(self, msg, host=None):
440
+ def vvvvv(self, msg: str, host: str | None = None) -> None:
422
441
  return self.verbose(msg, host=host, caplevel=4)
423
442
 
424
- def vvvvvv(self, msg, host=None):
443
+ def vvvvvv(self, msg: str, host: str | None = None) -> None:
425
444
  return self.verbose(msg, host=host, caplevel=5)
426
445
 
427
- def debug(self, msg, host=None):
446
+ def debug(self, msg: str, host: str | None = None) -> None:
428
447
  if C.DEFAULT_DEBUG:
429
448
  if host is None:
430
449
  self.display("%6d %0.5f: %s" % (os.getpid(), time.time(), msg), color=C.COLOR_DEBUG)
431
450
  else:
432
451
  self.display("%6d %0.5f [%s]: %s" % (os.getpid(), time.time(), host, msg), color=C.COLOR_DEBUG)
433
452
 
434
- def verbose(self, msg, host=None, caplevel=2):
453
+ def verbose(self, msg: str, host: str | None = None, caplevel: int = 2) -> None:
435
454
 
436
455
  to_stderr = C.VERBOSE_TO_STDERR
437
456
  if self.verbosity > caplevel:
@@ -440,7 +459,14 @@ class Display(metaclass=Singleton):
440
459
  else:
441
460
  self.display("<%s> %s" % (host, msg), color=C.COLOR_VERBOSE, stderr=to_stderr)
442
461
 
443
- def get_deprecation_message(self, msg, version=None, removed=False, date=None, collection_name=None):
462
+ def get_deprecation_message(
463
+ self,
464
+ msg: str,
465
+ version: str | None = None,
466
+ removed: bool = False,
467
+ date: str | None = None,
468
+ collection_name: str | None = None,
469
+ ) -> str:
444
470
  ''' used to print out a deprecation message.'''
445
471
  msg = msg.strip()
446
472
  if msg and msg[-1] not in ['!', '?', '.']:
@@ -475,7 +501,15 @@ class Display(metaclass=Singleton):
475
501
 
476
502
  return message_text
477
503
 
478
- def deprecated(self, msg, version=None, removed=False, date=None, collection_name=None):
504
+ @proxy_display
505
+ def deprecated(
506
+ self,
507
+ msg: str,
508
+ version: str | None = None,
509
+ removed: bool = False,
510
+ date: str | None = None,
511
+ collection_name: str | None = None,
512
+ ) -> None:
479
513
  if not removed and not C.DEPRECATION_WARNINGS:
480
514
  return
481
515
 
@@ -491,7 +525,8 @@ class Display(metaclass=Singleton):
491
525
  self.display(message_text.strip(), color=C.COLOR_DEPRECATE, stderr=True)
492
526
  self._deprecations[message_text] = 1
493
527
 
494
- def warning(self, msg, formatted=False):
528
+ @proxy_display
529
+ def warning(self, msg: str, formatted: bool = False) -> None:
495
530
 
496
531
  if not formatted:
497
532
  new_msg = "[WARNING]: %s" % msg
@@ -504,11 +539,11 @@ class Display(metaclass=Singleton):
504
539
  self.display(new_msg, color=C.COLOR_WARN, stderr=True)
505
540
  self._warns[new_msg] = 1
506
541
 
507
- def system_warning(self, msg):
542
+ def system_warning(self, msg: str) -> None:
508
543
  if C.SYSTEM_WARNINGS:
509
544
  self.warning(msg)
510
545
 
511
- def banner(self, msg, color=None, cows=True):
546
+ def banner(self, msg: str, color: str | None = None, cows: bool = True) -> None:
512
547
  '''
513
548
  Prints a header-looking line with cowsay or stars with length depending on terminal width (3 minimum)
514
549
  '''
@@ -531,7 +566,7 @@ class Display(metaclass=Singleton):
531
566
  stars = u"*" * star_len
532
567
  self.display(u"\n%s %s" % (msg, stars), color=color)
533
568
 
534
- def banner_cowsay(self, msg, color=None):
569
+ def banner_cowsay(self, msg: str, color: str | None = None) -> None:
535
570
  if u": [" in msg:
536
571
  msg = msg.replace(u"[", u"")
537
572
  if msg.endswith(u"]"):
@@ -548,7 +583,7 @@ class Display(metaclass=Singleton):
548
583
  (out, err) = cmd.communicate()
549
584
  self.display(u"%s\n" % to_text(out), color=color)
550
585
 
551
- def error(self, msg, wrap_text=True):
586
+ def error(self, msg: str, wrap_text: bool = True) -> None:
552
587
  if wrap_text:
553
588
  new_msg = u"\n[ERROR]: %s" % msg
554
589
  wrapped = textwrap.wrap(new_msg, self.columns)
@@ -560,14 +595,24 @@ class Display(metaclass=Singleton):
560
595
  self._errors[new_msg] = 1
561
596
 
562
597
  @staticmethod
563
- def prompt(msg, private=False):
598
+ def prompt(msg: str, private: bool = False) -> str:
564
599
  if private:
565
600
  return getpass.getpass(msg)
566
601
  else:
567
602
  return input(msg)
568
603
 
569
- def do_var_prompt(self, varname, private=True, prompt=None, encrypt=None, confirm=False, salt_size=None, salt=None, default=None, unsafe=None):
570
-
604
+ def do_var_prompt(
605
+ self,
606
+ varname: str,
607
+ private: bool = True,
608
+ prompt: str | None = None,
609
+ encrypt: str | None = None,
610
+ confirm: bool = False,
611
+ salt_size: int | None = None,
612
+ salt: str | None = None,
613
+ default: str | None = None,
614
+ unsafe: bool = False,
615
+ ) -> str:
571
616
  result = None
572
617
  if sys.__stdin__.isatty():
573
618
 
@@ -600,7 +645,7 @@ class Display(metaclass=Singleton):
600
645
  if encrypt:
601
646
  # Circular import because encrypt needs a display class
602
647
  from ansible.utils.encrypt import do_encrypt
603
- result = do_encrypt(result, encrypt, salt_size, salt)
648
+ result = do_encrypt(result, encrypt, salt_size=salt_size, salt=salt)
604
649
 
605
650
  # handle utf-8 chars
606
651
  result = to_text(result, errors='surrogate_or_strict')
@@ -609,14 +654,21 @@ class Display(metaclass=Singleton):
609
654
  result = wrap_var(result)
610
655
  return result
611
656
 
612
- def _set_column_width(self):
657
+ def _set_column_width(self) -> None:
613
658
  if os.isatty(1):
614
659
  tty_size = unpack('HHHH', fcntl.ioctl(1, termios.TIOCGWINSZ, pack('HHHH', 0, 0, 0, 0)))[1]
615
660
  else:
616
661
  tty_size = 0
617
662
  self.columns = max(79, tty_size - 1)
618
663
 
619
- def prompt_until(self, msg, private=False, seconds=None, interrupt_input=None, complete_input=None):
664
+ def prompt_until(
665
+ self,
666
+ msg: str,
667
+ private: bool = False,
668
+ seconds: int | None = None,
669
+ interrupt_input: c.Container[bytes] | None = None,
670
+ complete_input: c.Container[bytes] | None = None,
671
+ ) -> bytes:
620
672
  if self._final_q:
621
673
  from ansible.executor.process.worker import current_worker
622
674
  self._final_q.send_prompt(
@@ -668,12 +720,11 @@ class Display(metaclass=Singleton):
668
720
 
669
721
  def _read_non_blocking_stdin(
670
722
  self,
671
- echo=False, # type: bool
672
- seconds=None, # type: int
673
- interrupt_input=None, # type: t.Iterable[bytes]
674
- complete_input=None, # type: t.Iterable[bytes]
675
- ): # type: (...) -> bytes
676
-
723
+ echo: bool = False,
724
+ seconds: int | None = None,
725
+ interrupt_input: c.Container[bytes] | None = None,
726
+ complete_input: c.Container[bytes] | None = None,
727
+ ) -> bytes:
677
728
  if self._final_q:
678
729
  raise NotImplementedError
679
730
 
@@ -722,7 +773,7 @@ class Display(metaclass=Singleton):
722
773
  return result_string
723
774
 
724
775
  @property
725
- def _stdin(self):
776
+ def _stdin(self) -> t.BinaryIO | None:
726
777
  if self._final_q:
727
778
  raise NotImplementedError
728
779
  try:
@@ -731,20 +782,20 @@ class Display(metaclass=Singleton):
731
782
  return None
732
783
 
733
784
  @property
734
- def _stdin_fd(self):
785
+ def _stdin_fd(self) -> int | None:
735
786
  try:
736
787
  return self._stdin.fileno()
737
788
  except (ValueError, AttributeError):
738
789
  return None
739
790
 
740
791
  @property
741
- def _stdout(self):
792
+ def _stdout(self) -> t.BinaryIO:
742
793
  if self._final_q:
743
794
  raise NotImplementedError
744
795
  return sys.stdout.buffer
745
796
 
746
797
  @property
747
- def _stdout_fd(self):
798
+ def _stdout_fd(self) -> int | None:
748
799
  try:
749
800
  return self._stdout.fileno()
750
801
  except (ValueError, AttributeError):
ansible/utils/encrypt.py CHANGED
@@ -4,7 +4,6 @@
4
4
  from __future__ import (absolute_import, division, print_function)
5
5
  __metaclass__ = type
6
6
 
7
- import multiprocessing
8
7
  import random
9
8
  import re
10
9
  import string
@@ -15,7 +14,7 @@ from collections import namedtuple
15
14
  from ansible import constants as C
16
15
  from ansible.errors import AnsibleError, AnsibleAssertionError
17
16
  from ansible.module_utils.six import text_type
18
- from ansible.module_utils._text import to_text, to_bytes
17
+ from ansible.module_utils.common.text.converters import to_text, to_bytes
19
18
  from ansible.utils.display import Display
20
19
 
21
20
  PASSLIB_E = CRYPT_E = None
@@ -43,8 +42,6 @@ display = Display()
43
42
 
44
43
  __all__ = ['do_encrypt']
45
44
 
46
- _LOCK = multiprocessing.Lock()
47
-
48
45
  DEFAULT_PASSWORD_LENGTH = 20
49
46
 
50
47
 
@@ -105,7 +102,7 @@ class CryptHash(BaseHash):
105
102
  "Python crypt module is deprecated and will be removed from "
106
103
  "Python 3.13. Install the passlib library for continued "
107
104
  "encryption functionality.",
108
- version=2.17
105
+ version="2.17",
109
106
  )
110
107
 
111
108
  self.algo_data = self.algorithms[algorithm]
@@ -158,8 +155,7 @@ class CryptHash(BaseHash):
158
155
 
159
156
  saltstring += "$%s" % salt
160
157
 
161
- # crypt.crypt on Python < 3.9 returns None if it cannot parse saltstring
162
- # On Python >= 3.9, it throws OSError.
158
+ # crypt.crypt throws OSError on Python >= 3.9 if it cannot parse saltstring.
163
159
  try:
164
160
  result = crypt.crypt(secret, saltstring)
165
161
  orig_exc = None
@@ -167,7 +163,7 @@ class CryptHash(BaseHash):
167
163
  result = None
168
164
  orig_exc = e
169
165
 
170
- # None as result would be interpreted by the some modules (user module)
166
+ # None as result would be interpreted by some modules (user module)
171
167
  # as no password at all.
172
168
  if not result:
173
169
  raise AnsibleError(
@@ -271,12 +267,13 @@ class PasslibHash(BaseHash):
271
267
 
272
268
 
273
269
  def passlib_or_crypt(secret, algorithm, salt=None, salt_size=None, rounds=None, ident=None):
270
+ display.deprecated("passlib_or_crypt API is deprecated in favor of do_encrypt", version='2.20')
271
+ return do_encrypt(secret, algorithm, salt=salt, salt_size=salt_size, rounds=rounds, ident=ident)
272
+
273
+
274
+ def do_encrypt(result, encrypt, salt_size=None, salt=None, ident=None, rounds=None):
274
275
  if PASSLIB_AVAILABLE:
275
- return PasslibHash(algorithm).hash(secret, salt=salt, salt_size=salt_size, rounds=rounds, ident=ident)
276
+ return PasslibHash(encrypt).hash(result, salt=salt, salt_size=salt_size, rounds=rounds, ident=ident)
276
277
  if HAS_CRYPT:
277
- return CryptHash(algorithm).hash(secret, salt=salt, salt_size=salt_size, rounds=rounds, ident=ident)
278
+ return CryptHash(encrypt).hash(result, salt=salt, salt_size=salt_size, rounds=rounds, ident=ident)
278
279
  raise AnsibleError("Unable to encrypt nor hash, either crypt or passlib must be installed.", orig_exc=CRYPT_E)
279
-
280
-
281
- def do_encrypt(result, encrypt, salt_size=None, salt=None, ident=None):
282
- return passlib_or_crypt(result, encrypt, salt_size=salt_size, salt=salt, ident=ident)
ansible/utils/hashing.py CHANGED
@@ -30,7 +30,7 @@ except ImportError:
30
30
  _md5 = None
31
31
 
32
32
  from ansible.errors import AnsibleError
33
- from ansible.module_utils._text import to_bytes
33
+ from ansible.module_utils.common.text.converters import to_bytes
34
34
 
35
35
 
36
36
  def secure_hash_s(data, hash_func=sha1):
ansible/utils/jsonrpc.py CHANGED
@@ -8,7 +8,7 @@ import json
8
8
  import pickle
9
9
  import traceback
10
10
 
11
- from ansible.module_utils._text import to_text
11
+ from ansible.module_utils.common.text.converters import to_text
12
12
  from ansible.module_utils.connection import ConnectionError
13
13
  from ansible.module_utils.six import binary_type, text_type
14
14
  from ansible.utils.display import Display
ansible/utils/path.py CHANGED
@@ -22,7 +22,7 @@ import shutil
22
22
 
23
23
  from errno import EEXIST
24
24
  from ansible.errors import AnsibleError
25
- from ansible.module_utils._text import to_bytes, to_native, to_text
25
+ from ansible.module_utils.common.text.converters import to_bytes, to_native, to_text
26
26
 
27
27
 
28
28
  __all__ = ['unfrackpath', 'makedirs_safe']
@@ -11,7 +11,7 @@ from ansible import constants as C
11
11
  from ansible.release import __version__ as ansible_version
12
12
  from ansible.errors import AnsibleError, AnsibleParserError, AnsiblePluginNotFound
13
13
  from ansible.module_utils.six import string_types
14
- from ansible.module_utils._text import to_native
14
+ from ansible.module_utils.common.text.converters import to_native
15
15
  from ansible.parsing.plugin_docs import read_docstring
16
16
  from ansible.parsing.yaml.loader import AnsibleLoader
17
17
  from ansible.utils.display import Display
@@ -17,7 +17,7 @@ import sys
17
17
  from collections.abc import MutableMapping
18
18
 
19
19
  from ansible.module_utils.six import PY3
20
- from ansible.module_utils._text import to_bytes, to_text
20
+ from ansible.module_utils.common.text.converters import to_bytes, to_text
21
21
 
22
22
  __all__ = ('environ',)
23
23
 
ansible/utils/shlex.py CHANGED
@@ -20,15 +20,7 @@ from __future__ import (absolute_import, division, print_function)
20
20
  __metaclass__ = type
21
21
 
22
22
  import shlex
23
- from ansible.module_utils.six import PY3
24
- from ansible.module_utils._text import to_bytes, to_text
25
23
 
26
24
 
27
- if PY3:
28
- # shlex.split() wants Unicode (i.e. ``str``) input on Python 3
29
- shlex_split = shlex.split
30
- else:
31
- # shlex.split() wants bytes (i.e. ``str``) input on Python 2
32
- def shlex_split(s, comments=False, posix=True):
33
- return map(to_text, shlex.split(to_bytes(s), comments, posix))
34
- shlex_split.__doc__ = shlex.split.__doc__
25
+ # shlex.split() wants Unicode (i.e. ``str``) input on Python 3
26
+ shlex_split = shlex.split
@@ -23,8 +23,11 @@ __metaclass__ = type
23
23
  import subprocess
24
24
 
25
25
  from ansible import constants as C
26
- from ansible.module_utils._text import to_bytes
26
+ from ansible.module_utils.common.text.converters import to_bytes
27
27
  from ansible.module_utils.compat.paramiko import paramiko
28
+ from ansible.utils.display import Display
29
+
30
+ display = Display()
28
31
 
29
32
 
30
33
  _HAS_CONTROLPERSIST = {} # type: dict[str, bool]
@@ -51,13 +54,11 @@ def check_for_controlpersist(ssh_executable):
51
54
  return has_cp
52
55
 
53
56
 
54
- # TODO: move to 'smart' connection plugin that subclasses to ssh/paramiko as needed.
55
57
  def set_default_transport():
56
58
 
57
59
  # deal with 'smart' connection .. one time ..
58
60
  if C.DEFAULT_TRANSPORT == 'smart':
59
- # TODO: check if we can deprecate this as ssh w/o control persist should
60
- # not be as common anymore.
61
+ display.deprecated("The 'smart' option for connections is deprecated. Set the connection plugin directly instead.", version='2.20')
61
62
 
62
63
  # see if SSH can support ControlPersist if not use paramiko
63
64
  if not check_for_controlpersist('ssh') and paramiko is not None:
ansible/utils/unicode.py CHANGED
@@ -19,7 +19,7 @@
19
19
  from __future__ import (absolute_import, division, print_function)
20
20
  __metaclass__ = type
21
21
 
22
- from ansible.module_utils._text import to_text
22
+ from ansible.module_utils.common.text.converters import to_text
23
23
 
24
24
 
25
25
  __all__ = ('unicode_wrap',)
@@ -55,7 +55,7 @@ __metaclass__ = type
55
55
 
56
56
  from collections.abc import Mapping, Set
57
57
 
58
- from ansible.module_utils._text import to_bytes, to_text
58
+ from ansible.module_utils.common.text.converters import to_bytes, to_text
59
59
  from ansible.module_utils.common.collections import is_sequence
60
60
  from ansible.module_utils.six import binary_type, text_type
61
61
  from ansible.utils.native_jinja import NativeJinjaText