diff --git a/src/validators/domain.py b/src/validators/domain.py index 8109573c..265db181 100644 --- a/src/validators/domain.py +++ b/src/validators/domain.py @@ -76,6 +76,11 @@ def domain( if not value: return False + # The textual representation of a domain name is limited to 253 characters + # (RFC 1035), regardless of the individual label lengths. + if len(value.rstrip(".")) > 253: + return False + if consider_tld and not _IanaTLD.check(value.rstrip(".").rsplit(".", 1)[-1].upper()): return False diff --git a/tests/test_domain.py b/tests/test_domain.py index 63342f76..08b611ba 100644 --- a/tests/test_domain.py +++ b/tests/test_domain.py @@ -84,6 +84,18 @@ def test_returns_failed_validation_on_invalid_domain(value: str, rfc_1034: bool, assert isinstance(domain(value, rfc_1034=rfc_1034, rfc_2782=rfc_2782), ValidationError) +def test_returns_failed_validation_on_too_long_domain(): + """A domain over 253 characters is invalid regardless of label lengths.""" + label = "a" * 49 + too_long = ".".join([label] * 5) + ".aaaaa" # 255 characters, each label <= 63 + assert len(too_long) > 253 + assert isinstance(domain(too_long), ValidationError) + + at_limit = ".".join([label] * 5) + ".aaa" # exactly 253 characters + assert len(at_limit) == 253 + assert domain(at_limit) + + @pytest.mark.parametrize( ("value", "consider_tld", "rfc_1034", "rfc_2782"), [