ansible/ansible · error · AnsibleParserError
Detected range in host but was asked to ignore ranges
Error message
Detected range in host but was asked to ignore ranges
What it means
Raised by parse_address() in lib/ansible/parsing/utils/addresses.py when the string parsed successfully as a host pattern containing one or more '[' range specifications (e.g. foo[1:3].example.com) but the caller passed allow_ranges=False. The pattern is valid, but the caller explicitly declined to accept ranges, so it is treated as a parse failure via AnsibleParserError.
Source
Thrown at lib/ansible/parsing/utils/addresses.py:212
# What we're left with now must be an IPv4 or IPv6 address, possibly with
# numeric ranges, or a hostname with alphanumeric ranges.
host = None
for matching in ['ipv4', 'ipv6', 'hostname']:
m = patterns[matching].match(address)
if m:
host = address
continue
# If it isn't any of the above, we don't understand it.
if not host:
raise AnsibleError("Not a valid network hostname: %s" % address)
# If we get to this point, we know that any included ranges are valid.
# If the caller is prepared to handle them, all is well.
# Otherwise we treat it as a parse failure.
if not allow_ranges and '[' in host:
raise AnsibleParserError("Detected range in host but was asked to ignore ranges")
return (host, port)
View on GitHub (pinned to 9cf16a4aca)
Solutions
- Expand the range before parsing: use ansible.plugins.inventory.expand_hostname_range() or ansible.utils.display helpers to turn 'web[1:3]' into individual hosts, then call parse_address() on each.
- If you actually want a single host, remove the '[...]' range syntax and pass the literal hostname.
- If your code genuinely supports patterns, call parse_address(address, allow_ranges=True) and handle the range yourself.
Example fix
# before
host, port = parse_address('web[01:03]') # raises
# after
from ansible.plugins.inventory import expand_hostname_range
for h in expand_hostname_range('web[01:03]'):
host, port = parse_address(h) Defensive patterns
Strategy: validation
Validate before calling
from ansible.parsing.utils.addresses import parse_address
def parse_single_host(address: str):
# reject inventory range syntax before it reaches parse_address
if '[' in address or ']' in address:
raise ValueError(f'range pattern not allowed here: {address!r} — expand it first')
return parse_address(address, allow_ranges=False) Try / catch
from ansible.errors import AnsibleParserError, AnsibleError
from ansible.parsing.utils.addresses import parse_address
try:
host, port = parse_address(address)
except AnsibleParserError as e: # range in host
hosts = expand_hostname_range(address)
results = [parse_address(h) for h in hosts]
except AnsibleError:
raise Prevention
- Decide explicitly whether a code path accepts patterns; pass allow_ranges=True only where you handle ranges.
- Expand inventory ranges with expand_hostname_range() before single-host APIs like connection settings.
- Keep bracket range syntax inside inventory definitions, not module arguments.
When it happens
Trigger: Calling parse_address('web[01:05]', allow_ranges=False), which is the default; any code path that needs one concrete host (e.g. connection plugins resolving a single target) hitting inventory range syntax that was never expanded by the inventory layer.
Common situations: A playbook passes a range pattern like 'web[1:3]' directly to add_host, a module parameter, or a connection setting where only a single host is meaningful; the pattern failed to expand earlier (misconfigured inventory plugin or pattern used outside inventory context); user assumes bracket ranges are shell globbing rather than Ansible inventory syntax.
Related errors
- Not a valid network hostname: %s
- Empty {JINJA2_OVERRIDE!r} override pair not allowed.
- Missing key-value separator `:` in {JINJA2_OVERRIDE!r} overr
- The {0} inventory plugin does not take YAML type config sour
- Error reading config file (%s): %s
AI-assisted analysis of ansible/ansible@9cf16a4aca (2026-08-15).
Data as JSON: /api/errors/41b98ad498988fdb.
Report an issue: GitHub.