JSON escaping is a fundamental skill for developers working with APIs, databases, and data interchange. Understanding when and how to escape JSON strings can prevent parsing errors, security vulnerabilities, and data corruption. This comprehensive guide covers everything you need to know about JSON escaping and unescaping.
📋 Table of Contents
- Key Takeaways
- What is JSON Escaping
- Characters That Must Be Escaped
- How to Escape JSON Strings
- Handling Nested JSON
- Multi-Language Implementation
- Common Use Cases
- Common Mistakes
- FAQ
- Conclusion
Key Takeaways
- Escape Required Characters: Double quotes (
"), backslashes (\), and control characters must always be escaped in JSON strings. - Use Standard Libraries: Always use built-in JSON functions (
JSON.stringify,json.dumps) rather than manual escaping. - Nested JSON: When embedding JSON within JSON, the inner JSON must be escaped as a string.
- Unicode Support: JSON supports Unicode escaping using
\uXXXXformat for special characters. - Validation: Always validate JSON after escaping/unescaping to ensure data integrity.
Need to escape or unescape JSON quickly? Try our free online tool:
What is JSON Escaping?
JSON escaping is the process of converting special characters in a string into escape sequences that are safe to include in a JSON document. This ensures that the JSON remains valid and parseable.
Why Escaping is Necessary
Consider this example:
// Invalid JSON - unescaped quotes break the structure
{ "message": "He said "Hello"" }
// Valid JSON - quotes are escaped
{ "message": "He said \"Hello\"" }
Without escaping, special characters can:
- Break JSON syntax
- Cause parsing errors
- Create security vulnerabilities (injection attacks)
- Corrupt data during transmission
Escape vs Encode
| Term | Description | Example |
|---|---|---|
| Escape | Convert special chars to escape sequences | " → \" |
| Encode | Convert entire string to different format | String → Base64 |
| Serialize | Convert object to JSON string | Object → {"key":"value"} |
Characters That Must Be Escaped
According to the JSON specification (RFC 8259), these characters must be escaped:
| Character | Escape Sequence | Description |
|---|---|---|
" |
\" |
Double quote |
\ |
\\ |
Backslash |
/ |
\/ |
Forward slash (optional) |
\b |
\\b |
Backspace |
\f |
\\f |
Form feed |
\n |
\\n |
Newline |
\r |
\\r |
Carriage return |
\t |
\\t |
Tab |
| Control chars | \uXXXX |
Unicode escape |
Visual Examples
// Original string with special characters
const original = 'Line 1\nLine 2\tTabbed "quoted"';
// After JSON escaping
const escaped = "Line 1\\nLine 2\\tTabbed \\\"quoted\\\"";
// In JSON format
{
"text": "Line 1\nLine 2\tTabbed \"quoted\""
}
How to Escape JSON Strings
Method 1: Using Our Online Tool
The easiest way to escape JSON is using our online tool:
- Visit JSON Escape Tool
- Paste your JSON or string in the input area
- Click "Escape" to convert special characters
- Copy the escaped result
Method 2: Using Built-in Functions
JavaScript:
// Escape a string for JSON
const str = 'Hello "World"\nNew line';
const escaped = JSON.stringify(str);
// Result: "Hello \"World\"\nNew line"
// Unescape JSON string
const unescaped = JSON.parse(escaped);
// Result: Hello "World"
// New line
Python:
import json
# Escape a string for JSON
original = 'Hello "World"\nNew line'
escaped = json.dumps(original)
# Result: "Hello \"World\"\nNew line"
# Unescape JSON string
unescaped = json.loads(escaped)
# Result: Hello "World"
# New line
Java:
import com.fasterxml.jackson.databind.ObjectMapper;
ObjectMapper mapper = new ObjectMapper();
// Escape
String original = "Hello \"World\"\nNew line";
String escaped = mapper.writeValueAsString(original);
// Unescape
String unescaped = mapper.readValue(escaped, String.class);
Handling Nested JSON
One of the most common challenges is embedding JSON within JSON. This requires escaping the inner JSON as a string.
The Problem
// You want to store this JSON inside another JSON
const innerJson = { "name": "John", "age": 30 };
// Wrong - this creates nested object, not string
const wrong = { "data": innerJson };
// Result: { "data": { "name": "John", "age": 30 } }
// Correct - stringify first to create escaped string
const correct = { "data": JSON.stringify(innerJson) };
// Result: { "data": "{\"name\":\"John\",\"age\":30}" }
Multi-Level Nesting
// Level 1: Original object
const level1 = { message: "Hello" };
// Level 2: Embed in another JSON
const level2 = { payload: JSON.stringify(level1) };
// { "payload": "{\"message\":\"Hello\"}" }
// Level 3: Embed again
const level3 = { wrapper: JSON.stringify(level2) };
// { "wrapper": "{\"payload\":\"{\\\"message\\\":\\\"Hello\\\"}\"}" }
Escape Sequence Growth
| Nesting Level | Quote Representation |
|---|---|
| Level 0 | " |
| Level 1 | \" |
| Level 2 | \\\" |
| Level 3 | \\\\\\\" |
Multi-Language Implementation
JavaScript/Node.js
// Escape JSON string
function escapeJson(str) {
return JSON.stringify(str).slice(1, -1);
}
// Unescape JSON string
function unescapeJson(str) {
return JSON.parse(`"${str}"`);
}
// Escape entire JSON object as string
function jsonToEscapedString(obj) {
return JSON.stringify(JSON.stringify(obj));
}
// Examples
console.log(escapeJson('Hello "World"'));
// Output: Hello \"World\"
console.log(unescapeJson('Hello \\"World\\"'));
// Output: Hello "World"
Python
import json
def escape_json_string(s):
"""Escape a string for use in JSON."""
return json.dumps(s)[1:-1]
def unescape_json_string(s):
"""Unescape a JSON-escaped string."""
return json.loads(f'"{s}"')
def json_to_escaped_string(obj):
"""Convert JSON object to escaped string."""
return json.dumps(json.dumps(obj))
# Examples
print(escape_json_string('Hello "World"'))
# Output: Hello \"World\"
print(unescape_json_string('Hello \\"World\\"'))
# Output: Hello "World"
Go
package main
import (
"encoding/json"
"fmt"
)
func escapeJsonString(s string) string {
b, _ := json.Marshal(s)
return string(b[1 : len(b)-1])
}
func main() {
original := `Hello "World"`
escaped := escapeJsonString(original)
fmt.Println(escaped)
// Output: Hello \"World\"
}
PHP
<?php
// Escape JSON string
function escapeJsonString($str) {
$encoded = json_encode($str);
return substr($encoded, 1, -1);
}
// Unescape JSON string
function unescapeJsonString($str) {
return json_decode('"' . $str . '"');
}
// Examples
echo escapeJsonString('Hello "World"');
// Output: Hello \"World\"
?>
Common Use Cases
1. API Request/Response
// Sending JSON data in API request
const requestBody = {
query: 'SELECT * FROM users WHERE name = "John"',
metadata: JSON.stringify({ source: "api", timestamp: Date.now() })
};
fetch('/api/data', {
method: 'POST',
body: JSON.stringify(requestBody)
});
2. Database Storage
-- Storing JSON in database
INSERT INTO logs (data) VALUES ('{"message":"User said \"Hello\""}');
-- Querying escaped JSON
SELECT * FROM logs WHERE data LIKE '%\"Hello\"%';
3. Configuration Files
{
"script": "echo \"Hello World\"",
"template": "{\"name\": \"{{username}}\"}",
"regex": "\\d+\\.\\d+"
}
4. Log Messages
// Logging JSON safely
const userData = { name: 'John "The Dev"', role: 'admin' };
console.log(`User data: ${JSON.stringify(userData)}`);
// Output: User data: {"name":"John \"The Dev\"","role":"admin"}
Common Mistakes
❌ Manual Escaping
// Wrong - incomplete manual escaping
const bad = str.replace(/"/g, '\\"');
// Correct - use JSON.stringify
const good = JSON.stringify(str);
❌ Double Escaping
// Wrong - escaping already escaped string
const alreadyEscaped = 'Hello \\"World\\"';
const doubleEscaped = JSON.stringify(alreadyEscaped);
// Result: "Hello \\\\\"World\\\\\""
// Correct - check if already escaped first
❌ Forgetting Control Characters
// Wrong - only escaping quotes
const bad = str.replace(/"/g, '\\"');
// Missing: \n, \r, \t, \b, \f, \\
// Use JSON.stringify instead
❌ Incorrect Unescape
// Wrong - using eval (security risk!)
const bad = eval(`"${escapedString}"`);
// Correct - use JSON.parse
const good = JSON.parse(`"${escapedString}"`);
FAQ
What's the difference between JSON escape and URL encoding?
| Aspect | JSON Escape | URL Encoding |
|---|---|---|
| Purpose | Safe JSON strings | Safe URLs |
| Quote | " → \" |
" → %22 |
| Space | Not escaped | → %20 or + |
| Newline | \n → \\n |
\n → %0A |
When should I escape JSON?
Escape JSON when:
- Embedding JSON as a string within another JSON
- Storing JSON in databases as text
- Transmitting JSON through systems that don't handle raw JSON
- Including user input in JSON responses
How do I handle Unicode characters?
// Unicode characters can be escaped as \uXXXX
const str = "Hello 世界";
const escaped = JSON.stringify(str);
// Result: "Hello 世界" or "Hello \u4e16\u754c"
// Both are valid JSON
Can I escape JSON without a library?
While possible, it's not recommended:
// Manual escape (not recommended)
function manualEscape(str) {
return str
.replace(/\\/g, '\\\\')
.replace(/"/g, '\\"')
.replace(/\n/g, '\\n')
.replace(/\r/g, '\\r')
.replace(/\t/g, '\\t')
.replace(/\f/g, '\\f')
.replace(/\b/g, '\\b');
}
// Better: use JSON.stringify
How do I validate escaped JSON?
function isValidJson(str) {
try {
JSON.parse(str);
return true;
} catch (e) {
return false;
}
}
// Test
console.log(isValidJson('{"name":"John"}')); // true
console.log(isValidJson('{"name":"John}')); // false
Conclusion
JSON escaping is essential for working with APIs, databases, and data interchange. By understanding which characters need escaping and using the right tools, you can avoid common pitfalls and ensure your JSON data remains valid and secure.
Quick Reference:
- ✅ Use
JSON.stringify()for escaping - ✅ Use
JSON.parse()for unescaping - ✅ Validate JSON after transformation
- ❌ Don't manually escape strings
- ❌ Don't use
eval()for unescaping
Need to escape or unescape JSON quickly? Use our free online tool: