From 757527635dd00ae7dee61c9bf3c77c6d7bf02d6c Mon Sep 17 00:00:00 2001 From: Alex Willmer Date: Tue, 5 Nov 2024 01:33:40 +0000 Subject: [PATCH 01/11] Begin v0.3.17dev --- docs/changelog.rst | 5 +++++ mitogen/__init__.py | 2 +- 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/docs/changelog.rst b/docs/changelog.rst index e287c93b..d579544f 100644 --- a/docs/changelog.rst +++ b/docs/changelog.rst @@ -18,6 +18,11 @@ To avail of fixes in an unreleased version, please download a ZIP file `directly from GitHub `_. +In progress (unreleased) +------------------------ + + + v0.3.16 (2024-11-05) -------------------- diff --git a/mitogen/__init__.py b/mitogen/__init__.py index 50c2e377..40b6850e 100644 --- a/mitogen/__init__.py +++ b/mitogen/__init__.py @@ -35,7 +35,7 @@ be expected. On the slave, it is built dynamically during startup. #: Library version as a tuple. -__version__ = (0, 3, 16) +__version__ = (0, 3, 17, 'dev') #: This is :data:`False` in slave contexts. Previously it was used to prevent From 43cc937bc67110abea5d0f87bd6480afff2d2cc8 Mon Sep 17 00:00:00 2001 From: Alex Willmer Date: Tue, 5 Nov 2024 17:38:27 +0000 Subject: [PATCH 02/11] CI: Fix incorrect u=r,g=r,o=rw file permissions on mitogen__has_sudo_pubkey.key MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The wrong base was used when calculating the mode. So the file became world readable and writable on a CI runner, until ansible/integration/ssh/variables.yml happened to correct it near the end of the integration tests. I believe this was the only instance. ```console mitogen git:(issue1182) ✗ ag --python 'int\(.+7\)' . .ci | wc -l 0 ``` fixes #1182 --- .ci/ansible_tests.py | 2 +- docs/changelog.rst | 2 ++ tests/ansible/integration/ssh/variables.yml | 7 ++----- 3 files changed, 5 insertions(+), 6 deletions(-) diff --git a/.ci/ansible_tests.py b/.ci/ansible_tests.py index 62dfa8f5..4a7bedae 100755 --- a/.ci/ansible_tests.py +++ b/.ci/ansible_tests.py @@ -41,7 +41,7 @@ with ci_lib.Fold('docker_setup'): with ci_lib.Fold('job_setup'): os.chdir(TESTS_DIR) - os.chmod('../data/docker/mitogen__has_sudo_pubkey.key', int('0600', 7)) + os.chmod('../data/docker/mitogen__has_sudo_pubkey.key', int('0600', 8)) ci_lib.run("mkdir %s", HOSTS_DIR) for path in glob.glob(TESTS_DIR + '/hosts/*'): diff --git a/docs/changelog.rst b/docs/changelog.rst index d579544f..85ab9d2f 100644 --- a/docs/changelog.rst +++ b/docs/changelog.rst @@ -21,6 +21,8 @@ To avail of fixes in an unreleased version, please download a ZIP file In progress (unreleased) ------------------------ +* :gh:issue:`1182` CI: Fix incorrect world readable/writable file permissions + on SSH key ``mitogen__has_sudo_pubkey.key`` during Ansible tests. v0.3.16 (2024-11-05) diff --git a/tests/ansible/integration/ssh/variables.yml b/tests/ansible/integration/ssh/variables.yml index 541b29f9..51783881 100644 --- a/tests/ansible/integration/ssh/variables.yml +++ b/tests/ansible/integration/ssh/variables.yml @@ -13,11 +13,6 @@ -o "ControlPath /tmp/mitogen-ansible-test-{{18446744073709551615|random}}" tasks: - - name: setup ansible_ssh_private_key_file - shell: chmod 0600 ../data/docker/mitogen__has_sudo_pubkey.key - args: - chdir: ../.. - - name: ansible_user, ansible_ssh_private_key_file shell: > ANSIBLE_ANY_ERRORS_FATAL=false @@ -34,6 +29,7 @@ args: chdir: ../.. register: out + changed_when: false - name: ansible_user, wrong ansible_ssh_private_key_file shell: > @@ -52,6 +48,7 @@ args: chdir: ../.. register: out + changed_when: false ignore_errors: true - assert: From c7df5c97c16563a17e3f6f3512b2f2154292a757 Mon Sep 17 00:00:00 2001 From: Alex Willmer Date: Tue, 5 Nov 2024 18:12:36 +0000 Subject: [PATCH 03/11] ansible_mitogen: Templated SSH private key file --- ansible_mitogen/transport_config.py | 2 +- docs/changelog.rst | 2 ++ tests/ansible/hosts/default.hosts | 1 + .../ssh/templated_by_play_taskvar.yml | 21 ++++++++++++++++++- tests/ansible/templates/test-targets.j2 | 1 + 5 files changed, 25 insertions(+), 2 deletions(-) diff --git a/ansible_mitogen/transport_config.py b/ansible_mitogen/transport_config.py index 97f1b2f0..294e8914 100644 --- a/ansible_mitogen/transport_config.py +++ b/ansible_mitogen/transport_config.py @@ -508,7 +508,7 @@ class PlayContextSpec(Spec): return boolean(val) def private_key_file(self): - return self._play_context.private_key_file + return self._connection_option('private_key_file') def ssh_executable(self): return self._connection_option('ssh_executable') diff --git a/docs/changelog.rst b/docs/changelog.rst index 85ab9d2f..69e5e944 100644 --- a/docs/changelog.rst +++ b/docs/changelog.rst @@ -23,6 +23,8 @@ In progress (unreleased) * :gh:issue:`1182` CI: Fix incorrect world readable/writable file permissions on SSH key ``mitogen__has_sudo_pubkey.key`` during Ansible tests. +* :gh:issue:`1083` :mod:`ansible_mitogen`: Templated SSH private key file + (e.g. ``ansible_private_key_file``). v0.3.16 (2024-11-05) diff --git a/tests/ansible/hosts/default.hosts b/tests/ansible/hosts/default.hosts index eb04cf90..221d333d 100644 --- a/tests/ansible/hosts/default.hosts +++ b/tests/ansible/hosts/default.hosts @@ -45,6 +45,7 @@ ansible_user="{{ lookup('pipe', 'whoami') }}" [tt_targets_inventory] tt-password ansible_password="{{ 'has_sudo_nopw_password' | trim }}" ansible_user=mitogen__has_sudo_nopw tt-port ansible_password=has_sudo_nopw_password ansible_port="{{ 22 | int }}" ansible_user=mitogen__has_sudo_nopw +tt-private-key-file ansible_private_key_file="{{ git_basedir }}/tests/data/docker/mitogen__has_sudo_pubkey.key" ansible_user=mitogen__has_sudo_pubkey tt-remote-user ansible_password=has_sudo_nopw_password ansible_user="{{ 'mitogen__has_sudo_nopw' | trim }}" tt-ssh-executable ansible_password=has_sudo_nopw_password ansible_ssh_executable="{{ 'ssh' | trim }}" ansible_user=mitogen__has_sudo_nopw diff --git a/tests/ansible/integration/ssh/templated_by_play_taskvar.yml b/tests/ansible/integration/ssh/templated_by_play_taskvar.yml index 0662adcd..d3ae6117 100644 --- a/tests/ansible/integration/ssh/templated_by_play_taskvar.yml +++ b/tests/ansible/integration/ssh/templated_by_play_taskvar.yml @@ -9,5 +9,24 @@ tasks: - meta: reset_connection - - name: Templated variables in play + - name: Templated variables in play, password authentication + ping: + +- name: integration/ssh/templated_by_play_taskvar.yml + hosts: tt_targets_bare + gather_facts: false + vars: + ansible_private_key_file: "{{ git_basedir }}/tests/data/docker/mitogen__has_sudo_pubkey.key" + ansible_port: "{{ hostvars[groups['test-targets'][0]].ansible_port | default(22) }}" + ansible_ssh_executable: "{{ 'ssh' | trim }}" + ansible_user: "{{ 'mitogen__has_sudo_pubkey' | trim }}" + + tasks: + - meta: end_play + when: + # https://github.com/ansible/ansible/issues/84238 + - not is_mitogen + - ansible_version.full is version('2.19', '<', strict=True) + - meta: reset_connection + - name: Templated variables in play, key authentication ping: diff --git a/tests/ansible/templates/test-targets.j2 b/tests/ansible/templates/test-targets.j2 index 27949758..9e726d1f 100644 --- a/tests/ansible/templates/test-targets.j2 +++ b/tests/ansible/templates/test-targets.j2 @@ -73,6 +73,7 @@ ansible_user=mitogen__has_sudo_nopw [tt_targets_inventory] tt-password ansible_password="{{ '{{' }} 'has_sudo_nopw_password' | trim {{ '}}' }}" ansible_port={{ tt.port }} ansible_user=mitogen__has_sudo_nopw tt-port ansible_password=has_sudo_nopw_password ansible_port="{{ '{{' }} {{ tt.port }} | int {{ '}}' }}" ansible_user=mitogen__has_sudo_nopw +tt-private-key-file ansible_port={{ tt.port }} ansible_private_key_file="{{ '{{' }} git_basedir {{ '}}' }}/tests/data/docker/mitogen__has_sudo_pubkey.key" ansible_user=mitogen__has_sudo_pubkey tt-remote-user ansible_password=has_sudo_nopw_password ansible_port={{ tt.port }} ansible_user="{{ '{{' }} 'mitogen__has_sudo_nopw' | trim {{ '}}' }}" tt-ssh-executable ansible_password=has_sudo_nopw_password ansible_port={{ tt.port }} ansible_ssh_executable="{{ '{{' }} 'ssh' | trim {{ '}}' }}" ansible_user=mitogen__has_sudo_nopw From 9e0dad2a1a702ca02bfe2810073d3a3467bb0689 Mon Sep 17 00:00:00 2001 From: Alex Willmer Date: Wed, 6 Nov 2024 09:17:09 +0000 Subject: [PATCH 04/11] ansible_mitogen: Templated SSH host key checking refs #1083 --- ansible_mitogen/transport_config.py | 7 +------ docs/changelog.rst | 2 ++ tests/ansible/hosts/default.hosts | 1 + tests/ansible/templates/test-targets.j2 | 1 + 4 files changed, 5 insertions(+), 6 deletions(-) diff --git a/ansible_mitogen/transport_config.py b/ansible_mitogen/transport_config.py index 294e8914..650355ff 100644 --- a/ansible_mitogen/transport_config.py +++ b/ansible_mitogen/transport_config.py @@ -500,12 +500,7 @@ class PlayContextSpec(Spec): rediscover_python=rediscover_python) def host_key_checking(self): - def candidates(): - yield self._connection.get_task_var('ansible_ssh_host_key_checking') - yield self._connection.get_task_var('ansible_host_key_checking') - yield C.HOST_KEY_CHECKING - val = next((v for v in candidates() if v is not None), True) - return boolean(val) + return self._connection_option('host_key_checking') def private_key_file(self): return self._connection_option('private_key_file') diff --git a/docs/changelog.rst b/docs/changelog.rst index 69e5e944..88ad6bb1 100644 --- a/docs/changelog.rst +++ b/docs/changelog.rst @@ -25,6 +25,8 @@ In progress (unreleased) on SSH key ``mitogen__has_sudo_pubkey.key`` during Ansible tests. * :gh:issue:`1083` :mod:`ansible_mitogen`: Templated SSH private key file (e.g. ``ansible_private_key_file``). +* :gh:issue:`1083` :mod:`ansible_mitogen`: Templated SSH host key checking + (e.g. ``ansible_host_key_checking``, ``ansible_ssh_host_key_checking``). v0.3.16 (2024-11-05) diff --git a/tests/ansible/hosts/default.hosts b/tests/ansible/hosts/default.hosts index 221d333d..077865b0 100644 --- a/tests/ansible/hosts/default.hosts +++ b/tests/ansible/hosts/default.hosts @@ -43,6 +43,7 @@ ansible_host=localhost ansible_user="{{ lookup('pipe', 'whoami') }}" [tt_targets_inventory] +tt-host-key-checking ansible_host_key_checking="{{ 'false' | trim }}" ansible_password=has_sudo_nopw_password ansible_user=mitogen__has_sudo_nopw tt-password ansible_password="{{ 'has_sudo_nopw_password' | trim }}" ansible_user=mitogen__has_sudo_nopw tt-port ansible_password=has_sudo_nopw_password ansible_port="{{ 22 | int }}" ansible_user=mitogen__has_sudo_nopw tt-private-key-file ansible_private_key_file="{{ git_basedir }}/tests/data/docker/mitogen__has_sudo_pubkey.key" ansible_user=mitogen__has_sudo_pubkey diff --git a/tests/ansible/templates/test-targets.j2 b/tests/ansible/templates/test-targets.j2 index 9e726d1f..c829a6f6 100644 --- a/tests/ansible/templates/test-targets.j2 +++ b/tests/ansible/templates/test-targets.j2 @@ -71,6 +71,7 @@ ansible_python_interpreter={{ tt.python_path }} ansible_user=mitogen__has_sudo_nopw [tt_targets_inventory] +tt-host-key-checking ansible_host_key_checking="{{ '{{' }} 'false' | trim {{ '}}' }}" ansible_password=has_sudo_nopw_password ansible_port={{ tt.port }} ansible_user=mitogen__has_sudo_nopw tt-password ansible_password="{{ '{{' }} 'has_sudo_nopw_password' | trim {{ '}}' }}" ansible_port={{ tt.port }} ansible_user=mitogen__has_sudo_nopw tt-port ansible_password=has_sudo_nopw_password ansible_port="{{ '{{' }} {{ tt.port }} | int {{ '}}' }}" ansible_user=mitogen__has_sudo_nopw tt-private-key-file ansible_port={{ tt.port }} ansible_private_key_file="{{ '{{' }} git_basedir {{ '}}' }}/tests/data/docker/mitogen__has_sudo_pubkey.key" ansible_user=mitogen__has_sudo_pubkey From 8cfcb66cda44d8740383eeaa7641a58b3e3e9e04 Mon Sep 17 00:00:00 2001 From: Alex Willmer Date: Wed, 6 Nov 2024 23:56:55 +0000 Subject: [PATCH 05/11] CI: Refactor sshd configuration into a role Prep for applying it to macOS 13 GitHub runners. refs #1186 --- tests/image_prep/_container_setup.yml | 27 +++++++------------ tests/image_prep/roles/sshd/defaults/main.yml | 1 + .../roles/sshd/files/banner.txt} | 0 tests/image_prep/roles/sshd/tasks/main.yml | 18 +++++++++++++ 4 files changed, 28 insertions(+), 18 deletions(-) create mode 100644 tests/image_prep/roles/sshd/defaults/main.yml rename tests/{data/docker/ssh_login_banner.txt => image_prep/roles/sshd/files/banner.txt} (100%) create mode 100644 tests/image_prep/roles/sshd/tasks/main.yml diff --git a/tests/image_prep/_container_setup.yml b/tests/image_prep/_container_setup.yml index d41d1326..2972adda 100644 --- a/tests/image_prep/_container_setup.yml +++ b/tests/image_prep/_container_setup.yml @@ -23,10 +23,16 @@ gather_facts: true vars: distro: "{{ansible_distribution}}" - tasks: - - when: ansible_virtualization_type != "docker" - meta: end_play + pre_tasks: + - meta: end_play + when: + - ansible_facts.virtualization_type != "docker" + + roles: + - role: sshd + + tasks: - name: Ensure requisite apt packages are installed apt: name: "{{ common_packages + packages }}" @@ -134,10 +140,6 @@ content: | i-am-mitogen-test-docker-image - - copy: - dest: /etc/ssh/banner.txt - src: ../data/docker/ssh_login_banner.txt - - name: Ensure /etc/sudoers.d exists file: state: directory @@ -169,17 +171,6 @@ line: "%wheel ALL=(ALL) ALL" when: ansible_os_family == 'RedHat' - - name: Enable SSH banner - lineinfile: - path: /etc/ssh/sshd_config - line: Banner /etc/ssh/banner.txt - - - name: Allow remote SSH root login - lineinfile: - path: /etc/ssh/sshd_config - line: PermitRootLogin yes - regexp: '.*PermitRootLogin.*' - - name: Allow remote SSH root login lineinfile: path: /etc/pam.d/sshd diff --git a/tests/image_prep/roles/sshd/defaults/main.yml b/tests/image_prep/roles/sshd/defaults/main.yml new file mode 100644 index 00000000..4642c71f --- /dev/null +++ b/tests/image_prep/roles/sshd/defaults/main.yml @@ -0,0 +1 @@ +sshd_config_file: /etc/ssh/sshd_config diff --git a/tests/data/docker/ssh_login_banner.txt b/tests/image_prep/roles/sshd/files/banner.txt similarity index 100% rename from tests/data/docker/ssh_login_banner.txt rename to tests/image_prep/roles/sshd/files/banner.txt diff --git a/tests/image_prep/roles/sshd/tasks/main.yml b/tests/image_prep/roles/sshd/tasks/main.yml new file mode 100644 index 00000000..d160d298 --- /dev/null +++ b/tests/image_prep/roles/sshd/tasks/main.yml @@ -0,0 +1,18 @@ +- name: Create login banner + copy: + src: banner.txt + dest: /etc/ssh/banner.txt + mode: u=rw,go=r + +- name: Configure sshd_config + lineinfile: + path: "{{ sshd_config_file }}" + line: "{{ item.line }}" + regexp: "{{ item.regexp }}" + loop: + - line: Banner /etc/ssh/banner.txt + regexp: '^#? *Banner.*' + - line: PermitRootLogin yes + regexp: '.*PermitRootLogin.*' + loop_control: + label: "{{ item.line }}" From 3a1b5ec620f1f822e9c78f0d0ab84d8b1e8b7f59 Mon Sep 17 00:00:00 2001 From: Alex Willmer Date: Thu, 7 Nov 2024 00:16:22 +0000 Subject: [PATCH 06/11] CI: Increase sshd MaxAuthRetries to 50 on macOS runners refs #1186 --- .ci/localhost_ansible_tests.py | 3 +++ tests/image_prep/macos_localhost.yml | 7 +++++++ tests/image_prep/roles/sshd/defaults/main.yml | 2 ++ tests/image_prep/roles/sshd/tasks/main.yml | 13 +++++++++++++ 4 files changed, 25 insertions(+) create mode 100644 tests/image_prep/macos_localhost.yml diff --git a/.ci/localhost_ansible_tests.py b/.ci/localhost_ansible_tests.py index 502a9abc..e4b8329b 100755 --- a/.ci/localhost_ansible_tests.py +++ b/.ci/localhost_ansible_tests.py @@ -51,6 +51,9 @@ with ci_lib.Fold('machine_prep'): subprocess.check_call('sudo chmod 700 ~root/.ssh', shell=True) subprocess.check_call('sudo chmod 600 ~root/.ssh/authorized_keys', shell=True) + os.chdir(IMAGE_PREP_DIR) + ci_lib.run("ansible-playbook -c local -i localhost, macos_localhost.yml") + if os.path.expanduser('~mitogen__user1') == '~mitogen__user1': os.chdir(IMAGE_PREP_DIR) ci_lib.run("ansible-playbook -c local -i localhost, _user_accounts.yml") diff --git a/tests/image_prep/macos_localhost.yml b/tests/image_prep/macos_localhost.yml new file mode 100644 index 00000000..c046a2bc --- /dev/null +++ b/tests/image_prep/macos_localhost.yml @@ -0,0 +1,7 @@ +- name: Configure macOS + hosts: all + gather_facts: true + strategy: mitogen_free + become: true + roles: + - role: sshd diff --git a/tests/image_prep/roles/sshd/defaults/main.yml b/tests/image_prep/roles/sshd/defaults/main.yml index 4642c71f..dec0cf0c 100644 --- a/tests/image_prep/roles/sshd/defaults/main.yml +++ b/tests/image_prep/roles/sshd/defaults/main.yml @@ -1 +1,3 @@ sshd_config_file: /etc/ssh/sshd_config + +sshd_config__max_auth_tries: 50 diff --git a/tests/image_prep/roles/sshd/tasks/main.yml b/tests/image_prep/roles/sshd/tasks/main.yml index d160d298..837c7d15 100644 --- a/tests/image_prep/roles/sshd/tasks/main.yml +++ b/tests/image_prep/roles/sshd/tasks/main.yml @@ -12,7 +12,20 @@ loop: - line: Banner /etc/ssh/banner.txt regexp: '^#? *Banner.*' + - line: MaxAuthTries {{ sshd_config__max_auth_tries }} + regexp: '^#? *MaxAuthTries.*' - line: PermitRootLogin yes regexp: '.*PermitRootLogin.*' loop_control: label: "{{ item.line }}" + register: configure_sshd_result + +- name: Restart sshd + shell: | + launchctl unload /System/Library/LaunchDaemons/ssh.plist + wait 5 + launchctl load -w /System/Library/LaunchDaemons/ssh.plist + changed_when: true + when: + - ansible_facts.distribution == "MacOSX" + - configure_sshd_result is changed From 6d9f2e12d95e4f1bbc3b1ea9f1f9ddfc204e8516 Mon Sep 17 00:00:00 2001 From: Alex Willmer Date: Thu, 7 Nov 2024 10:18:00 +0000 Subject: [PATCH 07/11] tests: Switch remaining tt_targets_inventory group vars to host vars This is ground work for adding/testing templated hostnames and python interpreters. The extreme wideness will hopefully be temporary, e.g. by switching to YAML inventories. The INI inventory plugin doesn't support multiline host entries. > 640 K(olumns) should be enough for anyone > -- Apocryphal, not Bill Gates --- tests/ansible/hosts/default.hosts | 15 ++++++--------- tests/ansible/templates/test-targets.j2 | 16 ++++++---------- 2 files changed, 12 insertions(+), 19 deletions(-) diff --git a/tests/ansible/hosts/default.hosts b/tests/ansible/hosts/default.hosts index 077865b0..f16a4427 100644 --- a/tests/ansible/hosts/default.hosts +++ b/tests/ansible/hosts/default.hosts @@ -43,12 +43,9 @@ ansible_host=localhost ansible_user="{{ lookup('pipe', 'whoami') }}" [tt_targets_inventory] -tt-host-key-checking ansible_host_key_checking="{{ 'false' | trim }}" ansible_password=has_sudo_nopw_password ansible_user=mitogen__has_sudo_nopw -tt-password ansible_password="{{ 'has_sudo_nopw_password' | trim }}" ansible_user=mitogen__has_sudo_nopw -tt-port ansible_password=has_sudo_nopw_password ansible_port="{{ 22 | int }}" ansible_user=mitogen__has_sudo_nopw -tt-private-key-file ansible_private_key_file="{{ git_basedir }}/tests/data/docker/mitogen__has_sudo_pubkey.key" ansible_user=mitogen__has_sudo_pubkey -tt-remote-user ansible_password=has_sudo_nopw_password ansible_user="{{ 'mitogen__has_sudo_nopw' | trim }}" -tt-ssh-executable ansible_password=has_sudo_nopw_password ansible_ssh_executable="{{ 'ssh' | trim }}" ansible_user=mitogen__has_sudo_nopw - -[tt_targets_inventory:vars] -ansible_host=localhost +tt-host-key-checking ansible_host=localhost ansible_host_key_checking="{{ 'false' | trim }}" ansible_password=has_sudo_nopw_password ansible_user=mitogen__has_sudo_nopw +tt-password ansible_host=localhost ansible_password="{{ 'has_sudo_nopw_password' | trim }}" ansible_user=mitogen__has_sudo_nopw +tt-port ansible_host=localhost ansible_password=has_sudo_nopw_password ansible_port="{{ 22 | int }}" ansible_user=mitogen__has_sudo_nopw +tt-private-key-file ansible_host=localhost ansible_private_key_file="{{ git_basedir }}/tests/data/docker/mitogen__has_sudo_pubkey.key" ansible_user=mitogen__has_sudo_pubkey +tt-remote-user ansible_host=localhost ansible_password=has_sudo_nopw_password ansible_user="{{ 'mitogen__has_sudo_nopw' | trim }}" +tt-ssh-executable ansible_host=localhost ansible_password=has_sudo_nopw_password ansible_ssh_executable="{{ 'ssh' | trim }}" ansible_user=mitogen__has_sudo_nopw diff --git a/tests/ansible/templates/test-targets.j2 b/tests/ansible/templates/test-targets.j2 index c829a6f6..2df20613 100644 --- a/tests/ansible/templates/test-targets.j2 +++ b/tests/ansible/templates/test-targets.j2 @@ -71,13 +71,9 @@ ansible_python_interpreter={{ tt.python_path }} ansible_user=mitogen__has_sudo_nopw [tt_targets_inventory] -tt-host-key-checking ansible_host_key_checking="{{ '{{' }} 'false' | trim {{ '}}' }}" ansible_password=has_sudo_nopw_password ansible_port={{ tt.port }} ansible_user=mitogen__has_sudo_nopw -tt-password ansible_password="{{ '{{' }} 'has_sudo_nopw_password' | trim {{ '}}' }}" ansible_port={{ tt.port }} ansible_user=mitogen__has_sudo_nopw -tt-port ansible_password=has_sudo_nopw_password ansible_port="{{ '{{' }} {{ tt.port }} | int {{ '}}' }}" ansible_user=mitogen__has_sudo_nopw -tt-private-key-file ansible_port={{ tt.port }} ansible_private_key_file="{{ '{{' }} git_basedir {{ '}}' }}/tests/data/docker/mitogen__has_sudo_pubkey.key" ansible_user=mitogen__has_sudo_pubkey -tt-remote-user ansible_password=has_sudo_nopw_password ansible_port={{ tt.port }} ansible_user="{{ '{{' }} 'mitogen__has_sudo_nopw' | trim {{ '}}' }}" -tt-ssh-executable ansible_password=has_sudo_nopw_password ansible_port={{ tt.port }} ansible_ssh_executable="{{ '{{' }} 'ssh' | trim {{ '}}' }}" ansible_user=mitogen__has_sudo_nopw - -[tt_targets_inventory:vars] -ansible_host={{ tt.hostname }} -ansible_python_interpreter={{ tt.python_path }} +tt-host-key-checking ansible_host={{ tt.hostname }} ansible_host_key_checking="{{ '{{' }} 'false' | trim {{ '}}' }}" ansible_password=has_sudo_nopw_password ansible_port={{ tt.port }} ansible_python_interpreter={{ tt.python_path }} ansible_user=mitogen__has_sudo_nopw +tt-password ansible_host={{ tt.hostname }} ansible_password="{{ '{{' }} 'has_sudo_nopw_password' | trim {{ '}}' }}" ansible_port={{ tt.port }} ansible_python_interpreter={{ tt.python_path }} ansible_user=mitogen__has_sudo_nopw +tt-port ansible_host={{ tt.hostname }} ansible_password=has_sudo_nopw_password ansible_port="{{ '{{' }} {{ tt.port }} | int {{ '}}' }}" ansible_python_interpreter={{ tt.python_path }} ansible_user=mitogen__has_sudo_nopw +tt-private-key-file ansible_host={{ tt.hostname }} ansible_port={{ tt.port }} ansible_private_key_file="{{ '{{' }} git_basedir {{ '}}' }}/tests/data/docker/mitogen__has_sudo_pubkey.key" ansible_python_interpreter={{ tt.python_path }} ansible_user=mitogen__has_sudo_pubkey +tt-remote-user ansible_host={{ tt.hostname }} ansible_password=has_sudo_nopw_password ansible_port={{ tt.port }} ansible_python_interpreter={{ tt.python_path }} ansible_user="{{ '{{' }} 'mitogen__has_sudo_nopw' | trim {{ '}}' }}" +tt-ssh-executable ansible_host={{ tt.hostname }} ansible_password=has_sudo_nopw_password ansible_port={{ tt.port }} ansible_python_interpreter={{ tt.python_path }} ansible_ssh_executable="{{ '{{' }} 'ssh' | trim {{ '}}' }}" ansible_user=mitogen__has_sudo_nopw From f50a61f9810b3d5a015a3c59d50fd7f3db4b7b24 Mon Sep 17 00:00:00 2001 From: Alex Willmer Date: Thu, 7 Nov 2024 10:39:37 +0000 Subject: [PATCH 08/11] ansible_mitogen: Templated host option (e.g. ansible_host, ansible_ssh_host) A twist - for the connection option "host" the corresponding legacy PlayContext attribute is PlayContext.remote_addr. This may be the only case where a connection option name and the PlayContext attribute name differ. --- ansible_mitogen/transport_config.py | 18 +++++++++++------- tests/ansible/hosts/default.hosts | 4 +--- .../integration/ssh/args_by_play_taskvar.yml | 1 + .../ssh/templated_by_play_keyword.yml | 1 + .../ssh/templated_by_play_taskvar.yml | 2 ++ .../ssh/templated_by_task_keyword.yml | 2 ++ tests/ansible/templates/test-targets.j2 | 2 +- 7 files changed, 19 insertions(+), 11 deletions(-) diff --git a/ansible_mitogen/transport_config.py b/ansible_mitogen/transport_config.py index 650355ff..e4de34f1 100644 --- a/ansible_mitogen/transport_config.py +++ b/ansible_mitogen/transport_config.py @@ -442,18 +442,22 @@ class PlayContextSpec(Spec): raise LOG.info( - 'Used PlayContext fallback for plugin=%r, option=%r', - self._connection, name, + 'Used fallback=PlayContext.%s for plugin=%r, option=%r', + name, self._connection, name, ) return getattr(self._play_context, name) - - def _connection_option(self, name): + def _connection_option(self, name, fallback_attr=None): try: return self._connection.get_option(name, hostvars=self._task_vars) except KeyError: - LOG.debug('Used PlayContext fallback for option=%r', name) - return getattr(self._play_context, name) + if fallback_attr is None: + fallback_attr = name + LOG.info( + 'Used fallback=PlayContext.%s for plugin=%r, option=%r', + fallback_attr, self._connection, name, + ) + return getattr(self._play_context, fallback_attr) def transport(self): return self._transport @@ -462,7 +466,7 @@ class PlayContextSpec(Spec): return self._inventory_name def remote_addr(self): - return self._play_context.remote_addr + return self._connection_option('host', fallback_attr='remote_addr') def remote_user(self): return self._connection_option('remote_user') diff --git a/tests/ansible/hosts/default.hosts b/tests/ansible/hosts/default.hosts index f16a4427..6bb21fc6 100644 --- a/tests/ansible/hosts/default.hosts +++ b/tests/ansible/hosts/default.hosts @@ -22,9 +22,6 @@ ssh_args_canary_file=/tmp/ssh_args_by_inv_{{ inventory_hostname }} [tt_targets_bare] tt-bare -[tt_targets_bare:vars] -ansible_host=localhost - [tt_become_bare] tt-become-bare @@ -43,6 +40,7 @@ ansible_host=localhost ansible_user="{{ lookup('pipe', 'whoami') }}" [tt_targets_inventory] +tt-host ansible_host="{{ 'localhost' | trim }}" ansible_password=has_sudo_nopw_password ansible_user=mitogen__has_sudo_nopw tt-host-key-checking ansible_host=localhost ansible_host_key_checking="{{ 'false' | trim }}" ansible_password=has_sudo_nopw_password ansible_user=mitogen__has_sudo_nopw tt-password ansible_host=localhost ansible_password="{{ 'has_sudo_nopw_password' | trim }}" ansible_user=mitogen__has_sudo_nopw tt-port ansible_host=localhost ansible_password=has_sudo_nopw_password ansible_port="{{ 22 | int }}" ansible_user=mitogen__has_sudo_nopw diff --git a/tests/ansible/integration/ssh/args_by_play_taskvar.yml b/tests/ansible/integration/ssh/args_by_play_taskvar.yml index 5ae83f2a..073265b2 100644 --- a/tests/ansible/integration/ssh/args_by_play_taskvar.yml +++ b/tests/ansible/integration/ssh/args_by_play_taskvar.yml @@ -2,6 +2,7 @@ hosts: tt_targets_bare gather_facts: false vars: + ansible_host: "{{ hostvars[groups['test-targets'][0]].host | default('localhost') }}" ansible_password: "{{ 'has_sudo_nopw_password' | trim }}" ansible_port: "{{ hostvars[groups['test-targets'][0]].ansible_port | default(22) }}" ansible_ssh_common_args: >- diff --git a/tests/ansible/integration/ssh/templated_by_play_keyword.yml b/tests/ansible/integration/ssh/templated_by_play_keyword.yml index e66cc5f3..c6ff1674 100644 --- a/tests/ansible/integration/ssh/templated_by_play_keyword.yml +++ b/tests/ansible/integration/ssh/templated_by_play_keyword.yml @@ -3,6 +3,7 @@ gather_facts: false remote_user: "{{ 'mitogen__has_sudo_nopw' | trim }}" vars: + ansible_host: "{{ hostvars[groups['test-targets'][0]].host | default('localhost') }}" ansible_password: has_sudo_nopw_password ansible_port: "{{ hostvars[groups['test-targets'][0]].ansible_port | default(22) }}" tasks: diff --git a/tests/ansible/integration/ssh/templated_by_play_taskvar.yml b/tests/ansible/integration/ssh/templated_by_play_taskvar.yml index d3ae6117..151aa614 100644 --- a/tests/ansible/integration/ssh/templated_by_play_taskvar.yml +++ b/tests/ansible/integration/ssh/templated_by_play_taskvar.yml @@ -2,6 +2,7 @@ hosts: tt_targets_bare gather_facts: false vars: + ansible_host: "{{ hostvars[groups['test-targets'][0]].host | default('localhost') }}" ansible_password: "{{ 'has_sudo_nopw_password' | trim }}" ansible_port: "{{ hostvars[groups['test-targets'][0]].ansible_port | default(22) }}" ansible_ssh_executable: "{{ 'ssh' | trim }}" @@ -16,6 +17,7 @@ hosts: tt_targets_bare gather_facts: false vars: + ansible_host: "{{ hostvars[groups['test-targets'][0]].host | default('localhost') }}" ansible_private_key_file: "{{ git_basedir }}/tests/data/docker/mitogen__has_sudo_pubkey.key" ansible_port: "{{ hostvars[groups['test-targets'][0]].ansible_port | default(22) }}" ansible_ssh_executable: "{{ 'ssh' | trim }}" diff --git a/tests/ansible/integration/ssh/templated_by_task_keyword.yml b/tests/ansible/integration/ssh/templated_by_task_keyword.yml index df956af5..dc16205a 100644 --- a/tests/ansible/integration/ssh/templated_by_task_keyword.yml +++ b/tests/ansible/integration/ssh/templated_by_task_keyword.yml @@ -5,6 +5,7 @@ # https://github.com/mitogen-hq/mitogen/issues/1132 remote_user: "{{ 'mitogen__has_sudo_nopw' | trim }}" vars: + ansible_host: "{{ hostvars[groups['test-targets'][0]].host | default('localhost') }}" ansible_password: has_sudo_nopw_password ansible_port: "{{ hostvars[groups['test-targets'][0]].ansible_port | default(22) }}" tasks: @@ -19,6 +20,7 @@ delegate_to: "{{ groups.tt_targets_bare[0] }}" remote_user: "{{ 'mitogen__has_sudo_nopw' | trim }}" vars: + ansible_host: "{{ hostvars[groups['test-targets'][0]].host | default('localhost') }}" ansible_password: has_sudo_nopw_password ansible_port: "{{ hostvars[groups['test-targets'][0]].ansible_port | default(22) }}" ping: diff --git a/tests/ansible/templates/test-targets.j2 b/tests/ansible/templates/test-targets.j2 index 2df20613..cebf7067 100644 --- a/tests/ansible/templates/test-targets.j2 +++ b/tests/ansible/templates/test-targets.j2 @@ -44,7 +44,6 @@ ssh_args_canary_file=/tmp/ssh_args_by_inv_{{ '{{' }} inventory_hostname {{ '}}' tt-bare [tt_targets_bare:vars] -ansible_host={{ tt.hostname }} ansible_python_interpreter={{ tt.python_path }} [tt_become_bare] @@ -71,6 +70,7 @@ ansible_python_interpreter={{ tt.python_path }} ansible_user=mitogen__has_sudo_nopw [tt_targets_inventory] +tt-host ansible_host="{{ '{{' }} '{{ tt.hostname }}' | trim {{ '}}' }}" ansible_password=has_sudo_nopw_password ansible_port={{ tt.port }} ansible_python_interpreter={{ tt.python_path }} ansible_user=mitogen__has_sudo_nopw tt-host-key-checking ansible_host={{ tt.hostname }} ansible_host_key_checking="{{ '{{' }} 'false' | trim {{ '}}' }}" ansible_password=has_sudo_nopw_password ansible_port={{ tt.port }} ansible_python_interpreter={{ tt.python_path }} ansible_user=mitogen__has_sudo_nopw tt-password ansible_host={{ tt.hostname }} ansible_password="{{ '{{' }} 'has_sudo_nopw_password' | trim {{ '}}' }}" ansible_port={{ tt.port }} ansible_python_interpreter={{ tt.python_path }} ansible_user=mitogen__has_sudo_nopw tt-port ansible_host={{ tt.hostname }} ansible_password=has_sudo_nopw_password ansible_port="{{ '{{' }} {{ tt.port }} | int {{ '}}' }}" ansible_python_interpreter={{ tt.python_path }} ansible_user=mitogen__has_sudo_nopw From 5ae5bb94ac0807b99280a0760c4a921fcff873eb Mon Sep 17 00:00:00 2001 From: Alex Willmer Date: Thu, 7 Nov 2024 12:21:10 +0000 Subject: [PATCH 09/11] docs: Changelog entry for templated ansible_host --- docs/changelog.rst | 2 ++ 1 file changed, 2 insertions(+) diff --git a/docs/changelog.rst b/docs/changelog.rst index 88ad6bb1..449e8d03 100644 --- a/docs/changelog.rst +++ b/docs/changelog.rst @@ -27,6 +27,8 @@ In progress (unreleased) (e.g. ``ansible_private_key_file``). * :gh:issue:`1083` :mod:`ansible_mitogen`: Templated SSH host key checking (e.g. ``ansible_host_key_checking``, ``ansible_ssh_host_key_checking``). +* :gh:issue:`1083` :mod:`ansible_mitogen`: Templated host address + (e.g. ``ansible_host``, ``ansible_ssh_host``) v0.3.16 (2024-11-05) From 905b87b71aa415f7dfbf8e7905a0f4ced691dbaa Mon Sep 17 00:00:00 2001 From: Alex Willmer Date: Thu, 7 Nov 2024 12:25:22 +0000 Subject: [PATCH 10/11] tests: Test templated ansible_host_key_checking provided by task vars missed by #1184 --- docs/changelog.rst | 1 + tests/ansible/integration/ssh/templated_by_play_taskvar.yml | 2 ++ 2 files changed, 3 insertions(+) diff --git a/docs/changelog.rst b/docs/changelog.rst index 449e8d03..ddcc24c9 100644 --- a/docs/changelog.rst +++ b/docs/changelog.rst @@ -29,6 +29,7 @@ In progress (unreleased) (e.g. ``ansible_host_key_checking``, ``ansible_ssh_host_key_checking``). * :gh:issue:`1083` :mod:`ansible_mitogen`: Templated host address (e.g. ``ansible_host``, ``ansible_ssh_host``) +* :gh:issue:`1184` Test templated SSH host key checking in task vars v0.3.16 (2024-11-05) diff --git a/tests/ansible/integration/ssh/templated_by_play_taskvar.yml b/tests/ansible/integration/ssh/templated_by_play_taskvar.yml index 151aa614..4d7e318e 100644 --- a/tests/ansible/integration/ssh/templated_by_play_taskvar.yml +++ b/tests/ansible/integration/ssh/templated_by_play_taskvar.yml @@ -3,6 +3,7 @@ gather_facts: false vars: ansible_host: "{{ hostvars[groups['test-targets'][0]].host | default('localhost') }}" + ansible_host_key_checking: "{{ 'false' | trim }}" ansible_password: "{{ 'has_sudo_nopw_password' | trim }}" ansible_port: "{{ hostvars[groups['test-targets'][0]].ansible_port | default(22) }}" ansible_ssh_executable: "{{ 'ssh' | trim }}" @@ -18,6 +19,7 @@ gather_facts: false vars: ansible_host: "{{ hostvars[groups['test-targets'][0]].host | default('localhost') }}" + ansible_host_key_checking: "{{ 'false' | trim }}" ansible_private_key_file: "{{ git_basedir }}/tests/data/docker/mitogen__has_sudo_pubkey.key" ansible_port: "{{ hostvars[groups['test-targets'][0]].ansible_port | default(22) }}" ansible_ssh_executable: "{{ 'ssh' | trim }}" From 6cf6f69751e4533eb4f77d2e277c5989571357a5 Mon Sep 17 00:00:00 2001 From: Alex Willmer Date: Thu, 7 Nov 2024 12:27:56 +0000 Subject: [PATCH 11/11] Prepare v0.3.17 --- docs/changelog.rst | 4 ++-- mitogen/__init__.py | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/docs/changelog.rst b/docs/changelog.rst index ddcc24c9..0dede63a 100644 --- a/docs/changelog.rst +++ b/docs/changelog.rst @@ -18,8 +18,8 @@ To avail of fixes in an unreleased version, please download a ZIP file `directly from GitHub `_. -In progress (unreleased) ------------------------- +v0.3.17 (2024-11-07) +-------------------- * :gh:issue:`1182` CI: Fix incorrect world readable/writable file permissions on SSH key ``mitogen__has_sudo_pubkey.key`` during Ansible tests. diff --git a/mitogen/__init__.py b/mitogen/__init__.py index 40b6850e..cbc58655 100644 --- a/mitogen/__init__.py +++ b/mitogen/__init__.py @@ -35,7 +35,7 @@ be expected. On the slave, it is built dynamically during startup. #: Library version as a tuple. -__version__ = (0, 3, 17, 'dev') +__version__ = (0, 3, 17) #: This is :data:`False` in slave contexts. Previously it was used to prevent