hjson/hjson-rust

Parse error on deserialization of enum value

Closed this issue · 8 comments

Trying to deserialize an struct that contains an enum on Rust nightly. However using hjson i get a parse error while the example seems to work when using json instead.

thread 'hjson_enum_serialize_deserialize_works' panicked at 'called `Result::unwrap()` on an `Err` value: Syntax(Found a punctuator where a key name was expected (check your syntax or use quotes if the key name includes {}[],: or whitespace), 1, 1)', /Users/rustbuild/src/rust-buildbot/slave/nightly-dist-rustc-mac/build/src/libcore/result.rs:845

Example test-case:

#![feature(proc_macro)]

#[macro_use]
extern crate serde_derive;
extern crate serde_hjson;

#[derive(Serialize, Deserialize, Debug, PartialEq)]
struct Config {
    color: Color,
}

#[derive(Serialize, Deserialize, Debug, PartialEq)]
enum Color {
    Green,
}

#[test]
fn hjson_enum_serialize_deserialize_works() {
    let config = Config { color: Color::Green };
    let serialized = serde_hjson::to_string(&config).unwrap();
    println!("serialized:\n{}", serialized);
    let deserialized: Config = serde_hjson::from_str(&serialized).unwrap();
    println!("deserialized:\n{:?}", deserialized);
    assert_eq!(config, deserialized);
}

Best regards,
Sander Hahn

@sanderhahn are you testing this with v0.8.2 (6710dab)?

Cargo gives 0.8.1 by default so added this line to my Toml:

serde-hjson = { git = "https://github.com/hjson/hjson-rust", rev = "6710dab" }

The result is the same error message however... also tried master branch.

I tried to compile your test but I get

error: #[derive] for custom traits is not stable enough for use and is subject to change (see issue #29644)

Do I need nightly? Can you give me a small sample (like this) that works on stable 1.13.0?

Yes sorry i was using nightly. Now i changed to stable:

active toolchain
----------------

stable-x86_64-apple-darwin (default)
rustc 1.14.0 (e8a012324 2016-12-16)

The example code i am trying to get to work is adjusted for stable and now available on https://github.com/sanderhahn/example-serde-hjson. Used the 1.14 stable version, is that okay?

I took a look and found the problem in deserialize_enum. While the code is well tested with deserialization to Map<String, Value>, the other cases (like enum) are not. When I ported the code from serde_json I didn't want to remove them outright but I should have added a note that they are not yet supported.

For the current implementation I can offer the following workaround:

    let obj: Map<String, Value> = serde_hjson::from_str(&sample_text).unwrap();
    let json = serde_json::to_string(&obj).unwrap();

You can then use serde_json to decode into your enum. This works into the other direction as well.

For the future it will probably best to remove everything but the map case as I don't have the time to support these and I'm low on collaborators 😏

Thank you for the work around! Was trying out your hjson library in an effort to learn Rust :)

Thought that the error seemed to indicate a bug in the parser because of the message. The deserialize documentation seems to hint that it can handle a serde_json::Value to become an enum (https://serde.rs/impl-deserialize.html). Maybe i have time next week to dive into this and see where things go wrong. The nom library also is interesting for parsing purposes (https://github.com/Geal/nom).

Ah that's nice because I was writing this (by taking a big chunk from serde_json) in an effort to learn Rust :)

Well, things go wrong in deserialize_enum (which can be seen on the latest master where I fixed the error message). The debugging experience with Rust still has some gaping holes ... (I'm debugging with Vim/gdb) so I didn't have the time to look further.

Get the feeling that VariantVisitor a missing element, however the source of json and hjson seem to have deverged with respect to Deserializer and DeserializerImpl. Adding the functionality might be easier if the parsing code was decoupled from deserialization (like toml's parser and serde decoder). The reason to use hjson for me was to experiment because its simplified syntax versus yaml seems attractive. Thank you for your efforts on hjson :) Sorry that i am not very useful as a contributor...