summaryrefslogtreecommitdiffstats
path: root/ansible_collections/community/hrobot
diff options
context:
space:
mode:
authorDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-18 05:52:22 +0000
committerDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-18 05:52:22 +0000
commit38b7c80217c4e72b1d8988eb1e60bb6e77334114 (patch)
tree356e9fd3762877d07cde52d21e77070aeff7e789 /ansible_collections/community/hrobot
parentAdding upstream version 7.7.0+dfsg. (diff)
downloadansible-38b7c80217c4e72b1d8988eb1e60bb6e77334114.tar.xz
ansible-38b7c80217c4e72b1d8988eb1e60bb6e77334114.zip
Adding upstream version 9.4.0+dfsg.upstream/9.4.0+dfsg
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'ansible_collections/community/hrobot')
-rw-r--r--ansible_collections/community/hrobot/.github/workflows/ansible-test.yml4
-rw-r--r--ansible_collections/community/hrobot/.github/workflows/ee.yml100
-rw-r--r--ansible_collections/community/hrobot/.github/workflows/extra-tests.yml6
-rw-r--r--ansible_collections/community/hrobot/.github/workflows/import-galaxy.yml78
-rw-r--r--ansible_collections/community/hrobot/.github/workflows/reuse.yml11
-rw-r--r--ansible_collections/community/hrobot/CHANGELOG.md358
-rw-r--r--ansible_collections/community/hrobot/CHANGELOG.md.license3
-rw-r--r--ansible_collections/community/hrobot/CHANGELOG.rst66
-rw-r--r--ansible_collections/community/hrobot/FILES.json100
-rw-r--r--ansible_collections/community/hrobot/MANIFEST.json4
-rw-r--r--ansible_collections/community/hrobot/README.md6
-rw-r--r--ansible_collections/community/hrobot/changelogs/changelog.yaml70
-rw-r--r--ansible_collections/community/hrobot/changelogs/config.yaml3
-rw-r--r--ansible_collections/community/hrobot/plugins/inventory/robot.py27
-rw-r--r--ansible_collections/community/hrobot/plugins/module_utils/robot.py37
-rw-r--r--ansible_collections/community/hrobot/plugins/modules/boot.py44
-rw-r--r--ansible_collections/community/hrobot/plugins/modules/failover_ip.py8
-rw-r--r--ansible_collections/community/hrobot/plugins/modules/failover_ip_info.py4
-rw-r--r--ansible_collections/community/hrobot/plugins/modules/firewall.py46
-rw-r--r--ansible_collections/community/hrobot/plugins/modules/firewall_info.py20
-rw-r--r--ansible_collections/community/hrobot/plugins/modules/reset.py8
-rw-r--r--ansible_collections/community/hrobot/plugins/modules/reverse_dns.py6
-rw-r--r--ansible_collections/community/hrobot/plugins/modules/server.py2
-rw-r--r--ansible_collections/community/hrobot/plugins/modules/server_info.py24
-rw-r--r--ansible_collections/community/hrobot/plugins/modules/ssh_key.py16
-rw-r--r--ansible_collections/community/hrobot/plugins/modules/v_switch.py6
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.json5
-rwxr-xr-xansible_collections/community/hrobot/tests/sanity/extra/extra-docs.py11
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.16.txt1
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.16.txt.license3
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.17.txt1
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.17.txt.license3
-rw-r--r--ansible_collections/community/hrobot/tests/unit/plugins/inventory/test_robot.py62
-rw-r--r--ansible_collections/community/hrobot/tests/unit/plugins/module_utils/test_failover.py45
-rw-r--r--ansible_collections/community/hrobot/tests/unit/plugins/module_utils/test_robot.py80
-rw-r--r--ansible_collections/community/hrobot/tests/unit/requirements.yml (renamed from ansible_collections/community/hrobot/tests/requirements.yml)2
36 files changed, 994 insertions, 276 deletions
diff --git a/ansible_collections/community/hrobot/.github/workflows/ansible-test.yml b/ansible_collections/community/hrobot/.github/workflows/ansible-test.yml
index 10a685f4c..1e66b7d29 100644
--- a/ansible_collections/community/hrobot/.github/workflows/ansible-test.yml
+++ b/ansible_collections/community/hrobot/.github/workflows/ansible-test.yml
@@ -32,6 +32,8 @@ jobs:
- stable-2.12
- stable-2.13
- stable-2.14
+ - stable-2.15
+ - stable-2.16
- devel
# Ansible-test on various stable branches does not yet work well with cgroups v2.
# Since ubuntu-latest now uses Ubuntu 22.04, we need to fall back to the ubuntu-20.04
@@ -71,6 +73,8 @@ jobs:
- stable-2.12
- stable-2.13
- stable-2.14
+ - stable-2.15
+ - stable-2.16
- devel
steps:
diff --git a/ansible_collections/community/hrobot/.github/workflows/ee.yml b/ansible_collections/community/hrobot/.github/workflows/ee.yml
index 04787e8ed..c4e751a79 100644
--- a/ansible_collections/community/hrobot/.github/workflows/ee.yml
+++ b/ansible_collections/community/hrobot/.github/workflows/ee.yml
@@ -22,25 +22,73 @@ env:
jobs:
build:
- name: Build and test EE (Ⓐ${{ matrix.runner_tag }})
+ name: Build and test EE (${{ matrix.name }})
strategy:
+ fail-fast: false
matrix:
- runner_tag:
- - devel
- - stable-2.12-latest
- - stable-2.11-latest
- - stable-2.9-latest
+ name:
+ - ''
+ ansible_core:
+ - ''
+ ansible_runner:
+ - ''
+ base_image:
+ - ''
+ pre_base:
+ - ''
+ extra_vars:
+ - ''
+ other_deps:
+ - ''
+ exclude:
+ - ansible_core: ''
+ include:
+ - name: ansible-core devel @ RHEL UBI 9
+ ansible_core: https://github.com/ansible/ansible/archive/devel.tar.gz
+ ansible_runner: ansible-runner
+ other_deps: |2
+ python_interpreter:
+ package_system: python3.11 python3.11-pip python3.11-wheel python3.11-cryptography
+ python_path: "/usr/bin/python3.11"
+ base_image: docker.io/redhat/ubi9:latest
+ pre_base: '"#"'
+ - name: ansible-core 2.15 @ Rocky Linux 9
+ ansible_core: https://github.com/ansible/ansible/archive/stable-2.15.tar.gz
+ ansible_runner: ansible-runner
+ base_image: quay.io/rockylinux/rockylinux:9
+ pre_base: '"#"'
+ - name: ansible-core 2.14 @ CentOS Stream 9
+ ansible_core: https://github.com/ansible/ansible/archive/stable-2.14.tar.gz
+ ansible_runner: ansible-runner
+ base_image: quay.io/centos/centos:stream9
+ pre_base: '"#"'
+ - name: ansible-core 2.13 @ RHEL UBI 8
+ ansible_core: https://github.com/ansible/ansible/archive/stable-2.13.tar.gz
+ ansible_runner: ansible-runner
+ other_deps: |2
+ python_interpreter:
+ package_system: python39 python39-pip python39-wheel python39-cryptography
+ base_image: docker.io/redhat/ubi8:latest
+ pre_base: '"#"'
+ - name: ansible-core 2.12 @ CentOS Stream 8
+ ansible_core: https://github.com/ansible/ansible/archive/stable-2.12.tar.gz
+ ansible_runner: ansible-runner
+ other_deps: |2
+ python_interpreter:
+ package_system: python39 python39-pip python39-wheel python39-cryptography
+ base_image: quay.io/centos/centos:stream8
+ pre_base: '"#"'
runs-on: ubuntu-latest
steps:
- name: Check out code
- uses: actions/checkout@v3
+ uses: actions/checkout@v4
with:
path: ansible_collections/${{ env.NAMESPACE }}/${{ env.COLLECTION_NAME }}
- name: Set up Python
- uses: actions/setup-python@v4
+ uses: actions/setup-python@v5
with:
- python-version: '3.10'
+ python-version: '3.11'
- name: Install ansible-builder and ansible-navigator
run: pip install ansible-builder ansible-navigator
@@ -74,11 +122,26 @@ jobs:
# EE config
cat > execution-environment.yml <<EOF
---
- version: 1
- build_arg_defaults:
- EE_BASE_IMAGE: 'quay.io/ansible/ansible-runner:${{ matrix.runner_tag }}'
+ version: 3
dependencies:
+ ansible_core:
+ package_pip: ${{ matrix.ansible_core }}
+ ansible_runner:
+ package_pip: ${{ matrix.ansible_runner }}
galaxy: requirements.yml
+ ${{ matrix.other_deps }}
+
+ images:
+ base_image:
+ name: ${{ matrix.base_image }}
+
+ additional_build_files:
+ - src: ${COLLECTION_FILENAME}
+ dest: src
+
+ additional_build_steps:
+ prepend_base:
+ - ${{ matrix.pre_base }}
EOF
echo "::group::execution-environment.yml"
cat execution-environment.yml
@@ -88,26 +151,29 @@ jobs:
cat > requirements.yml <<EOF
---
collections:
- - name: ${COLLECTION_FILENAME}
+ - name: src/${COLLECTION_FILENAME}
type: file
EOF
echo "::group::requirements.yml"
cat requirements.yml
echo "::endgroup::"
- - name: Build image based on ${{ matrix.runner_tag }}
+ - name: Build image based on ${{ matrix.base_image }}
run: |
- mkdir -p context/_build/
- cp "${{ env.NAMESPACE }}-${{ env.COLLECTION_NAME }}"-*.tar.gz context/_build/
- ansible-builder build -v 3 -t test-ee:latest --container-runtime=podman
+ ansible-builder build --verbosity 3 --tag test-ee:latest --container-runtime docker
+
+ - name: Show images
+ run: docker image ls
- name: Run basic tests
run: >
ansible-navigator run
--mode stdout
+ --container-engine docker
--pull-policy never
--set-environment-variable ANSIBLE_PRIVATE_ROLE_VARS=true
--execution-environment-image test-ee:latest
-v
all.yml
+ ${{ matrix.extra_vars }}
working-directory: ansible_collections/${{ env.NAMESPACE }}/${{ env.COLLECTION_NAME }}/tests/ee
diff --git a/ansible_collections/community/hrobot/.github/workflows/extra-tests.yml b/ansible_collections/community/hrobot/.github/workflows/extra-tests.yml
index e00d93822..ee8964c3f 100644
--- a/ansible_collections/community/hrobot/.github/workflows/extra-tests.yml
+++ b/ansible_collections/community/hrobot/.github/workflows/extra-tests.yml
@@ -26,14 +26,14 @@ jobs:
steps:
- name: Check out code
- uses: actions/checkout@v3
+ uses: actions/checkout@v4
with:
path: ansible_collections/${{env.NAMESPACE}}/${{env.COLLECTION_NAME}}
- name: Set up Python
- uses: actions/setup-python@v4
+ uses: actions/setup-python@v5
with:
- python-version: '3.10'
+ python-version: '3.11'
- name: Install ansible-core
run: pip install https://github.com/ansible/ansible/archive/devel.tar.gz --disable-pip-version-check
diff --git a/ansible_collections/community/hrobot/.github/workflows/import-galaxy.yml b/ansible_collections/community/hrobot/.github/workflows/import-galaxy.yml
index 8a5d43177..0c0ee402a 100644
--- a/ansible_collections/community/hrobot/.github/workflows/import-galaxy.yml
+++ b/ansible_collections/community/hrobot/.github/workflows/import-galaxy.yml
@@ -4,7 +4,7 @@
# SPDX-License-Identifier: GPL-3.0-or-later
name: import-galaxy
-on:
+'on':
# Run CI against all pushes (direct commits, also merged PRs) to main, and all Pull Requests
push:
branches:
@@ -12,77 +12,9 @@ on:
- stable-*
pull_request:
-env:
- # Adjust this to your collection
- NAMESPACE: community
- COLLECTION_NAME: hrobot
-
jobs:
- build-collection:
- name: Build collection artifact
- runs-on: ubuntu-latest
- steps:
- - name: Check out code
- uses: actions/checkout@v3
- with:
- path: ./checkout
-
- - name: Set up Python
- uses: actions/setup-python@v4
- with:
- python-version: '3.10'
-
- - name: Install ansible-core
- run: pip install https://github.com/ansible/ansible/archive/devel.tar.gz --disable-pip-version-check
-
- - name: Make sure galaxy.yml has version entry
- run: >-
- python -c
- 'import yaml ;
- f = open("galaxy.yml", "rb") ;
- data = yaml.safe_load(f) ;
- f.close() ;
- data["version"] = data.get("version") or "0.0.1" ;
- f = open("galaxy.yml", "wb") ;
- f.write(yaml.dump(data).encode("utf-8")) ;
- f.close() ;
- '
- working-directory: ./checkout
-
- - name: Build collection
- run: ansible-galaxy collection build
- working-directory: ./checkout
-
- - name: Copy artifact into subdirectory
- run: mkdir ./artifact && mv ./checkout/${{ env.NAMESPACE }}-${{ env.COLLECTION_NAME }}-*.tar.gz ./artifact
-
- - name: Upload artifact
- uses: actions/upload-artifact@v3
- with:
- name: ${{ env.NAMESPACE }}-${{ env.COLLECTION_NAME }}-${{ github.sha }}
- path: ./artifact/
-
import-galaxy:
- name: Import artifact with Galaxy importer
- runs-on: ubuntu-latest
- needs:
- - build-collection
- steps:
- - name: Set up Python
- uses: actions/setup-python@v4
- with:
- python-version: '3.10'
-
- - name: Install ansible-core
- run: pip install https://github.com/ansible/ansible/archive/devel.tar.gz --disable-pip-version-check
-
- - name: Install galaxy-importer
- run: pip install galaxy-importer --disable-pip-version-check
-
- - name: Download artifact
- uses: actions/download-artifact@v3
- with:
- name: ${{ env.NAMESPACE }}-${{ env.COLLECTION_NAME }}-${{ github.sha }}
-
- - name: Run Galaxy importer
- run: python -m galaxy_importer.main ${{ env.NAMESPACE }}-${{ env.COLLECTION_NAME }}-*.tar.gz
+ permissions:
+ contents: read
+ name: Test to import built collection artifact with Galaxy importer
+ uses: ansible-community/github-action-test-galaxy-import/.github/workflows/test-galaxy-import.yml@main
diff --git a/ansible_collections/community/hrobot/.github/workflows/reuse.yml b/ansible_collections/community/hrobot/.github/workflows/reuse.yml
index 06a3fa455..51d9ac2fb 100644
--- a/ansible_collections/community/hrobot/.github/workflows/reuse.yml
+++ b/ansible_collections/community/hrobot/.github/workflows/reuse.yml
@@ -21,12 +21,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- - uses: actions/checkout@v3
+ - uses: actions/checkout@v4
- - name: Install dependencies
- run: |
- pip install reuse
-
- - name: Check REUSE compliance
- run: |
- reuse lint
+ - name: REUSE Compliance Check
+ uses: fsfe/reuse-action@v3
diff --git a/ansible_collections/community/hrobot/CHANGELOG.md b/ansible_collections/community/hrobot/CHANGELOG.md
new file mode 100644
index 000000000..d09d85be0
--- /dev/null
+++ b/ansible_collections/community/hrobot/CHANGELOG.md
@@ -0,0 +1,358 @@
+# Community Hetzner Robot Collection Release Notes
+
+**Topics**
+
+- <a href="#v1-9-1">v1\.9\.1</a>
+ - <a href="#release-summary">Release Summary</a>
+ - <a href="#security-fixes">Security Fixes</a>
+- <a href="#v1-9-0">v1\.9\.0</a>
+ - <a href="#release-summary-1">Release Summary</a>
+ - <a href="#minor-changes">Minor Changes</a>
+ - <a href="#deprecated-features">Deprecated Features</a>
+- <a href="#v1-8-2">v1\.8\.2</a>
+ - <a href="#release-summary-2">Release Summary</a>
+ - <a href="#bugfixes">Bugfixes</a>
+- <a href="#v1-8-1">v1\.8\.1</a>
+ - <a href="#release-summary-3">Release Summary</a>
+ - <a href="#known-issues">Known Issues</a>
+- <a href="#v1-8-0">v1\.8\.0</a>
+ - <a href="#release-summary-4">Release Summary</a>
+ - <a href="#major-changes">Major Changes</a>
+ - <a href="#minor-changes-1">Minor Changes</a>
+- <a href="#v1-7-0">v1\.7\.0</a>
+ - <a href="#release-summary-5">Release Summary</a>
+ - <a href="#new-modules">New Modules</a>
+- <a href="#v1-6-0">v1\.6\.0</a>
+ - <a href="#release-summary-6">Release Summary</a>
+ - <a href="#minor-changes-2">Minor Changes</a>
+- <a href="#v1-5-2">v1\.5\.2</a>
+ - <a href="#release-summary-7">Release Summary</a>
+ - <a href="#minor-changes-3">Minor Changes</a>
+- <a href="#v1-5-1">v1\.5\.1</a>
+ - <a href="#release-summary-8">Release Summary</a>
+- <a href="#v1-5-0">v1\.5\.0</a>
+ - <a href="#release-summary-9">Release Summary</a>
+ - <a href="#minor-changes-4">Minor Changes</a>
+- <a href="#v1-4-0">v1\.4\.0</a>
+ - <a href="#release-summary-10">Release Summary</a>
+ - <a href="#minor-changes-5">Minor Changes</a>
+- <a href="#v1-3-1">v1\.3\.1</a>
+ - <a href="#release-summary-11">Release Summary</a>
+ - <a href="#bugfixes-1">Bugfixes</a>
+- <a href="#v1-3-0">v1\.3\.0</a>
+ - <a href="#release-summary-12">Release Summary</a>
+ - <a href="#minor-changes-6">Minor Changes</a>
+ - <a href="#bugfixes-2">Bugfixes</a>
+- <a href="#v1-2-3">v1\.2\.3</a>
+ - <a href="#release-summary-13">Release Summary</a>
+- <a href="#v1-2-2">v1\.2\.2</a>
+ - <a href="#release-summary-14">Release Summary</a>
+ - <a href="#bugfixes-3">Bugfixes</a>
+- <a href="#v1-2-1">v1\.2\.1</a>
+ - <a href="#release-summary-15">Release Summary</a>
+ - <a href="#minor-changes-7">Minor Changes</a>
+- <a href="#v1-2-0">v1\.2\.0</a>
+ - <a href="#release-summary-16">Release Summary</a>
+ - <a href="#minor-changes-8">Minor Changes</a>
+ - <a href="#new-modules-1">New Modules</a>
+- <a href="#v1-1-1">v1\.1\.1</a>
+ - <a href="#release-summary-17">Release Summary</a>
+ - <a href="#bugfixes-4">Bugfixes</a>
+- <a href="#v1-1-0">v1\.1\.0</a>
+ - <a href="#release-summary-18">Release Summary</a>
+ - <a href="#new-plugins">New Plugins</a>
+ - <a href="#inventory">Inventory</a>
+- <a href="#v1-0-0">v1\.0\.0</a>
+ - <a href="#release-summary-19">Release Summary</a>
+ - <a href="#breaking-changes--porting-guide">Breaking Changes / Porting Guide</a>
+
+<a id="v1-9-1"></a>
+## v1\.9\.1
+
+<a id="release-summary"></a>
+### Release Summary
+
+Bugfix release\.
+
+<a id="security-fixes"></a>
+### Security Fixes
+
+* robot inventory plugin \- make sure all data received from the Hetzner robot service server is marked as unsafe\, so remote code execution by obtaining texts that can be evaluated as templates is not possible \([https\://www\.die\-welt\.net/2024/03/remote\-code\-execution\-in\-ansible\-dynamic\-inventory\-plugins/](https\://www\.die\-welt\.net/2024/03/remote\-code\-execution\-in\-ansible\-dynamic\-inventory\-plugins/)\, [https\://github\.com/ansible\-collections/community\.hrobot/pull/99](https\://github\.com/ansible\-collections/community\.hrobot/pull/99)\)\.
+
+<a id="v1-9-0"></a>
+## v1\.9\.0
+
+<a id="release-summary-1"></a>
+### Release Summary
+
+Feature and maintenance release\.
+
+<a id="minor-changes"></a>
+### Minor Changes
+
+* robot inventory plugin \- the <code>filters</code> option has been renamed to <code>simple\_filters</code>\. The old name still works until community\.hrobot 2\.0\.0\. Then it will change to allow more complex filtering with the <code>community\.library\_inventory\_filtering\_v1</code> collection\'s functionality \([https\://github\.com/ansible\-collections/community\.hrobot/pull/94](https\://github\.com/ansible\-collections/community\.hrobot/pull/94)\)\.
+
+<a id="deprecated-features"></a>
+### Deprecated Features
+
+* robot inventory plugin \- the <code>filters</code> option has been renamed to <code>simple\_filters</code>\. The old name will stop working in community\.hrobot 2\.0\.0 \([https\://github\.com/ansible\-collections/community\.hrobot/pull/94](https\://github\.com/ansible\-collections/community\.hrobot/pull/94)\)\.
+
+<a id="v1-8-2"></a>
+## v1\.8\.2
+
+<a id="release-summary-2"></a>
+### Release Summary
+
+Maintenance release with updated documentation\.
+
+<a id="bugfixes"></a>
+### Bugfixes
+
+* Show more information \(if available\) from error messages \([https\://github\.com/ansible\-collections/community\.hrobot/pull/89](https\://github\.com/ansible\-collections/community\.hrobot/pull/89)\)\.
+
+<a id="v1-8-1"></a>
+## v1\.8\.1
+
+<a id="release-summary-3"></a>
+### Release Summary
+
+Maintenance release with updated documentation\.
+
+From this version on\, community\.hrobot is using the new [Ansible semantic markup](https\://docs\.ansible\.com/ansible/devel/dev\_guide/developing\_modules\_documenting\.html\#semantic\-markup\-within\-module\-documentation)
+in its documentation\. If you look at documentation with the ansible\-doc CLI tool
+from ansible\-core before 2\.15\, please note that it does not render the markup
+correctly\. You should be still able to read it in most cases\, but you need
+ansible\-core 2\.15 or later to see it as it is intended\. Alternatively you can
+look at [the devel docsite](https\://docs\.ansible\.com/ansible/devel/collections/community/hrobot/)
+for the rendered HTML version of the documentation of the latest release\.
+
+<a id="known-issues"></a>
+### Known Issues
+
+* Ansible markup will show up in raw form on ansible\-doc text output for ansible\-core before 2\.15\. If you have trouble deciphering the documentation markup\, please upgrade to ansible\-core 2\.15 \(or newer\)\, or read the HTML documentation on [https\://docs\.ansible\.com/ansible/devel/collections/community/hrobot/](https\://docs\.ansible\.com/ansible/devel/collections/community/hrobot/)\.
+
+<a id="v1-8-0"></a>
+## v1\.8\.0
+
+<a id="release-summary-4"></a>
+### Release Summary
+
+Feature release for the Hetzner firewall changes\.
+
+<a id="major-changes"></a>
+### Major Changes
+
+* firewall \- Hetzner added output rules support to the firewall\. This change unfortunately means that using old versions of the firewall module will always set the output rule list to empty\, thus disallowing the server to send out packets \([https\://github\.com/ansible\-collections/community\.hrobot/issues/75](https\://github\.com/ansible\-collections/community\.hrobot/issues/75)\, [https\://github\.com/ansible\-collections/community\.hrobot/pull/76](https\://github\.com/ansible\-collections/community\.hrobot/pull/76)\)\.
+
+<a id="minor-changes-1"></a>
+### Minor Changes
+
+* firewall\, firewall\_info \- add <code>filter\_ipv6</code> and <code>rules\.output</code> output to support the new IPv6 filtering and output rules features \([https\://github\.com/ansible\-collections/community\.hrobot/issues/75](https\://github\.com/ansible\-collections/community\.hrobot/issues/75)\, [https\://github\.com/ansible\-collections/community\.hrobot/pull/76](https\://github\.com/ansible\-collections/community\.hrobot/pull/76)\)\.
+* firewall\, firewall\_info \- add <code>server\_number</code> option that can be used instead of <code>server\_ip</code> to identify the server\. Hetzner deprecated configuring the firewall by <code>server\_ip</code>\, so using <code>server\_ip</code> will stop at some point in the future \([https\://github\.com/ansible\-collections/community\.hrobot/pull/77](https\://github\.com/ansible\-collections/community\.hrobot/pull/77)\)\.
+
+<a id="v1-7-0"></a>
+## v1\.7\.0
+
+<a id="release-summary-5"></a>
+### Release Summary
+
+Feature release\.
+
+<a id="new-modules"></a>
+### New Modules
+
+* community\.hrobot\.v\_switch \- Manage Hetzner\'s vSwitch
+
+<a id="v1-6-0"></a>
+## v1\.6\.0
+
+<a id="release-summary-6"></a>
+### Release Summary
+
+Feature release with improved documentation\.
+
+<a id="minor-changes-2"></a>
+### Minor Changes
+
+* Added a <code>community\.hrobot\.robot</code> module defaults group / action group\. Use with <code>group/community\.hrobot\.robot</code> to provide options for all Hetzner Robot modules \([https\://github\.com/ansible\-collections/community\.hrobot/pull/65](https\://github\.com/ansible\-collections/community\.hrobot/pull/65)\)\.
+
+<a id="v1-5-2"></a>
+## v1\.5\.2
+
+<a id="release-summary-7"></a>
+### Release Summary
+
+Maintenance release with a documentation improvement\.
+
+<a id="minor-changes-3"></a>
+### Minor Changes
+
+* The collection repository conforms to the [REUSE specification](https\://reuse\.software/spec/) except for the changelog fragments \([https\://github\.com/ansible\-collections/community\.hrobot/pull/60](https\://github\.com/ansible\-collections/community\.hrobot/pull/60)\)\.
+
+<a id="v1-5-1"></a>
+## v1\.5\.1
+
+<a id="release-summary-8"></a>
+### Release Summary
+
+Maintenance release with small documentation fixes\.
+
+<a id="v1-5-0"></a>
+## v1\.5\.0
+
+<a id="release-summary-9"></a>
+### Release Summary
+
+Maintenance release changing the way licenses are declared\. No functional changes\.
+
+<a id="minor-changes-4"></a>
+### Minor Changes
+
+* All software licenses are now in the <code>LICENSES/</code> directory of the collection root\. Moreover\, <code>SPDX\-License\-Identifier\:</code> is used to declare the applicable license for every file that is not automatically generated \([https\://github\.com/ansible\-collections/community\.hrobot/pull/52](https\://github\.com/ansible\-collections/community\.hrobot/pull/52)\)\.
+
+<a id="v1-4-0"></a>
+## v1\.4\.0
+
+<a id="release-summary-10"></a>
+### Release Summary
+
+Feature release\.
+
+<a id="minor-changes-5"></a>
+### Minor Changes
+
+* robot inventory plugin \- allow to template <code>hetzner\_user</code> and <code>hetzner\_password</code> \([https\://github\.com/ansible\-collections/community\.hrobot/pull/49](https\://github\.com/ansible\-collections/community\.hrobot/pull/49)\)\.
+
+<a id="v1-3-1"></a>
+## v1\.3\.1
+
+<a id="release-summary-11"></a>
+### Release Summary
+
+Maintenance release\.
+
+<a id="bugfixes-1"></a>
+### Bugfixes
+
+* Include <code>simplified\_bsd\.txt</code> license file for the <code>robot</code> and <code>failover</code> module utils\.
+
+<a id="v1-3-0"></a>
+## v1\.3\.0
+
+<a id="release-summary-12"></a>
+### Release Summary
+
+Feature and bugfix release\.
+
+<a id="minor-changes-6"></a>
+### Minor Changes
+
+* Prepare collection for inclusion in an Execution Environment by declaring its dependencies \([https\://github\.com/ansible\-collections/community\.hrobot/pull/45](https\://github\.com/ansible\-collections/community\.hrobot/pull/45)\)\.
+
+<a id="bugfixes-2"></a>
+### Bugfixes
+
+* robot inventory plugin \- do not crash if a server neither has name or primary IP set\. Instead\, fall back to using the server\'s number as the name\. This can happen if unnamed rack reservations show up in your server list \([https\://github\.com/ansible\-collections/community\.hrobot/issues/40](https\://github\.com/ansible\-collections/community\.hrobot/issues/40)\, [https\://github\.com/ansible\-collections/community\.hrobot/pull/47](https\://github\.com/ansible\-collections/community\.hrobot/pull/47)\)\.
+
+<a id="v1-2-3"></a>
+## v1\.2\.3
+
+<a id="release-summary-13"></a>
+### Release Summary
+
+Docs update release\.
+
+<a id="v1-2-2"></a>
+## v1\.2\.2
+
+<a id="release-summary-14"></a>
+### Release Summary
+
+Bugfix release\.
+
+<a id="bugfixes-3"></a>
+### Bugfixes
+
+* boot \- fix incorrect handling of SSH authorized keys \([https\://github\.com/ansible\-collections/community\.hrobot/issues/32](https\://github\.com/ansible\-collections/community\.hrobot/issues/32)\, [https\://github\.com/ansible\-collections/community\.hrobot/pull/33](https\://github\.com/ansible\-collections/community\.hrobot/pull/33)\)\.
+
+<a id="v1-2-1"></a>
+## v1\.2\.1
+
+<a id="release-summary-15"></a>
+### Release Summary
+
+Maintenance release\.
+
+<a id="minor-changes-7"></a>
+### Minor Changes
+
+* Generic module HTTP support code \- fix usage of <code>fetch\_url</code> with changes in latest ansible\-core <code>devel</code> branch \([https\://github\.com/ansible\-collections/community\.hrobot/pull/30](https\://github\.com/ansible\-collections/community\.hrobot/pull/30)\)\.
+
+<a id="v1-2-0"></a>
+## v1\.2\.0
+
+<a id="release-summary-16"></a>
+### Release Summary
+
+Feature release with multiple new modules\.
+
+<a id="minor-changes-8"></a>
+### Minor Changes
+
+* Avoid internal ansible\-core module\_utils in favor of equivalent public API available since at least Ansible 2\.9 \([https\://github\.com/ansible\-collections/community\.hrobot/pull/18](https\://github\.com/ansible\-collections/community\.hrobot/pull/18)\)\.
+* firewall \- rename option <code>whitelist\_hos</code> to <code>allowlist\_hos</code>\, keep old name as alias \([https\://github\.com/ansible\-collections/community\.hrobot/pull/15](https\://github\.com/ansible\-collections/community\.hrobot/pull/15)\)\.
+* firewall\, firewall\_info \- add return value <code>allowlist\_hos</code>\, which contains the same value as <code>whitelist\_hos</code>\. The old name <code>whitelist\_hos</code> will be removed eventually \([https\://github\.com/ansible\-collections/community\.hrobot/pull/15](https\://github\.com/ansible\-collections/community\.hrobot/pull/15)\)\.
+* robot module utils \- add <code>allow\_empty\_result</code> parameter to <code>plugin\_open\_url\_json</code> and <code>fetch\_url\_json</code> \([https\://github\.com/ansible\-collections/community\.hrobot/pull/16](https\://github\.com/ansible\-collections/community\.hrobot/pull/16)\)\.
+
+<a id="new-modules-1"></a>
+### New Modules
+
+* community\.hrobot\.boot \- Set boot configuration
+* community\.hrobot\.reset \- Reset a dedicated server
+* community\.hrobot\.reverse\_dns \- Set or remove reverse DNS entry for IP
+* community\.hrobot\.server \- Update server information
+* community\.hrobot\.server\_info \- Query information on one or more servers
+* community\.hrobot\.ssh\_key \- Add\, remove or update SSH key
+* community\.hrobot\.ssh\_key\_info \- Query information on SSH keys
+
+<a id="v1-1-1"></a>
+## v1\.1\.1
+
+<a id="release-summary-17"></a>
+### Release Summary
+
+Bugfix release which reduces the number of HTTPS queries for the modules and plugins\.
+
+<a id="bugfixes-4"></a>
+### Bugfixes
+
+* robot \- force HTTP basic authentication to reduce number of HTTPS requests \([https\://github\.com/ansible\-collections/community\.hrobot/pull/9](https\://github\.com/ansible\-collections/community\.hrobot/pull/9)\)\.
+
+<a id="v1-1-0"></a>
+## v1\.1\.0
+
+<a id="release-summary-18"></a>
+### Release Summary
+
+Release with a new inventory plugin\.
+
+<a id="new-plugins"></a>
+### New Plugins
+
+<a id="inventory"></a>
+#### Inventory
+
+* community\.hrobot\.robot \- Hetzner Robot inventory source
+
+<a id="v1-0-0"></a>
+## v1\.0\.0
+
+<a id="release-summary-19"></a>
+### Release Summary
+
+The <code>community\.hrobot</code> continues the work on the Hetzner Robot modules from their state in <code>community\.general</code> 1\.2\.0\. The changes listed here are thus relative to the modules <code>community\.general\.hetzner\_\*</code>\.
+
+<a id="breaking-changes--porting-guide"></a>
+### Breaking Changes / Porting Guide
+
+* firewall \- now requires the [ipaddress](https\://pypi\.org/project/ipaddress/) library \([https\://github\.com/ansible\-collections/community\.hrobot/pull/2](https\://github\.com/ansible\-collections/community\.hrobot/pull/2)\)\.
diff --git a/ansible_collections/community/hrobot/CHANGELOG.md.license b/ansible_collections/community/hrobot/CHANGELOG.md.license
new file mode 100644
index 000000000..edff8c768
--- /dev/null
+++ b/ansible_collections/community/hrobot/CHANGELOG.md.license
@@ -0,0 +1,3 @@
+GNU General Public License v3.0+ (see LICENSES/GPL-3.0-or-later.txt or https://www.gnu.org/licenses/gpl-3.0.txt)
+SPDX-License-Identifier: GPL-3.0-or-later
+SPDX-FileCopyrightText: Ansible Project
diff --git a/ansible_collections/community/hrobot/CHANGELOG.rst b/ansible_collections/community/hrobot/CHANGELOG.rst
index 9b7559cbf..847d3dbda 100644
--- a/ansible_collections/community/hrobot/CHANGELOG.rst
+++ b/ansible_collections/community/hrobot/CHANGELOG.rst
@@ -4,6 +4,71 @@ Community Hetzner Robot Collection Release Notes
.. contents:: Topics
+v1.9.1
+======
+
+Release Summary
+---------------
+
+Bugfix release.
+
+Security Fixes
+--------------
+
+- robot inventory plugin - make sure all data received from the Hetzner robot service server is marked as unsafe, so remote code execution by obtaining texts that can be evaluated as templates is not possible (https://www.die-welt.net/2024/03/remote-code-execution-in-ansible-dynamic-inventory-plugins/, https://github.com/ansible-collections/community.hrobot/pull/99).
+
+v1.9.0
+======
+
+Release Summary
+---------------
+
+Feature and maintenance release.
+
+Minor Changes
+-------------
+
+- robot inventory plugin - the ``filters`` option has been renamed to ``simple_filters``. The old name still works until community.hrobot 2.0.0. Then it will change to allow more complex filtering with the ``community.library_inventory_filtering_v1`` collection's functionality (https://github.com/ansible-collections/community.hrobot/pull/94).
+
+Deprecated Features
+-------------------
+
+- robot inventory plugin - the ``filters`` option has been renamed to ``simple_filters``. The old name will stop working in community.hrobot 2.0.0 (https://github.com/ansible-collections/community.hrobot/pull/94).
+
+v1.8.2
+======
+
+Release Summary
+---------------
+
+Maintenance release with updated documentation.
+
+Bugfixes
+--------
+
+- Show more information (if available) from error messages (https://github.com/ansible-collections/community.hrobot/pull/89).
+
+v1.8.1
+======
+
+Release Summary
+---------------
+
+Maintenance release with updated documentation.
+
+From this version on, community.hrobot is using the new `Ansible semantic markup
+<https://docs.ansible.com/ansible/devel/dev_guide/developing_modules_documenting.html#semantic-markup-within-module-documentation>`__
+in its documentation. If you look at documentation with the ansible-doc CLI tool
+from ansible-core before 2.15, please note that it does not render the markup
+correctly. You should be still able to read it in most cases, but you need
+ansible-core 2.15 or later to see it as it is intended. Alternatively you can
+look at `the devel docsite <https://docs.ansible.com/ansible/devel/collections/community/hrobot/>`__
+for the rendered HTML version of the documentation of the latest release.
+
+Known Issues
+------------
+
+- Ansible markup will show up in raw form on ansible-doc text output for ansible-core before 2.15. If you have trouble deciphering the documentation markup, please upgrade to ansible-core 2.15 (or newer), or read the HTML documentation on https://docs.ansible.com/ansible/devel/collections/community/hrobot/.
v1.8.0
======
@@ -226,7 +291,6 @@ Release Summary
The ``community.hrobot`` continues the work on the Hetzner Robot modules from their state in ``community.general`` 1.2.0. The changes listed here are thus relative to the modules ``community.general.hetzner_*``.
-
Breaking Changes / Porting Guide
--------------------------------
diff --git a/ansible_collections/community/hrobot/FILES.json b/ansible_collections/community/hrobot/FILES.json
index 9576b95d8..54c28f1e6 100644
--- a/ansible_collections/community/hrobot/FILES.json
+++ b/ansible_collections/community/hrobot/FILES.json
@@ -25,7 +25,7 @@
"name": ".github/workflows/ansible-test.yml",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "3a0024831cf7cc7a832b0478ae964e70e3713af496ce78904f1c820b3878507c",
+ "chksum_sha256": "b221558d1b9e91f2f1b3087eca7455efea6016a313388315d94c748a736f6d0c",
"format": 1
},
{
@@ -46,28 +46,28 @@
"name": ".github/workflows/ee.yml",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "2ec44891b83956d4816fef844f14e692e56dcd9f46b96aa55dcfa838f1290181",
+ "chksum_sha256": "03c5a4a0a65ebe7d5b9683d95f2752cdbbcac4d4b8cca513d4332d80dd1c79c2",
"format": 1
},
{
"name": ".github/workflows/extra-tests.yml",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "1dddc4fefe3721d4daf55419948d65be8f05579a015b37e4229fbb1475ae3958",
+ "chksum_sha256": "3d4972a65972c0091b7343e287eba10382716e29fd184091b1f8b4df4892fe44",
"format": 1
},
{
"name": ".github/workflows/import-galaxy.yml",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "220b0bab6530dfbbe6031eb7d7e569b20af32cfcb82b4bfa8d3e08e7450d9b89",
+ "chksum_sha256": "739c36223d6e0e6ccc98907c43cba53296e7b1ccd64a2d995c2ff21df4ab25a5",
"format": 1
},
{
"name": ".github/workflows/reuse.yml",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "c9cc8b1cebfde4ee00c680356325d514c3ee3fa792e04cc6f5d74740fbfd61b4",
+ "chksum_sha256": "bc2800b679cfe401b8c7a7188a8669f2717425390947fd0dba6477797d2dc614",
"format": 1
},
{
@@ -137,7 +137,7 @@
"name": "changelogs/changelog.yaml",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "3a3089a66ec4db61793fea71c17024c3aeef4e89818d70ea3d15a67bb2b7a1a9",
+ "chksum_sha256": "7bb1dd839047930188a470f49ab846872b8b5fed15a0ad79f2a4f6badc7ca08f",
"format": 1
},
{
@@ -151,7 +151,7 @@
"name": "changelogs/config.yaml",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "34aff4539b48607175563a83f71ec1c66ee23a2e94906915fe3ac3d89a4d68ef",
+ "chksum_sha256": "a7b8fa9406e8d12b8783432c8dcbec5e940b502649eb8d4c1bbc18bcac0c7ede",
"format": 1
},
{
@@ -235,7 +235,7 @@
"name": "plugins/inventory/robot.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "f012c1189cc2df209e97e7dd5fa8d2502f192abeb922d7dff3d4918fe3f9ca83",
+ "chksum_sha256": "08386e031100da8e3ae8d8a76fdf511b71ebce6d5b9648dc24f32784ee497fda",
"format": 1
},
{
@@ -256,7 +256,7 @@
"name": "plugins/module_utils/robot.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "dcfd4d5f6854cc2c82f9239d05c0625fdcf38b18b67b4cab8ecdf391afdb6e9e",
+ "chksum_sha256": "61fd87bec43eae7bc08f2414c51b4f479ebca17d7e0be5d9d337c75392dd6bf0",
"format": 1
},
{
@@ -270,70 +270,70 @@
"name": "plugins/modules/boot.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "f9f0adbcd0ce63cebde36f20795961d5c678465b764bd037900cf3c14fb540a7",
+ "chksum_sha256": "6e602be89c58a047b8b0874a462e950340f1ae5c0066876efc3c6826f9fd1464",
"format": 1
},
{
"name": "plugins/modules/failover_ip.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "c22701e1a41409a583dc8d9bc8f3aee0c5caf61711d1796729c571ce6baf68bc",
+ "chksum_sha256": "73945727cd5ebb8330f0089d7ac6c429b457863fffc0fbfb3fd3309041b23c4c",
"format": 1
},
{
"name": "plugins/modules/failover_ip_info.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "a732a481bf7bd2d7956e2b7c73b58e4631dff3a491a38cea47aafa7fc87d70b3",
+ "chksum_sha256": "6876f306910f6b3339eb45482bba2563789b92a529f026e174e1d35f4bf6e39d",
"format": 1
},
{
"name": "plugins/modules/firewall.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "8fd6d3567e7077bd4f94c40be87e6519f5e3fe24dcb60559b3c28c133fe1d0e5",
+ "chksum_sha256": "91a1096959175c8a038b4baeadd13cea05f852579f7f09542f653136bd9f9b6e",
"format": 1
},
{
"name": "plugins/modules/firewall_info.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "2492c517ba7e4440913d7760f1cb47b33fe5dbc41ae6e738d08986b0eacdcbce",
+ "chksum_sha256": "c4b7b4012cda86c3ad336c148ceafead1454c3a8de2325372dbb3ba797ca8024",
"format": 1
},
{
"name": "plugins/modules/reset.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "c326bd880106c020c0a923b9b2239e5fa7ca02f92df5a2100aef8fd8a2ea83ef",
+ "chksum_sha256": "e6a78514fec243ac08dbdb9f258b297b9e10dd3374b98941694e9ef67008c22a",
"format": 1
},
{
"name": "plugins/modules/reverse_dns.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "64521ba301cc273f59deb696ab80d8529f3297d9e1dc8d2470926f45ff114c7b",
+ "chksum_sha256": "5a976d175cc922ecb5cc04d2c076a84794b5c8033369870ff648344fa2c6c4e9",
"format": 1
},
{
"name": "plugins/modules/server.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "2448b78e391940eb6fb4a955c1d24f5e54a1f519d24dc3e60b30efb4cca916f2",
+ "chksum_sha256": "7d2fa319fa2ed98d511daab1f576d46d551b4785d3a9e18a7d44d95b43234934",
"format": 1
},
{
"name": "plugins/modules/server_info.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "08f5cb04db19a18ca3ec6fc3cfb01adf6f174dc94c4befb826f854ac0fab42d7",
+ "chksum_sha256": "057ee56dbd104fb5bd2031ebef68c6c93cf378342029cab26e4c671d9346716c",
"format": 1
},
{
"name": "plugins/modules/ssh_key.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "56d3a5ef901a3c692d6f5f3dc7a07da8a384fdfefb1d7ad7bcde0e7cae0092ae",
+ "chksum_sha256": "8df71f0d30ffbfc928851111c023ee1c2907194a73e1f9abf2b485c09dcaa823",
"format": 1
},
{
@@ -347,7 +347,7 @@
"name": "plugins/modules/v_switch.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "0769c7829fc91038fb4b7ea446d3a5f3fafc3a3d0ec4c6085158d8ae741fe053",
+ "chksum_sha256": "bfd0a37f238dead342b88bcce0ea8f6d1e45819d6e1e1335f1cfef450529828d",
"format": 1
},
{
@@ -431,7 +431,7 @@
"name": "tests/sanity/extra/extra-docs.json",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "63af024dcda47dda7e3cead05953d33c858853d2adc046efb47af28a6a0dc96b",
+ "chksum_sha256": "6c7fbc8a07fa803ce062387232eb0d0198a311f5347493f06c19a07aa45a9bf6",
"format": 1
},
{
@@ -445,7 +445,7 @@
"name": "tests/sanity/extra/extra-docs.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "00ae2a5eeec7f3a621074473ee4d0d16f763c67e1c6c1b2f4b7dcd3ca171262c",
+ "chksum_sha256": "c52e316daf1292bbb063be19429fd1f06e02bce3c9d4622a8dfc61fa3af06688",
"format": 1
},
{
@@ -582,6 +582,34 @@
"format": 1
},
{
+ "name": "tests/sanity/ignore-2.16.txt",
+ "ftype": "file",
+ "chksum_type": "sha256",
+ "chksum_sha256": "5264853edb2c6ff138f5496111c1e758a3a54b61e82d96c0072cb9429fb31c6e",
+ "format": 1
+ },
+ {
+ "name": "tests/sanity/ignore-2.16.txt.license",
+ "ftype": "file",
+ "chksum_type": "sha256",
+ "chksum_sha256": "6eb915239f9f35407fa68fdc41ed6522f1fdcce11badbdcd6057548023179ac1",
+ "format": 1
+ },
+ {
+ "name": "tests/sanity/ignore-2.17.txt",
+ "ftype": "file",
+ "chksum_type": "sha256",
+ "chksum_sha256": "5264853edb2c6ff138f5496111c1e758a3a54b61e82d96c0072cb9429fb31c6e",
+ "format": 1
+ },
+ {
+ "name": "tests/sanity/ignore-2.17.txt.license",
+ "ftype": "file",
+ "chksum_type": "sha256",
+ "chksum_sha256": "6eb915239f9f35407fa68fdc41ed6522f1fdcce11badbdcd6057548023179ac1",
+ "format": 1
+ },
+ {
"name": "tests/sanity/ignore-2.9.txt",
"ftype": "file",
"chksum_type": "sha256",
@@ -620,7 +648,7 @@
"name": "tests/unit/plugins/inventory/test_robot.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "1e7aebcb567bfb2c8dd055e5ea6ccb4cb175b4e7df992868e0ef0df2b47cbaf1",
+ "chksum_sha256": "673ffae43e3a3584719643a42bbdd33321b2b8331629a9d069793c3925d21c35",
"format": 1
},
{
@@ -634,14 +662,14 @@
"name": "tests/unit/plugins/module_utils/test_failover.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "19106763b057e212a13597775a82f939f5b6959b317e93fe3188a64284d8797f",
+ "chksum_sha256": "d6072cde4dbaef7af6400d9e417c7e647607628826c732dbc1b16f53f2e46f6c",
"format": 1
},
{
"name": "tests/unit/plugins/module_utils/test_robot.py",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "c8ccfce1d5a536b29c4ce5ab7529e75dc893e4d15f66032fc7b6fa9c6af4e1f0",
+ "chksum_sha256": "20bb76b45cfd9c002089324c941f9ed34e48635781b30c3a808ce3892bbfae03",
"format": 1
},
{
@@ -743,6 +771,13 @@
"format": 1
},
{
+ "name": "tests/unit/requirements.yml",
+ "ftype": "file",
+ "chksum_type": "sha256",
+ "chksum_sha256": "999b6bb4a4234b1f38abb63cbd57d40af2d93bcff2260ab088e09157a055abaf",
+ "format": 1
+ },
+ {
"name": "tests/config.yml",
"ftype": "file",
"chksum_type": "sha256",
@@ -750,17 +785,24 @@
"format": 1
},
{
- "name": "tests/requirements.yml",
+ "name": "CHANGELOG.md",
+ "ftype": "file",
+ "chksum_type": "sha256",
+ "chksum_sha256": "2c4facb0c77d486fd61f1ea78cd2bee7c6cf833fc4dd328b57a9a440efe43db3",
+ "format": 1
+ },
+ {
+ "name": "CHANGELOG.md.license",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "d556aaf12dcf49749ad88e27cb3b2c9995de47c1eccde8b73de744b21ca218cc",
+ "chksum_sha256": "6eb915239f9f35407fa68fdc41ed6522f1fdcce11badbdcd6057548023179ac1",
"format": 1
},
{
"name": "CHANGELOG.rst",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "240999c1e8b017228a03f0c6fb48e35a637e650fa4fb022fdc2c35d480ba7615",
+ "chksum_sha256": "ca10d6a2a30e1165b9325897d7c6335ff8b3a50859742e2e4333070df0e6c38f",
"format": 1
},
{
@@ -781,7 +823,7 @@
"name": "README.md",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "7ffc02a04b50194cf13c5b6b54372e3e29939dafc7efe965ca5193d27f64b6ea",
+ "chksum_sha256": "b26ea8090f24cde8afb282f7779abf6ce363edbf65068631c38984c5ed51ba70",
"format": 1
},
{
diff --git a/ansible_collections/community/hrobot/MANIFEST.json b/ansible_collections/community/hrobot/MANIFEST.json
index 74cd2a6f1..5fd6295d8 100644
--- a/ansible_collections/community/hrobot/MANIFEST.json
+++ b/ansible_collections/community/hrobot/MANIFEST.json
@@ -2,7 +2,7 @@
"collection_info": {
"namespace": "community",
"name": "hrobot",
- "version": "1.8.0",
+ "version": "1.9.1",
"authors": [
"Felix Fontein (github.com/felixfontein)"
],
@@ -30,7 +30,7 @@
"name": "FILES.json",
"ftype": "file",
"chksum_type": "sha256",
- "chksum_sha256": "1d5553b60ed857cfc979fd52b7531a8135bec6bde395b4ec3e1356daa2fab3bb",
+ "chksum_sha256": "cada2fa56571e4857ace197d0dd1c09e665fdd718cea048c0327ba8ef3447245",
"format": 1
},
"format": 1
diff --git a/ansible_collections/community/hrobot/README.md b/ansible_collections/community/hrobot/README.md
index 2f78a9aef..44ee9ddcd 100644
--- a/ansible_collections/community/hrobot/README.md
+++ b/ansible_collections/community/hrobot/README.md
@@ -15,7 +15,7 @@ Please note that this collection does **not** support Windows targets.
## Tested with Ansible
-Tested with the current Ansible 2.9, ansible-base 2.10, ansible-core 2.11, ansible-core 2.12, ansible-core 2.13, and ansible-core 2.14 releases and the current development version of ansible-core. Ansible versions before 2.9.10 are not supported.
+Tested with the current Ansible 2.9, ansible-base 2.10, ansible-core 2.11, ansible-core 2.12, ansible-core 2.13, ansible-core 2.14, ansible-core 2.15, and ansible-core 2.16 releases and the current development version of ansible-core. Ansible versions before 2.9.10 are not supported.
## External requirements
@@ -37,7 +37,7 @@ If you use the Ansible package and do not update collections independently, use
- `community.hrobot.failover_ip_info` module
- `community.hrobot.firewall` module
- `community.hrobot.firewall_info` module
-- `community.hrobot.hrobot` inventory plugin
+- `community.hrobot.robot` inventory plugin
You can find [documentation for the modules and plugins in this collection here](https://docs.ansible.com/ansible/devel/collections/community/hrobot/).
@@ -64,7 +64,7 @@ You can find more information in the [developer guide for collections](https://d
## Release notes
-See the [changelog](https://github.com/ansible-collections/community.hrobot/tree/main/CHANGELOG.rst).
+See the [changelog](https://github.com/ansible-collections/community.hrobot/tree/main/CHANGELOG.md).
## More information
diff --git a/ansible_collections/community/hrobot/changelogs/changelog.yaml b/ansible_collections/community/hrobot/changelogs/changelog.yaml
index 94785155c..ff49e627a 100644
--- a/ansible_collections/community/hrobot/changelogs/changelog.yaml
+++ b/ansible_collections/community/hrobot/changelogs/changelog.yaml
@@ -210,3 +210,73 @@ releases:
- 76-firewall-ipv6-output.yml
- 77-firewall-server_number.yml
release_date: '2023-03-15'
+ 1.8.1:
+ changes:
+ known_issues:
+ - Ansible markup will show up in raw form on ansible-doc text output for ansible-core
+ before 2.15. If you have trouble deciphering the documentation markup, please
+ upgrade to ansible-core 2.15 (or newer), or read the HTML documentation on
+ https://docs.ansible.com/ansible/devel/collections/community/hrobot/.
+ release_summary: 'Maintenance release with updated documentation.
+
+
+ From this version on, community.hrobot is using the new `Ansible semantic
+ markup
+
+ <https://docs.ansible.com/ansible/devel/dev_guide/developing_modules_documenting.html#semantic-markup-within-module-documentation>`__
+
+ in its documentation. If you look at documentation with the ansible-doc CLI
+ tool
+
+ from ansible-core before 2.15, please note that it does not render the markup
+
+ correctly. You should be still able to read it in most cases, but you need
+
+ ansible-core 2.15 or later to see it as it is intended. Alternatively you
+ can
+
+ look at `the devel docsite <https://docs.ansible.com/ansible/devel/collections/community/hrobot/>`__
+
+ for the rendered HTML version of the documentation of the latest release.
+
+ '
+ fragments:
+ - 1.8.1.yml
+ - semantic-markup.yml
+ release_date: '2023-06-27'
+ 1.8.2:
+ changes:
+ bugfixes:
+ - Show more information (if available) from error messages (https://github.com/ansible-collections/community.hrobot/pull/89).
+ release_summary: Maintenance release with updated documentation.
+ fragments:
+ - 1.8.2.yml
+ - 89-firewall.yml
+ release_date: '2023-11-11'
+ 1.9.0:
+ changes:
+ deprecated_features:
+ - robot inventory plugin - the ``filters`` option has been renamed to ``simple_filters``.
+ The old name will stop working in community.hrobot 2.0.0 (https://github.com/ansible-collections/community.hrobot/pull/94).
+ minor_changes:
+ - robot inventory plugin - the ``filters`` option has been renamed to ``simple_filters``.
+ The old name still works until community.hrobot 2.0.0. Then it will change
+ to allow more complex filtering with the ``community.library_inventory_filtering_v1``
+ collection's functionality (https://github.com/ansible-collections/community.hrobot/pull/94).
+ release_summary: Feature and maintenance release.
+ fragments:
+ - 1.9.0.yml
+ - 94-inventory-filters.yml
+ release_date: '2024-01-21'
+ 1.9.1:
+ changes:
+ release_summary: Bugfix release.
+ security_fixes:
+ - robot inventory plugin - make sure all data received from the Hetzner robot
+ service server is marked as unsafe, so remote code execution by obtaining
+ texts that can be evaluated as templates is not possible (https://www.die-welt.net/2024/03/remote-code-execution-in-ansible-dynamic-inventory-plugins/,
+ https://github.com/ansible-collections/community.hrobot/pull/99).
+ fragments:
+ - 1.9.1.yml
+ - inventory-rce.yml
+ release_date: '2024-03-16'
diff --git a/ansible_collections/community/hrobot/changelogs/config.yaml b/ansible_collections/community/hrobot/changelogs/config.yaml
index 4d6ee1a9b..ed2ab2a71 100644
--- a/ansible_collections/community/hrobot/changelogs/config.yaml
+++ b/ansible_collections/community/hrobot/changelogs/config.yaml
@@ -11,6 +11,9 @@ keep_fragments: false
mention_ancestor: true
new_plugins_after_name: removed_features
notesdir: fragments
+output_formats:
+- rst
+- md
prelude_section_name: release_summary
prelude_section_title: Release Summary
sections:
diff --git a/ansible_collections/community/hrobot/plugins/inventory/robot.py b/ansible_collections/community/hrobot/plugins/inventory/robot.py
index 1d5af4537..19a2f1aa4 100644
--- a/ansible_collections/community/hrobot/plugins/inventory/robot.py
+++ b/ansible_collections/community/hrobot/plugins/inventory/robot.py
@@ -26,7 +26,7 @@ DOCUMENTATION = r"""
- ansible.builtin.inventory_cache
- community.hrobot.robot
notes:
- - The I(hetzner_user) and I(hetzner_password) options can be templated.
+ - The O(hetzner_user) and O(hetzner_password) options can be templated.
options:
plugin:
description: Token that ensures this is a source file for the plugin.
@@ -38,13 +38,17 @@ DOCUMENTATION = r"""
hetzner_password:
env:
- name: HROBOT_API_PASSWORD
- filters:
+ simple_filters:
description:
- A dictionary of filter value pairs.
- Available filters are listed here are keys of server like C(status) or C(server_ip).
- See U(https://robot.your-server.de/doc/webservice/en.html#get-server) for all values that can be used.
+ - This option has been renamed from O(filters) to O(simple_filters) in community.hrobot 1.9.0.
+ The old name can still be used until community.hrobot 2.0.0.
type: dict
default: {}
+ aliases:
+ - filters
"""
EXAMPLES = r"""
@@ -63,7 +67,7 @@ hetzner_password: '{{ (lookup("community.sops.sops", "keys/hetzner.sops.yaml") |
# Example using constructed features to create groups
plugin: community.hrobot.robot
-filters:
+simple_filters:
status: ready
traffic: unlimited
# keyed_groups may be used to create custom groups
@@ -81,6 +85,7 @@ from ansible.errors import AnsibleError
from ansible.plugins.inventory import BaseInventoryPlugin, Constructable, Cacheable
from ansible.template import Templar
from ansible.utils.display import Display
+from ansible.utils.unsafe_proxy import wrap_var as make_unsafe
from ansible_collections.community.hrobot.plugins.module_utils.robot import (
BASE_URL,
@@ -109,10 +114,18 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable):
def parse(self, inventory, loader, path, cache=True):
super(InventoryModule, self).parse(inventory, loader, path)
servers = {}
- config = self._read_config_data(path)
+ orig_config = self._read_config_data(path)
self.load_cache_plugin()
cache_key = self.get_cache_key(path)
+ if 'filters' in orig_config:
+ display.deprecated(
+ 'The `filters` option of the community.hrobot.robot inventory plugin has been renamed to `simple_filters`. '
+ 'The old name will stop working in community.hrobot 2.0.0.',
+ collection_name='community.hrobot',
+ version='2.0.0',
+ )
+
self.templar = Templar(loader=loader)
# cache may be True or False at this point to indicate if the inventory is being refreshed
@@ -143,7 +156,7 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable):
self.populate(servers)
def populate(self, servers):
- filters = self.get_option('filters')
+ filters = self.get_option('simple_filters')
strict = self.get_option('strict')
server_lists = []
for server in servers:
@@ -162,9 +175,9 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable):
self.inventory.add_host(server_name)
server_lists.append(server_name)
if 'server_ip' in s:
- self.inventory.set_variable(server_name, 'ansible_host', s['server_ip'])
+ self.inventory.set_variable(server_name, 'ansible_host', make_unsafe(s['server_ip']))
for hostvar, hostval in s.items():
- self.inventory.set_variable(server_name, "{0}_{1}".format('hrobot', hostvar), hostval)
+ self.inventory.set_variable(server_name, "{0}_{1}".format('hrobot', hostvar), make_unsafe(hostval))
# Composed variables
server_vars = self.inventory.get_host(server_name).get_vars()
diff --git a/ansible_collections/community/hrobot/plugins/module_utils/robot.py b/ansible_collections/community/hrobot/plugins/module_utils/robot.py
index 034a3fc48..f01409083 100644
--- a/ansible_collections/community/hrobot/plugins/module_utils/robot.py
+++ b/ansible_collections/community/hrobot/plugins/module_utils/robot.py
@@ -8,6 +8,7 @@ from __future__ import absolute_import, division, print_function
__metaclass__ = type
+from ansible.module_utils.common.text.converters import to_native
from ansible.module_utils.six import PY3
from ansible.module_utils.six.moves.urllib.error import HTTPError
from ansible.module_utils.urls import fetch_url, open_url
@@ -33,6 +34,30 @@ def get_x_www_form_urlenconded_dict_from_list(key, values):
return dict(('{key}[{index}]'.format(key=key, index=i), x) for i, x in enumerate(values))
+def _format_list(obj):
+ if not isinstance(obj, (list, tuple)):
+ return to_native(obj)
+ return [_format_list(e) for e in obj]
+
+
+def format_error_msg(error):
+ # Reference: https://robot.hetzner.com/doc/webservice/en.html#errors
+ msg = 'Request failed: {0} {1} ({2})'.format(
+ error['status'],
+ error['code'],
+ error['message'],
+ )
+ if error.get('missing'):
+ msg += '. Missing input parameters: {0}'.format(_format_list(error['missing']))
+ if error.get('invalid'):
+ msg += '. Invalid input parameters: {0}'.format(_format_list(error['invalid']))
+ if error.get('max_request') is not None:
+ msg += '. Maximum allowed requests: {0}'.format(error['max_request'])
+ if error.get('interval') is not None:
+ msg += '. Time interval in seconds: {0}'.format(error['interval'])
+ return msg
+
+
class PluginException(Exception):
def __init__(self, message):
super(PluginException, self).__init__(message)
@@ -85,11 +110,7 @@ def plugin_open_url_json(plugin, url, method='GET', timeout=10, data=None, heade
if accept_errors:
if result['error']['code'] in accept_errors:
return result, result['error']['code']
- raise PluginException('Request failed: {0} {1} ({2})'.format(
- result['error']['status'],
- result['error']['code'],
- result['error']['message']
- ))
+ raise PluginException(format_error_msg(result['error']))
return result, None
except ValueError:
raise PluginException('Cannot decode content retrieved from {0}'.format(url))
@@ -125,11 +146,7 @@ def fetch_url_json(module, url, method='GET', timeout=10, data=None, headers=Non
if accept_errors:
if result['error']['code'] in accept_errors:
return result, result['error']['code']
- module.fail_json(msg='Request failed: {0} {1} ({2})'.format(
- result['error']['status'],
- result['error']['code'],
- result['error']['message']
- ))
+ module.fail_json(msg=format_error_msg(result['error']), error=result['error'])
return result, None
except ValueError:
module.fail_json(msg='Cannot decode content retrieved from {0}'.format(url))
diff --git a/ansible_collections/community/hrobot/plugins/modules/boot.py b/ansible_collections/community/hrobot/plugins/modules/boot.py
index 64917d9b8..bcf6f3c47 100644
--- a/ansible_collections/community/hrobot/plugins/modules/boot.py
+++ b/ansible_collections/community/hrobot/plugins/modules/boot.py
@@ -46,31 +46,31 @@ options:
description:
- If this option is provided, all special boot configurations are removed and
the installed operating system will be booted up next (assuming it is bootable).
- - Precisely one of I(regular_boot), I(rescue), I(install_linux), I(install_vnc),
- I(install_windows), I(install_plesk), and I(install_cpanel) must be provided.
+ - Precisely one of O(regular_boot), O(rescue), O(install_linux), O(install_vnc),
+ O(install_windows), O(install_plesk), and O(install_cpanel) must be provided.
type: bool
choices:
- true
rescue:
description:
- If this option is provided, the rescue system will be activated for the next boot.
- - Precisely one of I(regular_boot), I(rescue), I(install_linux), I(install_vnc),
- I(install_windows), I(install_plesk), and I(install_cpanel) must be provided.
+ - Precisely one of O(regular_boot), O(rescue), O(install_linux), O(install_vnc),
+ O(install_windows), O(install_plesk), and O(install_cpanel) must be provided.
type: dict
suboptions:
os:
description:
- The operating system to use for the rescue system. Possible choices can
change over time.
- - Currently, C(linux), C(linuxold), C(freebsd), C(freebsdold), C(freebsdax),
- C(freebsdbetaax), C(vkvm), and C(vkvmold) seem to be available.
+ - Currently, V(linux), V(linuxold), V(freebsd), V(freebsdold), V(freebsdax),
+ V(freebsdbetaax), V(vkvm), and V(vkvmold) seem to be available.
type: str
required: true
arch:
description:
- The architecture to use for the rescue system.
- Not all architectures are available for all operating systems.
- - Defaults to C(64).
+ - Defaults to V(64).
type: int
choices:
- 32
@@ -87,8 +87,8 @@ options:
install_linux:
description:
- If this option is provided, a Linux system install will be activated for the next boot.
- - Precisely one of I(regular_boot), I(rescue), I(install_linux), I(install_vnc),
- I(install_windows), I(install_plesk), and I(install_cpanel) must be provided.
+ - Precisely one of O(regular_boot), O(rescue), O(install_linux), O(install_vnc),
+ O(install_windows), O(install_plesk), and O(install_cpanel) must be provided.
type: dict
suboptions:
dist:
@@ -100,7 +100,7 @@ options:
description:
- The architecture to use for the install.
- Not all architectures are available for all distributions.
- - Defaults to C(64).
+ - Defaults to V(64).
type: int
choices:
- 32
@@ -122,8 +122,8 @@ options:
install_vnc:
description:
- If this option is provided, a VNC installation will be activated for the next boot.
- - Precisely one of I(regular_boot), I(rescue), I(install_linux), I(install_vnc),
- I(install_windows), I(install_plesk), and I(install_cpanel) must be provided.
+ - Precisely one of O(regular_boot), O(rescue), O(install_linux), O(install_vnc),
+ O(install_windows), O(install_plesk), and O(install_cpanel) must be provided.
type: dict
suboptions:
dist:
@@ -135,7 +135,7 @@ options:
description:
- The architecture to use for the install.
- Not all architectures are available for all distributions.
- - Defaults to C(64).
+ - Defaults to V(64).
type: int
choices:
- 32
@@ -148,8 +148,8 @@ options:
install_windows:
description:
- If this option is provided, a Windows installation will be activated for the next boot.
- - Precisely one of I(regular_boot), I(rescue), I(install_linux), I(install_vnc),
- I(install_windows), I(install_plesk), and I(install_cpanel) must be provided.
+ - Precisely one of O(regular_boot), O(rescue), O(install_linux), O(install_vnc),
+ O(install_windows), O(install_plesk), and O(install_cpanel) must be provided.
type: dict
suboptions:
lang:
@@ -160,8 +160,8 @@ options:
install_plesk:
description:
- If this option is provided, a Plesk installation will be activated for the next boot.
- - Precisely one of I(regular_boot), I(rescue), I(install_linux), I(install_vnc),
- I(install_windows), I(install_plesk), and I(install_cpanel) must be provided.
+ - Precisely one of O(regular_boot), O(rescue), O(install_linux), O(install_vnc),
+ O(install_windows), O(install_plesk), and O(install_cpanel) must be provided.
type: dict
suboptions:
dist:
@@ -173,7 +173,7 @@ options:
description:
- The architecture to use for the install.
- Not all architectures are available for all distributions.
- - Defaults to C(64).
+ - Defaults to V(64).
type: int
choices:
- 32
@@ -191,8 +191,8 @@ options:
install_cpanel:
description:
- If this option is provided, a cPanel installation will be activated for the next boot.
- - Precisely one of I(regular_boot), I(rescue), I(install_linux), I(install_vnc),
- I(install_windows), I(install_plesk), and I(install_cpanel) must be provided.
+ - Precisely one of O(regular_boot), O(rescue), O(install_linux), O(install_vnc),
+ O(install_windows), O(install_plesk), and O(install_cpanel) must be provided.
type: dict
suboptions:
dist:
@@ -204,7 +204,7 @@ options:
description:
- The architecture to use for the install.
- Not all architectures are available for all distributions.
- - Defaults to C(64).
+ - Defaults to V(64).
type: int
choices:
- 32
@@ -266,7 +266,7 @@ password:
- The root password for the active boot configuration, if available.
- For non-rescue boot configurations, it is avised to change the root password
as soon as possible.
- returned: success and if a boot configuration other than C(regular_boot) is active
+ returned: success and if RV(configuration_type) is not V(regular_boot)
type: str
'''
diff --git a/ansible_collections/community/hrobot/plugins/modules/failover_ip.py b/ansible_collections/community/hrobot/plugins/modules/failover_ip.py
index da2da356a..e5d0fdae7 100644
--- a/ansible_collections/community/hrobot/plugins/modules/failover_ip.py
+++ b/ansible_collections/community/hrobot/plugins/modules/failover_ip.py
@@ -44,7 +44,7 @@ options:
state:
description:
- Defines whether the IP will be routed or not.
- - If set to C(routed), I(value) must be specified.
+ - If set to V(routed), O(value) must be specified.
type: str
choices:
- routed
@@ -53,7 +53,7 @@ options:
value:
description:
- The new value for the failover IP address.
- - Required when setting I(state) to C(routed).
+ - Required when setting O(state) to V(routed).
type: str
timeout:
description:
@@ -85,12 +85,12 @@ RETURN = r'''
value:
description:
- The value of the failover IP.
- - Will be C(none) if the IP is unrouted.
+ - Will be V(none) if the IP is unrouted.
returned: success
type: str
state:
description:
- - Will be C(routed) or C(unrouted).
+ - Will be V(routed) or V(unrouted).
returned: success
type: str
'''
diff --git a/ansible_collections/community/hrobot/plugins/modules/failover_ip_info.py b/ansible_collections/community/hrobot/plugins/modules/failover_ip_info.py
index b656b0499..1db0d1b2c 100644
--- a/ansible_collections/community/hrobot/plugins/modules/failover_ip_info.py
+++ b/ansible_collections/community/hrobot/plugins/modules/failover_ip_info.py
@@ -59,12 +59,12 @@ RETURN = r'''
value:
description:
- The value of the failover IP.
- - Will be C(none) if the IP is unrouted.
+ - Will be V(none) if the IP is unrouted.
returned: success
type: str
state:
description:
- - Will be C(routed) or C(unrouted).
+ - Will be V(routed) or V(unrouted).
returned: success
type: str
failover_ip:
diff --git a/ansible_collections/community/hrobot/plugins/modules/firewall.py b/ansible_collections/community/hrobot/plugins/modules/firewall.py
index 2677a1186..8f158eaa6 100644
--- a/ansible_collections/community/hrobot/plugins/modules/firewall.py
+++ b/ansible_collections/community/hrobot/plugins/modules/firewall.py
@@ -44,14 +44,14 @@ options:
server_ip:
description:
- The server's main IP address.
- - Exactly one of I(server_ip) and I(server_number) must be specified.
+ - Exactly one of O(server_ip) and O(server_number) must be specified.
- Note that Hetzner deprecated identifying the server's firewall by the server's main IP.
- Using this option can thus stop working at any time in the future. Use I(server_number) instead.
+ Using this option can thus stop working at any time in the future. Use O(server_number) instead.
type: str
server_number:
description:
- The server's number.
- - Exactly one of I(server_ip) and I(server_number) must be specified.
+ - Exactly one of O(server_ip) and O(server_number) must be specified.
type: int
version_added: 1.8.0
filter_ipv6:
@@ -69,7 +69,7 @@ options:
state:
description:
- Status of the firewall.
- - Firewall is active if state is C(present), and disabled if state is C(absent).
+ - Firewall is active if state is V(present), and disabled if state is V(absent).
type: str
default: present
choices: [ present, absent ]
@@ -93,11 +93,14 @@ options:
name:
description:
- Name of the firewall rule.
+ - Note that Hetzner restricts the characters that can be used for rule names. At the moment, only
+ letters C(a-z), C(A-Z), space, and the symbols C(.), C(-), C(+), C(_), and C(@) are allowed.
type: str
ip_version:
description:
- Internet protocol version.
- - Leave away to filter both protocols. Note that in that case, none of I(dst_ip), I(src_ip), or I(protocol) can be specified.
+ - Leave away to filter both protocols. Note that in that case, none of O(rules.input[].dst_ip),
+ O(rules.input[].src_ip), or O(rules.input[].protocol) can be specified.
type: str
dst_ip:
description:
@@ -124,8 +127,8 @@ options:
tcp_flags:
description:
- TCP flags or logical combination of flags.
- - Flags supported by Hetzner are C(syn), C(fin), C(rst), C(psh) and C(urg).
- - They can be combined with C(|) (logical or) and C(&) (logical and).
+ - Flags supported by Hetzner are V(syn), V(fin), V(rst), V(psh) and V(urg).
+ - They can be combined with V(|) (logical or) and V(&) (logical and).
- See L(the documentation,https://wiki.hetzner.de/index.php/Robot_Firewall/en#Parameter)
for more information.
type: str
@@ -145,11 +148,14 @@ options:
name:
description:
- Name of the firewall rule.
+ - Note that Hetzner restricts the characters that can be used for rule names. At the moment, only
+ letters C(a-z), C(A-Z), space, and the symbols C(.), C(-), C(+), C(_), and C(@) are allowed.
type: str
ip_version:
description:
- Internet protocol version.
- - Leave away to filter both protocols. Note that in that case, none of I(dst_ip), I(src_ip), or I(protocol) can be specified.
+ - Leave away to filter both protocols. Note that in that case, none of O(rules.output[].dst_ip),
+ O(rules.output[].src_ip), or O(rules.output[].protocol) can be specified.
type: str
dst_ip:
description:
@@ -176,8 +182,8 @@ options:
tcp_flags:
description:
- TCP flags or logical combination of flags.
- - Flags supported by Hetzner are C(syn), C(fin), C(rst), C(psh) and C(urg).
- - They can be combined with C(|) (logical or) and C(&) (logical and).
+ - Flags supported by Hetzner are V(syn), V(fin), V(rst), V(psh) and V(urg).
+ - They can be combined with V(|) (logical or) and V(&) (logical and).
- See L(the documentation,https://wiki.hetzner.de/index.php/Robot_Firewall/en#Parameter)
for more information.
type: str
@@ -230,7 +236,8 @@ EXAMPLES = r'''
allowlist_hos: true
rules:
input:
- - name: Allow ICMP protocol, so you can ping your server
+ - name: Allow ICMP protocol
+ # This is needed so you can ping your server
ip_version: ipv4
protocol: icmp
action: accept
@@ -241,7 +248,8 @@ EXAMPLES = r'''
dst_port: '32768-65535'
tcp_flags: ack
action: accept
- - name: Allow everything to ports 20-23 from 4.3.2.1/24 (IPv4 only)
+ - name: Allow restricted access from some known IPv4 addresses
+ # Allow everything to ports 20-23 from 4.3.2.1/24 (IPv4 only)
ip_version: ipv4
src_ip: 4.3.2.1/24
dst_port: '20-23'
@@ -270,7 +278,7 @@ firewall:
port:
description:
- Switch port of firewall.
- - C(main) or C(kvm).
+ - V(main) or V(kvm).
type: str
sample: main
server_ip:
@@ -286,9 +294,9 @@ firewall:
status:
description:
- Status of the firewall.
- - C(active) or C(disabled).
- - Will be C(in process) if the firewall is currently updated, and
- I(wait_for_configured) is set to C(false) or I(timeout) to a too small value.
+ - V(active) or V(disabled).
+ - Will be V(in process) if the firewall is currently updated, and
+ O(wait_for_configured) is set to V(false) or O(timeout) to a too small value.
type: str
sample: active
allowlist_hos:
@@ -300,7 +308,7 @@ firewall:
whitelist_hos:
description:
- Whether Hetzner services have access.
- - Old name of return value C(allowlist_hos), will be removed eventually.
+ - Old name of return value V(allowlist_hos), will be removed eventually.
type: bool
sample: true
rules:
@@ -360,7 +368,7 @@ firewall:
action:
description:
- Action if rule matches.
- - C(accept) or C(discard).
+ - V(accept) or V(discard).
type: str
sample: accept
choices:
@@ -418,7 +426,7 @@ firewall:
action:
description:
- Action if rule matches.
- - C(accept) or C(discard).
+ - V(accept) or V(discard).
type: str
sample: accept
choices:
diff --git a/ansible_collections/community/hrobot/plugins/modules/firewall_info.py b/ansible_collections/community/hrobot/plugins/modules/firewall_info.py
index 49f98ab64..f72e253d7 100644
--- a/ansible_collections/community/hrobot/plugins/modules/firewall_info.py
+++ b/ansible_collections/community/hrobot/plugins/modules/firewall_info.py
@@ -37,14 +37,14 @@ options:
server_ip:
description:
- The server's main IP address.
- - Exactly one of I(server_ip) and I(server_number) must be specified.
+ - Exactly one of O(server_ip) and O(server_number) must be specified.
- Note that Hetzner deprecated identifying the server's firewall by the server's main IP.
- Using this option can thus stop working at any time in the future. Use I(server_number) instead.
+ Using this option can thus stop working at any time in the future. Use O(server_number) instead.
type: str
server_number:
description:
- The server's number.
- - Exactly one of I(server_ip) and I(server_number) must be specified.
+ - Exactly one of O(server_ip) and O(server_number) must be specified.
type: int
version_added: 1.8.0
wait_for_configured:
@@ -94,7 +94,7 @@ firewall:
port:
description:
- Switch port of firewall.
- - C(main) or C(kvm).
+ - V(main) or V(kvm).
type: str
sample: main
filter_ipv6:
@@ -115,9 +115,9 @@ firewall:
status:
description:
- Status of the firewall.
- - C(active) or C(disabled).
- - Will be C(in process) if the firewall is currently updated, and
- I(wait_for_configured) is set to C(false) or I(timeout) to a too small value.
+ - V(active) or V(disabled).
+ - Will be V(in process) if the firewall is currently updated, and
+ O(wait_for_configured) is set to V(false) or O(timeout) to a too small value.
type: str
sample: active
allowlist_hos:
@@ -129,7 +129,7 @@ firewall:
whitelist_hos:
description:
- Whether Hetzner services have access.
- - Old name of return value C(allowlist_hos), will be removed eventually.
+ - Old name of return value V(allowlist_hos), will be removed eventually.
type: bool
sample: true
rules:
@@ -189,7 +189,7 @@ firewall:
action:
description:
- Action if rule matches.
- - C(accept) or C(discard).
+ - V(accept) or V(discard).
type: str
sample: accept
choices:
@@ -247,7 +247,7 @@ firewall:
action:
description:
- Action if rule matches.
- - C(accept) or C(discard).
+ - V(accept) or V(discard).
type: str
sample: accept
choices:
diff --git a/ansible_collections/community/hrobot/plugins/modules/reset.py b/ansible_collections/community/hrobot/plugins/modules/reset.py
index d367936e0..eaeaa5853 100644
--- a/ansible_collections/community/hrobot/plugins/modules/reset.py
+++ b/ansible_collections/community/hrobot/plugins/modules/reset.py
@@ -40,11 +40,11 @@ options:
reset_type:
description:
- How to reset the server.
- - C(software) is a software reset. This should be similar to pressing Ctrl+Alt+Del on the keyboard.
- - C(power) is a hardware reset similar to pressing the Power button. An ACPI signal is sent, and if the
+ - V(software) is a software reset. This should be similar to pressing Ctrl+Alt+Del on the keyboard.
+ - V(power) is a hardware reset similar to pressing the Power button. An ACPI signal is sent, and if the
server is configured correctly, this will trigger a regular shutdown.
- - C(hardware) is a hardware reset similar to pressing the Restart button. The power is cycled for the server.
- - C(manual) is a manual reset. This requests a technician to manually do the shutdown while looking at the
+ - V(hardware) is a hardware reset similar to pressing the Restart button. The power is cycled for the server.
+ - V(manual) is a manual reset. This requests a technician to manually do the shutdown while looking at the
screen output. B(Be careful) and only use this when really necessary!
- Note that not every server supports every reset method!
type: str
diff --git a/ansible_collections/community/hrobot/plugins/modules/reverse_dns.py b/ansible_collections/community/hrobot/plugins/modules/reverse_dns.py
index 200489217..f3a914679 100644
--- a/ansible_collections/community/hrobot/plugins/modules/reverse_dns.py
+++ b/ansible_collections/community/hrobot/plugins/modules/reverse_dns.py
@@ -44,7 +44,7 @@ options:
required: true
state:
description:
- - Whether to set or update (C(present)) or delete (C(absent)) the reverse DNS entry for I(ip).
+ - Whether to set or update (V(present)) or delete (V(absent)) the reverse DNS entry for O(ip).
type: str
default: present
choices:
@@ -52,8 +52,8 @@ options:
- absent
value:
description:
- - The reverse DNS entry for I(ip).
- - Required if I(state=present).
+ - The reverse DNS entry for O(ip).
+ - Required if O(state=present).
type: str
'''
diff --git a/ansible_collections/community/hrobot/plugins/modules/server.py b/ansible_collections/community/hrobot/plugins/modules/server.py
index 2a24986e3..d32320af6 100644
--- a/ansible_collections/community/hrobot/plugins/modules/server.py
+++ b/ansible_collections/community/hrobot/plugins/modules/server.py
@@ -100,7 +100,7 @@ server:
traffic:
description:
- Free traffic quota.
- - C(unlimited) in case of unlimited traffic.
+ - V(unlimited) in case of unlimited traffic.
type: str
sample: 5 TB
returned: success
diff --git a/ansible_collections/community/hrobot/plugins/modules/server_info.py b/ansible_collections/community/hrobot/plugins/modules/server_info.py
index b3f6da11d..eed9f2289 100644
--- a/ansible_collections/community/hrobot/plugins/modules/server_info.py
+++ b/ansible_collections/community/hrobot/plugins/modules/server_info.py
@@ -40,9 +40,9 @@ options:
full_info:
description:
- Whether to provide full information for every server.
- - Setting this to C(true) requires one REST call per server,
+ - Setting this to V(true) requires one REST call per server,
which is slow and reduces your rate limit. Use with care.
- - When I(server_number) is specified, this option is set to C(true).
+ - When O(server_number) is specified, this option is set to V(true).
type: bool
default: false
'''
@@ -113,7 +113,7 @@ servers:
traffic:
description:
- Free traffic quota.
- - C(unlimited) in case of unlimited traffic.
+ - V(unlimited) in case of unlimited traffic.
type: str
sample: 5 TB
returned: success
@@ -171,55 +171,55 @@ servers:
- Whether the server can be automatically reset.
type: bool
sample: true
- returned: when I(full_info=true)
+ returned: when O(full_info=true)
rescue:
description:
- Whether the rescue system is available.
type: bool
sample: false
- returned: when I(full_info=true)
+ returned: when O(full_info=true)
vnc:
description:
- Flag of VNC installation availability.
type: bool
sample: true
- returned: when I(full_info=true)
+ returned: when O(full_info=true)
windows:
description:
- Flag of Windows installation availability.
type: bool
sample: true
- returned: when I(full_info=true)
+ returned: when O(full_info=true)
plesk:
description:
- Flag of Plesk installation availability.
type: bool
sample: true
- returned: when I(full_info=true)
+ returned: when O(full_info=true)
cpanel:
description:
- Flag of cPanel installation availability.
type: bool
sample: true
- returned: when I(full_info=true)
+ returned: when O(full_info=true)
wol:
description:
- Flag of Wake On Lan availability.
type: bool
sample: true
- returned: when I(full_info=true)
+ returned: when O(full_info=true)
hot_swap:
description:
- Flag of Hot Swap availability.
type: bool
sample: true
- returned: when I(full_info=true)
+ returned: when O(full_info=true)
linked_storagebox:
description:
- Linked Storage Box ID.
type: int
sample: 12345
- returned: when I(full_info=true)
+ returned: when O(full_info=true)
'''
from ansible.module_utils.basic import AnsibleModule
diff --git a/ansible_collections/community/hrobot/plugins/modules/ssh_key.py b/ansible_collections/community/hrobot/plugins/modules/ssh_key.py
index 2353514b9..e2064592c 100644
--- a/ansible_collections/community/hrobot/plugins/modules/ssh_key.py
+++ b/ansible_collections/community/hrobot/plugins/modules/ssh_key.py
@@ -38,9 +38,9 @@ options:
state:
description:
- Whether to make sure a public SSH key is present or absent.
- - C(present) makes sure that the SSH key is available, and
- potentially updates names for existing SHS public keys.
- - C(absent) makes sure that the SSH key is not available.
+ - V(present) makes sure that the SSH key is available, and
+ potentially updates names for existing SSH public keys.
+ - V(absent) makes sure that the SSH key is not available.
The fingerprint or public key data is used for matching the
key.
required: true
@@ -51,19 +51,19 @@ options:
name:
description:
- The public key's name.
- - Required if I(state=present), and ignored if I(state=absent).
+ - Required if O(state=present), and ignored if O(state=absent).
type: str
fingerprint:
description:
- The MD5 fingerprint of the public SSH key to remove.
- - One of I(public_key) and I(fingerprint) are required if I(state=absent).
+ - One of O(public_key) and O(fingerprint) are required if O(state=absent).
type: str
public_key:
description:
- The public key data in OpenSSH format.
- - "Example: C(ssh-rsa AAAAB3NzaC1yc+...)"
- - One of I(public_key) and I(fingerprint) are required if I(state=absent).
- - Required if I(state=present).
+ - "Example: V(ssh-rsa AAAAB3NzaC1yc+...)"
+ - One of O(public_key) and O(fingerprint) are required if O(state=absent).
+ - Required if O(state=present).
type: str
'''
diff --git a/ansible_collections/community/hrobot/plugins/modules/v_switch.py b/ansible_collections/community/hrobot/plugins/modules/v_switch.py
index 6035392a4..f4ab27a11 100644
--- a/ansible_collections/community/hrobot/plugins/modules/v_switch.py
+++ b/ansible_collections/community/hrobot/plugins/modules/v_switch.py
@@ -51,9 +51,9 @@ options:
state:
description:
- State of the vSwitch.
- - vSwitch is created if state is C(present), and deleted if state is C(absent).
- - C(absent) just cancels the vSwitch at the end of the current day.
- - When cancelling, you have to specify I(servers=[]) if you want to actively remove the servers in the vSwitch.
+ - vSwitch is created if state is V(present), and deleted if state is V(absent).
+ - V(absent) just cancels the vSwitch at the end of the current day.
+ - When cancelling, you have to specify O(servers=[]) if you want to actively remove the servers in the vSwitch.
type: str
default: present
choices: [ present, absent ]
diff --git a/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.json b/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.json
index c2e612e5f..9a28d174f 100644
--- a/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.json
+++ b/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.json
@@ -1,10 +1,13 @@
{
"include_symlinks": false,
"prefixes": [
- "docs/docsite/"
+ "docs/docsite/",
+ "plugins/",
+ "roles/"
],
"output": "path-line-column-message",
"requirements": [
+ "ansible-core",
"antsibull-docs"
]
}
diff --git a/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.py b/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.py
index 673104923..251e6d70f 100755
--- a/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.py
+++ b/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.py
@@ -13,9 +13,14 @@ import subprocess
def main():
"""Main entry point."""
- if not os.path.isdir(os.path.join('docs', 'docsite')):
- return
- p = subprocess.run(['antsibull-docs', 'lint-collection-docs', '.'], check=False)
+ env = os.environ.copy()
+ suffix = ':{env}'.format(env=env["ANSIBLE_COLLECTIONS_PATH"]) if 'ANSIBLE_COLLECTIONS_PATH' in env else ''
+ env['ANSIBLE_COLLECTIONS_PATH'] = '{root}{suffix}'.format(root=os.path.dirname(os.path.dirname(os.path.dirname(os.getcwd()))), suffix=suffix)
+ p = subprocess.run(
+ ['antsibull-docs', 'lint-collection-docs', '--plugin-docs', '--skip-rstcheck', '.'],
+ env=env,
+ check=False,
+ )
if p.returncode not in (0, 3):
print('{0}:0:0: unexpected return code {1}'.format(sys.argv[0], p.returncode))
diff --git a/ansible_collections/community/hrobot/tests/sanity/ignore-2.16.txt b/ansible_collections/community/hrobot/tests/sanity/ignore-2.16.txt
new file mode 100644
index 000000000..0d9329fad
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.16.txt
@@ -0,0 +1 @@
+tests/ee/roles/smoke/library/smoke_ipaddress.py shebang
diff --git a/ansible_collections/community/hrobot/tests/sanity/ignore-2.16.txt.license b/ansible_collections/community/hrobot/tests/sanity/ignore-2.16.txt.license
new file mode 100644
index 000000000..edff8c768
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.16.txt.license
@@ -0,0 +1,3 @@
+GNU General Public License v3.0+ (see LICENSES/GPL-3.0-or-later.txt or https://www.gnu.org/licenses/gpl-3.0.txt)
+SPDX-License-Identifier: GPL-3.0-or-later
+SPDX-FileCopyrightText: Ansible Project
diff --git a/ansible_collections/community/hrobot/tests/sanity/ignore-2.17.txt b/ansible_collections/community/hrobot/tests/sanity/ignore-2.17.txt
new file mode 100644
index 000000000..0d9329fad
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.17.txt
@@ -0,0 +1 @@
+tests/ee/roles/smoke/library/smoke_ipaddress.py shebang
diff --git a/ansible_collections/community/hrobot/tests/sanity/ignore-2.17.txt.license b/ansible_collections/community/hrobot/tests/sanity/ignore-2.17.txt.license
new file mode 100644
index 000000000..edff8c768
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.17.txt.license
@@ -0,0 +1,3 @@
+GNU General Public License v3.0+ (see LICENSES/GPL-3.0-or-later.txt or https://www.gnu.org/licenses/gpl-3.0.txt)
+SPDX-License-Identifier: GPL-3.0-or-later
+SPDX-FileCopyrightText: Ansible Project
diff --git a/ansible_collections/community/hrobot/tests/unit/plugins/inventory/test_robot.py b/ansible_collections/community/hrobot/tests/unit/plugins/inventory/test_robot.py
index 31d6adae0..d5514aee5 100644
--- a/ansible_collections/community/hrobot/tests/unit/plugins/inventory/test_robot.py
+++ b/ansible_collections/community/hrobot/tests/unit/plugins/inventory/test_robot.py
@@ -17,6 +17,7 @@ from ansible.inventory.data import InventoryData
from ansible.inventory.manager import InventoryManager
from ansible.module_utils.common.text.converters import to_native
from ansible.template import Templar
+from ansible.utils.unsafe_proxy import AnsibleUnsafe
from ansible_collections.community.internal_test_tools.tests.unit.mock.path import mock_unfrackpath_noop
from ansible_collections.community.internal_test_tools.tests.unit.mock.loader import DictDataLoader
@@ -60,7 +61,7 @@ def inventory():
def get_option(option):
- if option == 'filters':
+ if option == 'simple_filters':
return {}
if option == 'hetzner_user':
return 'test'
@@ -159,7 +160,7 @@ def test_inventory_file_simple(mocker):
plugin: community.hrobot.robot
hetzner_user: test
hetzner_password: hunter2
- filters:
+ simple_filters:
dc: foo
""")}
im = InventoryManager(loader=DictDataLoader(inventory_file), sources=inventory_filename)
@@ -216,7 +217,7 @@ def test_inventory_file_simple_2(mocker):
plugin: community.hrobot.robot
hetzner_user: '{{ "test" }}'
hetzner_password: '{{ "hunter2" }}'
- filters:
+ simple_filters:
dc: foo
""")}
im = InventoryManager(loader=DictDataLoader(inventory_file), sources=inventory_filename)
@@ -260,7 +261,7 @@ def test_inventory_file_fail(mocker, error_result):
plugin: community.hrobot.robot
hetzner_user: test
hetzner_password: hunter2
- filters:
+ simple_filters:
dc: foo
""")}
im = InventoryManager(loader=DictDataLoader(inventory_file), sources=inventory_filename)
@@ -359,3 +360,56 @@ def test_inventory_file_collision(mocker):
assert len(im._inventory.groups['ungrouped'].hosts) == 1
assert len(im._inventory.groups['all'].hosts) == 0
# TODO: check for warning
+
+
+def test_unsafe(inventory, mocker):
+ open_url = OpenUrlProxy([
+ OpenUrlCall('GET', 200)
+ .result_json([
+ {
+ 'server': {
+ 'server_ip': '1.2.3.4',
+ 'dc': 'abc',
+ },
+ },
+ {
+ 'server': {
+ 'server_ip': '1.2.3.5',
+ 'server_name': 'foo',
+ 'dc': 'EVALU{{ "" }}ATED',
+ },
+ },
+ ])
+ .expect_url('{0}/server'.format(BASE_URL)),
+ ])
+ mocker.patch('ansible_collections.community.hrobot.plugins.module_utils.robot.open_url', open_url)
+
+ inventory.get_option = mocker.MagicMock(side_effect=get_option)
+ inventory.populate(inventory.get_servers())
+
+ open_url.assert_is_done()
+
+ host_1 = inventory.inventory.get_host('1.2.3.4')
+ host_2 = inventory.inventory.get_host('foo')
+
+ host_1_vars = host_1.get_vars()
+ host_2_vars = host_2.get_vars()
+
+ assert host_1_vars['ansible_host'] == '1.2.3.4'
+ assert host_1_vars['hrobot_server_ip'] == '1.2.3.4'
+ assert host_1_vars['hrobot_dc'] == 'abc'
+
+ assert host_2_vars['ansible_host'] == '1.2.3.5'
+ assert host_2_vars['hrobot_server_ip'] == '1.2.3.5'
+ assert host_2_vars['hrobot_server_name'] == 'foo'
+ assert host_2_vars['hrobot_dc'] == 'EVALU{{ "" }}ATED'
+
+ # Make sure everything is unsafe
+ assert isinstance(host_1_vars['ansible_host'], AnsibleUnsafe)
+ assert isinstance(host_1_vars['hrobot_server_ip'], AnsibleUnsafe)
+ assert isinstance(host_1_vars['hrobot_dc'], AnsibleUnsafe)
+
+ assert isinstance(host_2_vars['ansible_host'], AnsibleUnsafe)
+ assert isinstance(host_2_vars['hrobot_server_ip'], AnsibleUnsafe)
+ assert isinstance(host_2_vars['hrobot_server_name'], AnsibleUnsafe)
+ assert isinstance(host_2_vars['hrobot_dc'], AnsibleUnsafe)
diff --git a/ansible_collections/community/hrobot/tests/unit/plugins/module_utils/test_failover.py b/ansible_collections/community/hrobot/tests/unit/plugins/module_utils/test_failover.py
index 56cd02944..dc1a3911d 100644
--- a/ansible_collections/community/hrobot/tests/unit/plugins/module_utils/test_failover.py
+++ b/ansible_collections/community/hrobot/tests/unit/plugins/module_utils/test_failover.py
@@ -67,14 +67,22 @@ GET_FAILOVER_FAIL = [
),
)).encode('utf-8'),
)),
- 'Request failed: 400 foo (bar)'
+ 'Request failed: 400 foo (bar)',
+ {
+ 'error': {
+ 'code': 'foo',
+ 'status': 400,
+ 'message': 'bar',
+ },
+ },
),
(
'1.2.3.4',
(None, dict(
body='{"foo": "bar"}'.encode('utf-8'),
)),
- 'Cannot interpret result: {"foo": "bar"}'
+ 'Cannot interpret result: {"foo": "bar"}',
+ {},
),
]
@@ -87,16 +95,16 @@ def test_get_failover_record(monkeypatch, ip, return_value, result, record):
assert failover.get_failover_record(module, ip) == record
-@pytest.mark.parametrize("ip, return_value, result", GET_FAILOVER_FAIL)
-def test_get_failover_record_fail(monkeypatch, ip, return_value, result):
+@pytest.mark.parametrize("ip, return_value, fail_msg, fail_kwargs", GET_FAILOVER_FAIL)
+def test_get_failover_record_fail(monkeypatch, ip, return_value, fail_msg, fail_kwargs):
module = get_module_mock()
robot.fetch_url = MagicMock(return_value=copy.deepcopy(return_value))
with pytest.raises(ModuleFailException) as exc:
failover.get_failover_record(module, ip)
- assert exc.value.fail_msg == result
- assert exc.value.fail_kwargs == dict()
+ assert exc.value.fail_msg == fail_msg
+ assert exc.value.fail_kwargs == fail_kwargs
@pytest.mark.parametrize("ip, return_value, result, record", GET_FAILOVER_SUCCESS)
@@ -107,16 +115,16 @@ def test_get_failover(monkeypatch, ip, return_value, result, record):
assert failover.get_failover(module, ip) == result
-@pytest.mark.parametrize("ip, return_value, result", GET_FAILOVER_FAIL)
-def test_get_failover_fail(monkeypatch, ip, return_value, result):
+@pytest.mark.parametrize("ip, return_value, fail_msg, fail_kwargs", GET_FAILOVER_FAIL)
+def test_get_failover_fail(monkeypatch, ip, return_value, fail_msg, fail_kwargs):
module = get_module_mock()
robot.fetch_url = MagicMock(return_value=copy.deepcopy(return_value))
with pytest.raises(ModuleFailException) as exc:
failover.get_failover(module, ip)
- assert exc.value.fail_msg == result
- assert exc.value.fail_kwargs == dict()
+ assert exc.value.fail_msg == fail_msg
+ assert exc.value.fail_kwargs == fail_kwargs
# ########################################################################################
@@ -164,7 +172,14 @@ SET_FAILOVER_FAIL = [
),
)).encode('utf-8'),
)),
- 'Request failed: 400 foo (bar)'
+ 'Request failed: 400 foo (bar)',
+ {
+ 'error': {
+ 'code': 'foo',
+ 'status': 400,
+ 'message': 'bar',
+ },
+ },
),
]
@@ -177,13 +192,13 @@ def test_set_failover(monkeypatch, ip, value, return_value, result):
assert failover.set_failover(module, ip, value) == result
-@pytest.mark.parametrize("ip, value, return_value, result", SET_FAILOVER_FAIL)
-def test_set_failover_fail(monkeypatch, ip, value, return_value, result):
+@pytest.mark.parametrize("ip, value, return_value, fail_msg, fail_kwargs", SET_FAILOVER_FAIL)
+def test_set_failover_fail(monkeypatch, ip, value, return_value, fail_msg, fail_kwargs):
module = get_module_mock()
robot.fetch_url = MagicMock(return_value=copy.deepcopy(return_value))
with pytest.raises(ModuleFailException) as exc:
failover.set_failover(module, ip, value)
- assert exc.value.fail_msg == result
- assert exc.value.fail_kwargs == dict()
+ assert exc.value.fail_msg == fail_msg
+ assert exc.value.fail_kwargs == fail_kwargs
diff --git a/ansible_collections/community/hrobot/tests/unit/plugins/module_utils/test_robot.py b/ansible_collections/community/hrobot/tests/unit/plugins/module_utils/test_robot.py
index b53049e8b..8f5c5cd67 100644
--- a/ansible_collections/community/hrobot/tests/unit/plugins/module_utils/test_robot.py
+++ b/ansible_collections/community/hrobot/tests/unit/plugins/module_utils/test_robot.py
@@ -80,7 +80,14 @@ FETCH_URL_JSON_FAIL = [
)).encode('utf-8'),
)),
None,
- 'Request failed: 400 foo (bar)'
+ 'Request failed: 400 foo (bar)',
+ {
+ 'error': {
+ 'code': "foo",
+ 'status': 400,
+ 'message': "bar",
+ },
+ },
),
(
(None, dict(
@@ -89,21 +96,67 @@ FETCH_URL_JSON_FAIL = [
code="foo",
status=400,
message="bar",
+ missing=None,
+ invalid=None,
+ max_request=None,
+ interval=None,
),
)).encode('utf-8'),
)),
['bar'],
- 'Request failed: 400 foo (bar)'
+ 'Request failed: 400 foo (bar)',
+ {
+ 'error': {
+ 'code': "foo",
+ 'status': 400,
+ 'message': "bar",
+ 'missing': None,
+ 'invalid': None,
+ 'max_request': None,
+ 'interval': None,
+ },
+ },
+ ),
+ (
+ (None, dict(
+ body=json.dumps(dict(
+ error=dict(
+ code="foo",
+ status=400,
+ message="bar",
+ missing=["foo"],
+ invalid=["bar"],
+ max_request=0,
+ interval=0,
+ ),
+ )).encode('utf-8'),
+ )),
+ None,
+ "Request failed: 400 foo (bar). Missing input parameters: ['foo']. Invalid input"
+ " parameters: ['bar']. Maximum allowed requests: 0. Time interval in seconds: 0",
+ {
+ 'error': {
+ 'code': "foo",
+ 'status': 400,
+ 'message': "bar",
+ 'missing': ["foo"],
+ 'invalid': ["bar"],
+ 'max_request': 0,
+ 'interval': 0,
+ },
+ },
),
(
(None, dict(body='{this is not json}'.encode('utf-8'))),
[],
- 'Cannot decode content retrieved from https://foo/bar'
+ 'Cannot decode content retrieved from https://foo/bar',
+ {},
),
(
(None, dict(status=400)),
[],
- 'Cannot retrieve content from https://foo/bar, HTTP status code 400'
+ 'Cannot retrieve content from https://foo/bar, HTTP status code 400',
+ {},
),
]
@@ -116,16 +169,18 @@ def test_fetch_url_json(monkeypatch, return_value, accept_errors, result):
assert robot.fetch_url_json(module, 'https://foo/bar', accept_errors=accept_errors) == result
-@pytest.mark.parametrize("return_value, accept_errors, result", FETCH_URL_JSON_FAIL)
-def test_fetch_url_json_fail(monkeypatch, return_value, accept_errors, result):
+@pytest.mark.parametrize("return_value, accept_errors, fail_msg, fail_kwargs", FETCH_URL_JSON_FAIL)
+def test_fetch_url_json_fail(monkeypatch, return_value, accept_errors, fail_msg, fail_kwargs):
module = get_module_mock()
robot.fetch_url = MagicMock(return_value=return_value)
with pytest.raises(ModuleFailException) as exc:
robot.fetch_url_json(module, 'https://foo/bar', accept_errors=accept_errors)
- assert exc.value.fail_msg == result
- assert exc.value.fail_kwargs == dict()
+ print(exc.value.fail_msg)
+ print(exc.value.fail_kwargs)
+ assert exc.value.fail_msg == fail_msg
+ assert exc.value.fail_kwargs == fail_kwargs
def test_fetch_url_json_empty(monkeypatch):
@@ -139,6 +194,8 @@ def test_fetch_url_json_empty(monkeypatch):
with pytest.raises(ModuleFailException) as exc:
robot.fetch_url_json(module, 'https://foo/bar', allow_empty_result=True)
+ print(exc.value.fail_msg)
+ print(exc.value.fail_kwargs)
assert exc.value.fail_msg == 'Cannot retrieve content from https://foo/bar, HTTP status code 400'
assert exc.value.fail_kwargs == dict()
@@ -153,8 +210,8 @@ def test_plugin_open_url_json(monkeypatch, return_value, accept_errors, result):
assert robot.plugin_open_url_json(plugin, 'https://foo/bar', accept_errors=accept_errors) == result
-@pytest.mark.parametrize("return_value, accept_errors, result", FETCH_URL_JSON_FAIL)
-def test_plugin_open_url_json_fail(monkeypatch, return_value, accept_errors, result):
+@pytest.mark.parametrize("return_value, accept_errors, fail_msg, fail_kwargs", FETCH_URL_JSON_FAIL)
+def test_plugin_open_url_json_fail(monkeypatch, return_value, accept_errors, fail_msg, fail_kwargs):
response = MagicMock()
response.read = MagicMock(return_value=return_value[1].get('body', ''))
robot.open_url = MagicMock(side_effect=robot.HTTPError('https://foo/bar', 400, 'Error!', {}, response))
@@ -163,7 +220,8 @@ def test_plugin_open_url_json_fail(monkeypatch, return_value, accept_errors, res
with pytest.raises(robot.PluginException) as exc:
robot.plugin_open_url_json(plugin, 'https://foo/bar', accept_errors=accept_errors)
- assert exc.value.error_message == result
+ print(exc.value.error_message)
+ assert exc.value.error_message == fail_msg
def test_plugin_open_url_json_fail_other(monkeypatch):
diff --git a/ansible_collections/community/hrobot/tests/requirements.yml b/ansible_collections/community/hrobot/tests/unit/requirements.yml
index dde980c10..586a6a1b3 100644
--- a/ansible_collections/community/hrobot/tests/requirements.yml
+++ b/ansible_collections/community/hrobot/tests/unit/requirements.yml
@@ -3,5 +3,5 @@
# GNU General Public License v3.0+ (see LICENSES/GPL-3.0-or-later.txt or https://www.gnu.org/licenses/gpl-3.0.txt)
# SPDX-License-Identifier: GPL-3.0-or-later
-unit_tests_dependencies:
+collections:
- community.internal_test_tools