1
use std::num::NonZeroU32;
2

            
3
use ron::error::{Error, Position, SpannedError};
4
use serde::{
5
    de::{Deserialize, Error as DeError, Unexpected},
6
    Deserializer,
7
};
8

            
9
112
#[derive(Debug, serde::Deserialize, PartialEq)]
10
#[serde(deny_unknown_fields)]
11
enum Test {
12
    TupleVariant(i32, String),
13
    StructVariant { a: bool, b: NonZeroU32, c: i32 },
14
}
15

            
16
#[derive(Debug, PartialEq)] // GRCOV_EXCL_LINE
17
struct TypeError;
18

            
19
impl<'de> Deserialize<'de> for TypeError {
20
4
    fn deserialize<D: Deserializer<'de>>(_deserializer: D) -> Result<Self, D::Error> {
21
4
        Err(D::Error::invalid_type(Unexpected::Unit, &"impossible"))
22
4
    }
23
}
24

            
25
#[test]
26
4
fn test_error_positions() {
27
4
    assert_eq!(
28
4
        ron::from_str::<TypeError>("  ()"),
29
4
        Err(SpannedError {
30
4
            code: Error::InvalidValueForType {
31
4
                expected: String::from("impossible"),
32
4
                found: String::from("a unit value"),
33
4
            },
34
4
            position: Position { line: 1, col: 3 },
35
4
        })
36
4
    );
37

            
38
4
    assert_eq!(
39
4
        ron::from_str::<Test>("StructVariant(a: true, b: 0, c: -42)"),
40
4
        Err(SpannedError {
41
4
            code: Error::InvalidValueForType {
42
4
                expected: String::from("a nonzero u32"),
43
4
                found: String::from("the unsigned integer `0`"),
44
4
            },
45
4
            position: Position { line: 1, col: 28 },
46
4
        })
47
4
    );
48

            
49
4
    assert_eq!(
50
4
        ron::from_str::<Test>("TupleVariant(42)"),
51
4
        Err(SpannedError {
52
4
            code: Error::ExpectedDifferentLength {
53
4
                expected: String::from("tuple variant Test::TupleVariant with 2 elements"),
54
4
                found: 1,
55
4
            },
56
4
            position: Position { line: 1, col: 16 },
57
4
        })
58
4
    );
59

            
60
4
    assert_eq!(
61
4
        ron::from_str::<Test>("NotAVariant"),
62
4
        Err(SpannedError {
63
4
            code: Error::NoSuchEnumVariant {
64
4
                expected: &["TupleVariant", "StructVariant"],
65
4
                found: String::from("NotAVariant"),
66
4
                outer: Some(String::from("Test")),
67
4
            },
68
4
            position: Position { line: 1, col: 12 },
69
4
        })
70
4
    );
71

            
72
4
    assert_eq!(
73
4
        ron::from_str::<Test>("StructVariant(a: true, b: 1, c: -42, d: \"gotcha\")"),
74
4
        Err(SpannedError {
75
4
            code: Error::NoSuchStructField {
76
4
                expected: &["a", "b", "c"],
77
4
                found: String::from("d"),
78
4
                outer: Some(String::from("StructVariant")),
79
4
            },
80
4
            position: Position { line: 1, col: 39 },
81
4
        })
82
4
    );
83

            
84
4
    assert_eq!(
85
4
        ron::from_str::<Test>("StructVariant(a: true, c: -42)"),
86
4
        Err(SpannedError {
87
4
            code: Error::MissingStructField {
88
4
                field: "b",
89
4
                outer: Some(String::from("StructVariant")),
90
4
            },
91
4
            position: Position { line: 1, col: 30 },
92
4
        })
93
4
    );
94

            
95
4
    assert_eq!(
96
4
        ron::from_str::<Test>("StructVariant(a: true, b: 1, a: false, c: -42)"),
97
4
        Err(SpannedError {
98
4
            code: Error::DuplicateStructField {
99
4
                field: "a",
100
4
                outer: Some(String::from("StructVariant")),
101
4
            },
102
4
            position: Position { line: 1, col: 31 },
103
4
        })
104
4
    );
105
4
}