callum-oakley/json5-rs

A Rust JSON5 serializer and deserializer which speaks Serde

Deserialize a JSON5 string with from_str

JSON5

A Rust JSON5 serializer and deserializer which speaks Serde.

API

Deserialize a JSON5 string with from_str. Go the other way with to_string. The serializer is very basic at the moment, it just produces plain old JSON. See the Serde documentation for details on implementing Serialize and Deserialize. (Usually it's just a case of sprinkling in some derives.)

The Serde data model is mostly supported, with the exception of bytes and borrowed strings.

Example

Read some config into a struct.

use json5;
use serde_derive::Deserialize;

#[derive(Deserialize, Debug, PartialEq)]
struct Config {
    message: String,
    n: i32,
}

fn main() {
    let config = "
        {
          // A traditional message.
          message: 'hello world',

          // A number for some reason.
          n: 42,
        }
    ";

    assert_eq!(
        json5::from_str(config),
        Ok(Config {
            message: "hello world".to_string(),
            n: 42,
        }),
    );
}
Issues

Collection of the latest Issues

TheButlah

TheButlah

Comment Icon0

I wanted to parse some JSON5 strings on an embedded microcontroller. I have access to an allocator via alloc, but no standard library (only core). Can I use this crate?

woody77

woody77

Comment Icon0

I found that json5 was taking many minutes to parse a single 180KB json file, which caused me to write up a benchmark-ish app which deserializes the following struct:

with the items being 100-char strings, varying in number from 10 to 1,000,000, using both serde_json and json5.

With cargo run --release, I get the following results:

But when running in --debug, it's much worse:

And with more complicated structures like the following, the disparity in --debug is much, much greater (such as an hour vs. seconds to parse the same file):

times are from a 2015 MacBook Pro, running rustc 1.52.1 (9bc8c42bb 2021-05-09)

stefan-at-dfinity

stefan-at-dfinity

Comment Icon0

Description

  • Contrary to recommendations of the spec, the Unicode code points U+2028 and U+2029 are not escaped upon serialization. See Section 5.2 of the specification.
  • Deserialization fails when an input string contains Unicode code points U+2028 or U+2029.

Tested Versions

Testcase

lowercase1024

lowercase1024

Comment Icon0

Currently tests don't really cover error cases. The tests are mostly for happy path. Maybe we need to cover some more cases especially the cases leading to errors.

Also a remark regarding the testing code. The helper function deserializes_with_error requires the second parameter to be of generic type T in order to tell deserializer what type to deserialize. For example:

The call to deserializes_with_error looks a bit messy and a bit hard to read. Of course we could move the struct into a local variable and then pass it to the function. But we don't even use the second parameter within the function, and which is more important - we don't need to. The parameter can be removed and then simply write test like this:

Fortunately, there is not a lot of error-testing code (like 4-6 tests), so fixing it won't take long. If that makes sense, I can do it.

lowercase1024

lowercase1024

Comment Icon0

Currently if I we try to parse an integer, say i8 the value would be first parsed as f64 (here) and then converted via as operator to i8 (here). The problem here is that as operator will convert with overflow/underflow. That is, for JSON value -129, the converted i8 will be 127. Most of the time this is not what user wants.

I see two solutions here:

  • Conversion via str::parse() and use of built-in errors for overflows/underflows (e.g. visitor.visit_i8(pair.parse().map(|e| e.to_string())?) instead of visitor.visit_i8(parse_number(&pair)? as i8)) (and the same for the rest of integer types).
  • Add option to deserializer that makes it possible for user to decide whether to convert integers with overflow/underflow or return error. Basically this is a choice between how it works now and what's proposed int the previous solution.

P.S.: this also leads to a strange test-case for integers here. Instead of testing errors of deserializing i64 it tests against the seder_json::Value, which is really strange.

LPGhatguy

LPGhatguy

Comment Icon0

A lot of crates use serde_json, but JSON5 is probably a better fit for a lot of projects.

Introducing benchmarks relative to serde_json would make it more clear whether using the json5 crate instead would be a clear win, since it is from an ergonomics perspective!

I'd love to help with this, maybe using something like Criterion.rs?

LPGhatguy

LPGhatguy

Comment Icon0

It would be awesome if json5 (or maybe a crate next to json5?) could provide a core API that's a drop-in or near drop-in replacement for serde_json.

I'd love to let users experimentally opt into JSON5 configs instead of JSON in my project, but I'm not ready to commit 100%. This would make it extremely easy for crates to experiment with switching to json5 from serde_json.

I'm down to do this work if you think it's a good idea!

flaviojs

flaviojs

Comment Icon0

I have a json config file that has comments. It is meant to be edited manually or with a GUI launcher.

Ideally there would be a way to roundtrip the comments in the launcher with rust but I can't find anything.

The minimum I need is a way to serialize default comments. Maybe something like:

would be serialized into something like:

callum-oakley

callum-oakley

Comment Icon0

We should be able to specify the style to be used for serializing. Such as:

  • trailing commas?
  • how much indentation?
  • whitespace?
  • single quotes or double?
  • property names without quotes?
callum-oakley

callum-oakley

Comment Icon0

Errors from serde, pest, etc are all collapsed in to a single stringy error type at the moment. This is less than ideal. We shouldn't be throwing away any information about underlying errors.

Information - Updated Jan 04, 2022

Stars: 111
Forks: 12
Issues: 15

Serde is a framework for serializing and deserializing Rust data structures efficiently and generically

Rust Greatest JSON weapon is Serde with over 4.4K stars on github and a massive developer community. This is considered a core Rust library for every developer to learn in BRC's opinion

Serde is a framework for serializing and deserializing Rust data structures efficiently and generically

Rust 버전 JsonPath 구현으로 Webassembly와 Javascript에서도 유사한 API 인터페이스를 제공 한다

JsonPath 구현으로 Webassembly와 Javascript에서도 유사한 API 인터페이스를 제공 한다

Rust 버전 JsonPath 구현으로 Webassembly와 Javascript에서도 유사한 API 인터페이스를 제공 한다

SIMD JSON for Rust  

Rust port of extremely fast serde compatibility

SIMD JSON for Rust  

JSON-E Rust data-struct paramter crate for lightweight embedded content with objects and much more

What makes JSON-e unique is that it extensive documentation and ease of use

JSON-E Rust data-struct paramter crate for lightweight embedded content with objects and much more

Rust JSON Parser Benchmark

Download and Generate JSON Data

Rust JSON Parser Benchmark

Read JSON values quickly - Rust JSON Parser

AJSON get json value with specified path, such as project

Read JSON values quickly - Rust JSON Parser

Rust actix json request example

Send a json request to actix, and parse it

Rust actix json request example
JSON

140

json_typegen - Rust types from JSON samples

json_typegen is a collection of tools for generating types from

json_typegen - Rust types from JSON samples

Rust JSON parsing benchmarks

This project aims to provide benchmarks to show how various JSON-parsing libraries in the Rust programming language perform at various JSON-parsing tasks

Rust JSON parsing benchmarks

A tiny command line tool written in rust to print json data as a formatted...

A tiny command line tool written in rust to print json data as a formatted table

A tiny command line tool written in rust to print json data as a formatted...

A Rust implementation of the JSON-RPC 2

A Rust implementation of the serde) for JSON-RPC

A Rust implementation of the JSON-RPC 2
Facebook Instagram Twitter GitHub Dribbble
Privacy