What is the difference between encodeURI and encodeURIComponent?+
encodeURIComponent encodes one piece of a URL and assumes that piece is data, so it escapes the delimiters that give a URL its shape: the slash, the question mark, the hash, the ampersand, the equals sign, the colon, the at sign, the plus sign, and the dollar sign. encodeURI encodes a URL that is already assembled and assumes those delimiters are structure, so it leaves them alone. The practical rule is that you almost always want the component version, because you are almost always building a URL out of pieces rather than fixing one that already exists. Reach for the whole-URL version only when someone has handed you a complete link with a space or an accented character in it that needs cleaning up.
Why is a space sometimes %20 and sometimes a plus sign?+
Because two standards were written at different times and both survived. RFC 3986, which describes URLs generally, encodes a space as %20 everywhere. The older HTML form submission format, application/x-www-form-urlencoded, encodes a space as a plus sign, and that is what browsers still send when a form is submitted and what URLSearchParams produces. Both are read correctly inside a query string by essentially every server, because query string parsers know about both conventions. The trouble starts when a value encoded one way is decoded by the other: decode a form-encoded value with a plain percent decoder and a name like Anna Marie comes out as Anna+Marie. That is why this page shows both readings of a decode rather than picking one for you.
What does %2520 mean?+
It means a space that was percent-encoded twice. A space first becomes %20. If that %20 is then passed through an encoder again, the percent sign itself gets encoded as %25 and you end up with %2520. Seeing %25 followed by two more hex digits anywhere in a link is the fingerprint of a double encode. It usually happens when a redirect parameter is built by encoding a URL that had already been encoded, or when a value passes through two frameworks that each helpfully encode it. Paste it into decode mode here and the layer count tells you exactly how many passes to undo.
Which characters actually have to be encoded?+
RFC 3986 defines an unreserved set that never needs escaping: A to Z, a to z, 0 to 9, and the four marks hyphen, full stop, underscore, and tilde. Everything else falls into the reserved set, which is split into general delimiters (colon, slash, question mark, hash, square brackets, at sign) and sub-delimiters (exclamation mark, dollar, ampersand, apostrophe, parentheses, asterisk, plus, comma, semicolon, equals). A reserved character is legal where it is doing its structural job and must be escaped where it is data. Beyond that, space and the characters double quote, less than, greater than, percent, backslash, caret, backtick, and the braces are not allowed to appear raw at all. The reference table on this page lists each one with how the four encoders treat it.
Why does one accented letter become two percent codes?+
Because percent-encoding operates on bytes, not on characters, and modern URLs carry text as UTF-8. In UTF-8 the letter e with an acute accent is two bytes, C3 and A9, so it encodes as %C3%A9. A CJK character is three bytes and becomes three triplets, and an emoji is four bytes and becomes four triplets, which is twelve characters for one visible symbol. That is why an encoded string can be several times longer than the text you typed, and why a length limit measured in characters behaves differently before and after encoding. The byte view on this page shows the expansion character by character.
Can I just encode the whole URL to be safe?+
No, and this is the mistake that produces the most broken links. Running an already-correct URL through an encoder turns every structural character into an escape: the slashes become %2F, the question mark becomes %3F, and any existing escape has its percent sign turned into %25. What comes out is no longer a URL, it is a string that happens to look like one. If the link already works, leave it alone. If a link has a raw space or an accented character in it, whole-URL encoding is the right tool, because it fixes those without touching the delimiters. Try the already encoded preset in encode mode to see exactly what re-encoding does to a healthy link.
What is punycode, and why does the host look different from what I typed?+
The domain name system only carries a restricted set of ASCII characters, so a domain written in Arabic, Cyrillic, Greek, Chinese, or simply with a German umlaut has to be translated into ASCII before it can be looked up. That translation is punycode, and it produces labels that start with xn--. The browser does this conversion silently, which means the host you read and the host that is actually resolved are two different strings. Showing both is a security check, not a curiosity: a homograph attack works precisely because a name built from lookalike characters reads as a familiar brand while resolving to something else entirely. This page decodes punycode back to Unicode in the browser, since there is no built-in way to reverse it.
Is it safe to put a username and password in a URL?+
Treat any credential that has appeared in a URL as already leaked. The user information part of a URL, everything before the at sign, is sent in the clear as part of the request line on older protocols, gets written to server access logs and proxy logs, is stored in browser history, and has historically leaked through the Referer header sent to the next site you visit. Some browsers now strip it or warn about it, but the copies already written to logs do not go away. If a link with credentials in it has been shared, pasted into a ticket, or clicked from an email, rotate the password rather than relying on the link staying private. This page flags credentials whenever it finds them and masks the password rather than displaying it.
Why does decodeURIComponent throw, and what should I do instead?+
It throws a URIError whenever the input is not a valid percent-encoded UTF-8 string, which covers a percent sign with nothing after it, a pair that is not hex such as %ZZ, a truncated multi-byte character such as a bare %C3, an overlong encoding, and an escaped surrogate half. The error names neither the position nor the cause, so in production it usually turns into a blank page or a 500. The fix in your own code is to wrap the call and handle the failure explicitly rather than letting it escape. The fix while debugging is to paste the value here: the decoder on this page walks the string by hand and tells you which character is at fault and why, instead of refusing to say.
Is anything I paste sent to a server?+
No. Every encoder, the decoder, the URL parser, the punycode decoder, and the query workbench all run in this tab as plain JavaScript, and no link is ever fetched. That matters here more than on most tools, because the URLs people bring to a decoder are exactly the ones that contain session tokens, signed download links, password reset parameters, and internal hostnames. Input is capped at 100,000 characters, which is far beyond any usable URL, and nothing is stored between visits.