Guide
How URL percent-encoding works
Learn which characters to encode in a URL component, how UTF-8 becomes percent triplets, and why + does not always mean space.
by Tools in a Tab · Published on · Updated
Short answer
Percent-encoding represents one byte as % followed by two hexadecimal digits.
It lets data appear inside a URI component without being confused with
structural delimiters.
text: café & tea
component: caf%C3%A9%20%26%20tea
é first becomes UTF-8 bytes C3 A9, written as %C3%A9. The space becomes
%20, while & becomes %26 so it is not read as a parameter separator.
Unreserved and reserved characters
RFC 3986 defines
letters, digits, -, ., _, and ~ as unreserved. Reserved characters can
have structural roles, including :, /, ?, #, [, ], and @, or
separate subcomponents, such as & and =.
Do not encode an entire URL as if it were one value: that would also encode /,
?, and other delimiters needed by the structure. Encode the individual name
or value you insert.
To reproduce the example, select URL component in the
URL encoder. The tool also has Complete URL
or path mode, which preserves structural delimiters, and Form/query value
mode, which writes spaces as + and a literal plus as %2B. Choose the
mode for the layer you are editing; complete-URL mode cannot tell which & or
? characters you intended as data inside a value.
The + case
In application/x-www-form-urlencoded, a space is commonly represented as
+. In general URI percent-encoding, a space is %20, and a literal +
remains + unless the form-decoding layer applies its own rule. Know which
decoder receives the value.
Common mistakes
- Encoding
%C3%A9a second time as%25C3%25A9. - Decoding before separating components and turning data into structure.
- Placing standard Base64 in a URL without handling
+,/, and=. - Accepting incomplete
%sequences or bytes that are not valid UTF-8.
When JavaScript throws URIError: URI malformed, follow the strict diagnosis
for incomplete escapes, UTF-8, and lone
surrogates instead of replacing every percent
sign or decoding repeatedly.
Keep URL construction, component encoding, and form serialization as separate layers. They are related, but not interchangeable.