DevPad
← Back to blog
·url-encoding, web, developer-tools

URL Encoding Explained: How Percent-Encoding Works

Understand URL encoding (percent-encoding), when to encode and decode URLs, and how to handle special characters in query strings and paths.

URL encoding, also called percent-encoding, is the mechanism that allows URLs to contain characters beyond the basic ASCII set. Without it, a URL with spaces, Unicode, or special characters would break.

What Is URL Encoding?

URL encoding replaces unsafe characters with a % followed by two hexadecimal digits. For example:

  • Space → %20
  • @%40
  • &%26
  • Newline → %0A

The full form of URL encoding is percent-encoding, defined in RFC 3986.

Which Characters Need Encoding?

URLs can only contain a limited set of characters unencoded:

Unreserved (safe):

  • Letters: A-Z, a-z
  • Digits: 0-9
  • Special: -, _, ., ~

Reserved (have special meaning):

  • : / ? # [ ] @ ! $ & ' ( ) * + , ; =

Must always be encoded:

  • Space, <, >, ", {, }, |, \, ^, `

Everything else should be encoded.

Query String vs Path Encoding

Not all parts of a URL are encoded the same way:

| Component | Encoding | Example | |-----------|----------|---------| | Path | / is literal, spaces → %20 | /tools/base64 | | Query | & and = are separators | ?q=hello+world | | Fragment | Not sent to server | #section-1 |

Query String Encoding

In query strings, + represents a space (legacy from application/x-www-form-urlencoded):

?q=hello+world    ← + means space
?q=hello%20world  ← %20 also means space

Modern practice prefers %20 over + for spaces.

Common Use Cases

Encoding User Input

Never put user input directly into a URL:

const query = "hello world & special chars";
const url = `https://api.example.com/search?q=${encodeURIComponent(query)}`;
// "https://api.example.com/search?q=hello%20world%20%26%20special%20chars"

Encoding a Full URL

const url = "https://example.com/path?q=hello";
const encoded = encodeURI(url);
// "https://example.com/path?q=hello" (keeps valid URL structure)

Decoding

const decoded = decodeURIComponent("hello%20world%20%26%20special");
// "hello world & special"

encodeURI vs encodeURIComponent

| Function | Encodes | Use Case | |----------|---------|----------| | encodeURI | Only unsafe chars, preserves URL structure | Encoding a complete URL | | encodeURIComponent | Almost everything except A-Z a-z 0-9 - _ . ! ~ * ' ( ) | Encoding a single component (query param, path segment) |

const url = "https://example.com/path?name=John Doe";

encodeURI(url);
// "https://example.com/path?name=John%20Doe" (preserves URL)

encodeURIComponent(url);
// "https%3A%2F%2Fexample.com%2Fpath%3Fname%3DJohn%20Doe" (encodes everything)

Common Mistakes

  1. Double encoding — encoding an already-encoded string gives %2520 instead of %20

  2. Not encoding user input — always use encodeURIComponent for query parameters

  3. Using + for spaces in paths — paths should use %20, not +

  4. Forgetting to decode — server-side languages auto-decode query params; don't decode twice

  5. Encoding : and / in query values — these are safe inside query values, but encodeURIComponent encodes them anyway (which is fine)

Unicode and Non-ASCII Characters

Non-ASCII characters are first UTF-8 encoded, then each byte is percent-encoded:

é → UTF-8: 0xC3 0xA9 → %C3%A9
€ → UTF-8: 0xE2 0x82 0xAC → %E2%82%AC

Most modern APIs handle UTF-8 directly, but some legacy systems require explicit encoding.

Try It Now

Use our free URL Encoder/Decoder to encode and decode URLs instantly — with component vs full URL encoding modes.