1
0
Fork 0
mirror of https://github.com/ansible-collections/community.general.git synced 2026-02-04 16:01:55 +00:00
community.general/plugins/test/fqdn_valid.py
patchback[bot] b769b0bc01
[PR #11400/236b9c0e backport][stable-12] Sort imports with ruff check --fix (#11409)
Sort imports with ruff check --fix (#11400)

Sort imports with ruff check --fix.

(cherry picked from commit 236b9c0e04)

Co-authored-by: Felix Fontein <felix@fontein.de>
2026-01-09 19:36:52 +01:00

116 lines
3.7 KiB
Python

# Copyright (c) 2023, Vladimir Botka <vbotka@gmail.com>
# 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
from __future__ import annotations
DOCUMENTATION = """
name: fqdn_valid
short_description: Validates fully-qualified domain names against RFC 1123
version_added: 8.1.0
author: Vladimir Botka (@vbotka)
requirements:
- fqdn>=1.5.1 (PyPI)
description:
- This test validates Fully Qualified Domain Names (FQDNs)
conforming to the Internet Engineering Task Force specification
RFC 1123 and RFC 952.
- The design intent is to validate that a string would be
traditionally acceptable as a public Internet hostname to
RFC-conforming software, which is a strict subset of the logic
in modern web browsers like Mozilla Firefox and Chromium that
determines whether make a DNS lookup.
- Certificate Authorities like Let's Encrypt run a narrower set of
string validation logic to determine validity for issuance. This
test is not intended to achieve functional parity with CA
issuance.
- Single label names are allowed by default (O(min_labels=1)).
options:
_input:
description: Name of the host.
type: str
required: true
min_labels:
description: Required minimum of labels, separated by period.
default: 1
type: int
required: false
allow_underscores:
description: Allow underscore characters.
default: false
type: bool
required: false
"""
EXAMPLES = """
- name: Make sure that hostname is valid
ansible.builtin.assert:
that: hostname is community.general.fqdn_valid
- name: Make sure that hostname is at least 3 labels long (a.b.c)
ansible.builtin.assert:
that: hostname is community.general.fqdn_valid(min_labels=3)
- name: Make sure that hostname is at least 2 labels long (a.b). Allow '_'
ansible.builtin.assert:
that: hostname is community.general.fqdn_valid(min_labels=2, allow_underscores=True)
"""
RETURN = """
_value:
description: Whether the name is valid.
type: bool
"""
import typing as t
from collections.abc import Callable
from ansible.errors import AnsibleFilterError
ANOTHER_LIBRARY_IMPORT_ERROR: ImportError | None
try:
from fqdn import FQDN
except ImportError as imp_exc:
ANOTHER_LIBRARY_IMPORT_ERROR = imp_exc
else:
ANOTHER_LIBRARY_IMPORT_ERROR = None
def fqdn_valid(name: t.Any, min_labels: t.Any = 1, allow_underscores: t.Any = False) -> bool:
"""
Example:
- 'srv.example.com' is community.general.fqdn_valid
- 'foo_bar.example.com' is community.general.fqdn_valid(allow_underscores=True)
"""
if ANOTHER_LIBRARY_IMPORT_ERROR:
raise AnsibleFilterError(
"Python package fqdn must be installed to use this test."
) from ANOTHER_LIBRARY_IMPORT_ERROR
if not isinstance(name, str):
raise AnsibleFilterError(f"The name parameter must be a string, got {name!r} of type {type(name)}")
if not isinstance(min_labels, int):
raise AnsibleFilterError(
f"The min_labels parameter must be an integer, got {min_labels!r} of type {type(min_labels)}"
)
if not isinstance(allow_underscores, bool):
raise AnsibleFilterError(
f"The allow_underscores parameter must be a boolean, got {allow_underscores!r} of type {type(allow_underscores)}"
)
fobj = FQDN(name, min_labels=min_labels, allow_underscores=allow_underscores)
return fobj.is_valid
class TestModule:
"""Ansible test hostname validity.
https://pypi.org/project/fqdn/
"""
def tests(self) -> dict[str, Callable]:
return {
"fqdn_valid": fqdn_valid,
}