pypa/pip · error · IDNAError
Label too long
Error message
Label too long
What it means
Raised by idna.check_bidi when the input label handed to the Bidi Rule check exceeds _max_input_length (1024 characters). It is a defensive guard placed at the top of check_bidi to reject pathologically long inputs before any per-codepoint work, distinct from the DNS 63-octet label limit enforced elsewhere.
Source
Thrown at src/pip/_vendor/idna/core.py:116
def check_bidi(label: str, check_ltr: bool = False) -> bool:
"""Validate the Bidi Rule from :rfc:`5893` for a single label.
The Bidi Rule constrains how bidirectional characters (Hebrew, Arabic,
etc.) may appear within a label. By default the check is only applied
when the label contains at least one right-to-left character (Unicode
bidirectional categories ``R``, ``AL``, or ``AN``); set ``check_ltr``
to ``True`` to apply it to LTR-only labels as well.
:param label: The label to validate, as a Unicode string.
:param check_ltr: If ``True``, apply the rules even when the label
contains no RTL characters.
:returns: ``True`` if the label satisfies the Bidi Rule.
:raises IDNABidiError: If any of Bidi Rule conditions 1-6 are violated,
or if the directional category of a codepoint cannot be determined.
"""
if len(label) > _max_input_length:
raise IDNAError("Label too long")
# Bidi rules should only be applied if string contains RTL characters
bidi_label = False
for idx, cp in enumerate(label, 1):
direction = unicodedata.bidirectional(cp)
if direction == "":
# String likely comes from a newer version of Unicode
raise IDNABidiError(f"Unknown directionality in label {label!r} at position {idx}")
if direction in _bidi_rtl_categories:
bidi_label = True
if not bidi_label and not check_ltr:
return True
# Bidi rule 1
direction = unicodedata.bidirectional(label[0])
if direction in _bidi_rtl_first:
rtl = True
elif direction == "L":
rtl = FalseView on GitHub (pinned to d7d0d0a394)
Solutions
- Validate the input length before calling idna: reject or truncate labels longer than 63 characters (the real DNS limit) rather than 1024.
- Split the domain into labels on '.' (and the Unicode dot equivalents) and encode each label separately.
- Sanitize upstream so hostnames come from a bounded, trusted source.
Example fix
# before
idna.encode(user_supplied_long_string) # Label too long
# after
if len(label) > 63:
raise ValueError('label exceeds DNS 63-octet limit')
idna.encode(label) Defensive patterns
Strategy: validation
Validate before calling
MAX_LABEL = 63
def validate_label(label: str) -> str:
if len(label) > MAX_LABEL:
raise ValueError(f'label too long ({len(label)} > {MAX_LABEL})')
return label Type guard
def is_valid_label_length(label: str) -> bool:
return 0 < len(label) <= 63 Try / catch
from idna import IDNAError
try:
idna.check_bidi(label)
except IDNAError as e:
if 'too long' in str(e).lower():
raise ValueError('label exceeds length limit') from e
raise Prevention
- Enforce a 63-char per-label cap at the input boundary, well below idna's 1024 defensive guard.
- Split multi-label domains on '.' before IDNA rather than passing the whole domain as one label.
- Reject unbounded user text as hostnames; hostnames come from trusted, bounded sources.
When it happens
Trigger: Calling idna.encode/decode/check_bidi/alabel/ulabel with a single label longer than 1024 chars; passing an unsplit full domain string (with no dot separators) into a code path that ends in check_bidi.
Common situations: User input or scraped data containing a huge unbroken token being treated as a hostname; a bug in a URL parser that fails to split labels before IDNA encoding; fuzzing / property-based tests feeding arbitrary long strings.
Related errors
- Empty Label
- Label has disallowed hyphens in 3rd and 4th position
- Label must not start or end with a hyphen
- {name} has an invalid wheel, {e}
- multiple .dist-info directories found: {}
AI-assisted analysis of pypa/pip@d7d0d0a394 (2026-08-04).
Data as JSON: /data/errors/94c78f58c78e2ec6.json.
Report an issue: GitHub.