Skip to content

ddn.util.json_escape

JSON and JSON5 string escaping utilities for the D programming language.

Overview

The ddn.util.json_escape module provides efficient, allocation-aware routines for escaping strings according to JSON and JSON5 specifications. It is used internally by ddn.var and ddn.data.json5 to produce correctly escaped string literals during serialization.

Features

Feature Description
Fast-path detection Strings requiring no escaping are returned as-is
Standard short escapes \b, \f, \n, \r, \t for common control characters
Unicode escapes \uXXXX for control characters and optionally all non-ASCII
Surrogate pairs Proper handling for code points above U+FFFF
Configurable quotes Support for both " and ' (JSON5 single-quoted strings)
Memory safe @safe implementations throughout

Usage Examples

Basic String Escaping

import ddn.util.json_escape;

// Escape a string (without surrounding quotes)
string escaped = escapeJSONString("hello\nworld");
assert(escaped == "hello\\nworld");

// String with quotes
string withQuotes = escapeJSONString("say \"hi\"");
assert(withQuotes == "say \\\"hi\\\"");

Writing Quoted Strings

import ddn.util.json_escape;
import std.array : appender;

// Write a quoted JSON string directly to an output buffer
auto buf = appender!string();
writeJSONString("say \"hi\"", buf);
assert(buf.data == `"say \"hi\""`);

Single-Quoted Strings (JSON5)

import ddn.util.json_escape;
import std.array : appender;

// Use single quotes for JSON5
auto buf = appender!string();
writeJSONString("it's easy", buf, '\'');
assert(buf.data == "'it\\'s easy'");

ASCII-Only Output

import ddn.util.json_escape;

// Escape all non-ASCII characters as \uXXXX
string ascii = escapeJSONString("café ☕", '"', true);
// Result: "caf\\u00E9 \\u2615"

Performance Considerations

  • Zero-copy fast path: Strings without special characters are returned without allocation
  • Pre-allocated buffers: Output buffer is pre-sized based on input length
  • Efficient hex encoding: Manual hex digit emission avoids std.format overhead
  • Single pass: Input is scanned once for both detection and transformation

Integration

This module is used internally by:

  • ddn.var.toJSON() — For JSON serialization of var values
  • ddn.data.json5.toJSON5() — For JSON5 serialization
  • ddn.data.json5.toJSON() — For strict JSON serialization

You can also use it directly when building custom serializers or when you need fine-grained control over string escaping.

See Also

  • ddn.var — Dynamic value type with toJSON() method.
  • ddn.data.json5 — JSON5 parsing and serialization.
  • ddn.adam — Memory-efficient dynamic value type.