dtolnay / serde-yaml

Strongly typed YAML library for Rust
Apache License 2.0
960 stars 157 forks source link

test: add untagged de tests #376

Open Fishrock123 opened 1 year ago

Fishrock123 commented 1 year ago

I was unconvinced that serde_yaml's deserializer was handling untagged enums correctly, but it appears that it is.

polarathene commented 1 year ago

For reference, there's a known failure that affects untagged enums: https://github.com/dtolnay/serde-yaml/issues/165


The reproduction example (original Rust Playground):

use std::collections::BTreeMap;
use serde_yaml;
use serde::Deserialize;

fn main() {
    let input = r#"
items:
    bar: 42
    baz: 123
    200: 321
"#;

    // Deserializing into `Items` will work, but not `Wrapper` as an untagged enum:
    let wrapped: Wrapper = serde_yaml::from_str(input).expect("Couldn't deserialize");
    println!("{:#?}", wrapped);
}

#[derive(Debug, Deserialize, PartialEq)]
#[serde(untagged)]
enum Wrapper {
  Item(Items),
}

#[derive(Debug, Deserialize, PartialEq)]
struct Items {
  items: BTreeMap<String, usize>,
}

Fails with:

Couldn't deserialize: Message("data did not match any variant of untagged enum Wrapper", None)

EDIT: The above playground reproduction uses an 0.8.x release. The same failure occurs with 0.9.x too however.

It's due to number key 200 not being quote wrapped. Seems to be an issue with converting it to the desired String key in the Items struct.