moonbitstack · Apache-2.0

One tree. Every way of writing it.

The JSON family for MoonBit: strict JSON, JSONC, JSON5 and JSON Lines over core's Json, with JSON Pointer, JSON Patch and Merge Patch. A number keeps the digits it was written with, members keep their order, and a failure names the line and the column.

$ moon add moonbitstack/moonjson Read the docs See examples
moonbit
let config = @json.loads("{\"host\":\"localhost\",\"port\":8080}")
@json.dumps(config)            // {"host":"localhost","port":8080}
@json.dumps(config, indent=2)  // over several lines

// The same document, written the way a settings file is written.
@jsonc.loads("{\"port\": 8080,  // the one we bound\n}")

// One place in a document, named (RFC 6901).
@pointer.get(config, "/host")  // "localhost"
the surface

One set of verbs across the family

The s is on the form that takes or answers a string. The plural set exists exactly where the format defines a stream — lines is a stream and has only those; the others define one document and have only the singular set.

text → tree bytes → tree tree → text tree → bytes
one document loads load dumps dump
a stream of them loads_all load_all dumps_all dump_all
the packages

A tree, and every dialect that reads and writes one

One tree, and a package for each way of writing it. The text dialects have the same four faces; the binary formats have the two that take bytes. Writing is always strict JSON, whatever the document was written in.

why one tree

Three promises the whole family is built on

01

A number keeps its text

A document read and written again comes back unchanged — including a twenty-digit integer and 1e400, which a double cannot hold and a parser that goes through one silently rewrites.

02

Members keep their order

The order a document was written in is information. A diff is a reason to discard it, and a diff can ask — dumps(sort=true).

03

A failure says where

Reading raises Refused with the offset, the line and the column. An error a person cannot find in their file is half an error.

the whole surface

In one run

The tour exercises every package at once. Run it yourself with moon run src/examples/tour.

moon run src/examples/tour
$ moon run src/examples/tour
jsonc == json -> true
json5 == json -> true
compact       -> {"host":"localhost","port":8080,"tls":false}
round trip    -> true
json5 extras  -> [null,null,255]
records       -> 3
pointer       -> 20
missing       -> false
patch         -> {"host":"localhost","port":9090,"tls":true}
merge         -> {"host":"localhost","port":9090}
jsonpath      -> ["A","C"]
cbor          -> a363746c73f464686f7374696c6f63616c686f737464706f7274191f90
cbor == json  -> true
canonical     -> {"host":"localhost","port":8080,"tls":false}
failure       -> line 3, column 8
install

One command

MoonBit 0.1.20261021 or later. The package is published to mooncakes under the moonbitstack account; source and issues live on GitHub.

bash
moon add moonbitstack/moonjson