summaryrefslogtreecommitdiffstats
path: root/ansible_collections/community/hrobot/tests/sanity
diff options
context:
space:
mode:
authorDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-13 12:04:41 +0000
committerDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-13 12:04:41 +0000
commit975f66f2eebe9dadba04f275774d4ab83f74cf25 (patch)
tree89bd26a93aaae6a25749145b7e4bca4a1e75b2be /ansible_collections/community/hrobot/tests/sanity
parentInitial commit. (diff)
downloadansible-975f66f2eebe9dadba04f275774d4ab83f74cf25.tar.xz
ansible-975f66f2eebe9dadba04f275774d4ab83f74cf25.zip
Adding upstream version 7.7.0+dfsg.upstream/7.7.0+dfsg
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'ansible_collections/community/hrobot/tests/sanity')
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.json10
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.json.license3
-rwxr-xr-xansible_collections/community/hrobot/tests/sanity/extra/extra-docs.py24
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/extra/licenses.json4
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/extra/licenses.json.license3
-rwxr-xr-xansible_collections/community/hrobot/tests/sanity/extra/licenses.py110
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/extra/licenses.py.license3
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/extra/no-unwanted-files.json7
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/extra/no-unwanted-files.json.license3
-rwxr-xr-xansible_collections/community/hrobot/tests/sanity/extra/no-unwanted-files.py44
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.10.txt8
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.10.txt.license3
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.11.txt7
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.11.txt.license3
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.12.txt7
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.12.txt.license3
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.13.txt1
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.13.txt.license3
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.14.txt1
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.14.txt.license3
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.15.txt1
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.15.txt.license3
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.9.txt3
-rw-r--r--ansible_collections/community/hrobot/tests/sanity/ignore-2.9.txt.license3
24 files changed, 260 insertions, 0 deletions
diff --git a/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.json b/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.json
new file mode 100644
index 000000000..c2e612e5f
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.json
@@ -0,0 +1,10 @@
+{
+ "include_symlinks": false,
+ "prefixes": [
+ "docs/docsite/"
+ ],
+ "output": "path-line-column-message",
+ "requirements": [
+ "antsibull-docs"
+ ]
+}
diff --git a/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.json.license b/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.json.license
new file mode 100644
index 000000000..edff8c768
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.json.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/extra/extra-docs.py b/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.py
new file mode 100755
index 000000000..673104923
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/extra/extra-docs.py
@@ -0,0 +1,24 @@
+#!/usr/bin/env python
+# Copyright (c) Ansible Project
+# 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
+"""Check extra collection docs with antsibull-docs."""
+from __future__ import (absolute_import, division, print_function)
+__metaclass__ = type
+
+import os
+import sys
+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)
+ if p.returncode not in (0, 3):
+ print('{0}:0:0: unexpected return code {1}'.format(sys.argv[0], p.returncode))
+
+
+if __name__ == '__main__':
+ main()
diff --git a/ansible_collections/community/hrobot/tests/sanity/extra/licenses.json b/ansible_collections/community/hrobot/tests/sanity/extra/licenses.json
new file mode 100644
index 000000000..50e47ca88
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/extra/licenses.json
@@ -0,0 +1,4 @@
+{
+ "include_symlinks": false,
+ "output": "path-message"
+}
diff --git a/ansible_collections/community/hrobot/tests/sanity/extra/licenses.json.license b/ansible_collections/community/hrobot/tests/sanity/extra/licenses.json.license
new file mode 100644
index 000000000..edff8c768
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/extra/licenses.json.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/extra/licenses.py b/ansible_collections/community/hrobot/tests/sanity/extra/licenses.py
new file mode 100755
index 000000000..80eb795ef
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/extra/licenses.py
@@ -0,0 +1,110 @@
+#!/usr/bin/env python
+# Copyright (c) 2022, Felix Fontein <felix@fontein.de>
+# 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
+"""Prevent files without a correct license identifier from being added to the source tree."""
+from __future__ import (absolute_import, division, print_function)
+__metaclass__ = type
+
+import os
+import glob
+import sys
+
+
+def format_license_list(licenses):
+ if not licenses:
+ return '(empty)'
+ return ', '.join(['"%s"' % license for license in licenses])
+
+
+def find_licenses(filename, relax=False):
+ spdx_license_identifiers = []
+ other_license_identifiers = []
+ has_copyright = False
+ try:
+ with open(filename, 'r', encoding='utf-8') as f:
+ for line in f:
+ line = line.rstrip()
+ if 'Copyright ' in line:
+ has_copyright = True
+ if 'Copyright: ' in line:
+ print('%s: found copyright line with "Copyright:". Please remove the colon.' % (filename, ))
+ if 'SPDX-FileCopyrightText: ' in line:
+ has_copyright = True
+ idx = line.find('SPDX-License-Identifier: ')
+ if idx >= 0:
+ lic_id = line[idx + len('SPDX-License-Identifier: '):]
+ spdx_license_identifiers.extend(lic_id.split(' OR '))
+ if 'GNU General Public License' in line:
+ if 'v3.0+' in line:
+ other_license_identifiers.append('GPL-3.0-or-later')
+ if 'version 3 or later' in line:
+ other_license_identifiers.append('GPL-3.0-or-later')
+ if 'Simplified BSD License' in line:
+ other_license_identifiers.append('BSD-2-Clause')
+ if 'Apache License 2.0' in line:
+ other_license_identifiers.append('Apache-2.0')
+ if 'PSF License' in line or 'Python-2.0' in line:
+ other_license_identifiers.append('PSF-2.0')
+ if 'MIT License' in line:
+ other_license_identifiers.append('MIT')
+ except Exception as exc:
+ print('%s: error while processing file: %s' % (filename, exc))
+ if len(set(spdx_license_identifiers)) < len(spdx_license_identifiers):
+ print('%s: found identical SPDX-License-Identifier values' % (filename, ))
+ if other_license_identifiers and set(other_license_identifiers) != set(spdx_license_identifiers):
+ print('%s: SPDX-License-Identifier yielded the license list %s, while manual guessing yielded the license list %s' % (
+ filename, format_license_list(spdx_license_identifiers), format_license_list(other_license_identifiers)))
+ if not has_copyright and not relax:
+ print('%s: found no copyright notice' % (filename, ))
+ return sorted(spdx_license_identifiers)
+
+
+def main():
+ """Main entry point."""
+ paths = sys.argv[1:] or sys.stdin.read().splitlines()
+
+ # The following paths are allowed to have no license identifier
+ no_comments_allowed = [
+ 'changelogs/fragments/*.yml',
+ 'changelogs/fragments/*.yaml',
+ ]
+
+ # These files are completely ignored
+ ignore_paths = [
+ '.ansible-test-timeout.json',
+ '.reuse/dep5',
+ 'LICENSES/*.txt',
+ 'COPYING',
+ ]
+
+ no_comments_allowed = [fn for pattern in no_comments_allowed for fn in glob.glob(pattern)]
+ ignore_paths = [fn for pattern in ignore_paths for fn in glob.glob(pattern)]
+
+ valid_licenses = [license_file[len('LICENSES/'):-len('.txt')] for license_file in glob.glob('LICENSES/*.txt')]
+
+ for path in paths:
+ if path.startswith('./'):
+ path = path[2:]
+ if path in ignore_paths or path.startswith('tests/output/'):
+ continue
+ if os.stat(path).st_size == 0:
+ continue
+ if not path.endswith('.license') and os.path.exists(path + '.license'):
+ path = path + '.license'
+ valid_licenses_for_path = valid_licenses
+ if path.startswith('plugins/') and not path.startswith(('plugins/modules/', 'plugins/module_utils/')):
+ valid_licenses_for_path = [license for license in valid_licenses if license == 'GPL-3.0-or-later']
+ licenses = find_licenses(path, relax=path in no_comments_allowed)
+ if not licenses:
+ if path not in no_comments_allowed:
+ print('%s: must have at least one license' % (path, ))
+ else:
+ for license in licenses:
+ if license not in valid_licenses_for_path:
+ print('%s: found not allowed license "%s", must be one of %s' % (
+ path, license, format_license_list(valid_licenses_for_path)))
+
+
+if __name__ == '__main__':
+ main()
diff --git a/ansible_collections/community/hrobot/tests/sanity/extra/licenses.py.license b/ansible_collections/community/hrobot/tests/sanity/extra/licenses.py.license
new file mode 100644
index 000000000..6c4958feb
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/extra/licenses.py.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: 2022, Felix Fontein <felix@fontein.de>
diff --git a/ansible_collections/community/hrobot/tests/sanity/extra/no-unwanted-files.json b/ansible_collections/community/hrobot/tests/sanity/extra/no-unwanted-files.json
new file mode 100644
index 000000000..c789a7fd3
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/extra/no-unwanted-files.json
@@ -0,0 +1,7 @@
+{
+ "include_symlinks": true,
+ "prefixes": [
+ "plugins/"
+ ],
+ "output": "path-message"
+}
diff --git a/ansible_collections/community/hrobot/tests/sanity/extra/no-unwanted-files.json.license b/ansible_collections/community/hrobot/tests/sanity/extra/no-unwanted-files.json.license
new file mode 100644
index 000000000..edff8c768
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/extra/no-unwanted-files.json.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/extra/no-unwanted-files.py b/ansible_collections/community/hrobot/tests/sanity/extra/no-unwanted-files.py
new file mode 100755
index 000000000..51444ab75
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/extra/no-unwanted-files.py
@@ -0,0 +1,44 @@
+#!/usr/bin/env python
+# Copyright (c) Ansible Project
+# 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
+"""Prevent unwanted files from being added to the source tree."""
+from __future__ import (absolute_import, division, print_function)
+__metaclass__ = type
+
+import os
+import sys
+
+
+def main():
+ """Main entry point."""
+ paths = sys.argv[1:] or sys.stdin.read().splitlines()
+
+ allowed_extensions = (
+ '.cs',
+ '.ps1',
+ '.psm1',
+ '.py',
+ )
+
+ skip_paths = set([
+ ])
+
+ skip_directories = (
+ )
+
+ for path in paths:
+ if path in skip_paths:
+ continue
+
+ if any(path.startswith(skip_directory) for skip_directory in skip_directories):
+ continue
+
+ ext = os.path.splitext(path)[1]
+
+ if ext not in allowed_extensions:
+ print('%s: extension must be one of: %s' % (path, ', '.join(allowed_extensions)))
+
+
+if __name__ == '__main__':
+ main()
diff --git a/ansible_collections/community/hrobot/tests/sanity/ignore-2.10.txt b/ansible_collections/community/hrobot/tests/sanity/ignore-2.10.txt
new file mode 100644
index 000000000..c368addc9
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.10.txt
@@ -0,0 +1,8 @@
+plugins/modules/boot.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/firewall.py pylint:bad-option-value # a pylint test that is disabled was modified over time
+plugins/modules/firewall.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/firewall_info.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/server.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/server_info.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/v_switch.py validate-modules:return-syntax-error # only allowed in 2.13+
+tests/ee/roles/smoke/library/smoke_ipaddress.py shebang
diff --git a/ansible_collections/community/hrobot/tests/sanity/ignore-2.10.txt.license b/ansible_collections/community/hrobot/tests/sanity/ignore-2.10.txt.license
new file mode 100644
index 000000000..edff8c768
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.10.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.11.txt b/ansible_collections/community/hrobot/tests/sanity/ignore-2.11.txt
new file mode 100644
index 000000000..cfbc8b045
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.11.txt
@@ -0,0 +1,7 @@
+plugins/modules/boot.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/firewall.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/firewall_info.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/server.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/server_info.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/v_switch.py validate-modules:return-syntax-error # only allowed in 2.13+
+tests/ee/roles/smoke/library/smoke_ipaddress.py shebang
diff --git a/ansible_collections/community/hrobot/tests/sanity/ignore-2.11.txt.license b/ansible_collections/community/hrobot/tests/sanity/ignore-2.11.txt.license
new file mode 100644
index 000000000..edff8c768
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.11.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.12.txt b/ansible_collections/community/hrobot/tests/sanity/ignore-2.12.txt
new file mode 100644
index 000000000..cfbc8b045
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.12.txt
@@ -0,0 +1,7 @@
+plugins/modules/boot.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/firewall.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/firewall_info.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/server.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/server_info.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/v_switch.py validate-modules:return-syntax-error # only allowed in 2.13+
+tests/ee/roles/smoke/library/smoke_ipaddress.py shebang
diff --git a/ansible_collections/community/hrobot/tests/sanity/ignore-2.12.txt.license b/ansible_collections/community/hrobot/tests/sanity/ignore-2.12.txt.license
new file mode 100644
index 000000000..edff8c768
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.12.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.13.txt b/ansible_collections/community/hrobot/tests/sanity/ignore-2.13.txt
new file mode 100644
index 000000000..0d9329fad
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.13.txt
@@ -0,0 +1 @@
+tests/ee/roles/smoke/library/smoke_ipaddress.py shebang
diff --git a/ansible_collections/community/hrobot/tests/sanity/ignore-2.13.txt.license b/ansible_collections/community/hrobot/tests/sanity/ignore-2.13.txt.license
new file mode 100644
index 000000000..edff8c768
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.13.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.14.txt b/ansible_collections/community/hrobot/tests/sanity/ignore-2.14.txt
new file mode 100644
index 000000000..0d9329fad
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.14.txt
@@ -0,0 +1 @@
+tests/ee/roles/smoke/library/smoke_ipaddress.py shebang
diff --git a/ansible_collections/community/hrobot/tests/sanity/ignore-2.14.txt.license b/ansible_collections/community/hrobot/tests/sanity/ignore-2.14.txt.license
new file mode 100644
index 000000000..edff8c768
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.14.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.15.txt b/ansible_collections/community/hrobot/tests/sanity/ignore-2.15.txt
new file mode 100644
index 000000000..0d9329fad
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.15.txt
@@ -0,0 +1 @@
+tests/ee/roles/smoke/library/smoke_ipaddress.py shebang
diff --git a/ansible_collections/community/hrobot/tests/sanity/ignore-2.15.txt.license b/ansible_collections/community/hrobot/tests/sanity/ignore-2.15.txt.license
new file mode 100644
index 000000000..edff8c768
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.15.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.9.txt b/ansible_collections/community/hrobot/tests/sanity/ignore-2.9.txt
new file mode 100644
index 000000000..fd7a4e740
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.9.txt
@@ -0,0 +1,3 @@
+plugins/modules/boot.py validate-modules:return-syntax-error # only allowed in 2.13+
+plugins/modules/firewall.py pylint:bad-option-value # a pylint test that is disabled was modified over time
+tests/ee/roles/smoke/library/smoke_ipaddress.py shebang
diff --git a/ansible_collections/community/hrobot/tests/sanity/ignore-2.9.txt.license b/ansible_collections/community/hrobot/tests/sanity/ignore-2.9.txt.license
new file mode 100644
index 000000000..edff8c768
--- /dev/null
+++ b/ansible_collections/community/hrobot/tests/sanity/ignore-2.9.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