JSON escape characters
Eight escape sequences plus \uXXXX. Everything else after a backslash is a syntax error.
Last reviewed
The complete list
There is no \' — single quotes are not special in JSON and must not be escaped. There is no \x, no \0 and no \e.
\" double quote
\\ backslash
\/ forward slash (optional — "/" is also fine)
\b backspace U+0008
\f form feed U+000C
\n line feed U+000A
\r carriage return U+000D
\t tab U+0009
\uXXXX any code unit, four hex digitsWhat must be escaped
Everything else may appear literally. Accented letters, CJK text and emoji are all fine as raw UTF-8; escaping them is optional and only useful when something downstream cannot be trusted with non-ASCII bytes.
- The double quote, always.
- The backslash, always. This is what breaks Windows paths: write "C:\\Users\\ada".
- Every control character below U+0020 — a literal newline or tab inside a string is invalid, even though it looks harmless.
Surrogate pairs
\uXXXX encodes one UTF-16 code unit, not one character. Anything above U+FFFF therefore needs two escapes — a high surrogate followed by a low one. An emoji written as a single \uXXXX escape is malformed, and a lone surrogate is invalid.
{ "reaction": "\ud83d\ude80" } // 🚀 U+1F680Double-escaped JSON
A document stored inside a string field — in a database column, a log line, a message queue payload — comes back with every quote backslashed and the whole thing wrapped in quotes. It is not corrupt; it is a JSON string that contains JSON text.
Decode it once to get the inner document. If the escaping was applied twice, decode twice. A tool that unstringifies rather than "repairs" is the right one here — repair would try to fix text that is not actually broken.
"{\"id\":1,\"name\":\"Ada\"}"{ "id": 1, "name": "Ada" }Escape versus stringify
They are different operations and the names get used interchangeably, which causes confusion. Escaping takes arbitrary text and makes it safe to place inside a JSON string — no surrounding quotes are added. Stringifying takes a whole JSON document and wraps it as a string literal, quotes included.
The practical test is what you are holding. If you have a paragraph of text, a Windows path or a regular expression and you need to put it into a JSON value, you want escape. If you have a complete JSON document and you need to store it in a field that only accepts a string, you want stringify. Running stringify on plain text will succeed and give you something you did not want; running escape on a document will escape all its structural quotes and braces into an unusable blob.
Escaping non-ASCII text is optional
Accented letters, CJK characters and emoji are valid inside a JSON string exactly as they are, provided the document is UTF-8 — which RFC 8259 requires for anything exchanged between systems. You never have to escape them, and a modern parser will read them either way.
There is one reason to do it anyway: when something downstream cannot be trusted with non-ASCII bytes. An older transport that mangles high bytes, a terminal with a fixed code page, a legacy system that declares the wrong charset, or a log pipeline that re-encodes. Converting every non-ASCII character to \uXXXX produces a document that is pure ASCII, byte-identical in meaning, and immune to all of those.
The cost is readability and size — a Japanese document roughly triples in length — so escape at the boundary where you need it, not by default.
Where escaping bugs come from
- Building JSON with string concatenation instead of a serialiser. A value containing a quote breaks the document, and a value containing a brace can change its structure. Use the serialiser your language ships with.
- Escaping something that is already escaped. Applying escape twice turns \n into \\n, and the receiving end gets a literal backslash-n rather than a newline.
- Regular expressions in configuration. A pattern like \d+ has to be written \\d+ inside JSON, and it is the single most common source of "my regex does not match" in a JSON config file.
- Windows paths. Every separator needs doubling. Forward slashes work on Windows in almost every API and avoid the problem entirely.
- Copying a value out of a debugger. Debuggers usually show the decoded string, so pasting it back into JSON drops the escaping that made it valid.
Keep reading
- Common JSON syntax errors — Nearly every failed parse is one of a dozen mistakes. Here is each one, what the parser says about it, and the fix.
- JSON data types explained — Six types, and about a dozen edge cases that cause almost all real-world bugs.