Great work!

XP to next level

BugEater

Domain Architecture & IDN

Intermediate Manual QA 96 XP 74 min

Updated: 07/07/2026

Start Module

The Structure of a Domain Name

A domain name is a hierarchical sequence of labels separated by dots. Reading right to left, the hierarchy is:

mail.example.co.uk
│    │       │  └── Top-level domain (TLD)
│    │       └───── Second-level domain (under .uk)
│    └───────────── Registered domain
└────────────────── Subdomain

The rightmost label is the top-level domain (TLD). Everything registered under it forms second-level, third-level, and deeper labels as needed.

Rules for each label (per RFC 1123):

  • 1 to 63 characters in length
  • May contain letters (A-Z, a-z), digits (0-9), and hyphens
  • May not start or end with a hyphen
  • May not contain consecutive hyphens in positions 3-4 (reserved for IDN encoding — see below)
  • Labels are case-insensitive: EXAMPLE.COM = example.com = Example.Com

Rules for the full domain:

  • Total length must not exceed 253 characters (including dots)
  • Must have at least two labels (a TLD and something registered under it)
  • Labels are separated by dots

TLD Types and the New gTLD Explosion

When the Internet was designed, there were only a handful of TLDs: .com, .net, .org, .edu, .gov, .mil, and two-letter country codes (ccTLDs) like .uk, .de, .jp.

Since 2012, ICANN opened applications for new generic TLDs (new gTLDs). Today there are over 1,500 TLDs including:

  • Short: .io, .co, .ai
  • Descriptive: .restaurant, .photography, .cancerresearch
  • Brand: .google, .apple, .amazon
  • Geographic: .london, .berlin, .tokyo
  • Internationalized: .中文 (Chinese), .москва (Russian for Moscow), .مصر (Arabic for Egypt)

This matters for validators that hardcode "TLD must be 2-4 characters" or "TLD must match this list." Both assumptions are now wrong.

Internationalized Domain Names (IDN)

The original DNS system was designed for ASCII only. To support non-ASCII domain names (Arabic, Chinese, Cyrillic, Hindi, Japanese, etc.), the IDNA standard (RFC 5891) was developed. It uses punycode encoding to represent Unicode labels in ASCII form.

Punycode encoding converts a Unicode label to an ASCII-compatible encoding (ACE) by prefixing it with xn-- and appending an ASCII encoding of the Unicode characters:

Unicode label Punycode
münchen (German) mnchen-3ya → full ACE: xn--mnchen-3ya
日本語 (Japanese) wgv71a309e → full ACE: xn--wgv71a309e
مثال (Arabic "example") mgbh0fb → full ACE: xn--mgbh0fb
пример (Russian "example") e1afmapc → full ACE: xn--e1afmapc

The browser handles the conversion transparently — when you type münchen.de in an address bar, it sends the DNS query as xn--mnchen-3ya.de.

Why xn-- Reserved Labels Matter for Testing

The label prefix xn-- is reserved for IDN. Domain names where the 3rd and 4th characters are -- (but not xn--) are technically invalid per IDNA. This is the source of the rule "labels cannot have -- in positions 3 and 4."

For validators, this means:

  • mail--server.example.com — valid (hyphens not in positions 3-4)
  • ma--server.example.com — technically ambiguous; most validators accept it
  • xn--example.com — valid punycode label (even if the Unicode form is rejected, the ACE form is syntactically valid)
  • xn--invalid.com — the xn-- prefix claims this is punycode, but "invalid" is not valid punycode; this should be rejected by IDNA-aware validators

A validator that rejects all labels containing -- is over-restrictive and will reject legitimate IDN domains. A validator that accepts all xn-- labels without verifying they decode to valid Unicode is potentially accepting garbled or spoofed domain labels.

Homograph Attacks

IDN introduces a security concern: characters from different scripts can look visually identical but have different code points. The Cyrillic letter а (U+0430) is visually indistinguishable from the Latin letter a (U+0061) in most fonts. A domain pаypal.com that looks like paypal.com but uses Cyrillic а is a different domain.

This is called a homograph attack (or IDN homograph attack). Browsers have partially mitigated it by displaying punycode in the address bar when a domain mixes scripts. But applications that process domain names without IDN awareness may be vulnerable.

For testers: if your application processes or displays domain names from user input, submitting domains with lookalike Unicode characters from other scripts is a valid security test.

Subdomain Edge Cases

Subdomains follow the same label rules but add nuance:

  • There is no limit to the number of subdomain levels, only the total domain length (253 chars)
  • a.b.c.d.e.f.g.example.com is valid if under 253 chars total
  • The wildcard * is not a valid character in domain names submitted by users (it is used in DNS records, not in client-submitted addresses)
  • An empty label (example..com) is invalid — the double dot would imply an empty label between them
  • A trailing dot (example.com.) is technically valid in DNS (it makes the root explicit) but is rarely accepted by application-level validators

Common Domain Validator Bugs

Bug: Hardcoded TLD length

if (tld.length() < 2 || tld.length() > 4) return invalid;

Rejects .museum (6), .photography (11), .cancerresearch (14), and every new gTLD longer than 4 characters.

Bug: Static TLD list

A validator that checks TLDs against a hardcoded list will become incorrect as new TLDs are added. By the time the list is updated, real users with valid TLDs have been rejected.

Bug: Rejecting labels starting with digit

RFC 1123 explicitly updated RFC 952 to allow labels to start with a digit. 3com.com is valid. Validators based on the older RFC or on folk knowledge often reject it.

Bug: Not normalizing to lowercase before comparison

Domain names are case-insensitive. EXAMPLE.COM and example.com are the same domain. A system that stores EXAMPLE.COM and later checks equality against example.com will fail the check. The fix is to lowercase on input or use case-insensitive comparison everywhere.

Bug: Not handling trailing dot

Some input sources (like certain DNS resolution tools or API responses) include a trailing dot to make the root explicit (example.com.). If your validator rejects this, you will fail to process valid input from those sources.

Challenge: Email Validation

The practice challenge for this module is the Email Validation challenge, which tests the full email address including the domain part. Apply what you know from this module about domain structure, subdomain rules, and internationalized names.

Notice in particular which domain formats the validator accepts and which it rejects — and whether those decisions align with the rules you have learned.

Module content