react-json-pretty
A lightweight React component that renders JSON data as syntax-highlighted, themeable HTML.
Repository Health
Technical Analysis
react-json-pretty is a small React component dedicated to one job: turning a JSON string or plain JavaScript object into readable, color-coded HTML. It stringifies the input, walks the resulting text line by line with a regular expression, and wraps keys, string values, numeric values, and booleans in their own <span> classes so they can be styled independently.
Because it renders through dangerouslySetInnerHTML rather than building a React element tree, it stays fast even for large payloads, and it escapes HTML-special characters before injecting them to guard against XSS from untrusted JSON content. Invalid JSON is caught and surfaces through an onJSONPrettyError callback (or a console warning) instead of crashing the component tree.
Five drop-in themes (default, Adventure Time, 1337, acai, monikai) ship as separate CSS files, and every element type also accepts an inline style string (keyStyle, valueStyle, stringStyle, booleanStyle, mainStyle, errorStyle) for one-off customization without writing CSS. A custom replacer and space prop pass straight through to the underlying JSON.stringify call, so existing formatting logic keeps working unchanged.
It is commonly dropped into API explorers, admin panels, debugging tools, and any UI that needs to show a JSON payload to a human without hand-rolling a formatter.
What You Get
- A single
<JSONPretty>component that accepts either a raw JSON string (json) or a pre-parsed object (data) - Five ready-made CSS themes (default, Adventure Time, 1337, acai, monikai) that can be imported directly
- Per-element inline style overrides (
keyStyle,valueStyle,stringStyle,booleanStyle,mainStyle,errorStyle) for styling without CSS - Built-in XSS escaping of rendered content and a callback-based error path (
onJSONPrettyError) for invalid JSON - Pass-through support for
JSON.stringify’sreplacerandspacearguments - TypeScript type definitions shipped in the package (
types/JSONPretty.d.ts)
Common Use Cases
- Rendering API responses inside an internal API explorer or Postman-like tool built in React
- Showing raw JSON payloads in admin dashboards for debugging or support tooling
- Displaying webhook or event payloads in a developer-facing logging UI
- Pretty-printing config or request/response objects inside browser-based dev tools
Under The Hood
Architecture
The entire library lives in one class component, src/JSONPretty.tsx, with no sub-components and no internal state — every render derives its output purely from props. render() runs the current data/json prop through JSON.stringify, then a single dense regular expression walks the resulting text line by line to classify each token (key, string, number, boolean, brace/bracket) and wrap it in a themed <span>, and the final markup is injected via dangerouslySetInnerHTML. This keeps the component fast and trivial to reason about, at the cost of bypassing React’s own element diffing for the formatted output — any change to the highlighting logic means touching one regex-and-string-replace pipeline rather than a component tree.
Tech Stack
Written in TypeScript and compiled to dist/ via tsc (targeting ES5, CommonJS output, with declaration files emitted to types/). Runtime dependencies are minimal — only prop-types, with react/react-dom as peer dependencies (>=15.0). Themes are authored in Stylus (src/*.styl) and compiled to plain CSS under themes/. The example app bundles with an older Webpack 4 config, and releases are cut with standard-version.
Code Quality
Tests live in a single file, tests/JSONPretty.test.tsx, using Jest with Enzyme’s shallow renderer and coverage collection via lcov. Coverage is reasonably thorough for the component’s scope — it exercises string vs. object input, custom themes, missing theme keys, invalid JSON, the deprecated onError callback, XSS-escaping, and per-token style overrides — but there is only the one test file and no evidence of an active CI pipeline beyond a stale .travis.yml. Linting uses tslint, a tool the TypeScript ecosystem has since deprecated in favor of ESLint, and the project’s last commit predates that shift by several years.
API Design
The public surface is intentionally tiny: a data/json prop for input, an optional theme object or CSS import for styling, and a handful of *Style props for one-off overrides — there is essentially no boilerplate to get a first render on screen. The trade-off is a somewhat unusual dual-input design (data vs json, silently preferring data) and a deprecated onError prop kept only for backward compatibility alongside its replacement, onJSONPrettyError.