URL Encoding Explained: Percent-Encoding, Query Strings and Form Data
Why does a space become %20 in one place and + in another? A practical guide to URL encoding, query strings, encodeURIComponent and how HTML forms encode what users type.
formvoxo Team
Developer Relations
Try it as you read
Encode, decode and break down any URL into its parameters. No login.
You have seen URLs full of %20, %2F and %C3%A9, and you have probably seen a space turn into a + instead. Get URL encoding wrong and search terms split in half, redirects break, and special characters arrive garbled. Get it right and none of that happens.
What is URL encoding?
A URL can only contain a limited set of ASCII characters. Everything else, including spaces, quotes, emoji and letters such as é or ش, has to be written as a percent sign followed by two hex digits for each byte. That is why it is also called percent-encoding.
space → %20
& → %26
/ → %2F
é → %C3%A9 (two UTF-8 bytes)
👋 → %F0%9F%91%8B (four UTF-8 bytes)
Reserved characters: why some need encoding
Some characters have a job inside a URL:
?starts the query string&separates parameters=separates a name from its value#starts the fragment/separates path segments
If one of these appears inside a value, it must be encoded. Otherwise the URL means something else. A search for fish & chips sent as ?q=fish & chips arrives as q=fish plus a mystery parameter called chips. Encoded, it is ?q=fish%20%26%20chips and arrives intact.
encodeURIComponent vs encodeURI
JavaScript has two built-in functions, and mixing them up is the most common bug:
encodeURIComponent('fish & chips/ok?')
// "fish%20%26%20chips%2Fok%3F" (escapes everything, use for VALUES)
encodeURI('https://site.com/my page?q=a b')
// "https://site.com/my%20page?q=a%20b" (keeps the URL structure)
The rule of thumb: use encodeURIComponent on each value you insert into a URL, and only use encodeURI to tidy up a complete address. Better still, let the browser do it with URLSearchParams:
const url = new URL('https://example.com/search');
url.searchParams.set('q', 'fish & chips');
url.searchParams.set('city', 'Lahore');
url.toString();
// "https://example.com/search?q=fish+%26+chips&city=Lahore"
%20 or +? Both, depending on where
Notice that URLSearchParams wrote the spaces as +. That comes from the application/x-www-form-urlencoded format used by HTML forms, where a space is written as +. In the path of a URL, however, + is just a plus sign, and a space must be %20.
- Path:
/my%20file.pdf. A+here is a literal plus. - Query string and form data:
?q=hello+worldor?q=hello%20world. Both mean a space.
When decoding data copied from a form post or a server log, remember to turn + back into spaces. The URL Encoder & Decoder has a "Treat + as space" option for exactly this.
How HTML forms encode what users type
When a visitor submits a classic HTML form, the browser builds the request body for you:
name=Ali+Khan&email=ali%40example.com&message=Hi%2C+is+this+available%3F
Every field becomes name=value, the pairs are joined with &, and each name and value is URL-encoded. Your server then has to decode all of it. This is one of the chores a form backend removes: formvoxo receives the post, decodes every field and emails you a clean, readable submission.
Common URL encoding mistakes
Double encoding
Encoding an already encoded value turns %20 into %2520, because the % itself gets encoded. If a link shows %25, something encoded it twice. Decode first when you are not sure.
Encoding the whole URL as a component
encodeURIComponent('https://site.com/a') gives https%3A%2F%2Fsite.com%2Fa, which is no longer a working link. That is only correct when the entire URL is itself a parameter value, such as a redirect= target.
Building URLs by string concatenation
'/search?q=' + userInput breaks as soon as someone types & or #. Use URLSearchParams or encode every value.
Forgetting non-English text
Modern browsers display /شہر nicely in the address bar, but on the wire it is percent-encoded UTF-8. Server code and analytics often show the encoded form, so decode before you compare strings.
Quick reference
- Encode every value you put into a URL with
encodeURIComponentorURLSearchParams. - Use
%20for spaces in paths.+means a space only in query strings and form data. - Never encode twice, and watch for
%25as the warning sign. - Decode with "+ as space" when reading form posts and logs.
Paste any messy link into the free URL Encoder & Decoder to see every part and parameter decoded side by side.
Share this article