toml_edit/parser/
value.rs1use crate::RawString;
2use crate::Value;
3use crate::parser::array::on_array;
4use crate::parser::inline_table::on_inline_table;
5use crate::parser::prelude::*;
6use crate::repr::{Formatted, Repr};
7
8pub(crate) fn value(
12 input: &mut Input<'_>,
13 source: toml_parser::Source<'_>,
14 errors: &mut dyn ErrorSink,
15) -> Value {
16 #[cfg(feature = "debug")]
17 let _scope = TraceScope::new("value");
18 if let Some(event) = input.next_token() {
19 match event.kind() {
20 EventKind::StdTableOpen
21 | EventKind::ArrayTableOpen
22 | EventKind::InlineTableClose
23 | EventKind::ArrayClose
24 | EventKind::ValueSep
25 | EventKind::Comment
26 | EventKind::Newline
27 | EventKind::Error
28 | EventKind::SimpleKey
29 | EventKind::KeySep
30 | EventKind::KeyValSep
31 | EventKind::StdTableClose
32 | EventKind::ArrayTableClose => {
33 #[cfg(feature = "debug")]
34 trace(
35 &format!("unexpected {event:?}"),
36 anstyle::AnsiColor::Red.on_default(),
37 );
38 }
39 EventKind::Whitespace => {
40 #[cfg(feature = "debug")]
41 trace(
42 &format!("unexpected {event:?}"),
43 anstyle::AnsiColor::Red.on_default(),
44 );
45 }
46 EventKind::InlineTableOpen => {
47 return on_inline_table(event, input, source, errors);
48 }
49 EventKind::ArrayOpen => {
50 return on_array(event, input, source, errors);
51 }
52 EventKind::Scalar => {
53 return on_scalar(event, source, errors);
54 }
55 }
56 }
57
58 let value_raw = RawString::with_span(0..0);
59 let mut f = Formatted::new(0);
60 f.set_repr_unchecked(Repr::new_unchecked(value_raw));
61 Value::Integer(f)
62}
63
64pub(crate) fn on_scalar(
65 event: &toml_parser::parser::Event,
66 source: toml_parser::Source<'_>,
67 errors: &mut dyn ErrorSink,
68) -> Value {
69 #[cfg(feature = "debug")]
70 let _scope = TraceScope::new("on_scalar");
71 let value_span = event.span();
72 let value_raw = RawString::with_span(value_span.start()..value_span.end());
73
74 let raw = source.get(event).unwrap();
75 let mut decoded = std::borrow::Cow::Borrowed("");
76 let kind = raw.decode_scalar(&mut decoded, errors);
77 match kind {
78 toml_parser::decoder::ScalarKind::String => {
79 let mut f = Formatted::new(decoded.into());
80 f.set_repr_unchecked(Repr::new_unchecked(value_raw));
81 Value::String(f)
82 }
83 toml_parser::decoder::ScalarKind::Boolean(value) => {
84 let mut f = Formatted::new(value);
85 f.set_repr_unchecked(Repr::new_unchecked(value_raw));
86 Value::Boolean(f)
87 }
88 toml_parser::decoder::ScalarKind::DateTime => {
89 let value = match decoded.parse::<toml_datetime::Datetime>() {
90 Ok(value) => value,
91 Err(err) => {
92 errors.report_error(
93 ParseError::new(err.to_string()).with_unexpected(event.span()),
94 );
95 toml_datetime::Datetime {
96 date: None,
97 time: None,
98 offset: None,
99 }
100 }
101 };
102 let mut f = Formatted::new(value);
103 f.set_repr_unchecked(Repr::new_unchecked(value_raw));
104 Value::Datetime(f)
105 }
106 toml_parser::decoder::ScalarKind::Float => {
107 let value = match decoded.parse::<f64>() {
108 Ok(value) => {
109 if value.is_infinite()
110 && !(decoded
111 .strip_prefix(['+', '-'])
112 .unwrap_or(&decoded)
113 .chars()
114 .all(|c| c.is_ascii_alphabetic()))
115 {
116 errors.report_error(
117 ParseError::new("floating-point number overflowed")
118 .with_unexpected(event.span()),
119 );
120 }
121 value
122 }
123 Err(_) => {
124 errors.report_error(
125 ParseError::new(kind.invalid_description()).with_unexpected(event.span()),
126 );
127 f64::NAN
128 }
129 };
130 let mut f = Formatted::new(value);
131 f.set_repr_unchecked(Repr::new_unchecked(value_raw));
132 Value::Float(f)
133 }
134 toml_parser::decoder::ScalarKind::Integer(radix) => {
135 let value = match i64::from_str_radix(&decoded, radix.value()) {
136 Ok(value) => value,
137 Err(_) => {
138 errors.report_error(
140 ParseError::new("integer number overflowed").with_unexpected(event.span()),
141 );
142 i64::MAX
143 }
144 };
145 let mut f = Formatted::new(value);
146 f.set_repr_unchecked(Repr::new_unchecked(value_raw));
147 Value::Integer(f)
148 }
149 }
150}