A focused collection of valid, invalid, and edge-case JSON test cases for parsers, validators, editors, APIs, syntax highlighting, and error handling.
Happy-path JSON samples do not exercise diagnostics, strictness, numeric limits, Unicode handling, or interoperability hazards. This repository keeps those inputs small, named, documented, and machine-indexed so they can be reused in unit tests, compatibility suites, editor demos, and regression tests.
The suite tests selected syntax and implementation boundaries. It is not a certification suite and does not claim exhaustive RFC coverage.
valid/ Strict JSON inputs expected to parse
invalid/ Deliberately malformed inputs expected to fail
edge-cases/ Valid inputs with implementation or interoperability concerns
scripts/ Dependency-free validation and test-case generation tools
test-cases.json Machine-readable test-case manifest
Invalid subdirectories include short notes explaining the grammar error, common causes, and included files.
Node.js 22 or newer is required for the repository scripts. The test cases themselves have no runtime dependency.
git clone https://github.com/UtilHatch/json-validation-test-cases.git
cd json-validation-test-cases
npm testThe validator resolves paths from its own location, so node /path/to/repository/scripts/validate.js also works from another working directory. It confirms that the manifest and filesystem agree, accepted cases parse, and rejected cases throw in JSON.parse.
- Valid test cases are JSON texts a strict parser should accept, including primitive root values. Their manifest expectation is
accept. - Invalid test cases intentionally violate JSON grammar. Their expectation is
reject; do not run a formatter over them. - Edge cases are generally syntactically valid JSON but may lose precision, exceed numeric ranges, trigger depth limits, normalize differently, or produce surprising downstream behavior. Their expectation is
implementation-dependentso the validator reports them separately.
Duplicate names in an object are an important example: many parsers accept them and retain one value, but RFC 8259 describes behavior as unpredictable when names are not unique. Likewise, 9007199254740993 is valid JSON, but JavaScript's binary Number type cannot represent that integer exactly because it exceeds Number.MAX_SAFE_INTEGER.
test-cases.json lists every test case exactly once. Each entry has a stable ID, relative path, category, subcategory, title, description, expectation, standards context, and notes. Entries are sorted by path, making diffs predictable.
const fs = require('node:fs');
const path = require('node:path');
const root = process.cwd();
const cases = JSON.parse(fs.readFileSync(path.join(root, 'test-cases.json'), 'utf8'));
for (const testCase of cases.filter((item) => item.expected === 'accept')) {
const source = fs.readFileSync(path.join(root, testCase.path), 'utf8');
JSON.parse(source);
console.log(`accepted ${testCase.id}`);
}package main
import (
"encoding/json"
"fmt"
"os"
)
func main() {
data, err := os.ReadFile("valid/objects/simple-object.json")
if err != nil {
panic(err)
}
var value any
if err := json.Unmarshal(data, &value); err != nil {
panic(err)
}
fmt.Printf("%#v\n", value)
}Use the manifest rather than relying on directory names when a test runner needs expected outcomes or metadata.
Regenerate the tracked 100-level test case:
npm run generate:deepPass a depth from 1 through 10,000 after --:
npm run generate:deep -- 250Non-default depths create edge-cases/nesting/deep-<depth>.json; add a matching manifest entry before committing. The upper bound prevents accidentally allocating an unreasonably large test case.
The syntax expectations are based on RFC 8259 and ECMA-404. Syntax validity does not guarantee identical in-memory values across languages. Number range and precision, duplicate-member handling, Unicode comparison, maximum nesting, resource limits, and mapping into native objects are implementation concerns.
Some ecosystems support JSON-derived formats such as JSON5 or JSONC. Accepting comments, trailing commas, or single quotes in such a mode does not make those inputs valid JSON.
Read CONTRIBUTING.md before adding a test case. A contribution should cover a distinct behavior, use a descriptive filename, update the manifest, document parser-specific results when relevant, and pass npm test.
For manual inspection, paste a test case into UtilHatch's JSON Array Validator. These browser tools are convenient for exploring diagnostics; automated assertions should still use the parser and configuration relevant to your application.
Released under the MIT License.