#json #json-object #string #writer #intermediate #basic

json-writer

Simple and fast crate for writing JSON to a string without creating intermediate objects

3 unstable releases

0.3.0 May 23, 2023
0.2.1 Nov 26, 2022
0.2.0 Dec 21, 2021

#1605 in Encoding

Download history 2188/week @ 2023-11-24 3538/week @ 2023-12-01 2638/week @ 2023-12-08 2555/week @ 2023-12-15 1249/week @ 2023-12-22 2433/week @ 2023-12-29 3304/week @ 2024-01-05 3050/week @ 2024-01-12 3654/week @ 2024-01-19 3447/week @ 2024-01-26 3405/week @ 2024-02-02 2716/week @ 2024-02-09 2256/week @ 2024-02-16 3047/week @ 2024-02-23 3803/week @ 2024-03-01 1516/week @ 2024-03-08

11,192 downloads per month
Used in 4 crates (2 directly)

Unlicense

35KB
783 lines

json-writer-rs

CI license Current Crates.io Version

Simple and fast JSON writer for Rust.


lib.rs:

Simple and fast crate for writing JSON to a string without creating intermediate objects.

Usage

Basic usage:

use json_writer::JSONObjectWriter;
let number: i32 = 42;
let mut object_str = String::new();
{
	let mut object_writer = JSONObjectWriter::new(&mut object_str);
	object_writer.value("number", number);
}
assert_eq!(&object_str, "{\"number\":42}");

Various examples:

use json_writer::{to_json_string, NULL, JSONObjectWriter, JSONArrayWriter };
// Values
assert_eq!(to_json_string("Hello World\n"), "\"Hello World\\n\"");
assert_eq!(to_json_string(3.141592653589793f64), "3.141592653589793");
assert_eq!(to_json_string(true), "true");
assert_eq!(to_json_string(false), "false");
assert_eq!(to_json_string(NULL), "null");

// Options of values
assert_eq!(to_json_string(Option::<u8>::Some(42)), "42");
assert_eq!(to_json_string(Option::<u8>::None), "null");

// Slices and vectors
let numbers: [u8; 4] = [1,2,3,4];
assert_eq!(to_json_string(&numbers[..]), "[1,2,3,4]");
let numbers_vec: Vec<u8> = vec!(1u8,2u8,3u8,4u8);
assert_eq!(to_json_string(&numbers_vec), "[1,2,3,4]");
let strings: [&str; 4] = ["a","b","c","d"];
assert_eq!(to_json_string(&strings[..]), "[\"a\",\"b\",\"c\",\"d\"]");

// Hash-maps:
let mut map = std::collections::HashMap::<String,String>::new();
map.insert("Hello".to_owned(), "World".to_owned());
assert_eq!(to_json_string(&map), "{\"Hello\":\"World\"}");

// Objects:
let mut object_str = String::new();
let mut object_writer = JSONObjectWriter::new(&mut object_str);

// Values
object_writer.value("number", 42i32);
object_writer.value("slice", &numbers[..]);

// Nested arrays
let mut nested_array = object_writer.array("array");
nested_array.value(42u32);
nested_array.value("?");
nested_array.end();

// Nested objects
let nested_object = object_writer.object("object");
nested_object.end();

object_writer.end();
assert_eq!(&object_str, "{\"number\":42,\"slice\":[1,2,3,4],\"array\":[42,\"?\"],\"object\":{}}");

Writing large files

You can manually flush the buffer to a file in order to write large files without running out of memory.

Example:

use json_writer::JSONArrayWriter;
fn write_numbers(file: &mut std::fs::File) -> std::io::Result<()> {
	let mut buffer = String::new();
	let mut array = JSONArrayWriter::new(&mut buffer);
	for i in 1i32 ..= 1000000i32 {
		array.value(i);
		if array.buffer_len() > 2000 {
			// Manual flush
			array.output_buffered_data(file)?;
		}
	}
	array.end();
	std::io::Write::write_all(file, buffer.as_bytes())?;

	return Ok(());
}

Limitations

Because there is no intermediate representations, all values must be written in the order they appear in the JSON output. The Borrow checker ensures sub-objects are closed before anything else can be written after them.

use json_writer::JSONObjectWriter;
let mut object_str = String::new();
let mut object_writer = JSONObjectWriter::new(&mut object_str);
let mut nested_a = object_writer.object("a");
let mut nested_b = object_writer.object("b");

// Compile error: The borrow checker ensures the values are appended in the correct order.
// You can only write one object at a time.
nested_a.value("id", "a");
nested_b.value("id", "b");

The writer does not check for duplicate keys

use json_writer::JSONObjectWriter;
let mut object_str = String::new();
{
	let mut object_writer = JSONObjectWriter::new(&mut object_str);
	object_writer.value("number", 42i32);
	object_writer.value("number", 43i32);
}
assert_eq!(&object_str, "{\"number\":42,\"number\":43}");

Dependencies

~76KB