JSON Complete Guide: Syntax, Validation, Schema, and Practical Tools
What Is JSON?
JSON (JavaScript Object Notation) is a lightweight text format for structuring and describing data. Although it originated from JavaScript's object notation syntax, it has become a language-independent, universal data interchange format used across the industry.
From REST API responses and configuration files to database storage, JSON appears in virtually every aspect of web development. Its simplicity and readability are the reasons it has replaced XML as the de facto standard.
The official JSON specification is defined by RFC 8259 and ECMA-404. Any conforming parser must accept exactly the same inputs, which is why JSON interoperability across languages is so reliable.
Syntax Basics and Data Types
JSON supports exactly six data types:
| Data Type | Description | Example |
|---|---|---|
| String | Enclosed in double quotes | "Hello" |
| Number | Integer or floating-point | 42, 3.14 |
| Boolean | true or false | true |
| null | Empty value | null |
| Object | Key-value pairs | {"key": "value"} |
| Array | Ordered list of values | [1, 2, 3] |
Object Syntax
Objects are enclosed in curly braces {}, with key-value pairs separated by colons. Multiple pairs are separated by commas.
{
"name": "John Doe",
"age": 30,
"isActive": true,
"email": "john@example.com"
}
An important rule: keys must always be enclosed in double quotes. Single quotes or unquoted keys are invalid JSON.
Array Syntax
Arrays are enclosed in square brackets [], with values separated by commas. Different data types can be mixed within an array.
{
"fruits": ["apple", "orange", "grape"],
"mixed": [1, "hello", true, null]
}
Nested Structures
Objects and arrays can be freely nested, allowing you to represent complex data structures.
{
"company": "Example Corp",
"employees": [
{
"name": "Alice",
"department": "Engineering",
"skills": ["JavaScript", "Python"]
},
{
"name": "Bob",
"department": "Design",
"skills": ["Figma", "CSS"]
}
]
}
Common Errors and How to Fix Them
JSON syntax errors are frequently encountered during development. Let's look at the main causes and solutions.
1. Trailing Commas
While trailing commas are allowed in JavaScript, they cause syntax errors in JSON.
// Invalid JSON
{
"name": "John",
"age": 30,
}
// Valid JSON
{
"name": "John",
"age": 30
}
2. Using Single Quotes
Only double quotes are valid in JSON.
// Invalid JSON
{'name': 'John'}
// Valid JSON
{"name": "John"}
3. Adding Comments
The JSON specification does not include a comment syntax. Including // or /* */ will cause a parse error. If you need comments in configuration files, consider using JSON5 or JSONC instead (see the dedicated section below).
4. Leading Zeros in Numbers
Numbers other than 0 are invalid if they have leading zeros.
// Invalid JSON
{"code": 0123}
// Valid JSON
{"code": 123}
5. Unescaped Special Characters in Strings
Certain characters inside strings must be escaped with a backslash:
| Character | Escape Sequence |
|---|---|
| Double quote | \" |
| Backslash | \\ |
| Newline | \n |
| Tab | \t |
| Carriage return | \r |
{
"message": "He said, \"Hello!\"",
"path": "C:\\Users\\John",
"multiline": "Line 1\nLine 2"
}
Use our free JSON Formatter to validate your JSON and spot errors instantly.
Formatting Best Practices
Follow these best practices to improve readability and maintainability.
Consistent Indentation
When JSON files are meant to be read by humans, use 2-space or 4-space indentation. Consistency across your team is key.
{
"settings": {
"theme": "dark",
"fontSize": 14,
"autoSave": true
}
}
Key Naming Conventions
In API design, maintain a consistent key naming convention. camelCase or snake_case are the most common choices.
{
"userName": "john",
"createdAt": "2026-03-08T10:00:00Z"
}
Choosing the Right Data Types
Avoid storing numbers as strings. Use the appropriate data type.
// Avoid this pattern
{"price": "1000", "isAvailable": "true"}
// Recommended pattern
{"price": 1000, "isAvailable": true}
Minified vs. Pretty-Printed JSON
For APIs and storage, use minified JSON to reduce payload size. For configuration files and human-readable output, use pretty-printed JSON. You can convert between the two instantly with the JSON Formatter.
JSON Schema: Validating JSON Structure
JSON Schema is a vocabulary that describes the structure and constraints of JSON data. It lets you define what a valid JSON document looks like, and then automatically validate incoming data against that definition.
Why Use JSON Schema?
- Validate API request and response bodies
- Document the expected shape of configuration files
- Generate forms and documentation automatically
- Catch data quality issues before they reach your application logic
Basic JSON Schema Example
{
"$schema": "https://json-schema.org/draft/2020-12/schema",
"title": "User",
"type": "object",
"required": ["id", "name", "email"],
"properties": {
"id": {
"type": "integer",
"description": "Unique user identifier"
},
"name": {
"type": "string",
"minLength": 1,
"maxLength": 100
},
"email": {
"type": "string",
"format": "email"
},
"age": {
"type": "integer",
"minimum": 0,
"maximum": 150
},
"roles": {
"type": "array",
"items": {
"type": "string",
"enum": ["admin", "editor", "viewer"]
}
}
}
}
Common JSON Schema Keywords
| Keyword | Applies To | Description |
|---|---|---|
type |
All | Specifies the data type |
required |
Object | Lists required property names |
properties |
Object | Defines the shape of each property |
minimum / maximum |
Number | Numeric range constraints |
minLength / maxLength |
String | String length constraints |
pattern |
String | Regular expression constraint |
enum |
All | Restricts to a fixed set of values |
items |
Array | Schema for array elements |
format |
String | Semantic format hints (e.g., "email", "date-time") |
JSON Schema is supported by libraries in virtually every language. Popular validators include ajv for JavaScript, jsonschema for Python, and gojsonschema for Go.
JSON vs JSON5 vs JSONC: Which Should You Use?
Standard JSON is strict by design—it prioritizes interoperability over authoring convenience. JSON5 and JSONC are supersets of JSON that add human-friendly features, primarily for configuration files.
Standard JSON
- Defined by RFC 8259 / ECMA-404
- No comments, no trailing commas, strings must use double quotes
- Supported natively in every language and runtime
- Best for: API responses, data storage, inter-service communication
JSON5
JSON5 extends JSON with ECMAScript 5 syntax features:
// JSON5 allows comments
{
name: "John", // Unquoted keys are allowed
'greeting': 'Hello', // Single quotes are allowed
age: 30, // Trailing commas are allowed
hex: 0xFF, // Hexadecimal numbers
infinity: Infinity, // Special numeric values
}
- Use for: configuration files where authors want comments and a relaxed syntax
- Not suitable for: data exchange between services (not universally parsed)
JSONC (JSON with Comments)
JSONC allows // and /* */ comments but is otherwise identical to standard JSON:
{
// Editor settings
"editor.tabSize": 2,
"editor.formatOnSave": true,
/* These settings affect all languages */
"files.autoSave": "onFocusChange"
}
- Used by: VS Code (
settings.json,launch.json), TypeScript (tsconfig.json) - Supported by: editors and specific tooling, not general-purpose parsers
Quick Comparison
| Feature | JSON | JSON5 | JSONC |
|---|---|---|---|
| Comments | No | Yes | Yes |
| Trailing commas | No | Yes | No |
| Single quotes | No | Yes | No |
| Unquoted keys | No | Yes | No |
| Universal parser support | Yes | Limited | Limited |
| Best for | APIs, data | Config files | Editor configs |
Working with JSON in Different Languages
JavaScript / Node.js
JavaScript has built-in JSON support through the global JSON object.
// Parse JSON string to object
const jsonString = '{"name": "Alice", "age": 30}';
const user = JSON.parse(jsonString);
console.log(user.name); // "Alice"
// Serialize object to JSON string
const data = { name: "Bob", scores: [95, 87, 92] };
const pretty = JSON.stringify(data, null, 2); // Pretty-print with 2-space indent
const minified = JSON.stringify(data); // Minified
// Handling parse errors safely
function safeJsonParse(str) {
try {
return { ok: true, data: JSON.parse(str) };
} catch (e) {
return { ok: false, error: e.message };
}
}
Deep cloning with JSON (simple but has limitations):
// Works for plain objects, but loses functions, undefined, Date objects, etc.
const clone = JSON.parse(JSON.stringify(original));
Python
Python's built-in json module handles encoding and decoding.
import json
# Parse JSON string
json_string = '{"name": "Alice", "age": 30}'
data = json.loads(json_string)
print(data["name"]) # Alice
# Serialize to JSON string
user = {"name": "Bob", "scores": [95, 87, 92]}
pretty = json.dumps(user, indent=2, ensure_ascii=False) # ensure_ascii=False for Unicode
minified = json.dumps(user, separators=(',', ':'))
# Read from file
with open("data.json", "r", encoding="utf-8") as f:
config = json.load(f)
# Write to file
with open("output.json", "w", encoding="utf-8") as f:
json.dump(data, f, indent=2, ensure_ascii=False)
Go
Go uses the encoding/json package with struct tags for mapping.
package main
import (
"encoding/json"
"fmt"
)
type User struct {
Name string `json:"name"`
Age int `json:"age"`
Email string `json:"email,omitempty"` // omitempty skips zero values
}
func main() {
// Unmarshal (parse)
jsonStr := []byte(`{"name":"Alice","age":30}`)
var user User
if err := json.Unmarshal(jsonStr, &user); err != nil {
panic(err)
}
fmt.Println(user.Name) // Alice
// Marshal (serialize)
output, _ := json.MarshalIndent(user, "", " ")
fmt.Println(string(output))
// Parse into a map (dynamic structure)
var dynamic map[string]interface{}
json.Unmarshal(jsonStr, &dynamic)
}
Java
Java does not have built-in JSON support, but popular libraries like Jackson and Gson are widely used.
Jackson:
import com.fasterxml.jackson.databind.ObjectMapper;
public class JsonExample {
static class User {
public String name;
public int age;
}
public static void main(String[] args) throws Exception {
ObjectMapper mapper = new ObjectMapper();
// Deserialize
String json = "{\"name\":\"Alice\",\"age\":30}";
User user = mapper.readValue(json, User.class);
System.out.println(user.name); // Alice
// Serialize
String output = mapper.writerWithDefaultPrettyPrinter()
.writeValueAsString(user);
System.out.println(output);
// Parse to generic map
var map = mapper.readValue(json, Map.class);
}
}
Gson (Google):
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
Gson gson = new GsonBuilder().setPrettyPrinting().create();
User user = gson.fromJson(jsonString, User.class);
String output = gson.toJson(user);
JSON Parsing and Security
JSON parsing is generally safe, but there are important security considerations to keep in mind.
JSON Injection
JSON injection occurs when unsanitized user input is embedded directly into a JSON string being built by string concatenation. An attacker can break out of the intended string context.
Vulnerable pattern:
// NEVER do this
const userInput = '", "isAdmin": true, "x": "';
const json = `{"username": "${userInput}", "isAdmin": false}`;
// Resulting JSON: {"username": "", "isAdmin": true, "x": "", "isAdmin": false}
Safe pattern — always use JSON.stringify:
// Always construct JSON with proper serialization
const payload = {
username: userInput, // Any input is safely escaped
isAdmin: false
};
const json = JSON.stringify(payload);
Prototype Pollution
In JavaScript, some insecure JSON parsers or manual object merging can lead to prototype pollution, where an attacker injects properties like __proto__ that affect all objects in the application.
// Dangerous: merging untrusted JSON into an existing object
const untrusted = JSON.parse('{"__proto__": {"isAdmin": true}}');
Object.assign({}, untrusted); // Can pollute Object.prototype
// Safe: use Object.create(null) for dictionaries, or validate schemas
const safe = Object.create(null);
Denial of Service via Large Payloads
Parsing extremely large or deeply nested JSON can exhaust memory or CPU. Always enforce limits on incoming data:
- Set maximum request body size at the HTTP server level (e.g.,
body-parserlimit in Express) - Validate the depth and size of parsed structures before processing
- Use streaming parsers (see Performance Tips) for large files
Numeric Precision
JSON numbers have no defined precision limit, but JavaScript's JSON.parse converts all numbers to IEEE 754 doubles. Numbers larger than Number.MAX_SAFE_INTEGER (2^53 - 1) will lose precision.
// Precision loss with large integers
JSON.parse('{"id": 9007199254740993}')
// → {id: 9007199254740992} ← wrong!
// Solution: represent large integers as strings, or use BigInt
JSON.parse('{"id": "9007199254740993"}')
JSON Performance Tips
Minify JSON for Production
Remove all unnecessary whitespace before sending JSON over the network. Even modest minification reduces payload size by 20–40% for typical API responses. The JSON Formatter can minify JSON instantly.
Use Streaming Parsers for Large Files
Loading a 500 MB JSON file into memory all at once is impractical. Streaming parsers read and process data incrementally:
- Node.js:
stream-json,JSONStream - Python:
ijson - Java: Jackson's
JsonParserin streaming mode
// Node.js streaming example with stream-json
const { parser } = require('stream-json');
const { streamArray } = require('stream-json/streamers/StreamArray');
const fs = require('fs');
fs.createReadStream('large-data.json')
.pipe(parser())
.pipe(streamArray())
.on('data', ({ key, value }) => {
// Process each item without loading the whole file
processItem(value);
});
Avoid Redundant Serialization
Re-serializing and re-parsing JSON unnecessarily wastes CPU. If you receive a JSON response and need to forward it, pass the raw string rather than parsing and re-stringifying.
Choose the Right Serialization Library
For high-throughput applications, consider faster JSON libraries:
| Language | Faster Alternative | Notes |
|---|---|---|
| JavaScript | fast-json-stringify, simdjson-js |
Up to 2–5× faster for large payloads |
| Python | orjson, ujson |
orjson handles dates natively |
| Java | jsoniter |
Often faster than Jackson for simple types |
| Go | encoding/json is already fast; jsoniter for extra speed |
Gzip Compression
JSON compresses extremely well because of its repetitive key names. Enabling gzip on API responses typically reduces size by 70–90%, far outweighing the CPU cost of compression.
Common Use Cases for JSON
JSON is indispensable in modern web development. Here are the most common use cases:
- REST APIs: The most widely used format for client-server data communication
- Configuration files: Used by development tools such as
package.json,tsconfig.json - Data storage: Adopted as the document format in NoSQL databases like MongoDB
- Logging: Output as structured logs in JSON format for processing by analysis tools
- GraphQL: Query responses are always returned as JSON
- WebSockets: Real-time messages are commonly encoded as JSON
Comparison with Other Data Formats
| Feature | JSON | YAML | XML | CSV |
|---|---|---|---|---|
| Readability | High | Very high | Moderate | High (tabular) |
| Data types | 6 types | Rich | None | None |
| Comments | No | Yes | Yes | No |
| File size | Small | Small | Large | Very small |
| Nesting | Supported | Supported | Supported | Not supported |
| Schema support | JSON Schema | JSON Schema / YAML Schema | XSD | None |
| Streaming | Yes | Limited | Yes (SAX) | Yes |
Choosing the right format depends on the use case. YAML is popular for configuration files where comments are useful, CSV works well for tabular data, and JSON is the standard for API responses. Need to convert between formats? Use the YAML-JSON Converter or CSV-JSON Converter.
JSON Tools and Validators
Having the right tools dramatically speeds up working with JSON in daily development.
Online Tools on This Site
| Tool | What It Does |
|---|---|
| JSON Formatter | Format, minify, and validate JSON; highlights syntax errors |
| YAML-JSON Converter | Convert between YAML and JSON bidirectionally |
| CSV-JSON Converter | Convert CSV spreadsheet data to JSON arrays and back |
Editor Plugins
Most modern editors have excellent JSON support:
- VS Code: Built-in JSON validation, IntelliSense for
settings.json; install the "JSON Schema Store" extension for schema auto-detection - JetBrains IDEs: Built-in JSON formatter and schema validation
- Vim/Neovim:
jsonlslanguage server via Mason/LSP
Command-Line Tools
- jq: The most powerful JSON processor for the command line. Filter, transform, and extract data from JSON streams.
# Extract a field
echo '{"name":"Alice","age":30}' | jq '.name'
# Filter array items
cat users.json | jq '.[] | select(.age > 25)'
# Pretty-print a file
jq . data.json
# Minify
jq -c . data.json
- fx: Interactive JSON viewer in the terminal
- python -m json.tool: Quick formatting with no extra install needed
FAQ
Can JSON have comments?
No. Standard JSON does not support comments. The JSON specification (RFC 8259) intentionally omits them to keep the format simple and universally parseable. If you need comments in configuration files, consider JSONC (used by VS Code) or JSON5. For application data exchanged over APIs, comments are not needed.
What is the maximum size of a JSON file?
There is no size limit defined in the JSON specification itself. In practice, the limit is imposed by the tools and runtimes processing the JSON:
- Most HTTP servers limit request bodies (commonly 1–10 MB by default)
- Browser
JSON.parsecan handle files in the hundreds of MB, but will block the main thread - For files over ~50 MB, use a streaming parser to avoid memory issues
Why does JSON.parse lose precision on large numbers?
JavaScript represents all numbers as 64-bit IEEE 754 floating-point, which can only represent integers exactly up to 2^53 - 1 (9,007,199,254,740,991). Integers larger than this lose precision when parsed. The solution is to transmit large integers as strings, or use the BigInt type in environments that support it.
What is the difference between null and undefined in JSON?
JSON has null but has no concept of undefined. When you call JSON.stringify on a JavaScript object, properties with undefined values are omitted entirely, while properties with null values are included as null. This is a common source of bugs when round-tripping data through JSON.
JSON.stringify({ a: null, b: undefined })
// → '{"a":null}' — b is omitted
Is JSON a subset of JavaScript?
Almost, but not exactly. In older versions of the ECMAScript spec, certain Unicode line terminators (U+2028 LINE SEPARATOR and U+2029 PARAGRAPH SEPARATOR) were valid in JSON strings but were syntax errors in JavaScript. This was fixed in ES2019, so JSON is now a syntactic subset of JavaScript.
How do I handle dates in JSON?
JSON has no native date type. The standard practice is to represent dates as ISO 8601 strings: "2026-03-16T10:00:00Z". When parsing, you must manually convert these strings to date objects in your language of choice. Some libraries (like Python's orjson) can automatically serialize and deserialize date objects.
What is application/json?
application/json is the MIME type (media type) used to indicate that an HTTP request or response body contains JSON data. Always set the Content-Type: application/json header when sending JSON over HTTP, and check for it when receiving.
Can JSON keys be duplicated?
The JSON specification says that key names within an object SHOULD be unique, but does not prohibit duplicates. In practice, different parsers handle duplicates differently—some take the last value, some take the first, and some throw an error. Avoid duplicate keys entirely to ensure consistent behavior across all environments.
Conclusion
JSON has established itself as the standard data interchange format for web development thanks to its simple syntax and broad compatibility. By mastering the basic syntax, understanding JSON Schema for validation, knowing when to reach for JSON5 or JSONC, and following security and performance best practices, you can use JSON confidently and efficiently in any project.
Use the free tools on this site to speed up your workflow: JSON Formatter for validation and formatting, YAML-JSON Converter for format conversion, and CSV-JSON Converter for working with tabular data.
