diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-05-30 03:57:31 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-05-30 03:57:31 +0000 |
commit | dc0db358abe19481e475e10c32149b53370f1a1c (patch) | |
tree | ab8ce99c4b255ce46f99ef402c27916055b899ee /vendor/toml-0.5.9/src | |
parent | Releasing progress-linux version 1.71.1+dfsg1-2~progress7.99u1. (diff) | |
download | rustc-dc0db358abe19481e475e10c32149b53370f1a1c.tar.xz rustc-dc0db358abe19481e475e10c32149b53370f1a1c.zip |
Merging upstream version 1.72.1+dfsg1.
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'vendor/toml-0.5.9/src')
-rw-r--r-- | vendor/toml-0.5.9/src/datetime.rs | 544 | ||||
-rw-r--r-- | vendor/toml-0.5.9/src/de.rs | 2262 | ||||
-rw-r--r-- | vendor/toml-0.5.9/src/lib.rs | 180 | ||||
-rw-r--r-- | vendor/toml-0.5.9/src/macros.rs | 462 | ||||
-rw-r--r-- | vendor/toml-0.5.9/src/map.rs | 595 | ||||
-rw-r--r-- | vendor/toml-0.5.9/src/ser.rs | 1859 | ||||
-rw-r--r-- | vendor/toml-0.5.9/src/spanned.rs | 168 | ||||
-rw-r--r-- | vendor/toml-0.5.9/src/tokens.rs | 740 | ||||
-rw-r--r-- | vendor/toml-0.5.9/src/value.rs | 1081 |
9 files changed, 0 insertions, 7891 deletions
diff --git a/vendor/toml-0.5.9/src/datetime.rs b/vendor/toml-0.5.9/src/datetime.rs deleted file mode 100644 index a68b07568..000000000 --- a/vendor/toml-0.5.9/src/datetime.rs +++ /dev/null @@ -1,544 +0,0 @@ -use std::error; -use std::fmt; -use std::str::{self, FromStr}; - -use serde::{de, ser}; - -/// A parsed TOML datetime value -/// -/// This structure is intended to represent the datetime primitive type that can -/// be encoded into TOML documents. This type is a parsed version that contains -/// all metadata internally. -/// -/// Currently this type is intentionally conservative and only supports -/// `to_string` as an accessor. Over time though it's intended that it'll grow -/// more support! -/// -/// Note that if you're using `Deserialize` to deserialize a TOML document, you -/// can use this as a placeholder for where you're expecting a datetime to be -/// specified. -/// -/// Also note though that while this type implements `Serialize` and -/// `Deserialize` it's only recommended to use this type with the TOML format, -/// otherwise encoded in other formats it may look a little odd. -/// -/// Depending on how the option values are used, this struct will correspond -/// with one of the following four datetimes from the [TOML v1.0.0 spec]: -/// -/// | `date` | `time` | `offset` | TOML type | -/// | --------- | --------- | --------- | ------------------ | -/// | `Some(_)` | `Some(_)` | `Some(_)` | [Offset Date-Time] | -/// | `Some(_)` | `Some(_)` | `None` | [Local Date-Time] | -/// | `Some(_)` | `None` | `None` | [Local Date] | -/// | `None` | `Some(_)` | `None` | [Local Time] | -/// -/// **1. Offset Date-Time**: If all the optional values are used, `Datetime` -/// corresponds to an [Offset Date-Time]. From the TOML v1.0.0 spec: -/// -/// > To unambiguously represent a specific instant in time, you may use an -/// > RFC 3339 formatted date-time with offset. -/// > -/// > ```toml -/// > odt1 = 1979-05-27T07:32:00Z -/// > odt2 = 1979-05-27T00:32:00-07:00 -/// > odt3 = 1979-05-27T00:32:00.999999-07:00 -/// > ``` -/// > -/// > For the sake of readability, you may replace the T delimiter between date -/// > and time with a space character (as permitted by RFC 3339 section 5.6). -/// > -/// > ```toml -/// > odt4 = 1979-05-27 07:32:00Z -/// > ``` -/// -/// **2. Local Date-Time**: If `date` and `time` are given but `offset` is -/// `None`, `Datetime` corresponds to a [Local Date-Time]. From the spec: -/// -/// > If you omit the offset from an RFC 3339 formatted date-time, it will -/// > represent the given date-time without any relation to an offset or -/// > timezone. It cannot be converted to an instant in time without additional -/// > information. Conversion to an instant, if required, is implementation- -/// > specific. -/// > -/// > ```toml -/// > ldt1 = 1979-05-27T07:32:00 -/// > ldt2 = 1979-05-27T00:32:00.999999 -/// > ``` -/// -/// **3. Local Date**: If only `date` is given, `Datetime` corresponds to a -/// [Local Date]; see the docs for [`Date`]. -/// -/// **4. Local Time**: If only `time` is given, `Datetime` corresponds to a -/// [Local Time]; see the docs for [`Time`]. -/// -/// [TOML v1.0.0 spec]: https://toml.io/en/v1.0.0 -/// [Offset Date-Time]: https://toml.io/en/v1.0.0#offset-date-time -/// [Local Date-Time]: https://toml.io/en/v1.0.0#local-date-time -/// [Local Date]: https://toml.io/en/v1.0.0#local-date -/// [Local Time]: https://toml.io/en/v1.0.0#local-time -#[derive(PartialEq, Clone)] -pub struct Datetime { - /// Optional date. - /// Required for: *Offset Date-Time*, *Local Date-Time*, *Local Date*. - pub date: Option<Date>, - - /// Optional time. - /// Required for: *Offset Date-Time*, *Local Date-Time*, *Local Time*. - pub time: Option<Time>, - - /// Optional offset. - /// Required for: *Offset Date-Time*. - pub offset: Option<Offset>, -} - -/// Error returned from parsing a `Datetime` in the `FromStr` implementation. -#[derive(Debug, Clone)] -pub struct DatetimeParseError { - _private: (), -} - -// Currently serde itself doesn't have a datetime type, so we map our `Datetime` -// to a special valid in the serde data model. Namely one with these special -// fields/struct names. -// -// In general the TOML encoder/decoder will catch this and not literally emit -// these strings but rather emit datetimes as they're intended. -pub const FIELD: &str = "$__toml_private_datetime"; -pub const NAME: &str = "$__toml_private_Datetime"; - -/// A parsed TOML date value -/// -/// May be part of a [`Datetime`]. Alone, `Date` corresponds to a [Local Date]. -/// From the TOML v1.0.0 spec: -/// -/// > If you include only the date portion of an RFC 3339 formatted date-time, -/// > it will represent that entire day without any relation to an offset or -/// > timezone. -/// > -/// > ```toml -/// > ld1 = 1979-05-27 -/// > ``` -/// -/// [Local Date]: https://toml.io/en/v1.0.0#local-date -#[derive(PartialEq, Clone)] -pub struct Date { - /// Year: four digits - pub year: u16, - /// Month: 1 to 12 - pub month: u8, - /// Day: 1 to {28, 29, 30, 31} (based on month/year) - pub day: u8, -} - -/// A parsed TOML time value -/// -/// May be part of a [`Datetime`]. Alone, `Time` corresponds to a [Local Time]. -/// From the TOML v1.0.0 spec: -/// -/// > If you include only the time portion of an RFC 3339 formatted date-time, -/// > it will represent that time of day without any relation to a specific -/// > day or any offset or timezone. -/// > -/// > ```toml -/// > lt1 = 07:32:00 -/// > lt2 = 00:32:00.999999 -/// > ``` -/// > -/// > Millisecond precision is required. Further precision of fractional -/// > seconds is implementation-specific. If the value contains greater -/// > precision than the implementation can support, the additional precision -/// > must be truncated, not rounded. -/// -/// [Local Time]: https://toml.io/en/v1.0.0#local-time -#[derive(PartialEq, Clone)] -pub struct Time { - /// Hour: 0 to 23 - pub hour: u8, - /// Minute: 0 to 59 - pub minute: u8, - /// Second: 0 to {58, 59, 60} (based on leap second rules) - pub second: u8, - /// Nanosecond: 0 to 999_999_999 - pub nanosecond: u32, -} - -/// A parsed TOML time offset -/// -#[derive(PartialEq, Clone)] -pub enum Offset { - /// > A suffix which, when applied to a time, denotes a UTC offset of 00:00; - /// > often spoken "Zulu" from the ICAO phonetic alphabet representation of - /// > the letter "Z". --- [RFC 3339 section 2] - /// - /// [RFC 3339 section 2]: https://datatracker.ietf.org/doc/html/rfc3339#section-2 - Z, - - /// Offset between local time and UTC - Custom { - /// Hours: -12 to +12 - hours: i8, - - /// Minutes: 0 to 59 - minutes: u8, - }, -} - -impl fmt::Debug for Datetime { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { - fmt::Display::fmt(self, f) - } -} - -impl fmt::Display for Datetime { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { - if let Some(ref date) = self.date { - write!(f, "{}", date)?; - } - if let Some(ref time) = self.time { - if self.date.is_some() { - write!(f, "T")?; - } - write!(f, "{}", time)?; - } - if let Some(ref offset) = self.offset { - write!(f, "{}", offset)?; - } - Ok(()) - } -} - -impl fmt::Display for Date { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { - write!(f, "{:04}-{:02}-{:02}", self.year, self.month, self.day) - } -} - -impl fmt::Display for Time { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { - write!(f, "{:02}:{:02}:{:02}", self.hour, self.minute, self.second)?; - if self.nanosecond != 0 { - let s = format!("{:09}", self.nanosecond); - write!(f, ".{}", s.trim_end_matches('0'))?; - } - Ok(()) - } -} - -impl fmt::Display for Offset { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { - match *self { - Offset::Z => write!(f, "Z"), - Offset::Custom { hours, minutes } => write!(f, "{:+03}:{:02}", hours, minutes), - } - } -} - -impl FromStr for Datetime { - type Err = DatetimeParseError; - - fn from_str(date: &str) -> Result<Datetime, DatetimeParseError> { - // Accepted formats: - // - // 0000-00-00T00:00:00.00Z - // 0000-00-00T00:00:00.00 - // 0000-00-00 - // 00:00:00.00 - if date.len() < 3 { - return Err(DatetimeParseError { _private: () }); - } - let mut offset_allowed = true; - let mut chars = date.chars(); - - // First up, parse the full date if we can - let full_date = if chars.clone().nth(2) == Some(':') { - offset_allowed = false; - None - } else { - let y1 = u16::from(digit(&mut chars)?); - let y2 = u16::from(digit(&mut chars)?); - let y3 = u16::from(digit(&mut chars)?); - let y4 = u16::from(digit(&mut chars)?); - - match chars.next() { - Some('-') => {} - _ => return Err(DatetimeParseError { _private: () }), - } - - let m1 = digit(&mut chars)?; - let m2 = digit(&mut chars)?; - - match chars.next() { - Some('-') => {} - _ => return Err(DatetimeParseError { _private: () }), - } - - let d1 = digit(&mut chars)?; - let d2 = digit(&mut chars)?; - - let date = Date { - year: y1 * 1000 + y2 * 100 + y3 * 10 + y4, - month: m1 * 10 + m2, - day: d1 * 10 + d2, - }; - - if date.month < 1 || date.month > 12 { - return Err(DatetimeParseError { _private: () }); - } - if date.day < 1 || date.day > 31 { - return Err(DatetimeParseError { _private: () }); - } - - Some(date) - }; - - // Next parse the "partial-time" if available - let next = chars.clone().next(); - let partial_time = if full_date.is_some() - && (next == Some('T') || next == Some('t') || next == Some(' ')) - { - chars.next(); - true - } else { - full_date.is_none() - }; - - let time = if partial_time { - let h1 = digit(&mut chars)?; - let h2 = digit(&mut chars)?; - match chars.next() { - Some(':') => {} - _ => return Err(DatetimeParseError { _private: () }), - } - let m1 = digit(&mut chars)?; - let m2 = digit(&mut chars)?; - match chars.next() { - Some(':') => {} - _ => return Err(DatetimeParseError { _private: () }), - } - let s1 = digit(&mut chars)?; - let s2 = digit(&mut chars)?; - - let mut nanosecond = 0; - if chars.clone().next() == Some('.') { - chars.next(); - let whole = chars.as_str(); - - let mut end = whole.len(); - for (i, byte) in whole.bytes().enumerate() { - match byte { - b'0'..=b'9' => { - if i < 9 { - let p = 10_u32.pow(8 - i as u32); - nanosecond += p * u32::from(byte - b'0'); - } - } - _ => { - end = i; - break; - } - } - } - if end == 0 { - return Err(DatetimeParseError { _private: () }); - } - chars = whole[end..].chars(); - } - - let time = Time { - hour: h1 * 10 + h2, - minute: m1 * 10 + m2, - second: s1 * 10 + s2, - nanosecond, - }; - - if time.hour > 24 { - return Err(DatetimeParseError { _private: () }); - } - if time.minute > 59 { - return Err(DatetimeParseError { _private: () }); - } - if time.second > 59 { - return Err(DatetimeParseError { _private: () }); - } - if time.nanosecond > 999_999_999 { - return Err(DatetimeParseError { _private: () }); - } - - Some(time) - } else { - offset_allowed = false; - None - }; - - // And finally, parse the offset - let offset = if offset_allowed { - let next = chars.clone().next(); - if next == Some('Z') || next == Some('z') { - chars.next(); - Some(Offset::Z) - } else if next.is_none() { - None - } else { - let sign = match next { - Some('+') => 1, - Some('-') => -1, - _ => return Err(DatetimeParseError { _private: () }), - }; - chars.next(); - let h1 = digit(&mut chars)? as i8; - let h2 = digit(&mut chars)? as i8; - match chars.next() { - Some(':') => {} - _ => return Err(DatetimeParseError { _private: () }), - } - let m1 = digit(&mut chars)?; - let m2 = digit(&mut chars)?; - - Some(Offset::Custom { - hours: sign * (h1 * 10 + h2), - minutes: m1 * 10 + m2, - }) - } - } else { - None - }; - - // Return an error if we didn't hit eof, otherwise return our parsed - // date - if chars.next().is_some() { - return Err(DatetimeParseError { _private: () }); - } - - Ok(Datetime { - date: full_date, - time, - offset, - }) - } -} - -fn digit(chars: &mut str::Chars<'_>) -> Result<u8, DatetimeParseError> { - match chars.next() { - Some(c) if '0' <= c && c <= '9' => Ok(c as u8 - b'0'), - _ => Err(DatetimeParseError { _private: () }), - } -} - -impl ser::Serialize for Datetime { - fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error> - where - S: ser::Serializer, - { - use serde::ser::SerializeStruct; - - let mut s = serializer.serialize_struct(NAME, 1)?; - s.serialize_field(FIELD, &self.to_string())?; - s.end() - } -} - -impl<'de> de::Deserialize<'de> for Datetime { - fn deserialize<D>(deserializer: D) -> Result<Datetime, D::Error> - where - D: de::Deserializer<'de>, - { - struct DatetimeVisitor; - - impl<'de> de::Visitor<'de> for DatetimeVisitor { - type Value = Datetime; - - fn expecting(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result { - formatter.write_str("a TOML datetime") - } - - fn visit_map<V>(self, mut visitor: V) -> Result<Datetime, V::Error> - where - V: de::MapAccess<'de>, - { - let value = visitor.next_key::<DatetimeKey>()?; - if value.is_none() { - return Err(de::Error::custom("datetime key not found")); - } - let v: DatetimeFromString = visitor.next_value()?; - Ok(v.value) - } - } - - static FIELDS: [&str; 1] = [FIELD]; - deserializer.deserialize_struct(NAME, &FIELDS, DatetimeVisitor) - } -} - -struct DatetimeKey; - -impl<'de> de::Deserialize<'de> for DatetimeKey { - fn deserialize<D>(deserializer: D) -> Result<DatetimeKey, D::Error> - where - D: de::Deserializer<'de>, - { - struct FieldVisitor; - - impl<'de> de::Visitor<'de> for FieldVisitor { - type Value = (); - - fn expecting(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result { - formatter.write_str("a valid datetime field") - } - - fn visit_str<E>(self, s: &str) -> Result<(), E> - where - E: de::Error, - { - if s == FIELD { - Ok(()) - } else { - Err(de::Error::custom("expected field with custom name")) - } - } - } - - deserializer.deserialize_identifier(FieldVisitor)?; - Ok(DatetimeKey) - } -} - -pub struct DatetimeFromString { - pub value: Datetime, -} - -impl<'de> de::Deserialize<'de> for DatetimeFromString { - fn deserialize<D>(deserializer: D) -> Result<DatetimeFromString, D::Error> - where - D: de::Deserializer<'de>, - { - struct Visitor; - - impl<'de> de::Visitor<'de> for Visitor { - type Value = DatetimeFromString; - - fn expecting(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result { - formatter.write_str("string containing a datetime") - } - - fn visit_str<E>(self, s: &str) -> Result<DatetimeFromString, E> - where - E: de::Error, - { - match s.parse() { - Ok(date) => Ok(DatetimeFromString { value: date }), - Err(e) => Err(de::Error::custom(e)), - } - } - } - - deserializer.deserialize_str(Visitor) - } -} - -impl fmt::Display for DatetimeParseError { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { - "failed to parse datetime".fmt(f) - } -} - -impl error::Error for DatetimeParseError {} diff --git a/vendor/toml-0.5.9/src/de.rs b/vendor/toml-0.5.9/src/de.rs deleted file mode 100644 index 40d88ae7d..000000000 --- a/vendor/toml-0.5.9/src/de.rs +++ /dev/null @@ -1,2262 +0,0 @@ -//! Deserializing TOML into Rust structures. -//! -//! This module contains all the Serde support for deserializing TOML documents -//! into Rust structures. Note that some top-level functions here are also -//! provided at the top of the crate. - -use std::borrow::Cow; -use std::collections::HashMap; -use std::error; -use std::f64; -use std::fmt; -use std::iter; -use std::marker::PhantomData; -use std::str; -use std::vec; - -use serde::de; -use serde::de::value::BorrowedStrDeserializer; -use serde::de::IntoDeserializer; - -use crate::datetime; -use crate::spanned; -use crate::tokens::{Error as TokenError, Span, Token, Tokenizer}; - -/// Type Alias for a TOML Table pair -type TablePair<'a> = ((Span, Cow<'a, str>), Value<'a>); - -/// Deserializes a byte slice into a type. -/// -/// This function will attempt to interpret `bytes` as UTF-8 data and then -/// deserialize `T` from the TOML document provided. -pub fn from_slice<'de, T>(bytes: &'de [u8]) -> Result<T, Error> -where - T: de::Deserialize<'de>, -{ - match str::from_utf8(bytes) { - Ok(s) => from_str(s), - Err(e) => Err(Error::custom(None, e.to_string())), - } -} - -/// Deserializes a string into a type. -/// -/// This function will attempt to interpret `s` as a TOML document and -/// deserialize `T` from the document. -/// -/// # Examples -/// -/// ``` -/// use serde_derive::Deserialize; -/// -/// #[derive(Deserialize)] -/// struct Config { -/// title: String, -/// owner: Owner, -/// } -/// -/// #[derive(Deserialize)] -/// struct Owner { -/// name: String, -/// } -/// -/// fn main() { -/// let config: Config = toml::from_str(r#" -/// title = 'TOML Example' -/// -/// [owner] -/// name = 'Lisa' -/// "#).unwrap(); -/// -/// assert_eq!(config.title, "TOML Example"); -/// assert_eq!(config.owner.name, "Lisa"); -/// } -/// ``` -pub fn from_str<'de, T>(s: &'de str) -> Result<T, Error> -where - T: de::Deserialize<'de>, -{ - let mut d = Deserializer::new(s); - let ret = T::deserialize(&mut d)?; - d.end()?; - Ok(ret) -} - -/// Errors that can occur when deserializing a type. -#[derive(Debug, PartialEq, Eq, Clone)] -pub struct Error { - inner: Box<ErrorInner>, -} - -#[derive(Debug, PartialEq, Eq, Clone)] -struct ErrorInner { - kind: ErrorKind, - line: Option<usize>, - col: usize, - at: Option<usize>, - message: String, - key: Vec<String>, -} - -/// Errors that can occur when deserializing a type. -#[derive(Debug, PartialEq, Eq, Clone)] -enum ErrorKind { - /// EOF was reached when looking for a value - UnexpectedEof, - - /// An invalid character not allowed in a string was found - InvalidCharInString(char), - - /// An invalid character was found as an escape - InvalidEscape(char), - - /// An invalid character was found in a hex escape - InvalidHexEscape(char), - - /// An invalid escape value was specified in a hex escape in a string. - /// - /// Valid values are in the plane of unicode codepoints. - InvalidEscapeValue(u32), - - /// A newline in a string was encountered when one was not allowed. - NewlineInString, - - /// An unexpected character was encountered, typically when looking for a - /// value. - Unexpected(char), - - /// An unterminated string was found where EOF was found before the ending - /// EOF mark. - UnterminatedString, - - /// A newline was found in a table key. - NewlineInTableKey, - - /// A number failed to parse - NumberInvalid, - - /// A date or datetime was invalid - DateInvalid, - - /// Wanted one sort of token, but found another. - Wanted { - /// Expected token type - expected: &'static str, - /// Actually found token type - found: &'static str, - }, - - /// A duplicate table definition was found. - DuplicateTable(String), - - /// A previously defined table was redefined as an array. - RedefineAsArray, - - /// An empty table key was found. - EmptyTableKey, - - /// Multiline strings are not allowed for key - MultilineStringKey, - - /// A custom error which could be generated when deserializing a particular - /// type. - Custom, - - /// A tuple with a certain number of elements was expected but something - /// else was found. - ExpectedTuple(usize), - - /// Expected table keys to be in increasing tuple index order, but something - /// else was found. - ExpectedTupleIndex { - /// Expected index. - expected: usize, - /// Key that was specified. - found: String, - }, - - /// An empty table was expected but entries were found - ExpectedEmptyTable, - - /// Dotted key attempted to extend something that is not a table. - DottedKeyInvalidType, - - /// An unexpected key was encountered. - /// - /// Used when deserializing a struct with a limited set of fields. - UnexpectedKeys { - /// The unexpected keys. - keys: Vec<String>, - /// Keys that may be specified. - available: &'static [&'static str], - }, - - /// Unquoted string was found when quoted one was expected - UnquotedString, - - #[doc(hidden)] - __Nonexhaustive, -} - -/// Deserialization implementation for TOML. -pub struct Deserializer<'a> { - require_newline_after_table: bool, - allow_duplciate_after_longer_table: bool, - input: &'a str, - tokens: Tokenizer<'a>, -} - -impl<'de, 'b> de::Deserializer<'de> for &'b mut Deserializer<'de> { - type Error = Error; - - fn deserialize_any<V>(self, visitor: V) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - let mut tables = self.tables()?; - let table_indices = build_table_indices(&tables); - let table_pindices = build_table_pindices(&tables); - - let res = visitor.visit_map(MapVisitor { - values: Vec::new().into_iter().peekable(), - next_value: None, - depth: 0, - cur: 0, - cur_parent: 0, - max: tables.len(), - table_indices: &table_indices, - table_pindices: &table_pindices, - tables: &mut tables, - array: false, - de: self, - }); - res.map_err(|mut err| { - // Errors originating from this library (toml), have an offset - // attached to them already. Other errors, like those originating - // from serde (like "missing field") or from a custom deserializer, - // do not have offsets on them. Here, we do a best guess at their - // location, by attributing them to the "current table" (the last - // item in `tables`). - err.fix_offset(|| tables.last().map(|table| table.at)); - err.fix_linecol(|at| self.to_linecol(at)); - err - }) - } - - // Called when the type to deserialize is an enum, as opposed to a field in the type. - fn deserialize_enum<V>( - self, - _name: &'static str, - _variants: &'static [&'static str], - visitor: V, - ) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - let (value, name) = self.string_or_table()?; - match value.e { - E::String(val) => visitor.visit_enum(val.into_deserializer()), - E::InlineTable(values) => { - if values.len() != 1 { - Err(Error::from_kind( - Some(value.start), - ErrorKind::Wanted { - expected: "exactly 1 element", - found: if values.is_empty() { - "zero elements" - } else { - "more than 1 element" - }, - }, - )) - } else { - visitor.visit_enum(InlineTableDeserializer { - values: values.into_iter(), - next_value: None, - }) - } - } - E::DottedTable(_) => visitor.visit_enum(DottedTableDeserializer { - name: name.expect("Expected table header to be passed."), - value, - }), - e => Err(Error::from_kind( - Some(value.start), - ErrorKind::Wanted { - expected: "string or table", - found: e.type_name(), - }, - )), - } - } - - fn deserialize_struct<V>( - self, - name: &'static str, - fields: &'static [&'static str], - visitor: V, - ) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - if name == spanned::NAME && fields == [spanned::START, spanned::END, spanned::VALUE] { - let start = 0; - let end = self.input.len(); - - let res = visitor.visit_map(SpannedDeserializer { - phantom_data: PhantomData, - start: Some(start), - value: Some(self), - end: Some(end), - }); - return res; - } - - self.deserialize_any(visitor) - } - - serde::forward_to_deserialize_any! { - bool u8 u16 u32 u64 i8 i16 i32 i64 f32 f64 char str string seq - bytes byte_buf map unit newtype_struct - ignored_any unit_struct tuple_struct tuple option identifier - } -} - -// Builds a datastructure that allows for efficient sublinear lookups. -// The returned HashMap contains a mapping from table header (like [a.b.c]) -// to list of tables with that precise name. The tables are being identified -// by their index in the passed slice. We use a list as the implementation -// uses this data structure for arrays as well as tables, -// so if any top level [[name]] array contains multiple entries, -// there are multiple entires in the list. -// The lookup is performed in the `SeqAccess` implementation of `MapVisitor`. -// The lists are ordered, which we exploit in the search code by using -// bisection. -fn build_table_indices<'de>(tables: &[Table<'de>]) -> HashMap<Vec<Cow<'de, str>>, Vec<usize>> { - let mut res = HashMap::new(); - for (i, table) in tables.iter().enumerate() { - let header = table.header.iter().map(|v| v.1.clone()).collect::<Vec<_>>(); - res.entry(header).or_insert_with(Vec::new).push(i); - } - res -} - -// Builds a datastructure that allows for efficient sublinear lookups. -// The returned HashMap contains a mapping from table header (like [a.b.c]) -// to list of tables whose name at least starts with the specified -// name. So searching for [a.b] would give both [a.b.c.d] as well as [a.b.e]. -// The tables are being identified by their index in the passed slice. -// -// A list is used for two reasons: First, the implementation also -// stores arrays in the same data structure and any top level array -// of size 2 or greater creates multiple entries in the list with the -// same shared name. Second, there can be multiple tables sharing -// the same prefix. -// -// The lookup is performed in the `MapAccess` implementation of `MapVisitor`. -// The lists are ordered, which we exploit in the search code by using -// bisection. -fn build_table_pindices<'de>(tables: &[Table<'de>]) -> HashMap<Vec<Cow<'de, str>>, Vec<usize>> { - let mut res = HashMap::new(); - for (i, table) in tables.iter().enumerate() { - let header = table.header.iter().map(|v| v.1.clone()).collect::<Vec<_>>(); - for len in 0..=header.len() { - res.entry(header[..len].to_owned()) - .or_insert_with(Vec::new) - .push(i); - } - } - res -} - -fn headers_equal<'a, 'b>(hdr_a: &[(Span, Cow<'a, str>)], hdr_b: &[(Span, Cow<'b, str>)]) -> bool { - if hdr_a.len() != hdr_b.len() { - return false; - } - hdr_a.iter().zip(hdr_b.iter()).all(|(h1, h2)| h1.1 == h2.1) -} - -struct Table<'a> { - at: usize, - header: Vec<(Span, Cow<'a, str>)>, - values: Option<Vec<TablePair<'a>>>, - array: bool, -} - -struct MapVisitor<'de, 'b> { - values: iter::Peekable<vec::IntoIter<TablePair<'de>>>, - next_value: Option<TablePair<'de>>, - depth: usize, - cur: usize, - cur_parent: usize, - max: usize, - table_indices: &'b HashMap<Vec<Cow<'de, str>>, Vec<usize>>, - table_pindices: &'b HashMap<Vec<Cow<'de, str>>, Vec<usize>>, - tables: &'b mut [Table<'de>], - array: bool, - de: &'b mut Deserializer<'de>, -} - -impl<'de, 'b> de::MapAccess<'de> for MapVisitor<'de, 'b> { - type Error = Error; - - fn next_key_seed<K>(&mut self, seed: K) -> Result<Option<K::Value>, Error> - where - K: de::DeserializeSeed<'de>, - { - if self.cur_parent == self.max || self.cur == self.max { - return Ok(None); - } - - loop { - assert!(self.next_value.is_none()); - if let Some((key, value)) = self.values.next() { - let ret = seed.deserialize(StrDeserializer::spanned(key.clone()))?; - self.next_value = Some((key, value)); - return Ok(Some(ret)); - } - - let next_table = { - let prefix_stripped = self.tables[self.cur_parent].header[..self.depth] - .iter() - .map(|v| v.1.clone()) - .collect::<Vec<_>>(); - self.table_pindices - .get(&prefix_stripped) - .and_then(|entries| { - let start = entries.binary_search(&self.cur).unwrap_or_else(|v| v); - if start == entries.len() || entries[start] < self.cur { - return None; - } - entries[start..] - .iter() - .filter_map(|i| if *i < self.max { Some(*i) } else { None }) - .map(|i| (i, &self.tables[i])) - .find(|(_, table)| table.values.is_some()) - .map(|p| p.0) - }) - }; - - let pos = match next_table { - Some(pos) => pos, - None => return Ok(None), - }; - self.cur = pos; - - // Test to see if we're duplicating our parent's table, and if so - // then this is an error in the toml format - if self.cur_parent != pos { - if headers_equal( - &self.tables[self.cur_parent].header, - &self.tables[pos].header, - ) { - let at = self.tables[pos].at; - let name = self.tables[pos] - .header - .iter() - .map(|k| k.1.to_owned()) - .collect::<Vec<_>>() - .join("."); - return Err(self.de.error(at, ErrorKind::DuplicateTable(name))); - } - - // If we're here we know we should share the same prefix, and if - // the longer table was defined first then we want to narrow - // down our parent's length if possible to ensure that we catch - // duplicate tables defined afterwards. - if !self.de.allow_duplciate_after_longer_table { - let parent_len = self.tables[self.cur_parent].header.len(); - let cur_len = self.tables[pos].header.len(); - if cur_len < parent_len { - self.cur_parent = pos; - } - } - } - - let table = &mut self.tables[pos]; - - // If we're not yet at the appropriate depth for this table then we - // just next the next portion of its header and then continue - // decoding. - if self.depth != table.header.len() { - let key = &table.header[self.depth]; - let key = seed.deserialize(StrDeserializer::spanned(key.clone()))?; - return Ok(Some(key)); - } - - // Rule out cases like: - // - // [[foo.bar]] - // [[foo]] - if table.array { - let kind = ErrorKind::RedefineAsArray; - return Err(self.de.error(table.at, kind)); - } - - self.values = table - .values - .take() - .expect("Unable to read table values") - .into_iter() - .peekable(); - } - } - - fn next_value_seed<V>(&mut self, seed: V) -> Result<V::Value, Error> - where - V: de::DeserializeSeed<'de>, - { - if let Some((k, v)) = self.next_value.take() { - match seed.deserialize(ValueDeserializer::new(v)) { - Ok(v) => return Ok(v), - Err(mut e) => { - e.add_key_context(&k.1); - return Err(e); - } - } - } - - let array = - self.tables[self.cur].array && self.depth == self.tables[self.cur].header.len() - 1; - self.cur += 1; - let res = seed.deserialize(MapVisitor { - values: Vec::new().into_iter().peekable(), - next_value: None, - depth: self.depth + if array { 0 } else { 1 }, - cur_parent: self.cur - 1, - cur: 0, - max: self.max, - array, - table_indices: &*self.table_indices, - table_pindices: &*self.table_pindices, - tables: &mut *self.tables, - de: &mut *self.de, - }); - res.map_err(|mut e| { - e.add_key_context(&self.tables[self.cur - 1].header[self.depth].1); - e - }) - } -} - -impl<'de, 'b> de::SeqAccess<'de> for MapVisitor<'de, 'b> { - type Error = Error; - - fn next_element_seed<K>(&mut self, seed: K) -> Result<Option<K::Value>, Error> - where - K: de::DeserializeSeed<'de>, - { - assert!(self.next_value.is_none()); - assert!(self.values.next().is_none()); - - if self.cur_parent == self.max { - return Ok(None); - } - - let header_stripped = self.tables[self.cur_parent] - .header - .iter() - .map(|v| v.1.clone()) - .collect::<Vec<_>>(); - let start_idx = self.cur_parent + 1; - let next = self - .table_indices - .get(&header_stripped) - .and_then(|entries| { - let start = entries.binary_search(&start_idx).unwrap_or_else(|v| v); - if start == entries.len() || entries[start] < start_idx { - return None; - } - entries[start..] - .iter() - .filter_map(|i| if *i < self.max { Some(*i) } else { None }) - .map(|i| (i, &self.tables[i])) - .find(|(_, table)| table.array) - .map(|p| p.0) - }) - .unwrap_or(self.max); - - let ret = seed.deserialize(MapVisitor { - values: self.tables[self.cur_parent] - .values - .take() - .expect("Unable to read table values") - .into_iter() - .peekable(), - next_value: None, - depth: self.depth + 1, - cur_parent: self.cur_parent, - max: next, - cur: 0, - array: false, - table_indices: &*self.table_indices, - table_pindices: &*self.table_pindices, - tables: &mut self.tables, - de: &mut self.de, - })?; - self.cur_parent = next; - Ok(Some(ret)) - } -} - -impl<'de, 'b> de::Deserializer<'de> for MapVisitor<'de, 'b> { - type Error = Error; - - fn deserialize_any<V>(self, visitor: V) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - if self.array { - visitor.visit_seq(self) - } else { - visitor.visit_map(self) - } - } - - // `None` is interpreted as a missing field so be sure to implement `Some` - // as a present field. - fn deserialize_option<V>(self, visitor: V) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - visitor.visit_some(self) - } - - fn deserialize_newtype_struct<V>( - self, - _name: &'static str, - visitor: V, - ) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - visitor.visit_newtype_struct(self) - } - - fn deserialize_struct<V>( - mut self, - name: &'static str, - fields: &'static [&'static str], - visitor: V, - ) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - if name == spanned::NAME - && fields == [spanned::START, spanned::END, spanned::VALUE] - && !(self.array && !self.values.peek().is_none()) - { - // TODO we can't actually emit spans here for the *entire* table/array - // due to the format that toml uses. Setting the start and end to 0 is - // *detectable* (and no reasonable span would look like that), - // it would be better to expose this in the API via proper - // ADTs like Option<T>. - let start = 0; - let end = 0; - - let res = visitor.visit_map(SpannedDeserializer { - phantom_data: PhantomData, - start: Some(start), - value: Some(self), - end: Some(end), - }); - return res; - } - - self.deserialize_any(visitor) - } - - fn deserialize_enum<V>( - self, - _name: &'static str, - _variants: &'static [&'static str], - visitor: V, - ) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - if self.tables.len() != 1 { - return Err(Error::custom( - Some(self.cur), - "enum table must contain exactly one table".into(), - )); - } - let table = &mut self.tables[0]; - let values = table.values.take().expect("table has no values?"); - if table.header.is_empty() { - return Err(self.de.error(self.cur, ErrorKind::EmptyTableKey)); - } - let name = table.header[table.header.len() - 1].1.to_owned(); - visitor.visit_enum(DottedTableDeserializer { - name, - value: Value { - e: E::DottedTable(values), - start: 0, - end: 0, - }, - }) - } - - serde::forward_to_deserialize_any! { - bool u8 u16 u32 u64 i8 i16 i32 i64 f32 f64 char str string seq - bytes byte_buf map unit identifier - ignored_any unit_struct tuple_struct tuple - } -} - -struct StrDeserializer<'a> { - span: Option<Span>, - key: Cow<'a, str>, -} - -impl<'a> StrDeserializer<'a> { - fn spanned(inner: (Span, Cow<'a, str>)) -> StrDeserializer<'a> { - StrDeserializer { - span: Some(inner.0), - key: inner.1, - } - } - fn new(key: Cow<'a, str>) -> StrDeserializer<'a> { - StrDeserializer { span: None, key } - } -} - -impl<'a, 'b> de::IntoDeserializer<'a, Error> for StrDeserializer<'a> { - type Deserializer = Self; - - fn into_deserializer(self) -> Self::Deserializer { - self - } -} - -impl<'de> de::Deserializer<'de> for StrDeserializer<'de> { - type Error = Error; - - fn deserialize_any<V>(self, visitor: V) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - match self.key { - Cow::Borrowed(s) => visitor.visit_borrowed_str(s), - Cow::Owned(s) => visitor.visit_string(s), - } - } - - fn deserialize_struct<V>( - self, - name: &'static str, - fields: &'static [&'static str], - visitor: V, - ) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - if name == spanned::NAME && fields == [spanned::START, spanned::END, spanned::VALUE] { - if let Some(span) = self.span { - return visitor.visit_map(SpannedDeserializer { - phantom_data: PhantomData, - start: Some(span.start), - value: Some(StrDeserializer::new(self.key)), - end: Some(span.end), - }); - } - } - self.deserialize_any(visitor) - } - - serde::forward_to_deserialize_any! { - bool u8 u16 u32 u64 i8 i16 i32 i64 f32 f64 char str string seq - bytes byte_buf map option unit newtype_struct - ignored_any unit_struct tuple_struct tuple enum identifier - } -} - -struct ValueDeserializer<'a> { - value: Value<'a>, - validate_struct_keys: bool, -} - -impl<'a> ValueDeserializer<'a> { - fn new(value: Value<'a>) -> ValueDeserializer<'a> { - ValueDeserializer { - value, - validate_struct_keys: false, - } - } - - fn with_struct_key_validation(mut self) -> Self { - self.validate_struct_keys = true; - self - } -} - -impl<'de> de::Deserializer<'de> for ValueDeserializer<'de> { - type Error = Error; - - fn deserialize_any<V>(self, visitor: V) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - let start = self.value.start; - let res = match self.value.e { - E::Integer(i) => visitor.visit_i64(i), - E::Boolean(b) => visitor.visit_bool(b), - E::Float(f) => visitor.visit_f64(f), - E::String(Cow::Borrowed(s)) => visitor.visit_borrowed_str(s), - E::String(Cow::Owned(s)) => visitor.visit_string(s), - E::Datetime(s) => visitor.visit_map(DatetimeDeserializer { - date: s, - visited: false, - }), - E::Array(values) => { - let mut s = de::value::SeqDeserializer::new(values.into_iter()); - let ret = visitor.visit_seq(&mut s)?; - s.end()?; - Ok(ret) - } - E::InlineTable(values) | E::DottedTable(values) => { - visitor.visit_map(InlineTableDeserializer { - values: values.into_iter(), - next_value: None, - }) - } - }; - res.map_err(|mut err| { - // Attribute the error to whatever value returned the error. - err.fix_offset(|| Some(start)); - err - }) - } - - fn deserialize_struct<V>( - self, - name: &'static str, - fields: &'static [&'static str], - visitor: V, - ) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - if name == datetime::NAME && fields == [datetime::FIELD] { - if let E::Datetime(s) = self.value.e { - return visitor.visit_map(DatetimeDeserializer { - date: s, - visited: false, - }); - } - } - - if self.validate_struct_keys { - match self.value.e { - E::InlineTable(ref values) | E::DottedTable(ref values) => { - let extra_fields = values - .iter() - .filter_map(|key_value| { - let (ref key, ref _val) = *key_value; - if !fields.contains(&&*(key.1)) { - Some(key.clone()) - } else { - None - } - }) - .collect::<Vec<_>>(); - - if !extra_fields.is_empty() { - return Err(Error::from_kind( - Some(self.value.start), - ErrorKind::UnexpectedKeys { - keys: extra_fields - .iter() - .map(|k| k.1.to_string()) - .collect::<Vec<_>>(), - available: fields, - }, - )); - } - } - _ => {} - } - } - - if name == spanned::NAME && fields == [spanned::START, spanned::END, spanned::VALUE] { - let start = self.value.start; - let end = self.value.end; - - return visitor.visit_map(SpannedDeserializer { - phantom_data: PhantomData, - start: Some(start), - value: Some(self.value), - end: Some(end), - }); - } - - self.deserialize_any(visitor) - } - - // `None` is interpreted as a missing field so be sure to implement `Some` - // as a present field. - fn deserialize_option<V>(self, visitor: V) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - visitor.visit_some(self) - } - - fn deserialize_enum<V>( - self, - _name: &'static str, - _variants: &'static [&'static str], - visitor: V, - ) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - match self.value.e { - E::String(val) => visitor.visit_enum(val.into_deserializer()), - E::InlineTable(values) => { - if values.len() != 1 { - Err(Error::from_kind( - Some(self.value.start), - ErrorKind::Wanted { - expected: "exactly 1 element", - found: if values.is_empty() { - "zero elements" - } else { - "more than 1 element" - }, - }, - )) - } else { - visitor.visit_enum(InlineTableDeserializer { - values: values.into_iter(), - next_value: None, - }) - } - } - e => Err(Error::from_kind( - Some(self.value.start), - ErrorKind::Wanted { - expected: "string or inline table", - found: e.type_name(), - }, - )), - } - } - - fn deserialize_newtype_struct<V>( - self, - _name: &'static str, - visitor: V, - ) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - visitor.visit_newtype_struct(self) - } - - serde::forward_to_deserialize_any! { - bool u8 u16 u32 u64 i8 i16 i32 i64 f32 f64 char str string seq - bytes byte_buf map unit identifier - ignored_any unit_struct tuple_struct tuple - } -} - -impl<'de, 'b> de::IntoDeserializer<'de, Error> for MapVisitor<'de, 'b> { - type Deserializer = MapVisitor<'de, 'b>; - - fn into_deserializer(self) -> Self::Deserializer { - self - } -} - -impl<'de, 'b> de::IntoDeserializer<'de, Error> for &'b mut Deserializer<'de> { - type Deserializer = Self; - - fn into_deserializer(self) -> Self::Deserializer { - self - } -} - -impl<'de> de::IntoDeserializer<'de, Error> for Value<'de> { - type Deserializer = ValueDeserializer<'de>; - - fn into_deserializer(self) -> Self::Deserializer { - ValueDeserializer::new(self) - } -} - -struct SpannedDeserializer<'de, T: de::IntoDeserializer<'de, Error>> { - phantom_data: PhantomData<&'de ()>, - start: Option<usize>, - end: Option<usize>, - value: Option<T>, -} - -impl<'de, T> de::MapAccess<'de> for SpannedDeserializer<'de, T> -where - T: de::IntoDeserializer<'de, Error>, -{ - type Error = Error; - - fn next_key_seed<K>(&mut self, seed: K) -> Result<Option<K::Value>, Error> - where - K: de::DeserializeSeed<'de>, - { - if self.start.is_some() { - seed.deserialize(BorrowedStrDeserializer::new(spanned::START)) - .map(Some) - } else if self.end.is_some() { - seed.deserialize(BorrowedStrDeserializer::new(spanned::END)) - .map(Some) - } else if self.value.is_some() { - seed.deserialize(BorrowedStrDeserializer::new(spanned::VALUE)) - .map(Some) - } else { - Ok(None) - } - } - - fn next_value_seed<V>(&mut self, seed: V) -> Result<V::Value, Error> - where - V: de::DeserializeSeed<'de>, - { - if let Some(start) = self.start.take() { - seed.deserialize(start.into_deserializer()) - } else if let Some(end) = self.end.take() { - seed.deserialize(end.into_deserializer()) - } else if let Some(value) = self.value.take() { - seed.deserialize(value.into_deserializer()) - } else { - panic!("next_value_seed called before next_key_seed") - } - } -} - -struct DatetimeDeserializer<'a> { - visited: bool, - date: &'a str, -} - -impl<'de> de::MapAccess<'de> for DatetimeDeserializer<'de> { - type Error = Error; - - fn next_key_seed<K>(&mut self, seed: K) -> Result<Option<K::Value>, Error> - where - K: de::DeserializeSeed<'de>, - { - if self.visited { - return Ok(None); - } - self.visited = true; - seed.deserialize(DatetimeFieldDeserializer).map(Some) - } - - fn next_value_seed<V>(&mut self, seed: V) -> Result<V::Value, Error> - where - V: de::DeserializeSeed<'de>, - { - seed.deserialize(StrDeserializer::new(self.date.into())) - } -} - -struct DatetimeFieldDeserializer; - -impl<'de> de::Deserializer<'de> for DatetimeFieldDeserializer { - type Error = Error; - - fn deserialize_any<V>(self, visitor: V) -> Result<V::Value, Error> - where - V: de::Visitor<'de>, - { - visitor.visit_borrowed_str(datetime::FIELD) - } - - serde::forward_to_deserialize_any! { - bool u8 u16 u32 u64 i8 i16 i32 i64 f32 f64 char str string seq - bytes byte_buf map struct option unit newtype_struct - ignored_any unit_struct tuple_struct tuple enum identifier - } -} - -struct DottedTableDeserializer<'a> { - name: Cow<'a, str>, - value: Value<'a>, -} - -impl<'de> de::EnumAccess<'de> for DottedTableDeserializer<'de> { - type Error = Error; - type Variant = TableEnumDeserializer<'de>; - - fn variant_seed<V>(self, seed: V) -> Result<(V::Value, Self::Variant), Self::Error> - where - V: de::DeserializeSeed<'de>, - { - let (name, value) = (self.name, self.value); - seed.deserialize(StrDeserializer::new(name)) - .map(|val| (val, TableEnumDeserializer { value })) - } -} - -struct InlineTableDeserializer<'a> { - values: vec::IntoIter<TablePair<'a>>, - next_value: Option<Value<'a>>, -} - -impl<'de> de::MapAccess<'de> for InlineTableDeserializer<'de> { - type Error = Error; - - fn next_key_seed<K>(&mut self, seed: K) -> Result<Option<K::Value>, Error> - where - K: de::DeserializeSeed<'de>, - { - let (key, value) = match self.values.next() { - Some(pair) => pair, - None => return Ok(None), - }; - self.next_value = Some(value); - seed.deserialize(StrDeserializer::spanned(key)).map(Some) - } - - fn next_value_seed<V>(&mut self, seed: V) -> Result<V::Value, Error> - where - V: de::DeserializeSeed<'de>, - { - let value = self.next_value.take().expect("Unable to read table values"); - seed.deserialize(ValueDeserializer::new(value)) - } -} - -impl<'de> de::EnumAccess<'de> for InlineTableDeserializer<'de> { - type Error = Error; - type Variant = TableEnumDeserializer<'de>; - - fn variant_seed<V>(mut self, seed: V) -> Result<(V::Value, Self::Variant), Self::Error> - where - V: de::DeserializeSeed<'de>, - { - let (key, value) = match self.values.next() { - Some(pair) => pair, - None => { - return Err(Error::from_kind( - None, // FIXME: How do we get an offset here? - ErrorKind::Wanted { - expected: "table with exactly 1 entry", - found: "empty table", - }, - )); - } - }; - - seed.deserialize(StrDeserializer::new(key.1)) - .map(|val| (val, TableEnumDeserializer { value })) - } -} - -/// Deserializes table values into enum variants. -struct TableEnumDeserializer<'a> { - value: Value<'a>, -} - -impl<'de> de::VariantAccess<'de> for TableEnumDeserializer<'de> { - type Error = Error; - - fn unit_variant(self) -> Result<(), Self::Error> { - match self.value.e { - E::InlineTable(values) | E::DottedTable(values) => { - if values.is_empty() { - Ok(()) - } else { - Err(Error::from_kind( - Some(self.value.start), - ErrorKind::ExpectedEmptyTable, - )) - } - } - e => Err(Error::from_kind( - Some(self.value.start), - ErrorKind::Wanted { - expected: "table", - found: e.type_name(), - }, - )), - } - } - - fn newtype_variant_seed<T>(self, seed: T) -> Result<T::Value, Self::Error> - where - T: de::DeserializeSeed<'de>, - { - seed.deserialize(ValueDeserializer::new(self.value)) - } - - fn tuple_variant<V>(self, len: usize, visitor: V) -> Result<V::Value, Self::Error> - where - V: de::Visitor<'de>, - { - match self.value.e { - E::InlineTable(values) | E::DottedTable(values) => { - let tuple_values = values - .into_iter() - .enumerate() - .map(|(index, (key, value))| match key.1.parse::<usize>() { - Ok(key_index) if key_index == index => Ok(value), - Ok(_) | Err(_) => Err(Error::from_kind( - Some(key.0.start), - ErrorKind::ExpectedTupleIndex { - expected: index, - found: key.1.to_string(), - }, - )), - }) - // Fold all values into a `Vec`, or return the first error. - .fold(Ok(Vec::with_capacity(len)), |result, value_result| { - result.and_then(move |mut tuple_values| match value_result { - Ok(value) => { - tuple_values.push(value); - Ok(tuple_values) - } - // `Result<de::Value, Self::Error>` to `Result<Vec<_>, Self::Error>` - Err(e) => Err(e), - }) - })?; - - if tuple_values.len() == len { - de::Deserializer::deserialize_seq( - ValueDeserializer::new(Value { - e: E::Array(tuple_values), - start: self.value.start, - end: self.value.end, - }), - visitor, - ) - } else { - Err(Error::from_kind( - Some(self.value.start), - ErrorKind::ExpectedTuple(len), - )) - } - } - e => Err(Error::from_kind( - Some(self.value.start), - ErrorKind::Wanted { - expected: "table", - found: e.type_name(), - }, - )), - } - } - - fn struct_variant<V>( - self, - fields: &'static [&'static str], - visitor: V, - ) -> Result<V::Value, Self::Error> - where - V: de::Visitor<'de>, - { - de::Deserializer::deserialize_struct( - ValueDeserializer::new(self.value).with_struct_key_validation(), - "", // TODO: this should be the variant name - fields, - visitor, - ) - } -} - -impl<'a> Deserializer<'a> { - /// Creates a new deserializer which will be deserializing the string - /// provided. - pub fn new(input: &'a str) -> Deserializer<'a> { - Deserializer { - tokens: Tokenizer::new(input), - input, - require_newline_after_table: true, - allow_duplciate_after_longer_table: false, - } - } - - /// The `Deserializer::end` method should be called after a value has been - /// fully deserialized. This allows the `Deserializer` to validate that the - /// input stream is at the end or that it only has trailing - /// whitespace/comments. - pub fn end(&mut self) -> Result<(), Error> { - Ok(()) - } - - /// Historical versions of toml-rs accidentally allowed a newline after a - /// table definition, but the TOML spec requires a newline after a table - /// definition header. - /// - /// This option can be set to `false` (the default is `true`) to emulate - /// this behavior for backwards compatibility with older toml-rs versions. - pub fn set_require_newline_after_table(&mut self, require: bool) { - self.require_newline_after_table = require; - } - - /// Historical versions of toml-rs accidentally allowed a duplicate table - /// header after a longer table header was previously defined. This is - /// invalid according to the TOML spec, however. - /// - /// This option can be set to `true` (the default is `false`) to emulate - /// this behavior for backwards compatibility with older toml-rs versions. - pub fn set_allow_duplicate_after_longer_table(&mut self, allow: bool) { - self.allow_duplciate_after_longer_table = allow; - } - - fn tables(&mut self) -> Result<Vec<Table<'a>>, Error> { - let mut tables = Vec::new(); - let mut cur_table = Table { - at: 0, - header: Vec::new(), - values: None, - array: false, - }; - - while let Some(line) = self.line()? { - match line { - Line::Table { - at, - mut header, - array, - } => { - if !cur_table.header.is_empty() || cur_table.values.is_some() { - tables.push(cur_table); - } - cur_table = Table { - at, - header: Vec::new(), - values: Some(Vec::new()), - array, - }; - loop { - let part = header.next().map_err(|e| self.token_error(e)); - match part? { - Some(part) => cur_table.header.push(part), - None => break, - } - } - } - Line::KeyValue(key, value) => { - if cur_table.values.is_none() { - cur_table.values = Some(Vec::new()); - } - self.add_dotted_key(key, value, cur_table.values.as_mut().unwrap())?; - } - } - } - if !cur_table.header.is_empty() || cur_table.values.is_some() { - tables.push(cur_table); - } - Ok(tables) - } - - fn line(&mut self) -> Result<Option<Line<'a>>, Error> { - loop { - self.eat_whitespace()?; - if self.eat_comment()? { - continue; - } - if self.eat(Token::Newline)? { - continue; - } - break; - } - - match self.peek()? { - Some((_, Token::LeftBracket)) => self.table_header().map(Some), - Some(_) => self.key_value().map(Some), - None => Ok(None), - } - } - - fn table_header(&mut self) -> Result<Line<'a>, Error> { - let start = self.tokens.current(); - self.expect(Token::LeftBracket)?; - let array = self.eat(Token::LeftBracket)?; - let ret = Header::new(self.tokens.clone(), array, self.require_newline_after_table); - if self.require_newline_after_table { - self.tokens.skip_to_newline(); - } else { - loop { - match self.next()? { - Some((_, Token::RightBracket)) => { - if array { - self.eat(Token::RightBracket)?; - } - break; - } - Some((_, Token::Newline)) | None => break, - _ => {} - } - } - self.eat_whitespace()?; - } - Ok(Line::Table { - at: start, - header: ret, - array, - }) - } - - fn key_value(&mut self) -> Result<Line<'a>, Error> { - let key = self.dotted_key()?; - self.eat_whitespace()?; - self.expect(Token::Equals)?; - self.eat_whitespace()?; - - let value = self.value()?; - self.eat_whitespace()?; - if !self.eat_comment()? { - self.eat_newline_or_eof()?; - } - - Ok(Line::KeyValue(key, value)) - } - - fn value(&mut self) -> Result<Value<'a>, Error> { - let at = self.tokens.current(); - let value = match self.next()? { - Some((Span { start, end }, Token::String { val, .. })) => Value { - e: E::String(val), - start, - end, - }, - Some((Span { start, end }, Token::Keylike("true"))) => Value { - e: E::Boolean(true), - start, - end, - }, - Some((Span { start, end }, Token::Keylike("false"))) => Value { - e: E::Boolean(false), - start, - end, - }, - Some((span, Token::Keylike(key))) => self.parse_keylike(at, span, key)?, - Some((span, Token::Plus)) => self.number_leading_plus(span)?, - Some((Span { start, .. }, Token::LeftBrace)) => { - self.inline_table().map(|(Span { end, .. }, table)| Value { - e: E::InlineTable(table), - start, - end, - })? - } - Some((Span { start, .. }, Token::LeftBracket)) => { - self.array().map(|(Span { end, .. }, array)| Value { - e: E::Array(array), - start, - end, - })? - } - Some(token) => { - return Err(self.error( - at, - ErrorKind::Wanted { - expected: "a value", - found: token.1.describe(), - }, - )); - } - None => return Err(self.eof()), - }; - Ok(value) - } - - fn parse_keylike(&mut self, at: usize, span: Span, key: &'a str) -> Result<Value<'a>, Error> { - if key == "inf" || key == "nan" { - return self.number_or_date(span, key); - } - - let first_char = key.chars().next().expect("key should not be empty here"); - match first_char { - '-' | '0'..='9' => self.number_or_date(span, key), - _ => Err(self.error(at, ErrorKind::UnquotedString)), - } - } - - fn number_or_date(&mut self, span: Span, s: &'a str) -> Result<Value<'a>, Error> { - if s.contains('T') - || s.contains('t') - || (s.len() > 1 && s[1..].contains('-') && !s.contains("e-") && !s.contains("E-")) - { - self.datetime(span, s, false) - .map(|(Span { start, end }, d)| Value { - e: E::Datetime(d), - start, - end, - }) - } else if self.eat(Token::Colon)? { - self.datetime(span, s, true) - .map(|(Span { start, end }, d)| Value { - e: E::Datetime(d), - start, - end, - }) - } else { - self.number(span, s) - } - } - - /// Returns a string or table value type. - /// - /// Used to deserialize enums. Unit enums may be represented as a string or a table, all other - /// structures (tuple, newtype, struct) must be represented as a table. - fn string_or_table(&mut self) -> Result<(Value<'a>, Option<Cow<'a, str>>), Error> { - match self.peek()? { - Some((span, Token::LeftBracket)) => { - let tables = self.tables()?; - if tables.len() != 1 { - return Err(Error::from_kind( - Some(span.start), - ErrorKind::Wanted { - expected: "exactly 1 table", - found: if tables.is_empty() { - "zero tables" - } else { - "more than 1 table" - }, - }, - )); - } - - let table = tables - .into_iter() - .next() - .expect("Expected exactly one table"); - let header = table - .header - .last() - .expect("Expected at least one header value for table."); - - let start = table.at; - let end = table - .values - .as_ref() - .and_then(|values| values.last()) - .map(|&(_, ref val)| val.end) - .unwrap_or_else(|| header.1.len()); - Ok(( - Value { - e: E::DottedTable(table.values.unwrap_or_else(Vec::new)), - start, - end, - }, - Some(header.1.clone()), - )) - } - Some(_) => self.value().map(|val| (val, None)), - None => Err(self.eof()), - } - } - - fn number(&mut self, Span { start, end }: Span, s: &'a str) -> Result<Value<'a>, Error> { - let to_integer = |f| Value { - e: E::Integer(f), - start, - end, - }; - if s.starts_with("0x") { - self.integer(&s[2..], 16).map(to_integer) - } else if s.starts_with("0o") { - self.integer(&s[2..], 8).map(to_integer) - } else if s.starts_with("0b") { - self.integer(&s[2..], 2).map(to_integer) - } else if s.contains('e') || s.contains('E') { - self.float(s, None).map(|f| Value { - e: E::Float(f), - start, - end, - }) - } else if self.eat(Token::Period)? { - let at = self.tokens.current(); - match self.next()? { - Some((Span { start, end }, Token::Keylike(after))) => { - self.float(s, Some(after)).map(|f| Value { - e: E::Float(f), - start, - end, - }) - } - _ => Err(self.error(at, ErrorKind::NumberInvalid)), - } - } else if s == "inf" { - Ok(Value { - e: E::Float(f64::INFINITY), - start, - end, - }) - } else if s == "-inf" { - Ok(Value { - e: E::Float(f64::NEG_INFINITY), - start, - end, - }) - } else if s == "nan" { - Ok(Value { - e: E::Float(f64::NAN), - start, - end, - }) - } else if s == "-nan" { - Ok(Value { - e: E::Float(-f64::NAN), - start, - end, - }) - } else { - self.integer(s, 10).map(to_integer) - } - } - - fn number_leading_plus(&mut self, Span { start, .. }: Span) -> Result<Value<'a>, Error> { - let start_token = self.tokens.current(); - match self.next()? { - Some((Span { end, .. }, Token::Keylike(s))) => self.number(Span { start, end }, s), - _ => Err(self.error(start_token, ErrorKind::NumberInvalid)), - } - } - - fn integer(&self, s: &'a str, radix: u32) -> Result<i64, Error> { - let allow_sign = radix == 10; - let allow_leading_zeros = radix != 10; - let (prefix, suffix) = self.parse_integer(s, allow_sign, allow_leading_zeros, radix)?; - let start = self.tokens.substr_offset(s); - if suffix != "" { - return Err(self.error(start, ErrorKind::NumberInvalid)); - } - i64::from_str_radix(&prefix.replace("_", "").trim_start_matches('+'), radix) - .map_err(|_e| self.error(start, ErrorKind::NumberInvalid)) - } - - fn parse_integer( - &self, - s: &'a str, - allow_sign: bool, - allow_leading_zeros: bool, - radix: u32, - ) -> Result<(&'a str, &'a str), Error> { - let start = self.tokens.substr_offset(s); - - let mut first = true; - let mut first_zero = false; - let mut underscore = false; - let mut end = s.len(); - for (i, c) in s.char_indices() { - let at = i + start; - if i == 0 && (c == '+' || c == '-') && allow_sign { - continue; - } - - if c == '0' && first { - first_zero = true; - } else if c.is_digit(radix) { - if !first && first_zero && !allow_leading_zeros { - return Err(self.error(at, ErrorKind::NumberInvalid)); - } - underscore = false; - } else if c == '_' && first { - return Err(self.error(at, ErrorKind::NumberInvalid)); - } else if c == '_' && !underscore { - underscore = true; - } else { - end = i; - break; - } - first = false; - } - if first || underscore { - return Err(self.error(start, ErrorKind::NumberInvalid)); - } - Ok((&s[..end], &s[end..])) - } - - fn float(&mut self, s: &'a str, after_decimal: Option<&'a str>) -> Result<f64, Error> { - let (integral, mut suffix) = self.parse_integer(s, true, false, 10)?; - let start = self.tokens.substr_offset(integral); - - let mut fraction = None; - if let Some(after) = after_decimal { - if suffix != "" { - return Err(self.error(start, ErrorKind::NumberInvalid)); - } - let (a, b) = self.parse_integer(after, false, true, 10)?; - fraction = Some(a); - suffix = b; - } - - let mut exponent = None; - if suffix.starts_with('e') || suffix.starts_with('E') { - let (a, b) = if suffix.len() == 1 { - self.eat(Token::Plus)?; - match self.next()? { - Some((_, Token::Keylike(s))) => self.parse_integer(s, false, true, 10)?, - _ => return Err(self.error(start, ErrorKind::NumberInvalid)), - } - } else { - self.parse_integer(&suffix[1..], true, true, 10)? - }; - if b != "" { - return Err(self.error(start, ErrorKind::NumberInvalid)); - } - exponent = Some(a); - } else if !suffix.is_empty() { - return Err(self.error(start, ErrorKind::NumberInvalid)); - } - - let mut number = integral - .trim_start_matches('+') - .chars() - .filter(|c| *c != '_') - .collect::<String>(); - if let Some(fraction) = fraction { - number.push_str("."); - number.extend(fraction.chars().filter(|c| *c != '_')); - } - if let Some(exponent) = exponent { - number.push_str("E"); - number.extend(exponent.chars().filter(|c| *c != '_')); - } - number - .parse() - .map_err(|_e| self.error(start, ErrorKind::NumberInvalid)) - .and_then(|n: f64| { - if n.is_finite() { - Ok(n) - } else { - Err(self.error(start, ErrorKind::NumberInvalid)) - } - }) - } - - fn datetime( - &mut self, - mut span: Span, - date: &'a str, - colon_eaten: bool, - ) -> Result<(Span, &'a str), Error> { - let start = self.tokens.substr_offset(date); - - // Check for space separated date and time. - let mut lookahead = self.tokens.clone(); - if let Ok(Some((_, Token::Whitespace(" ")))) = lookahead.next() { - // Check if hour follows. - if let Ok(Some((_, Token::Keylike(_)))) = lookahead.next() { - self.next()?; // skip space - self.next()?; // skip keylike hour - } - } - - if colon_eaten || self.eat(Token::Colon)? { - // minutes - match self.next()? { - Some((_, Token::Keylike(_))) => {} - _ => return Err(self.error(start, ErrorKind::DateInvalid)), - } - // Seconds - self.expect(Token::Colon)?; - match self.next()? { - Some((Span { end, .. }, Token::Keylike(_))) => { - span.end = end; - } - _ => return Err(self.error(start, ErrorKind::DateInvalid)), - } - // Fractional seconds - if self.eat(Token::Period)? { - match self.next()? { - Some((Span { end, .. }, Token::Keylike(_))) => { - span.end = end; - } - _ => return Err(self.error(start, ErrorKind::DateInvalid)), - } - } - - // offset - if self.eat(Token::Plus)? { - match self.next()? { - Some((Span { end, .. }, Token::Keylike(_))) => { - span.end = end; - } - _ => return Err(self.error(start, ErrorKind::DateInvalid)), - } - } - if self.eat(Token::Colon)? { - match self.next()? { - Some((Span { end, .. }, Token::Keylike(_))) => { - span.end = end; - } - _ => return Err(self.error(start, ErrorKind::DateInvalid)), - } - } - } - - let end = self.tokens.current(); - Ok((span, &self.tokens.input()[start..end])) - } - - // TODO(#140): shouldn't buffer up this entire table in memory, it'd be - // great to defer parsing everything until later. - fn inline_table(&mut self) -> Result<(Span, Vec<TablePair<'a>>), Error> { - let mut ret = Vec::new(); - self.eat_whitespace()?; - if let Some(span) = self.eat_spanned(Token::RightBrace)? { - return Ok((span, ret)); - } - loop { - let key = self.dotted_key()?; - self.eat_whitespace()?; - self.expect(Token::Equals)?; - self.eat_whitespace()?; - let value = self.value()?; - self.add_dotted_key(key, value, &mut ret)?; - - self.eat_whitespace()?; - if let Some(span) = self.eat_spanned(Token::RightBrace)? { - return Ok((span, ret)); - } - self.expect(Token::Comma)?; - self.eat_whitespace()?; - } - } - - // TODO(#140): shouldn't buffer up this entire array in memory, it'd be - // great to defer parsing everything until later. - fn array(&mut self) -> Result<(Span, Vec<Value<'a>>), Error> { - let mut ret = Vec::new(); - - let intermediate = |me: &mut Deserializer<'_>| { - loop { - me.eat_whitespace()?; - if !me.eat(Token::Newline)? && !me.eat_comment()? { - break; - } - } - Ok(()) - }; - - loop { - intermediate(self)?; - if let Some(span) = self.eat_spanned(Token::RightBracket)? { - return Ok((span, ret)); - } - let value = self.value()?; - ret.push(value); - intermediate(self)?; - if !self.eat(Token::Comma)? { - break; - } - } - intermediate(self)?; - let span = self.expect_spanned(Token::RightBracket)?; - Ok((span, ret)) - } - - fn table_key(&mut self) -> Result<(Span, Cow<'a, str>), Error> { - self.tokens.table_key().map_err(|e| self.token_error(e)) - } - - fn dotted_key(&mut self) -> Result<Vec<(Span, Cow<'a, str>)>, Error> { - let mut result = Vec::new(); - result.push(self.table_key()?); - self.eat_whitespace()?; - while self.eat(Token::Period)? { - self.eat_whitespace()?; - result.push(self.table_key()?); - self.eat_whitespace()?; - } - Ok(result) - } - - /// Stores a value in the appropriate hierachical structure positioned based on the dotted key. - /// - /// Given the following definition: `multi.part.key = "value"`, `multi` and `part` are - /// intermediate parts which are mapped to the relevant fields in the deserialized type's data - /// hierarchy. - /// - /// # Parameters - /// - /// * `key_parts`: Each segment of the dotted key, e.g. `part.one` maps to - /// `vec![Cow::Borrowed("part"), Cow::Borrowed("one")].` - /// * `value`: The parsed value. - /// * `values`: The `Vec` to store the value in. - fn add_dotted_key( - &self, - mut key_parts: Vec<(Span, Cow<'a, str>)>, - value: Value<'a>, - values: &mut Vec<TablePair<'a>>, - ) -> Result<(), Error> { - let key = key_parts.remove(0); - if key_parts.is_empty() { - values.push((key, value)); - return Ok(()); - } - match values.iter_mut().find(|&&mut (ref k, _)| *k.1 == key.1) { - Some(&mut ( - _, - Value { - e: E::DottedTable(ref mut v), - .. - }, - )) => { - return self.add_dotted_key(key_parts, value, v); - } - Some(&mut (_, Value { start, .. })) => { - return Err(self.error(start, ErrorKind::DottedKeyInvalidType)); - } - None => {} - } - // The start/end value is somewhat misleading here. - let table_values = Value { - e: E::DottedTable(Vec::new()), - start: value.start, - end: value.end, - }; - values.push((key, table_values)); - let last_i = values.len() - 1; - if let ( - _, - Value { - e: E::DottedTable(ref mut v), - .. - }, - ) = values[last_i] - { - self.add_dotted_key(key_parts, value, v)?; - } - Ok(()) - } - - fn eat_whitespace(&mut self) -> Result<(), Error> { - self.tokens - .eat_whitespace() - .map_err(|e| self.token_error(e)) - } - - fn eat_comment(&mut self) -> Result<bool, Error> { - self.tokens.eat_comment().map_err(|e| self.token_error(e)) - } - - fn eat_newline_or_eof(&mut self) -> Result<(), Error> { - self.tokens - .eat_newline_or_eof() - .map_err(|e| self.token_error(e)) - } - - fn eat(&mut self, expected: Token<'a>) -> Result<bool, Error> { - self.tokens.eat(expected).map_err(|e| self.token_error(e)) - } - - fn eat_spanned(&mut self, expected: Token<'a>) -> Result<Option<Span>, Error> { - self.tokens - .eat_spanned(expected) - .map_err(|e| self.token_error(e)) - } - - fn expect(&mut self, expected: Token<'a>) -> Result<(), Error> { - self.tokens - .expect(expected) - .map_err(|e| self.token_error(e)) - } - - fn expect_spanned(&mut self, expected: Token<'a>) -> Result<Span, Error> { - self.tokens - .expect_spanned(expected) - .map_err(|e| self.token_error(e)) - } - - fn next(&mut self) -> Result<Option<(Span, Token<'a>)>, Error> { - self.tokens.next().map_err(|e| self.token_error(e)) - } - - fn peek(&mut self) -> Result<Option<(Span, Token<'a>)>, Error> { - self.tokens.peek().map_err(|e| self.token_error(e)) - } - - fn eof(&self) -> Error { - self.error(self.input.len(), ErrorKind::UnexpectedEof) - } - - fn token_error(&self, error: TokenError) -> Error { - match error { - TokenError::InvalidCharInString(at, ch) => { - self.error(at, ErrorKind::InvalidCharInString(ch)) - } - TokenError::InvalidEscape(at, ch) => self.error(at, ErrorKind::InvalidEscape(ch)), - TokenError::InvalidEscapeValue(at, v) => { - self.error(at, ErrorKind::InvalidEscapeValue(v)) - } - TokenError::InvalidHexEscape(at, ch) => self.error(at, ErrorKind::InvalidHexEscape(ch)), - TokenError::NewlineInString(at) => self.error(at, ErrorKind::NewlineInString), - TokenError::Unexpected(at, ch) => self.error(at, ErrorKind::Unexpected(ch)), - TokenError::UnterminatedString(at) => self.error(at, ErrorKind::UnterminatedString), - TokenError::NewlineInTableKey(at) => self.error(at, ErrorKind::NewlineInTableKey), - TokenError::Wanted { - at, - expected, - found, - } => self.error(at, ErrorKind::Wanted { expected, found }), - TokenError::MultilineStringKey(at) => self.error(at, ErrorKind::MultilineStringKey), - } - } - - fn error(&self, at: usize, kind: ErrorKind) -> Error { - let mut err = Error::from_kind(Some(at), kind); - err.fix_linecol(|at| self.to_linecol(at)); - err - } - - /// Converts a byte offset from an error message to a (line, column) pair - /// - /// All indexes are 0-based. - fn to_linecol(&self, offset: usize) -> (usize, usize) { - let mut cur = 0; - // Use split_terminator instead of lines so that if there is a `\r`, - // it is included in the offset calculation. The `+1` values below - // account for the `\n`. - for (i, line) in self.input.split_terminator('\n').enumerate() { - if cur + line.len() + 1 > offset { - return (i, offset - cur); - } - cur += line.len() + 1; - } - (self.input.lines().count(), 0) - } -} - -impl Error { - /// Produces a (line, column) pair of the position of the error if available - /// - /// All indexes are 0-based. - pub fn line_col(&self) -> Option<(usize, usize)> { - self.inner.line.map(|line| (line, self.inner.col)) - } - - fn from_kind(at: Option<usize>, kind: ErrorKind) -> Error { - Error { - inner: Box::new(ErrorInner { - kind, - line: None, - col: 0, - at, - message: String::new(), - key: Vec::new(), - }), - } - } - - fn custom(at: Option<usize>, s: String) -> Error { - Error { - inner: Box::new(ErrorInner { - kind: ErrorKind::Custom, - line: None, - col: 0, - at, - message: s, - key: Vec::new(), - }), - } - } - - pub(crate) fn add_key_context(&mut self, key: &str) { - self.inner.key.insert(0, key.to_string()); - } - - fn fix_offset<F>(&mut self, f: F) - where - F: FnOnce() -> Option<usize>, - { - // An existing offset is always better positioned than anything we - // might want to add later. - if self.inner.at.is_none() { - self.inner.at = f(); - } - } - - fn fix_linecol<F>(&mut self, f: F) - where - F: FnOnce(usize) -> (usize, usize), - { - if let Some(at) = self.inner.at { - let (line, col) = f(at); - self.inner.line = Some(line); - self.inner.col = col; - } - } -} - -impl std::convert::From<Error> for std::io::Error { - fn from(e: Error) -> Self { - std::io::Error::new(std::io::ErrorKind::InvalidData, e.to_string()) - } -} - -impl fmt::Display for Error { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { - match &self.inner.kind { - ErrorKind::UnexpectedEof => "unexpected eof encountered".fmt(f)?, - ErrorKind::InvalidCharInString(c) => write!( - f, - "invalid character in string: `{}`", - c.escape_default().collect::<String>() - )?, - ErrorKind::InvalidEscape(c) => write!( - f, - "invalid escape character in string: `{}`", - c.escape_default().collect::<String>() - )?, - ErrorKind::InvalidHexEscape(c) => write!( - f, - "invalid hex escape character in string: `{}`", - c.escape_default().collect::<String>() - )?, - ErrorKind::InvalidEscapeValue(c) => write!(f, "invalid escape value: `{}`", c)?, - ErrorKind::NewlineInString => "newline in string found".fmt(f)?, - ErrorKind::Unexpected(ch) => write!( - f, - "unexpected character found: `{}`", - ch.escape_default().collect::<String>() - )?, - ErrorKind::UnterminatedString => "unterminated string".fmt(f)?, - ErrorKind::NewlineInTableKey => "found newline in table key".fmt(f)?, - ErrorKind::Wanted { expected, found } => { - write!(f, "expected {}, found {}", expected, found)? - } - ErrorKind::NumberInvalid => "invalid number".fmt(f)?, - ErrorKind::DateInvalid => "invalid date".fmt(f)?, - ErrorKind::DuplicateTable(ref s) => { - write!(f, "redefinition of table `{}`", s)?; - } - ErrorKind::RedefineAsArray => "table redefined as array".fmt(f)?, - ErrorKind::EmptyTableKey => "empty table key found".fmt(f)?, - ErrorKind::MultilineStringKey => "multiline strings are not allowed for key".fmt(f)?, - ErrorKind::Custom => self.inner.message.fmt(f)?, - ErrorKind::ExpectedTuple(l) => write!(f, "expected table with length {}", l)?, - ErrorKind::ExpectedTupleIndex { - expected, - ref found, - } => write!(f, "expected table key `{}`, but was `{}`", expected, found)?, - ErrorKind::ExpectedEmptyTable => "expected empty table".fmt(f)?, - ErrorKind::DottedKeyInvalidType => { - "dotted key attempted to extend non-table type".fmt(f)? - } - ErrorKind::UnexpectedKeys { - ref keys, - available, - } => write!( - f, - "unexpected keys in table: `{:?}`, available keys: `{:?}`", - keys, available - )?, - ErrorKind::UnquotedString => write!( - f, - "invalid TOML value, did you mean to use a quoted string?" - )?, - ErrorKind::__Nonexhaustive => panic!(), - } - - if !self.inner.key.is_empty() { - write!(f, " for key `")?; - for (i, k) in self.inner.key.iter().enumerate() { - if i > 0 { - write!(f, ".")?; - } - write!(f, "{}", k)?; - } - write!(f, "`")?; - } - - if let Some(line) = self.inner.line { - write!(f, " at line {} column {}", line + 1, self.inner.col + 1)?; - } - - Ok(()) - } -} - -impl error::Error for Error {} - -impl de::Error for Error { - fn custom<T: fmt::Display>(msg: T) -> Error { - Error::custom(None, msg.to_string()) - } -} - -enum Line<'a> { - Table { - at: usize, - header: Header<'a>, - array: bool, - }, - KeyValue(Vec<(Span, Cow<'a, str>)>, Value<'a>), -} - -struct Header<'a> { - first: bool, - array: bool, - require_newline_after_table: bool, - tokens: Tokenizer<'a>, -} - -impl<'a> Header<'a> { - fn new(tokens: Tokenizer<'a>, array: bool, require_newline_after_table: bool) -> Header<'a> { - Header { - first: true, - array, - tokens, - require_newline_after_table, - } - } - - fn next(&mut self) -> Result<Option<(Span, Cow<'a, str>)>, TokenError> { - self.tokens.eat_whitespace()?; - - if self.first || self.tokens.eat(Token::Period)? { - self.first = false; - self.tokens.eat_whitespace()?; - self.tokens.table_key().map(|t| t).map(Some) - } else { - self.tokens.expect(Token::RightBracket)?; - if self.array { - self.tokens.expect(Token::RightBracket)?; - } - - self.tokens.eat_whitespace()?; - if self.require_newline_after_table && !self.tokens.eat_comment()? { - self.tokens.eat_newline_or_eof()?; - } - Ok(None) - } - } -} - -#[derive(Debug)] -struct Value<'a> { - e: E<'a>, - start: usize, - end: usize, -} - -#[derive(Debug)] -enum E<'a> { - Integer(i64), - Float(f64), - Boolean(bool), - String(Cow<'a, str>), - Datetime(&'a str), - Array(Vec<Value<'a>>), - InlineTable(Vec<TablePair<'a>>), - DottedTable(Vec<TablePair<'a>>), -} - -impl<'a> E<'a> { - fn type_name(&self) -> &'static str { - match *self { - E::String(..) => "string", - E::Integer(..) => "integer", - E::Float(..) => "float", - E::Boolean(..) => "boolean", - E::Datetime(..) => "datetime", - E::Array(..) => "array", - E::InlineTable(..) => "inline table", - E::DottedTable(..) => "dotted table", - } - } -} diff --git a/vendor/toml-0.5.9/src/lib.rs b/vendor/toml-0.5.9/src/lib.rs deleted file mode 100644 index 00421b118..000000000 --- a/vendor/toml-0.5.9/src/lib.rs +++ /dev/null @@ -1,180 +0,0 @@ -//! A [TOML]-parsing library -//! -//! This library implements a [TOML] v0.5.0 compatible parser, -//! primarily supporting the [`serde`] library for encoding/decoding -//! various types in Rust. -//! -//! TOML itself is a simple, ergonomic, and readable configuration format: -//! -//! ```toml -//! [package] -//! name = "toml" -//! version = "0.4.2" -//! authors = ["Alex Crichton <alex@alexcrichton.com>"] -//! -//! [dependencies] -//! serde = "1.0" -//! ``` -//! -//! The TOML format tends to be relatively common throughout the Rust community -//! for configuration, notably being used by [Cargo], Rust's package manager. -//! -//! ## TOML values -//! -//! A value in TOML is represented with the [`Value`] enum in this crate: -//! -//! ```rust,ignore -//! pub enum Value { -//! String(String), -//! Integer(i64), -//! Float(f64), -//! Boolean(bool), -//! Datetime(Datetime), -//! Array(Array), -//! Table(Table), -//! } -//! ``` -//! -//! TOML is similar to JSON with the notable addition of a [`Datetime`] -//! type. In general, TOML and JSON are interchangeable in terms of -//! formats. -//! -//! ## Parsing TOML -//! -//! The easiest way to parse a TOML document is via the [`Value`] type: -//! -//! ```rust -//! use toml::Value; -//! -//! let value = "foo = 'bar'".parse::<Value>().unwrap(); -//! -//! assert_eq!(value["foo"].as_str(), Some("bar")); -//! ``` -//! -//! The [`Value`] type implements a number of convenience methods and -//! traits; the example above uses [`FromStr`] to parse a [`str`] into a -//! [`Value`]. -//! -//! ## Deserialization and Serialization -//! -//! This crate supports [`serde`] 1.0 with a number of -//! implementations of the `Deserialize`, `Serialize`, `Deserializer`, and -//! `Serializer` traits. Namely, you'll find: -//! -//! * `Deserialize for Value` -//! * `Serialize for Value` -//! * `Deserialize for Datetime` -//! * `Serialize for Datetime` -//! * `Deserializer for de::Deserializer` -//! * `Serializer for ser::Serializer` -//! * `Deserializer for Value` -//! -//! This means that you can use Serde to deserialize/serialize the -//! [`Value`] type as well as the [`Datetime`] type in this crate. You can also -//! use the [`Deserializer`], [`Serializer`], or [`Value`] type itself to act as -//! a deserializer/serializer for arbitrary types. -//! -//! An example of deserializing with TOML is: -//! -//! ```rust -//! use serde_derive::Deserialize; -//! -//! #[derive(Deserialize)] -//! struct Config { -//! ip: String, -//! port: Option<u16>, -//! keys: Keys, -//! } -//! -//! #[derive(Deserialize)] -//! struct Keys { -//! github: String, -//! travis: Option<String>, -//! } -//! -//! fn main() { -//! let config: Config = toml::from_str(r#" -//! ip = '127.0.0.1' -//! -//! [keys] -//! github = 'xxxxxxxxxxxxxxxxx' -//! travis = 'yyyyyyyyyyyyyyyyy' -//! "#).unwrap(); -//! -//! assert_eq!(config.ip, "127.0.0.1"); -//! assert_eq!(config.port, None); -//! assert_eq!(config.keys.github, "xxxxxxxxxxxxxxxxx"); -//! assert_eq!(config.keys.travis.as_ref().unwrap(), "yyyyyyyyyyyyyyyyy"); -//! } -//! ``` -//! -//! You can serialize types in a similar fashion: -//! -//! ```rust -//! use serde_derive::Serialize; -//! -//! #[derive(Serialize)] -//! struct Config { -//! ip: String, -//! port: Option<u16>, -//! keys: Keys, -//! } -//! -//! #[derive(Serialize)] -//! struct Keys { -//! github: String, -//! travis: Option<String>, -//! } -//! -//! fn main() { -//! let config = Config { -//! ip: "127.0.0.1".to_string(), -//! port: None, -//! keys: Keys { -//! github: "xxxxxxxxxxxxxxxxx".to_string(), -//! travis: Some("yyyyyyyyyyyyyyyyy".to_string()), -//! }, -//! }; -//! -//! let toml = toml::to_string(&config).unwrap(); -//! } -//! ``` -//! -//! [TOML]: https://github.com/toml-lang/toml -//! [Cargo]: https://crates.io/ -//! [`serde`]: https://serde.rs/ - -#![doc(html_root_url = "https://docs.rs/toml/0.5")] -#![deny(missing_docs)] -#![warn(rust_2018_idioms)] -// Makes rustc abort compilation if there are any unsafe blocks in the crate. -// Presence of this annotation is picked up by tools such as cargo-geiger -// and lets them ensure that there is indeed no unsafe code as opposed to -// something they couldn't detect (e.g. unsafe added via macro expansion, etc). -#![forbid(unsafe_code)] - -pub mod map; -pub mod value; -#[doc(no_inline)] -pub use crate::value::Value; -mod datetime; - -pub mod ser; -#[doc(no_inline)] -pub use crate::ser::{to_string, to_string_pretty, to_vec, Serializer}; -pub mod de; -#[doc(no_inline)] -pub use crate::de::{from_slice, from_str, Deserializer}; -mod tokens; - -#[doc(hidden)] -pub mod macros; - -mod spanned; -pub use crate::spanned::Spanned; - -// Just for rustdoc -#[allow(unused_imports)] -use crate::datetime::Datetime; -#[allow(unused_imports)] -use core::str::FromStr; diff --git a/vendor/toml-0.5.9/src/macros.rs b/vendor/toml-0.5.9/src/macros.rs deleted file mode 100644 index 0731afefd..000000000 --- a/vendor/toml-0.5.9/src/macros.rs +++ /dev/null @@ -1,462 +0,0 @@ -pub use serde::de::{Deserialize, IntoDeserializer}; - -use crate::value::{Array, Table, Value}; - -/// Construct a [`toml::Value`] from TOML syntax. -/// -/// [`toml::Value`]: value/enum.Value.html -/// -/// ```rust -/// fn main() { -/// let cargo_toml = toml::toml! { -/// [package] -/// name = "toml" -/// version = "0.4.5" -/// authors = ["Alex Crichton <alex@alexcrichton.com>"] -/// -/// [badges] -/// travis-ci = { repository = "alexcrichton/toml-rs" } -/// -/// [dependencies] -/// serde = "1.0" -/// -/// [dev-dependencies] -/// serde_derive = "1.0" -/// serde_json = "1.0" -/// }; -/// -/// println!("{:#?}", cargo_toml); -/// } -/// ``` -#[macro_export] -macro_rules! toml { - ($($toml:tt)+) => {{ - let table = $crate::value::Table::new(); - let mut root = $crate::Value::Table(table); - $crate::toml_internal!(@toplevel root [] $($toml)+); - root - }}; -} - -// TT-muncher to parse TOML syntax into a toml::Value. -// -// @toplevel -- Parse tokens outside of an inline table or inline array. In -// this state, `[table headers]` and `[[array headers]]` are -// allowed and `key = value` pairs are not separated by commas. -// -// @topleveldatetime -- Helper to parse a Datetime from string and insert it -// into a table, continuing in the @toplevel state. -// -// @path -- Turn a path segment into a string. Segments that look like idents -// are stringified, while quoted segments like `"cfg(windows)"` -// are not. -// -// @value -- Parse the value part of a `key = value` pair, which may be a -// primitive or inline table or inline array. -// -// @table -- Parse the contents of an inline table, returning them as a -// toml::Value::Table. -// -// @tabledatetime -- Helper to parse a Datetime from string and insert it -// into a table, continuing in the @table state. -// -// @array -- Parse the contents of an inline array, returning them as a -// toml::Value::Array. -// -// @arraydatetime -- Helper to parse a Datetime from string and push it into -// an array, continuing in the @array state. -// -// @trailingcomma -- Helper to append a comma to a sequence of tokens if the -// sequence is non-empty and does not already end in a trailing -// comma. -// -#[macro_export] -#[doc(hidden)] -macro_rules! toml_internal { - // Base case, no elements remaining. - (@toplevel $root:ident [$($path:tt)*]) => {}; - - // Parse negative number `key = -value`. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = - $v:tt $($rest:tt)*) => { - $crate::toml_internal!(@toplevel $root [$($path)*] $($($k)-+).+ = (-$v) $($rest)*); - }; - - // Parse positive number `key = +value`. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = + $v:tt $($rest:tt)*) => { - $crate::toml_internal!(@toplevel $root [$($path)*] $($($k)-+).+ = ($v) $($rest)*); - }; - - // Parse offset datetime `key = 1979-05-27T00:32:00.999999-07:00`. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = $yr:tt - $mo:tt - $dhr:tt : $min:tt : $sec:tt . $frac:tt - $tzh:tt : $tzm:tt $($rest:tt)*) => { - $crate::toml_internal!(@topleveldatetime $root [$($path)*] $($($k)-+).+ = ($yr - $mo - $dhr : $min : $sec . $frac - $tzh : $tzm) $($rest)*); - }; - // Space instead of T. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = $yr:tt - $mo:tt - $day:tt $hr:tt : $min:tt : $sec:tt . $frac:tt - $tzh:tt : $tzm:tt $($rest:tt)*) => { - $crate::toml_internal!(@topleveldatetime $root [$($path)*] $($($k)-+).+ = ($yr - $mo - $day T $hr : $min : $sec . $frac - $tzh : $tzm) $($rest)*); - }; - - // Parse offset datetime `key = 1979-05-27T00:32:00-07:00`. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = $yr:tt - $mo:tt - $dhr:tt : $min:tt : $sec:tt - $tzh:tt : $tzm:tt $($rest:tt)*) => { - $crate::toml_internal!(@topleveldatetime $root [$($path)*] $($($k)-+).+ = ($yr - $mo - $dhr : $min : $sec - $tzh : $tzm) $($rest)*); - }; - // Space instead of T. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = $yr:tt - $mo:tt - $day:tt $hr:tt : $min:tt : $sec:tt - $tzh:tt : $tzm:tt $($rest:tt)*) => { - $crate::toml_internal!(@topleveldatetime $root [$($path)*] $($($k)-+).+ = ($yr - $mo - $day T $hr : $min : $sec - $tzh : $tzm) $($rest)*); - }; - - // Parse local datetime `key = 1979-05-27T00:32:00.999999`. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = $yr:tt - $mo:tt - $dhr:tt : $min:tt : $sec:tt . $frac:tt $($rest:tt)*) => { - $crate::toml_internal!(@topleveldatetime $root [$($path)*] $($($k)-+).+ = ($yr - $mo - $dhr : $min : $sec . $frac) $($rest)*); - }; - // Space instead of T. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = $yr:tt - $mo:tt - $day:tt $hr:tt : $min:tt : $sec:tt . $frac:tt $($rest:tt)*) => { - $crate::toml_internal!(@topleveldatetime $root [$($path)*] $($($k)-+).+ = ($yr - $mo - $day T $hr : $min : $sec . $frac) $($rest)*); - }; - - // Parse offset datetime `key = 1979-05-27T07:32:00Z` and local datetime `key = 1979-05-27T07:32:00`. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = $yr:tt - $mo:tt - $dhr:tt : $min:tt : $sec:tt $($rest:tt)*) => { - $crate::toml_internal!(@topleveldatetime $root [$($path)*] $($($k)-+).+ = ($yr - $mo - $dhr : $min : $sec) $($rest)*); - }; - // Space instead of T. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = $yr:tt - $mo:tt - $day:tt $hr:tt : $min:tt : $sec:tt $($rest:tt)*) => { - $crate::toml_internal!(@topleveldatetime $root [$($path)*] $($($k)-+).+ = ($yr - $mo - $day T $hr : $min : $sec) $($rest)*); - }; - - // Parse local date `key = 1979-05-27`. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = $yr:tt - $mo:tt - $day:tt $($rest:tt)*) => { - $crate::toml_internal!(@topleveldatetime $root [$($path)*] $($($k)-+).+ = ($yr - $mo - $day) $($rest)*); - }; - - // Parse local time `key = 00:32:00.999999`. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = $hr:tt : $min:tt : $sec:tt . $frac:tt $($rest:tt)*) => { - $crate::toml_internal!(@topleveldatetime $root [$($path)*] $($($k)-+).+ = ($hr : $min : $sec . $frac) $($rest)*); - }; - - // Parse local time `key = 07:32:00`. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = $hr:tt : $min:tt : $sec:tt $($rest:tt)*) => { - $crate::toml_internal!(@topleveldatetime $root [$($path)*] $($($k)-+).+ = ($hr : $min : $sec) $($rest)*); - }; - - // Parse any other `key = value` including string, inline array, inline - // table, number, and boolean. - (@toplevel $root:ident [$($path:tt)*] $($($k:tt)-+).+ = $v:tt $($rest:tt)*) => {{ - $crate::macros::insert_toml( - &mut $root, - &[$($path)* $(&concat!($("-", $crate::toml_internal!(@path $k),)+)[1..], )+], - $crate::toml_internal!(@value $v)); - $crate::toml_internal!(@toplevel $root [$($path)*] $($rest)*); - }}; - - // Parse array header `[[bin]]`. - (@toplevel $root:ident $oldpath:tt [[$($($path:tt)-+).+]] $($rest:tt)*) => { - $crate::macros::push_toml( - &mut $root, - &[$(&concat!($("-", $crate::toml_internal!(@path $path),)+)[1..],)+]); - $crate::toml_internal!(@toplevel $root [$(&concat!($("-", $crate::toml_internal!(@path $path),)+)[1..],)+] $($rest)*); - }; - - // Parse table header `[patch.crates-io]`. - (@toplevel $root:ident $oldpath:tt [$($($path:tt)-+).+] $($rest:tt)*) => { - $crate::macros::insert_toml( - &mut $root, - &[$(&concat!($("-", $crate::toml_internal!(@path $path),)+)[1..],)+], - $crate::Value::Table($crate::value::Table::new())); - $crate::toml_internal!(@toplevel $root [$(&concat!($("-", $crate::toml_internal!(@path $path),)+)[1..],)+] $($rest)*); - }; - - // Parse datetime from string and insert into table. - (@topleveldatetime $root:ident [$($path:tt)*] $($($k:tt)-+).+ = ($($datetime:tt)+) $($rest:tt)*) => { - $crate::macros::insert_toml( - &mut $root, - &[$($path)* $(&concat!($("-", $crate::toml_internal!(@path $k),)+)[1..], )+], - $crate::Value::Datetime(concat!($(stringify!($datetime)),+).parse().unwrap())); - $crate::toml_internal!(@toplevel $root [$($path)*] $($rest)*); - }; - - // Turn a path segment into a string. - (@path $ident:ident) => { - stringify!($ident) - }; - - // For a path segment that is not an ident, expect that it is already a - // quoted string, like in `[target."cfg(windows)".dependencies]`. - (@path $quoted:tt) => { - $quoted - }; - - // Construct a Value from an inline table. - (@value { $($inline:tt)* }) => {{ - let mut table = $crate::Value::Table($crate::value::Table::new()); - $crate::toml_internal!(@trailingcomma (@table table) $($inline)*); - table - }}; - - // Construct a Value from an inline array. - (@value [ $($inline:tt)* ]) => {{ - let mut array = $crate::value::Array::new(); - $crate::toml_internal!(@trailingcomma (@array array) $($inline)*); - $crate::Value::Array(array) - }}; - - (@value (-nan)) => { - $crate::Value::Float(-::std::f64::NAN) - }; - - (@value (nan)) => { - $crate::Value::Float(::std::f64::NAN) - }; - - (@value nan) => { - $crate::Value::Float(::std::f64::NAN) - }; - - (@value (-inf)) => { - $crate::Value::Float(::std::f64::NEG_INFINITY) - }; - - (@value (inf)) => { - $crate::Value::Float(::std::f64::INFINITY) - }; - - (@value inf) => { - $crate::Value::Float(::std::f64::INFINITY) - }; - - // Construct a Value from any other type, probably string or boolean or number. - (@value $v:tt) => {{ - // TODO: Implement this with something like serde_json::to_value instead. - let de = $crate::macros::IntoDeserializer::<$crate::de::Error>::into_deserializer($v); - <$crate::Value as $crate::macros::Deserialize>::deserialize(de).unwrap() - }}; - - // Base case of inline table. - (@table $root:ident) => {}; - - // Parse negative number `key = -value`. - (@table $root:ident $($($k:tt)-+).+ = - $v:tt , $($rest:tt)*) => { - $crate::toml_internal!(@table $root $($($k)-+).+ = (-$v) , $($rest)*); - }; - - // Parse positive number `key = +value`. - (@table $root:ident $($($k:tt)-+).+ = + $v:tt , $($rest:tt)*) => { - $crate::toml_internal!(@table $root $($($k)-+).+ = ($v) , $($rest)*); - }; - - // Parse offset datetime `key = 1979-05-27T00:32:00.999999-07:00`. - (@table $root:ident $($($k:tt)-+).+ = $yr:tt - $mo:tt - $dhr:tt : $min:tt : $sec:tt . $frac:tt - $tzh:tt : $tzm:tt , $($rest:tt)*) => { - $crate::toml_internal!(@tabledatetime $root $($($k)-+).+ = ($yr - $mo - $dhr : $min : $sec . $frac - $tzh : $tzm) $($rest)*); - }; - // Space instead of T. - (@table $root:ident $($($k:tt)-+).+ = $yr:tt - $mo:tt - $day:tt $hr:tt : $min:tt : $sec:tt . $frac:tt - $tzh:tt : $tzm:tt , $($rest:tt)*) => { - $crate::toml_internal!(@tabledatetime $root $($($k)-+).+ = ($yr - $mo - $day T $hr : $min : $sec . $frac - $tzh : $tzm) $($rest)*); - }; - - // Parse offset datetime `key = 1979-05-27T00:32:00-07:00`. - (@table $root:ident $($($k:tt)-+).+ = $yr:tt - $mo:tt - $dhr:tt : $min:tt : $sec:tt - $tzh:tt : $tzm:tt , $($rest:tt)*) => { - $crate::toml_internal!(@tabledatetime $root $($($k)-+).+ = ($yr - $mo - $dhr : $min : $sec - $tzh : $tzm) $($rest)*); - }; - // Space instead of T. - (@table $root:ident $($($k:tt)-+).+ = $yr:tt - $mo:tt - $day:tt $hr:tt : $min:tt : $sec:tt - $tzh:tt : $tzm:tt , $($rest:tt)*) => { - $crate::toml_internal!(@tabledatetime $root $($($k)-+).+ = ($yr - $mo - $day T $hr : $min : $sec - $tzh : $tzm) $($rest)*); - }; - - // Parse local datetime `key = 1979-05-27T00:32:00.999999`. - (@table $root:ident $($($k:tt)-+).+ = $yr:tt - $mo:tt - $dhr:tt : $min:tt : $sec:tt . $frac:tt , $($rest:tt)*) => { - $crate::toml_internal!(@tabledatetime $root $($($k)-+).+ = ($yr - $mo - $dhr : $min : $sec . $frac) $($rest)*); - }; - // Space instead of T. - (@table $root:ident $($($k:tt)-+).+ = $yr:tt - $mo:tt - $day:tt $hr:tt : $min:tt : $sec:tt . $frac:tt , $($rest:tt)*) => { - $crate::toml_internal!(@tabledatetime $root $($($k)-+).+ = ($yr - $mo - $day T $hr : $min : $sec . $frac) $($rest)*); - }; - - // Parse offset datetime `key = 1979-05-27T07:32:00Z` and local datetime `key = 1979-05-27T07:32:00`. - (@table $root:ident $($($k:tt)-+).+ = $yr:tt - $mo:tt - $dhr:tt : $min:tt : $sec:tt , $($rest:tt)*) => { - $crate::toml_internal!(@tabledatetime $root $($($k)-+).+ = ($yr - $mo - $dhr : $min : $sec) $($rest)*); - }; - // Space instead of T. - (@table $root:ident $($($k:tt)-+).+ = $yr:tt - $mo:tt - $day:tt $hr:tt : $min:tt : $sec:tt , $($rest:tt)*) => { - $crate::toml_internal!(@tabledatetime $root $($($k)-+).+ = ($yr - $mo - $day T $hr : $min : $sec) $($rest)*); - }; - - // Parse local date `key = 1979-05-27`. - (@table $root:ident $($($k:tt)-+).+ = $yr:tt - $mo:tt - $day:tt , $($rest:tt)*) => { - $crate::toml_internal!(@tabledatetime $root $($($k)-+).+ = ($yr - $mo - $day) $($rest)*); - }; - - // Parse local time `key = 00:32:00.999999`. - (@table $root:ident $($($k:tt)-+).+ = $hr:tt : $min:tt : $sec:tt . $frac:tt , $($rest:tt)*) => { - $crate::toml_internal!(@tabledatetime $root $($($k)-+).+ = ($hr : $min : $sec . $frac) $($rest)*); - }; - - // Parse local time `key = 07:32:00`. - (@table $root:ident $($($k:tt)-+).+ = $hr:tt : $min:tt : $sec:tt , $($rest:tt)*) => { - $crate::toml_internal!(@tabledatetime $root $($($k)-+).+ = ($hr : $min : $sec) $($rest)*); - }; - - // Parse any other type, probably string or boolean or number. - (@table $root:ident $($($k:tt)-+).+ = $v:tt , $($rest:tt)*) => { - $crate::macros::insert_toml( - &mut $root, - &[$(&concat!($("-", $crate::toml_internal!(@path $k),)+)[1..], )+], - $crate::toml_internal!(@value $v)); - $crate::toml_internal!(@table $root $($rest)*); - }; - - // Parse a Datetime from string and continue in @table state. - (@tabledatetime $root:ident $($($k:tt)-+).+ = ($($datetime:tt)*) $($rest:tt)*) => { - $crate::macros::insert_toml( - &mut $root, - &[$(&concat!($("-", $crate::toml_internal!(@path $k),)+)[1..], )+], - $crate::Value::Datetime(concat!($(stringify!($datetime)),+).parse().unwrap())); - $crate::toml_internal!(@table $root $($rest)*); - }; - - // Base case of inline array. - (@array $root:ident) => {}; - - // Parse negative number `-value`. - (@array $root:ident - $v:tt , $($rest:tt)*) => { - $crate::toml_internal!(@array $root (-$v) , $($rest)*); - }; - - // Parse positive number `+value`. - (@array $root:ident + $v:tt , $($rest:tt)*) => { - $crate::toml_internal!(@array $root ($v) , $($rest)*); - }; - - // Parse offset datetime `1979-05-27T00:32:00.999999-07:00`. - (@array $root:ident $yr:tt - $mo:tt - $dhr:tt : $min:tt : $sec:tt . $frac:tt - $tzh:tt : $tzm:tt , $($rest:tt)*) => { - $crate::toml_internal!(@arraydatetime $root ($yr - $mo - $dhr : $min : $sec . $frac - $tzh : $tzm) $($rest)*); - }; - // Space instead of T. - (@array $root:ident $yr:tt - $mo:tt - $day:tt $hr:tt : $min:tt : $sec:tt . $frac:tt - $tzh:tt : $tzm:tt , $($rest:tt)*) => { - $crate::toml_internal!(@arraydatetime $root ($yr - $mo - $day T $hr : $min : $sec . $frac - $tzh : $tzm) $($rest)*); - }; - - // Parse offset datetime `1979-05-27T00:32:00-07:00`. - (@array $root:ident $yr:tt - $mo:tt - $dhr:tt : $min:tt : $sec:tt - $tzh:tt : $tzm:tt , $($rest:tt)*) => { - $crate::toml_internal!(@arraydatetime $root ($yr - $mo - $dhr : $min : $sec - $tzh : $tzm) $($rest)*); - }; - // Space instead of T. - (@array $root:ident $yr:tt - $mo:tt - $day:tt $hr:tt : $min:tt : $sec:tt - $tzh:tt : $tzm:tt , $($rest:tt)*) => { - $crate::toml_internal!(@arraydatetime $root ($yr - $mo - $day T $hr : $min : $sec - $tzh : $tzm) $($rest)*); - }; - - // Parse local datetime `1979-05-27T00:32:00.999999`. - (@array $root:ident $yr:tt - $mo:tt - $dhr:tt : $min:tt : $sec:tt . $frac:tt , $($rest:tt)*) => { - $crate::toml_internal!(@arraydatetime $root ($yr - $mo - $dhr : $min : $sec . $frac) $($rest)*); - }; - // Space instead of T. - (@array $root:ident $yr:tt - $mo:tt - $day:tt $hr:tt : $min:tt : $sec:tt . $frac:tt , $($rest:tt)*) => { - $crate::toml_internal!(@arraydatetime $root ($yr - $mo - $day T $hr : $min : $sec . $frac) $($rest)*); - }; - - // Parse offset datetime `1979-05-27T07:32:00Z` and local datetime `1979-05-27T07:32:00`. - (@array $root:ident $yr:tt - $mo:tt - $dhr:tt : $min:tt : $sec:tt , $($rest:tt)*) => { - $crate::toml_internal!(@arraydatetime $root ($yr - $mo - $dhr : $min : $sec) $($rest)*); - }; - // Space instead of T. - (@array $root:ident $yr:tt - $mo:tt - $day:tt $hr:tt : $min:tt : $sec:tt , $($rest:tt)*) => { - $crate::toml_internal!(@arraydatetime $root ($yr - $mo - $day T $hr : $min : $sec) $($rest)*); - }; - - // Parse local date `1979-05-27`. - (@array $root:ident $yr:tt - $mo:tt - $day:tt , $($rest:tt)*) => { - $crate::toml_internal!(@arraydatetime $root ($yr - $mo - $day) $($rest)*); - }; - - // Parse local time `00:32:00.999999`. - (@array $root:ident $hr:tt : $min:tt : $sec:tt . $frac:tt , $($rest:tt)*) => { - $crate::toml_internal!(@arraydatetime $root ($hr : $min : $sec . $frac) $($rest)*); - }; - - // Parse local time `07:32:00`. - (@array $root:ident $hr:tt : $min:tt : $sec:tt , $($rest:tt)*) => { - $crate::toml_internal!(@arraydatetime $root ($hr : $min : $sec) $($rest)*); - }; - - // Parse any other type, probably string or boolean or number. - (@array $root:ident $v:tt , $($rest:tt)*) => { - $root.push($crate::toml_internal!(@value $v)); - $crate::toml_internal!(@array $root $($rest)*); - }; - - // Parse a Datetime from string and continue in @array state. - (@arraydatetime $root:ident ($($datetime:tt)*) $($rest:tt)*) => { - $root.push($crate::Value::Datetime(concat!($(stringify!($datetime)),+).parse().unwrap())); - $crate::toml_internal!(@array $root $($rest)*); - }; - - // No trailing comma required if the tokens are empty. - (@trailingcomma ($($args:tt)*)) => { - $crate::toml_internal!($($args)*); - }; - - // Tokens end with a trailing comma, do not append another one. - (@trailingcomma ($($args:tt)*) ,) => { - $crate::toml_internal!($($args)* ,); - }; - - // Tokens end with something other than comma, append a trailing comma. - (@trailingcomma ($($args:tt)*) $last:tt) => { - $crate::toml_internal!($($args)* $last ,); - }; - - // Not yet at the last token. - (@trailingcomma ($($args:tt)*) $first:tt $($rest:tt)+) => { - $crate::toml_internal!(@trailingcomma ($($args)* $first) $($rest)+); - }; -} - -// Called when parsing a `key = value` pair. -// Inserts an entry into the table at the given path. -pub fn insert_toml(root: &mut Value, path: &[&str], value: Value) { - *traverse(root, path) = value; -} - -// Called when parsing an `[[array header]]`. -// Pushes an empty table onto the array at the given path. -pub fn push_toml(root: &mut Value, path: &[&str]) { - let target = traverse(root, path); - if !target.is_array() { - *target = Value::Array(Array::new()); - } - target - .as_array_mut() - .unwrap() - .push(Value::Table(Table::new())); -} - -fn traverse<'a>(root: &'a mut Value, path: &[&str]) -> &'a mut Value { - let mut cur = root; - for &key in path { - // Lexical lifetimes :D - let cur1 = cur; - let cur2; - - // From the TOML spec: - // - // > Each double-bracketed sub-table will belong to the most recently - // > defined table element above it. - if cur1.is_array() { - cur2 = cur1.as_array_mut().unwrap().last_mut().unwrap(); - } else { - cur2 = cur1; - }; - - // We are about to index into this value, so it better be a table. - if !cur2.is_table() { - *cur2 = Value::Table(Table::new()); - } - - if !cur2.as_table().unwrap().contains_key(key) { - // Insert an empty table for the next loop iteration to point to. - let empty = Value::Table(Table::new()); - cur2.as_table_mut().unwrap().insert(key.to_owned(), empty); - } - - // Step into the current table. - cur = cur2.as_table_mut().unwrap().get_mut(key).unwrap(); - } - cur -} diff --git a/vendor/toml-0.5.9/src/map.rs b/vendor/toml-0.5.9/src/map.rs deleted file mode 100644 index d130a1d54..000000000 --- a/vendor/toml-0.5.9/src/map.rs +++ /dev/null @@ -1,595 +0,0 @@ -// Copyright 2017 Serde Developers -// -// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or -// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license -// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your -// option. This file may not be copied, modified, or distributed -// except according to those terms. - -//! A map of String to toml::Value. -//! -//! By default the map is backed by a [`BTreeMap`]. Enable the `preserve_order` -//! feature of toml-rs to use [`LinkedHashMap`] instead. -//! -//! [`BTreeMap`]: https://doc.rust-lang.org/std/collections/struct.BTreeMap.html -//! [`LinkedHashMap`]: https://docs.rs/linked-hash-map/*/linked_hash_map/struct.LinkedHashMap.html - -use crate::value::Value; -use serde::{de, ser}; -use std::borrow::Borrow; -use std::fmt::{self, Debug}; -use std::hash::Hash; -use std::iter::FromIterator; -use std::ops; - -#[cfg(not(feature = "preserve_order"))] -use std::collections::{btree_map, BTreeMap}; - -#[cfg(feature = "preserve_order")] -use indexmap::{self, IndexMap}; - -/// Represents a TOML key/value type. -pub struct Map<K, V> { - map: MapImpl<K, V>, -} - -#[cfg(not(feature = "preserve_order"))] -type MapImpl<K, V> = BTreeMap<K, V>; -#[cfg(feature = "preserve_order")] -type MapImpl<K, V> = IndexMap<K, V>; - -impl Map<String, Value> { - /// Makes a new empty Map. - #[inline] - pub fn new() -> Self { - Map { - map: MapImpl::new(), - } - } - - #[cfg(not(feature = "preserve_order"))] - /// Makes a new empty Map with the given initial capacity. - #[inline] - pub fn with_capacity(capacity: usize) -> Self { - // does not support with_capacity - let _ = capacity; - Map { - map: BTreeMap::new(), - } - } - - #[cfg(feature = "preserve_order")] - /// Makes a new empty Map with the given initial capacity. - #[inline] - pub fn with_capacity(capacity: usize) -> Self { - Map { - map: IndexMap::with_capacity(capacity), - } - } - - /// Clears the map, removing all values. - #[inline] - pub fn clear(&mut self) { - self.map.clear() - } - - /// Returns a reference to the value corresponding to the key. - /// - /// The key may be any borrowed form of the map's key type, but the ordering - /// on the borrowed form *must* match the ordering on the key type. - #[inline] - pub fn get<Q: ?Sized>(&self, key: &Q) -> Option<&Value> - where - String: Borrow<Q>, - Q: Ord + Eq + Hash, - { - self.map.get(key) - } - - /// Returns true if the map contains a value for the specified key. - /// - /// The key may be any borrowed form of the map's key type, but the ordering - /// on the borrowed form *must* match the ordering on the key type. - #[inline] - pub fn contains_key<Q: ?Sized>(&self, key: &Q) -> bool - where - String: Borrow<Q>, - Q: Ord + Eq + Hash, - { - self.map.contains_key(key) - } - - /// Returns a mutable reference to the value corresponding to the key. - /// - /// The key may be any borrowed form of the map's key type, but the ordering - /// on the borrowed form *must* match the ordering on the key type. - #[inline] - pub fn get_mut<Q: ?Sized>(&mut self, key: &Q) -> Option<&mut Value> - where - String: Borrow<Q>, - Q: Ord + Eq + Hash, - { - self.map.get_mut(key) - } - - /// Inserts a key-value pair into the map. - /// - /// If the map did not have this key present, `None` is returned. - /// - /// If the map did have this key present, the value is updated, and the old - /// value is returned. The key is not updated, though; this matters for - /// types that can be `==` without being identical. - #[inline] - pub fn insert(&mut self, k: String, v: Value) -> Option<Value> { - self.map.insert(k, v) - } - - /// Removes a key from the map, returning the value at the key if the key - /// was previously in the map. - /// - /// The key may be any borrowed form of the map's key type, but the ordering - /// on the borrowed form *must* match the ordering on the key type. - #[inline] - pub fn remove<Q: ?Sized>(&mut self, key: &Q) -> Option<Value> - where - String: Borrow<Q>, - Q: Ord + Eq + Hash, - { - self.map.remove(key) - } - - /// Gets the given key's corresponding entry in the map for in-place - /// manipulation. - pub fn entry<S>(&mut self, key: S) -> Entry<'_> - where - S: Into<String>, - { - #[cfg(feature = "preserve_order")] - use indexmap::map::Entry as EntryImpl; - #[cfg(not(feature = "preserve_order"))] - use std::collections::btree_map::Entry as EntryImpl; - - match self.map.entry(key.into()) { - EntryImpl::Vacant(vacant) => Entry::Vacant(VacantEntry { vacant }), - EntryImpl::Occupied(occupied) => Entry::Occupied(OccupiedEntry { occupied }), - } - } - - /// Returns the number of elements in the map. - #[inline] - pub fn len(&self) -> usize { - self.map.len() - } - - /// Returns true if the map contains no elements. - #[inline] - pub fn is_empty(&self) -> bool { - self.map.is_empty() - } - - /// Gets an iterator over the entries of the map. - #[inline] - pub fn iter(&self) -> Iter<'_> { - Iter { - iter: self.map.iter(), - } - } - - /// Gets a mutable iterator over the entries of the map. - #[inline] - pub fn iter_mut(&mut self) -> IterMut<'_> { - IterMut { - iter: self.map.iter_mut(), - } - } - - /// Gets an iterator over the keys of the map. - #[inline] - pub fn keys(&self) -> Keys<'_> { - Keys { - iter: self.map.keys(), - } - } - - /// Gets an iterator over the values of the map. - #[inline] - pub fn values(&self) -> Values<'_> { - Values { - iter: self.map.values(), - } - } -} - -impl Default for Map<String, Value> { - #[inline] - fn default() -> Self { - Map { - map: MapImpl::new(), - } - } -} - -impl Clone for Map<String, Value> { - #[inline] - fn clone(&self) -> Self { - Map { - map: self.map.clone(), - } - } -} - -impl PartialEq for Map<String, Value> { - #[inline] - fn eq(&self, other: &Self) -> bool { - self.map.eq(&other.map) - } -} - -/// Access an element of this map. Panics if the given key is not present in the -/// map. -impl<'a, Q: ?Sized> ops::Index<&'a Q> for Map<String, Value> -where - String: Borrow<Q>, - Q: Ord + Eq + Hash, -{ - type Output = Value; - - fn index(&self, index: &Q) -> &Value { - self.map.index(index) - } -} - -/// Mutably access an element of this map. Panics if the given key is not -/// present in the map. -impl<'a, Q: ?Sized> ops::IndexMut<&'a Q> for Map<String, Value> -where - String: Borrow<Q>, - Q: Ord + Eq + Hash, -{ - fn index_mut(&mut self, index: &Q) -> &mut Value { - self.map.get_mut(index).expect("no entry found for key") - } -} - -impl Debug for Map<String, Value> { - #[inline] - fn fmt(&self, formatter: &mut fmt::Formatter<'_>) -> Result<(), fmt::Error> { - self.map.fmt(formatter) - } -} - -impl ser::Serialize for Map<String, Value> { - #[inline] - fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error> - where - S: ser::Serializer, - { - use serde::ser::SerializeMap; - let mut map = serializer.serialize_map(Some(self.len()))?; - for (k, v) in self { - map.serialize_key(k)?; - map.serialize_value(v)?; - } - map.end() - } -} - -impl<'de> de::Deserialize<'de> for Map<String, Value> { - #[inline] - fn deserialize<D>(deserializer: D) -> Result<Self, D::Error> - where - D: de::Deserializer<'de>, - { - struct Visitor; - - impl<'de> de::Visitor<'de> for Visitor { - type Value = Map<String, Value>; - - fn expecting(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result { - formatter.write_str("a map") - } - - #[inline] - fn visit_unit<E>(self) -> Result<Self::Value, E> - where - E: de::Error, - { - Ok(Map::new()) - } - - #[inline] - fn visit_map<V>(self, mut visitor: V) -> Result<Self::Value, V::Error> - where - V: de::MapAccess<'de>, - { - let mut values = Map::new(); - - while let Some((key, value)) = visitor.next_entry()? { - values.insert(key, value); - } - - Ok(values) - } - } - - deserializer.deserialize_map(Visitor) - } -} - -impl FromIterator<(String, Value)> for Map<String, Value> { - fn from_iter<T>(iter: T) -> Self - where - T: IntoIterator<Item = (String, Value)>, - { - Map { - map: FromIterator::from_iter(iter), - } - } -} - -impl Extend<(String, Value)> for Map<String, Value> { - fn extend<T>(&mut self, iter: T) - where - T: IntoIterator<Item = (String, Value)>, - { - self.map.extend(iter); - } -} - -macro_rules! delegate_iterator { - (($name:ident $($generics:tt)*) => $item:ty) => { - impl $($generics)* Iterator for $name $($generics)* { - type Item = $item; - #[inline] - fn next(&mut self) -> Option<Self::Item> { - self.iter.next() - } - #[inline] - fn size_hint(&self) -> (usize, Option<usize>) { - self.iter.size_hint() - } - } - - impl $($generics)* DoubleEndedIterator for $name $($generics)* { - #[inline] - fn next_back(&mut self) -> Option<Self::Item> { - self.iter.next_back() - } - } - - impl $($generics)* ExactSizeIterator for $name $($generics)* { - #[inline] - fn len(&self) -> usize { - self.iter.len() - } - } - } -} - -////////////////////////////////////////////////////////////////////////////// - -/// A view into a single entry in a map, which may either be vacant or occupied. -/// This enum is constructed from the [`entry`] method on [`Map`]. -/// -/// [`entry`]: struct.Map.html#method.entry -/// [`Map`]: struct.Map.html -pub enum Entry<'a> { - /// A vacant Entry. - Vacant(VacantEntry<'a>), - /// An occupied Entry. - Occupied(OccupiedEntry<'a>), -} - -/// A vacant Entry. It is part of the [`Entry`] enum. -/// -/// [`Entry`]: enum.Entry.html -pub struct VacantEntry<'a> { - vacant: VacantEntryImpl<'a>, -} - -/// An occupied Entry. It is part of the [`Entry`] enum. -/// -/// [`Entry`]: enum.Entry.html -pub struct OccupiedEntry<'a> { - occupied: OccupiedEntryImpl<'a>, -} - -#[cfg(not(feature = "preserve_order"))] -type VacantEntryImpl<'a> = btree_map::VacantEntry<'a, String, Value>; -#[cfg(feature = "preserve_order")] -type VacantEntryImpl<'a> = indexmap::map::VacantEntry<'a, String, Value>; - -#[cfg(not(feature = "preserve_order"))] -type OccupiedEntryImpl<'a> = btree_map::OccupiedEntry<'a, String, Value>; -#[cfg(feature = "preserve_order")] -type OccupiedEntryImpl<'a> = indexmap::map::OccupiedEntry<'a, String, Value>; - -impl<'a> Entry<'a> { - /// Returns a reference to this entry's key. - pub fn key(&self) -> &String { - match *self { - Entry::Vacant(ref e) => e.key(), - Entry::Occupied(ref e) => e.key(), - } - } - - /// Ensures a value is in the entry by inserting the default if empty, and - /// returns a mutable reference to the value in the entry. - pub fn or_insert(self, default: Value) -> &'a mut Value { - match self { - Entry::Vacant(entry) => entry.insert(default), - Entry::Occupied(entry) => entry.into_mut(), - } - } - - /// Ensures a value is in the entry by inserting the result of the default - /// function if empty, and returns a mutable reference to the value in the - /// entry. - pub fn or_insert_with<F>(self, default: F) -> &'a mut Value - where - F: FnOnce() -> Value, - { - match self { - Entry::Vacant(entry) => entry.insert(default()), - Entry::Occupied(entry) => entry.into_mut(), - } - } -} - -impl<'a> VacantEntry<'a> { - /// Gets a reference to the key that would be used when inserting a value - /// through the VacantEntry. - #[inline] - pub fn key(&self) -> &String { - self.vacant.key() - } - - /// Sets the value of the entry with the VacantEntry's key, and returns a - /// mutable reference to it. - #[inline] - pub fn insert(self, value: Value) -> &'a mut Value { - self.vacant.insert(value) - } -} - -impl<'a> OccupiedEntry<'a> { - /// Gets a reference to the key in the entry. - #[inline] - pub fn key(&self) -> &String { - self.occupied.key() - } - - /// Gets a reference to the value in the entry. - #[inline] - pub fn get(&self) -> &Value { - self.occupied.get() - } - - /// Gets a mutable reference to the value in the entry. - #[inline] - pub fn get_mut(&mut self) -> &mut Value { - self.occupied.get_mut() - } - - /// Converts the entry into a mutable reference to its value. - #[inline] - pub fn into_mut(self) -> &'a mut Value { - self.occupied.into_mut() - } - - /// Sets the value of the entry with the `OccupiedEntry`'s key, and returns - /// the entry's old value. - #[inline] - pub fn insert(&mut self, value: Value) -> Value { - self.occupied.insert(value) - } - - /// Takes the value of the entry out of the map, and returns it. - #[inline] - pub fn remove(self) -> Value { - self.occupied.remove() - } -} - -////////////////////////////////////////////////////////////////////////////// - -impl<'a> IntoIterator for &'a Map<String, Value> { - type Item = (&'a String, &'a Value); - type IntoIter = Iter<'a>; - #[inline] - fn into_iter(self) -> Self::IntoIter { - Iter { - iter: self.map.iter(), - } - } -} - -/// An iterator over a toml::Map's entries. -pub struct Iter<'a> { - iter: IterImpl<'a>, -} - -#[cfg(not(feature = "preserve_order"))] -type IterImpl<'a> = btree_map::Iter<'a, String, Value>; -#[cfg(feature = "preserve_order")] -type IterImpl<'a> = indexmap::map::Iter<'a, String, Value>; - -delegate_iterator!((Iter<'a>) => (&'a String, &'a Value)); - -////////////////////////////////////////////////////////////////////////////// - -impl<'a> IntoIterator for &'a mut Map<String, Value> { - type Item = (&'a String, &'a mut Value); - type IntoIter = IterMut<'a>; - #[inline] - fn into_iter(self) -> Self::IntoIter { - IterMut { - iter: self.map.iter_mut(), - } - } -} - -/// A mutable iterator over a toml::Map's entries. -pub struct IterMut<'a> { - iter: IterMutImpl<'a>, -} - -#[cfg(not(feature = "preserve_order"))] -type IterMutImpl<'a> = btree_map::IterMut<'a, String, Value>; -#[cfg(feature = "preserve_order")] -type IterMutImpl<'a> = indexmap::map::IterMut<'a, String, Value>; - -delegate_iterator!((IterMut<'a>) => (&'a String, &'a mut Value)); - -////////////////////////////////////////////////////////////////////////////// - -impl IntoIterator for Map<String, Value> { - type Item = (String, Value); - type IntoIter = IntoIter; - #[inline] - fn into_iter(self) -> Self::IntoIter { - IntoIter { - iter: self.map.into_iter(), - } - } -} - -/// An owning iterator over a toml::Map's entries. -pub struct IntoIter { - iter: IntoIterImpl, -} - -#[cfg(not(feature = "preserve_order"))] -type IntoIterImpl = btree_map::IntoIter<String, Value>; -#[cfg(feature = "preserve_order")] -type IntoIterImpl = indexmap::map::IntoIter<String, Value>; - -delegate_iterator!((IntoIter) => (String, Value)); - -////////////////////////////////////////////////////////////////////////////// - -/// An iterator over a toml::Map's keys. -pub struct Keys<'a> { - iter: KeysImpl<'a>, -} - -#[cfg(not(feature = "preserve_order"))] -type KeysImpl<'a> = btree_map::Keys<'a, String, Value>; -#[cfg(feature = "preserve_order")] -type KeysImpl<'a> = indexmap::map::Keys<'a, String, Value>; - -delegate_iterator!((Keys<'a>) => &'a String); - -////////////////////////////////////////////////////////////////////////////// - -/// An iterator over a toml::Map's values. -pub struct Values<'a> { - iter: ValuesImpl<'a>, -} - -#[cfg(not(feature = "preserve_order"))] -type ValuesImpl<'a> = btree_map::Values<'a, String, Value>; -#[cfg(feature = "preserve_order")] -type ValuesImpl<'a> = indexmap::map::Values<'a, String, Value>; - -delegate_iterator!((Values<'a>) => &'a Value); diff --git a/vendor/toml-0.5.9/src/ser.rs b/vendor/toml-0.5.9/src/ser.rs deleted file mode 100644 index 90c5acf61..000000000 --- a/vendor/toml-0.5.9/src/ser.rs +++ /dev/null @@ -1,1859 +0,0 @@ -//! Serializing Rust structures into TOML. -//! -//! This module contains all the Serde support for serializing Rust structures -//! into TOML documents (as strings). Note that some top-level functions here -//! are also provided at the top of the crate. -//! -//! Note that the TOML format has a restriction that if a table itself contains -//! tables, all keys with non-table values must be emitted first. This is -//! typically easy to ensure happens when you're defining a `struct` as you can -//! reorder the fields manually, but when working with maps (such as `BTreeMap` -//! or `HashMap`) this can lead to serialization errors. In those situations you -//! may use the `tables_last` function in this module like so: -//! -//! ```rust -//! # use serde_derive::Serialize; -//! # use std::collections::HashMap; -//! #[derive(Serialize)] -//! struct Manifest { -//! package: Package, -//! #[serde(serialize_with = "toml::ser::tables_last")] -//! dependencies: HashMap<String, Dependency>, -//! } -//! # type Package = String; -//! # type Dependency = String; -//! # fn main() {} -//! ``` - -use std::cell::Cell; -use std::error; -use std::fmt::{self, Write}; -use std::marker; -use std::rc::Rc; - -use crate::datetime; -use serde::ser; - -/// Serialize the given data structure as a TOML byte vector. -/// -/// Serialization can fail if `T`'s implementation of `Serialize` decides to -/// fail, if `T` contains a map with non-string keys, or if `T` attempts to -/// serialize an unsupported datatype such as an enum, tuple, or tuple struct. -pub fn to_vec<T: ?Sized>(value: &T) -> Result<Vec<u8>, Error> -where - T: ser::Serialize, -{ - to_string(value).map(|e| e.into_bytes()) -} - -/// Serialize the given data structure as a String of TOML. -/// -/// Serialization can fail if `T`'s implementation of `Serialize` decides to -/// fail, if `T` contains a map with non-string keys, or if `T` attempts to -/// serialize an unsupported datatype such as an enum, tuple, or tuple struct. -/// -/// # Examples -/// -/// ``` -/// use serde_derive::Serialize; -/// -/// #[derive(Serialize)] -/// struct Config { -/// database: Database, -/// } -/// -/// #[derive(Serialize)] -/// struct Database { -/// ip: String, -/// port: Vec<u16>, -/// connection_max: u32, -/// enabled: bool, -/// } -/// -/// fn main() { -/// let config = Config { -/// database: Database { -/// ip: "192.168.1.1".to_string(), -/// port: vec![8001, 8002, 8003], -/// connection_max: 5000, -/// enabled: false, -/// }, -/// }; -/// -/// let toml = toml::to_string(&config).unwrap(); -/// println!("{}", toml) -/// } -/// ``` -pub fn to_string<T: ?Sized>(value: &T) -> Result<String, Error> -where - T: ser::Serialize, -{ - let mut dst = String::with_capacity(128); - value.serialize(&mut Serializer::new(&mut dst))?; - Ok(dst) -} - -/// Serialize the given data structure as a "pretty" String of TOML. -/// -/// This is identical to `to_string` except the output string has a more -/// "pretty" output. See `Serializer::pretty` for more details. -pub fn to_string_pretty<T: ?Sized>(value: &T) -> Result<String, Error> -where - T: ser::Serialize, -{ - let mut dst = String::with_capacity(128); - value.serialize(&mut Serializer::pretty(&mut dst))?; - Ok(dst) -} - -/// Errors that can occur when serializing a type. -#[derive(Debug, PartialEq, Eq, Clone)] -pub enum Error { - /// Indicates that a Rust type was requested to be serialized but it was not - /// supported. - /// - /// Currently the TOML format does not support serializing types such as - /// enums, tuples and tuple structs. - UnsupportedType, - - /// The key of all TOML maps must be strings, but serialization was - /// attempted where the key of a map was not a string. - KeyNotString, - - /// An error that we never omit but keep for backwards compatibility - #[doc(hidden)] - KeyNewline, - - /// An array had to be homogenous, but now it is allowed to be heterogenous. - #[doc(hidden)] - ArrayMixedType, - - /// All values in a TOML table must be emitted before further tables are - /// emitted. If a value is emitted *after* a table then this error is - /// generated. - ValueAfterTable, - - /// A serialized date was invalid. - DateInvalid, - - /// A serialized number was invalid. - NumberInvalid, - - /// None was attempted to be serialized, but it's not supported. - UnsupportedNone, - - /// A custom error which could be generated when serializing a particular - /// type. - Custom(String), - - #[doc(hidden)] - __Nonexhaustive, -} - -#[derive(Debug, Default, Clone)] -/// Internal place for holding array setings -struct ArraySettings { - indent: usize, - trailing_comma: bool, -} - -impl ArraySettings { - fn pretty() -> ArraySettings { - ArraySettings { - indent: 4, - trailing_comma: true, - } - } -} - -#[derive(Debug, Default, Clone)] -/// String settings -struct StringSettings { - /// Whether to use literal strings when possible - literal: bool, -} - -impl StringSettings { - fn pretty() -> StringSettings { - StringSettings { literal: true } - } -} - -#[derive(Debug, Default, Clone)] -/// Internal struct for holding serialization settings -struct Settings { - array: Option<ArraySettings>, - string: Option<StringSettings>, -} - -/// Serialization implementation for TOML. -/// -/// This structure implements serialization support for TOML to serialize an -/// arbitrary type to TOML. Note that the TOML format does not support all -/// datatypes in Rust, such as enums, tuples, and tuple structs. These types -/// will generate an error when serialized. -/// -/// Currently a serializer always writes its output to an in-memory `String`, -/// which is passed in when creating the serializer itself. -pub struct Serializer<'a> { - dst: &'a mut String, - state: State<'a>, - settings: Rc<Settings>, -} - -#[derive(Debug, Copy, Clone)] -enum ArrayState { - Started, - StartedAsATable, -} - -#[derive(Debug, Clone)] -enum State<'a> { - Table { - key: &'a str, - parent: &'a State<'a>, - first: &'a Cell<bool>, - table_emitted: &'a Cell<bool>, - }, - Array { - parent: &'a State<'a>, - first: &'a Cell<bool>, - type_: &'a Cell<Option<ArrayState>>, - len: Option<usize>, - }, - End, -} - -#[doc(hidden)] -pub struct SerializeSeq<'a, 'b> { - ser: &'b mut Serializer<'a>, - first: Cell<bool>, - type_: Cell<Option<ArrayState>>, - len: Option<usize>, -} - -#[doc(hidden)] -pub enum SerializeTable<'a, 'b> { - Datetime(&'b mut Serializer<'a>), - Table { - ser: &'b mut Serializer<'a>, - key: String, - first: Cell<bool>, - table_emitted: Cell<bool>, - }, -} - -impl<'a> Serializer<'a> { - /// Creates a new serializer which will emit TOML into the buffer provided. - /// - /// The serializer can then be used to serialize a type after which the data - /// will be present in `dst`. - pub fn new(dst: &'a mut String) -> Serializer<'a> { - Serializer { - dst, - state: State::End, - settings: Rc::new(Settings::default()), - } - } - - /// Instantiate a "pretty" formatter - /// - /// By default this will use: - /// - /// - pretty strings: strings with newlines will use the `'''` syntax. See - /// `Serializer::pretty_string` - /// - pretty arrays: each item in arrays will be on a newline, have an indentation of 4 and - /// have a trailing comma. See `Serializer::pretty_array` - pub fn pretty(dst: &'a mut String) -> Serializer<'a> { - Serializer { - dst, - state: State::End, - settings: Rc::new(Settings { - array: Some(ArraySettings::pretty()), - string: Some(StringSettings::pretty()), - }), - } - } - - /// Enable or Disable pretty strings - /// - /// If enabled, literal strings will be used when possible and strings with - /// one or more newlines will use triple quotes (i.e.: `'''` or `"""`) - /// - /// # Examples - /// - /// Instead of: - /// - /// ```toml,ignore - /// single = "no newlines" - /// text = "\nfoo\nbar\n" - /// ``` - /// - /// You will have: - /// - /// ```toml,ignore - /// single = 'no newlines' - /// text = ''' - /// foo - /// bar - /// ''' - /// ``` - pub fn pretty_string(&mut self, value: bool) -> &mut Self { - Rc::get_mut(&mut self.settings).unwrap().string = if value { - Some(StringSettings::pretty()) - } else { - None - }; - self - } - - /// Enable or Disable Literal strings for pretty strings - /// - /// If enabled, literal strings will be used when possible and strings with - /// one or more newlines will use triple quotes (i.e.: `'''` or `"""`) - /// - /// If disabled, literal strings will NEVER be used and strings with one or - /// more newlines will use `"""` - /// - /// # Examples - /// - /// Instead of: - /// - /// ```toml,ignore - /// single = "no newlines" - /// text = "\nfoo\nbar\n" - /// ``` - /// - /// You will have: - /// - /// ```toml,ignore - /// single = "no newlines" - /// text = """ - /// foo - /// bar - /// """ - /// ``` - pub fn pretty_string_literal(&mut self, value: bool) -> &mut Self { - let use_default = if let Some(ref mut s) = Rc::get_mut(&mut self.settings).unwrap().string { - s.literal = value; - false - } else { - true - }; - - if use_default { - let mut string = StringSettings::pretty(); - string.literal = value; - Rc::get_mut(&mut self.settings).unwrap().string = Some(string); - } - self - } - - /// Enable or Disable pretty arrays - /// - /// If enabled, arrays will always have each item on their own line. - /// - /// Some specific features can be controlled via other builder methods: - /// - /// - `Serializer::pretty_array_indent`: set the indent to a value other - /// than 4. - /// - `Serializer::pretty_array_trailing_comma`: enable/disable the trailing - /// comma on the last item. - /// - /// # Examples - /// - /// Instead of: - /// - /// ```toml,ignore - /// array = ["foo", "bar"] - /// ``` - /// - /// You will have: - /// - /// ```toml,ignore - /// array = [ - /// "foo", - /// "bar", - /// ] - /// ``` - pub fn pretty_array(&mut self, value: bool) -> &mut Self { - Rc::get_mut(&mut self.settings).unwrap().array = if value { - Some(ArraySettings::pretty()) - } else { - None - }; - self - } - - /// Set the indent for pretty arrays - /// - /// See `Serializer::pretty_array` for more details. - pub fn pretty_array_indent(&mut self, value: usize) -> &mut Self { - let use_default = if let Some(ref mut a) = Rc::get_mut(&mut self.settings).unwrap().array { - a.indent = value; - false - } else { - true - }; - - if use_default { - let mut array = ArraySettings::pretty(); - array.indent = value; - Rc::get_mut(&mut self.settings).unwrap().array = Some(array); - } - self - } - - /// Specify whether to use a trailing comma when serializing pretty arrays - /// - /// See `Serializer::pretty_array` for more details. - pub fn pretty_array_trailing_comma(&mut self, value: bool) -> &mut Self { - let use_default = if let Some(ref mut a) = Rc::get_mut(&mut self.settings).unwrap().array { - a.trailing_comma = value; - false - } else { - true - }; - - if use_default { - let mut array = ArraySettings::pretty(); - array.trailing_comma = value; - Rc::get_mut(&mut self.settings).unwrap().array = Some(array); - } - self - } - - fn display<T: fmt::Display>(&mut self, t: T, type_: ArrayState) -> Result<(), Error> { - self.emit_key(type_)?; - write!(self.dst, "{}", t).map_err(ser::Error::custom)?; - if let State::Table { .. } = self.state { - self.dst.push_str("\n"); - } - Ok(()) - } - - fn emit_key(&mut self, type_: ArrayState) -> Result<(), Error> { - self.array_type(type_)?; - let state = self.state.clone(); - self._emit_key(&state) - } - - // recursive implementation of `emit_key` above - fn _emit_key(&mut self, state: &State<'_>) -> Result<(), Error> { - match *state { - State::End => Ok(()), - State::Array { - parent, - first, - type_, - len, - } => { - assert!(type_.get().is_some()); - if first.get() { - self._emit_key(parent)?; - } - self.emit_array(first, len) - } - State::Table { - parent, - first, - table_emitted, - key, - } => { - if table_emitted.get() { - return Err(Error::ValueAfterTable); - } - if first.get() { - self.emit_table_header(parent)?; - first.set(false); - } - self.escape_key(key)?; - self.dst.push_str(" = "); - Ok(()) - } - } - } - - fn emit_array(&mut self, first: &Cell<bool>, len: Option<usize>) -> Result<(), Error> { - match (len, &self.settings.array) { - (Some(0..=1), _) | (_, &None) => { - if first.get() { - self.dst.push_str("[") - } else { - self.dst.push_str(", ") - } - } - (_, &Some(ref a)) => { - if first.get() { - self.dst.push_str("[\n") - } else { - self.dst.push_str(",\n") - } - for _ in 0..a.indent { - self.dst.push_str(" "); - } - } - } - Ok(()) - } - - fn array_type(&mut self, type_: ArrayState) -> Result<(), Error> { - let prev = match self.state { - State::Array { type_, .. } => type_, - _ => return Ok(()), - }; - if prev.get().is_none() { - prev.set(Some(type_)); - } - Ok(()) - } - - fn escape_key(&mut self, key: &str) -> Result<(), Error> { - let ok = key.len() > 0 - && key.chars().all(|c| match c { - 'a'..='z' | 'A'..='Z' | '0'..='9' | '-' | '_' => true, - _ => false, - }); - if ok { - write!(self.dst, "{}", key).map_err(ser::Error::custom)?; - } else { - self.emit_str(key, true)?; - } - Ok(()) - } - - fn emit_str(&mut self, value: &str, is_key: bool) -> Result<(), Error> { - #[derive(PartialEq)] - enum Type { - NewlineTripple, - OnelineTripple, - OnelineSingle, - } - - enum Repr { - /// represent as a literal string (using '') - Literal(String, Type), - /// represent the std way (using "") - Std(Type), - } - - fn do_pretty(value: &str) -> Repr { - // For doing pretty prints we store in a new String - // because there are too many cases where pretty cannot - // work. We need to determine: - // - if we are a "multi-line" pretty (if there are \n) - // - if ['''] appears if multi or ['] if single - // - if there are any invalid control characters - // - // Doing it any other way would require multiple passes - // to determine if a pretty string works or not. - let mut out = String::with_capacity(value.len() * 2); - let mut ty = Type::OnelineSingle; - // found consecutive single quotes - let mut max_found_singles = 0; - let mut found_singles = 0; - let mut can_be_pretty = true; - - for ch in value.chars() { - if can_be_pretty { - if ch == '\'' { - found_singles += 1; - if found_singles >= 3 { - can_be_pretty = false; - } - } else { - if found_singles > max_found_singles { - max_found_singles = found_singles; - } - found_singles = 0 - } - match ch { - '\t' => {} - '\n' => ty = Type::NewlineTripple, - // Escape codes are needed if any ascii control - // characters are present, including \b \f \r. - c if c <= '\u{1f}' || c == '\u{7f}' => can_be_pretty = false, - _ => {} - } - out.push(ch); - } else { - // the string cannot be represented as pretty, - // still check if it should be multiline - if ch == '\n' { - ty = Type::NewlineTripple; - } - } - } - if can_be_pretty && found_singles > 0 && value.ends_with('\'') { - // We cannot escape the ending quote so we must use """ - can_be_pretty = false; - } - if !can_be_pretty { - debug_assert!(ty != Type::OnelineTripple); - return Repr::Std(ty); - } - if found_singles > max_found_singles { - max_found_singles = found_singles; - } - debug_assert!(max_found_singles < 3); - if ty == Type::OnelineSingle && max_found_singles >= 1 { - // no newlines, but must use ''' because it has ' in it - ty = Type::OnelineTripple; - } - Repr::Literal(out, ty) - } - - let repr = if !is_key && self.settings.string.is_some() { - match (&self.settings.string, do_pretty(value)) { - (&Some(StringSettings { literal: false, .. }), Repr::Literal(_, ty)) => { - Repr::Std(ty) - } - (_, r) => r, - } - } else { - Repr::Std(Type::OnelineSingle) - }; - match repr { - Repr::Literal(literal, ty) => { - // A pretty string - match ty { - Type::NewlineTripple => self.dst.push_str("'''\n"), - Type::OnelineTripple => self.dst.push_str("'''"), - Type::OnelineSingle => self.dst.push('\''), - } - self.dst.push_str(&literal); - match ty { - Type::OnelineSingle => self.dst.push('\''), - _ => self.dst.push_str("'''"), - } - } - Repr::Std(ty) => { - match ty { - Type::NewlineTripple => self.dst.push_str("\"\"\"\n"), - // note: OnelineTripple can happen if do_pretty wants to do - // '''it's one line''' - // but settings.string.literal == false - Type::OnelineSingle | Type::OnelineTripple => self.dst.push('"'), - } - for ch in value.chars() { - match ch { - '\u{8}' => self.dst.push_str("\\b"), - '\u{9}' => self.dst.push_str("\\t"), - '\u{a}' => match ty { - Type::NewlineTripple => self.dst.push('\n'), - Type::OnelineSingle => self.dst.push_str("\\n"), - _ => unreachable!(), - }, - '\u{c}' => self.dst.push_str("\\f"), - '\u{d}' => self.dst.push_str("\\r"), - '\u{22}' => self.dst.push_str("\\\""), - '\u{5c}' => self.dst.push_str("\\\\"), - c if c <= '\u{1f}' || c == '\u{7f}' => { - write!(self.dst, "\\u{:04X}", ch as u32).map_err(ser::Error::custom)?; - } - ch => self.dst.push(ch), - } - } - match ty { - Type::NewlineTripple => self.dst.push_str("\"\"\""), - Type::OnelineSingle | Type::OnelineTripple => self.dst.push('"'), - } - } - } - Ok(()) - } - - fn emit_table_header(&mut self, state: &State<'_>) -> Result<(), Error> { - let array_of_tables = match *state { - State::End => return Ok(()), - State::Array { .. } => true, - _ => false, - }; - - // Unlike [..]s, we can't omit [[..]] ancestors, so be sure to emit table - // headers for them. - let mut p = state; - if let State::Array { first, parent, .. } = *state { - if first.get() { - p = parent; - } - } - while let State::Table { first, parent, .. } = *p { - p = parent; - if !first.get() { - break; - } - if let State::Array { - parent: &State::Table { .. }, - .. - } = *parent - { - self.emit_table_header(parent)?; - break; - } - } - - match *state { - State::Table { first, .. } => { - if !first.get() { - // Newline if we are a table that is not the first - // table in the document. - self.dst.push('\n'); - } - } - State::Array { parent, first, .. } => { - if !first.get() { - // Always newline if we are not the first item in the - // table-array - self.dst.push('\n'); - } else if let State::Table { first, .. } = *parent { - if !first.get() { - // Newline if we are not the first item in the document - self.dst.push('\n'); - } - } - } - _ => {} - } - self.dst.push_str("["); - if array_of_tables { - self.dst.push_str("["); - } - self.emit_key_part(state)?; - if array_of_tables { - self.dst.push_str("]"); - } - self.dst.push_str("]\n"); - Ok(()) - } - - fn emit_key_part(&mut self, key: &State<'_>) -> Result<bool, Error> { - match *key { - State::Array { parent, .. } => self.emit_key_part(parent), - State::End => Ok(true), - State::Table { - key, - parent, - table_emitted, - .. - } => { - table_emitted.set(true); - let first = self.emit_key_part(parent)?; - if !first { - self.dst.push_str("."); - } - self.escape_key(key)?; - Ok(false) - } - } - } -} - -macro_rules! serialize_float { - ($this:expr, $v:expr) => {{ - $this.emit_key(ArrayState::Started)?; - match ($v.is_sign_negative(), $v.is_nan(), $v == 0.0) { - (true, true, _) => write!($this.dst, "-nan"), - (false, true, _) => write!($this.dst, "nan"), - (true, false, true) => write!($this.dst, "-0.0"), - (false, false, true) => write!($this.dst, "0.0"), - (_, false, false) => write!($this.dst, "{}", $v).and_then(|_| { - if $v % 1.0 == 0.0 { - write!($this.dst, ".0") - } else { - Ok(()) - } - }), - } - .map_err(ser::Error::custom)?; - - if let State::Table { .. } = $this.state { - $this.dst.push_str("\n"); - } - return Ok(()); - }}; -} - -impl<'a, 'b> ser::Serializer for &'b mut Serializer<'a> { - type Ok = (); - type Error = Error; - type SerializeSeq = SerializeSeq<'a, 'b>; - type SerializeTuple = SerializeSeq<'a, 'b>; - type SerializeTupleStruct = SerializeSeq<'a, 'b>; - type SerializeTupleVariant = SerializeSeq<'a, 'b>; - type SerializeMap = SerializeTable<'a, 'b>; - type SerializeStruct = SerializeTable<'a, 'b>; - type SerializeStructVariant = ser::Impossible<(), Error>; - - fn serialize_bool(self, v: bool) -> Result<(), Self::Error> { - self.display(v, ArrayState::Started) - } - - fn serialize_i8(self, v: i8) -> Result<(), Self::Error> { - self.display(v, ArrayState::Started) - } - - fn serialize_i16(self, v: i16) -> Result<(), Self::Error> { - self.display(v, ArrayState::Started) - } - - fn serialize_i32(self, v: i32) -> Result<(), Self::Error> { - self.display(v, ArrayState::Started) - } - - fn serialize_i64(self, v: i64) -> Result<(), Self::Error> { - self.display(v, ArrayState::Started) - } - - fn serialize_u8(self, v: u8) -> Result<(), Self::Error> { - self.display(v, ArrayState::Started) - } - - fn serialize_u16(self, v: u16) -> Result<(), Self::Error> { - self.display(v, ArrayState::Started) - } - - fn serialize_u32(self, v: u32) -> Result<(), Self::Error> { - self.display(v, ArrayState::Started) - } - - fn serialize_u64(self, v: u64) -> Result<(), Self::Error> { - self.display(v, ArrayState::Started) - } - - fn serialize_f32(self, v: f32) -> Result<(), Self::Error> { - serialize_float!(self, v) - } - - fn serialize_f64(self, v: f64) -> Result<(), Self::Error> { - serialize_float!(self, v) - } - - fn serialize_char(self, v: char) -> Result<(), Self::Error> { - let mut buf = [0; 4]; - self.serialize_str(v.encode_utf8(&mut buf)) - } - - fn serialize_str(self, value: &str) -> Result<(), Self::Error> { - self.emit_key(ArrayState::Started)?; - self.emit_str(value, false)?; - if let State::Table { .. } = self.state { - self.dst.push_str("\n"); - } - Ok(()) - } - - fn serialize_bytes(self, value: &[u8]) -> Result<(), Self::Error> { - use serde::ser::Serialize; - value.serialize(self) - } - - fn serialize_none(self) -> Result<(), Self::Error> { - Err(Error::UnsupportedNone) - } - - fn serialize_some<T: ?Sized>(self, value: &T) -> Result<(), Self::Error> - where - T: ser::Serialize, - { - value.serialize(self) - } - - fn serialize_unit(self) -> Result<(), Self::Error> { - Err(Error::UnsupportedType) - } - - fn serialize_unit_struct(self, _name: &'static str) -> Result<(), Self::Error> { - Err(Error::UnsupportedType) - } - - fn serialize_unit_variant( - self, - _name: &'static str, - _variant_index: u32, - variant: &'static str, - ) -> Result<(), Self::Error> { - self.serialize_str(variant) - } - - fn serialize_newtype_struct<T: ?Sized>( - self, - _name: &'static str, - value: &T, - ) -> Result<(), Self::Error> - where - T: ser::Serialize, - { - value.serialize(self) - } - - fn serialize_newtype_variant<T: ?Sized>( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - _value: &T, - ) -> Result<(), Self::Error> - where - T: ser::Serialize, - { - Err(Error::UnsupportedType) - } - - fn serialize_seq(self, len: Option<usize>) -> Result<Self::SerializeSeq, Self::Error> { - self.array_type(ArrayState::Started)?; - Ok(SerializeSeq { - ser: self, - first: Cell::new(true), - type_: Cell::new(None), - len, - }) - } - - fn serialize_tuple(self, len: usize) -> Result<Self::SerializeTuple, Self::Error> { - self.serialize_seq(Some(len)) - } - - fn serialize_tuple_struct( - self, - _name: &'static str, - len: usize, - ) -> Result<Self::SerializeTupleStruct, Self::Error> { - self.serialize_seq(Some(len)) - } - - fn serialize_tuple_variant( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - len: usize, - ) -> Result<Self::SerializeTupleVariant, Self::Error> { - self.serialize_seq(Some(len)) - } - - fn serialize_map(self, _len: Option<usize>) -> Result<Self::SerializeMap, Self::Error> { - self.array_type(ArrayState::StartedAsATable)?; - Ok(SerializeTable::Table { - ser: self, - key: String::new(), - first: Cell::new(true), - table_emitted: Cell::new(false), - }) - } - - fn serialize_struct( - self, - name: &'static str, - _len: usize, - ) -> Result<Self::SerializeStruct, Self::Error> { - if name == datetime::NAME { - self.array_type(ArrayState::Started)?; - Ok(SerializeTable::Datetime(self)) - } else { - self.array_type(ArrayState::StartedAsATable)?; - Ok(SerializeTable::Table { - ser: self, - key: String::new(), - first: Cell::new(true), - table_emitted: Cell::new(false), - }) - } - } - - fn serialize_struct_variant( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - _len: usize, - ) -> Result<Self::SerializeStructVariant, Self::Error> { - Err(Error::UnsupportedType) - } -} - -impl<'a, 'b> ser::SerializeSeq for SerializeSeq<'a, 'b> { - type Ok = (); - type Error = Error; - - fn serialize_element<T: ?Sized>(&mut self, value: &T) -> Result<(), Error> - where - T: ser::Serialize, - { - value.serialize(&mut Serializer { - dst: &mut *self.ser.dst, - state: State::Array { - parent: &self.ser.state, - first: &self.first, - type_: &self.type_, - len: self.len, - }, - settings: self.ser.settings.clone(), - })?; - self.first.set(false); - Ok(()) - } - - fn end(self) -> Result<(), Error> { - match self.type_.get() { - Some(ArrayState::StartedAsATable) => return Ok(()), - Some(ArrayState::Started) => match (self.len, &self.ser.settings.array) { - (Some(0..=1), _) | (_, &None) => { - self.ser.dst.push_str("]"); - } - (_, &Some(ref a)) => { - if a.trailing_comma { - self.ser.dst.push_str(","); - } - self.ser.dst.push_str("\n]"); - } - }, - None => { - assert!(self.first.get()); - self.ser.emit_key(ArrayState::Started)?; - self.ser.dst.push_str("[]") - } - } - if let State::Table { .. } = self.ser.state { - self.ser.dst.push_str("\n"); - } - Ok(()) - } -} - -impl<'a, 'b> ser::SerializeTuple for SerializeSeq<'a, 'b> { - type Ok = (); - type Error = Error; - - fn serialize_element<T: ?Sized>(&mut self, value: &T) -> Result<(), Error> - where - T: ser::Serialize, - { - ser::SerializeSeq::serialize_element(self, value) - } - - fn end(self) -> Result<(), Error> { - ser::SerializeSeq::end(self) - } -} - -impl<'a, 'b> ser::SerializeTupleVariant for SerializeSeq<'a, 'b> { - type Ok = (); - type Error = Error; - - fn serialize_field<T: ?Sized>(&mut self, value: &T) -> Result<(), Error> - where - T: ser::Serialize, - { - ser::SerializeSeq::serialize_element(self, value) - } - - fn end(self) -> Result<(), Error> { - ser::SerializeSeq::end(self) - } -} - -impl<'a, 'b> ser::SerializeTupleStruct for SerializeSeq<'a, 'b> { - type Ok = (); - type Error = Error; - - fn serialize_field<T: ?Sized>(&mut self, value: &T) -> Result<(), Error> - where - T: ser::Serialize, - { - ser::SerializeSeq::serialize_element(self, value) - } - - fn end(self) -> Result<(), Error> { - ser::SerializeSeq::end(self) - } -} - -impl<'a, 'b> ser::SerializeMap for SerializeTable<'a, 'b> { - type Ok = (); - type Error = Error; - - fn serialize_key<T: ?Sized>(&mut self, input: &T) -> Result<(), Error> - where - T: ser::Serialize, - { - match *self { - SerializeTable::Datetime(_) => panic!(), // shouldn't be possible - SerializeTable::Table { ref mut key, .. } => { - key.truncate(0); - *key = input.serialize(StringExtractor)?; - } - } - Ok(()) - } - - fn serialize_value<T: ?Sized>(&mut self, value: &T) -> Result<(), Error> - where - T: ser::Serialize, - { - match *self { - SerializeTable::Datetime(_) => panic!(), // shouldn't be possible - SerializeTable::Table { - ref mut ser, - ref key, - ref first, - ref table_emitted, - .. - } => { - let res = value.serialize(&mut Serializer { - dst: &mut *ser.dst, - state: State::Table { - key, - parent: &ser.state, - first, - table_emitted, - }, - settings: ser.settings.clone(), - }); - match res { - Ok(()) => first.set(false), - Err(Error::UnsupportedNone) => {} - Err(e) => return Err(e), - } - } - } - Ok(()) - } - - fn end(self) -> Result<(), Error> { - match self { - SerializeTable::Datetime(_) => panic!(), // shouldn't be possible - SerializeTable::Table { ser, first, .. } => { - if first.get() { - let state = ser.state.clone(); - ser.emit_table_header(&state)?; - } - } - } - Ok(()) - } -} - -impl<'a, 'b> ser::SerializeStruct for SerializeTable<'a, 'b> { - type Ok = (); - type Error = Error; - - fn serialize_field<T: ?Sized>(&mut self, key: &'static str, value: &T) -> Result<(), Error> - where - T: ser::Serialize, - { - match *self { - SerializeTable::Datetime(ref mut ser) => { - if key == datetime::FIELD { - value.serialize(DateStrEmitter(&mut *ser))?; - } else { - return Err(Error::DateInvalid); - } - } - SerializeTable::Table { - ref mut ser, - ref first, - ref table_emitted, - .. - } => { - let res = value.serialize(&mut Serializer { - dst: &mut *ser.dst, - state: State::Table { - key, - parent: &ser.state, - first, - table_emitted, - }, - settings: ser.settings.clone(), - }); - match res { - Ok(()) => first.set(false), - Err(Error::UnsupportedNone) => {} - Err(e) => return Err(e), - } - } - } - Ok(()) - } - - fn end(self) -> Result<(), Error> { - match self { - SerializeTable::Datetime(_) => {} - SerializeTable::Table { ser, first, .. } => { - if first.get() { - let state = ser.state.clone(); - ser.emit_table_header(&state)?; - } - } - } - Ok(()) - } -} - -struct DateStrEmitter<'a, 'b>(&'b mut Serializer<'a>); - -impl<'a, 'b> ser::Serializer for DateStrEmitter<'a, 'b> { - type Ok = (); - type Error = Error; - type SerializeSeq = ser::Impossible<(), Error>; - type SerializeTuple = ser::Impossible<(), Error>; - type SerializeTupleStruct = ser::Impossible<(), Error>; - type SerializeTupleVariant = ser::Impossible<(), Error>; - type SerializeMap = ser::Impossible<(), Error>; - type SerializeStruct = ser::Impossible<(), Error>; - type SerializeStructVariant = ser::Impossible<(), Error>; - - fn serialize_bool(self, _v: bool) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_i8(self, _v: i8) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_i16(self, _v: i16) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_i32(self, _v: i32) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_i64(self, _v: i64) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_u8(self, _v: u8) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_u16(self, _v: u16) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_u32(self, _v: u32) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_u64(self, _v: u64) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_f32(self, _v: f32) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_f64(self, _v: f64) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_char(self, _v: char) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_str(self, value: &str) -> Result<(), Self::Error> { - self.0.display(value, ArrayState::Started)?; - Ok(()) - } - - fn serialize_bytes(self, _value: &[u8]) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_none(self) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_some<T: ?Sized>(self, _value: &T) -> Result<(), Self::Error> - where - T: ser::Serialize, - { - Err(Error::DateInvalid) - } - - fn serialize_unit(self) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_unit_struct(self, _name: &'static str) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_unit_variant( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - ) -> Result<(), Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_newtype_struct<T: ?Sized>( - self, - _name: &'static str, - _value: &T, - ) -> Result<(), Self::Error> - where - T: ser::Serialize, - { - Err(Error::DateInvalid) - } - - fn serialize_newtype_variant<T: ?Sized>( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - _value: &T, - ) -> Result<(), Self::Error> - where - T: ser::Serialize, - { - Err(Error::DateInvalid) - } - - fn serialize_seq(self, _len: Option<usize>) -> Result<Self::SerializeSeq, Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_tuple(self, _len: usize) -> Result<Self::SerializeTuple, Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_tuple_struct( - self, - _name: &'static str, - _len: usize, - ) -> Result<Self::SerializeTupleStruct, Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_tuple_variant( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - _len: usize, - ) -> Result<Self::SerializeTupleVariant, Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_map(self, _len: Option<usize>) -> Result<Self::SerializeMap, Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_struct( - self, - _name: &'static str, - _len: usize, - ) -> Result<Self::SerializeStruct, Self::Error> { - Err(Error::DateInvalid) - } - - fn serialize_struct_variant( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - _len: usize, - ) -> Result<Self::SerializeStructVariant, Self::Error> { - Err(Error::DateInvalid) - } -} - -struct StringExtractor; - -impl ser::Serializer for StringExtractor { - type Ok = String; - type Error = Error; - type SerializeSeq = ser::Impossible<String, Error>; - type SerializeTuple = ser::Impossible<String, Error>; - type SerializeTupleStruct = ser::Impossible<String, Error>; - type SerializeTupleVariant = ser::Impossible<String, Error>; - type SerializeMap = ser::Impossible<String, Error>; - type SerializeStruct = ser::Impossible<String, Error>; - type SerializeStructVariant = ser::Impossible<String, Error>; - - fn serialize_bool(self, _v: bool) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_i8(self, _v: i8) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_i16(self, _v: i16) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_i32(self, _v: i32) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_i64(self, _v: i64) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_u8(self, _v: u8) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_u16(self, _v: u16) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_u32(self, _v: u32) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_u64(self, _v: u64) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_f32(self, _v: f32) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_f64(self, _v: f64) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_char(self, _v: char) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_str(self, value: &str) -> Result<String, Self::Error> { - Ok(value.to_string()) - } - - fn serialize_bytes(self, _value: &[u8]) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_none(self) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_some<T: ?Sized>(self, _value: &T) -> Result<String, Self::Error> - where - T: ser::Serialize, - { - Err(Error::KeyNotString) - } - - fn serialize_unit(self) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_unit_struct(self, _name: &'static str) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_unit_variant( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - ) -> Result<String, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_newtype_struct<T: ?Sized>( - self, - _name: &'static str, - value: &T, - ) -> Result<String, Self::Error> - where - T: ser::Serialize, - { - value.serialize(self) - } - - fn serialize_newtype_variant<T: ?Sized>( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - _value: &T, - ) -> Result<String, Self::Error> - where - T: ser::Serialize, - { - Err(Error::KeyNotString) - } - - fn serialize_seq(self, _len: Option<usize>) -> Result<Self::SerializeSeq, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_tuple(self, _len: usize) -> Result<Self::SerializeTuple, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_tuple_struct( - self, - _name: &'static str, - _len: usize, - ) -> Result<Self::SerializeTupleStruct, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_tuple_variant( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - _len: usize, - ) -> Result<Self::SerializeTupleVariant, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_map(self, _len: Option<usize>) -> Result<Self::SerializeMap, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_struct( - self, - _name: &'static str, - _len: usize, - ) -> Result<Self::SerializeStruct, Self::Error> { - Err(Error::KeyNotString) - } - - fn serialize_struct_variant( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - _len: usize, - ) -> Result<Self::SerializeStructVariant, Self::Error> { - Err(Error::KeyNotString) - } -} - -impl fmt::Display for Error { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { - match *self { - Error::UnsupportedType => "unsupported Rust type".fmt(f), - Error::KeyNotString => "map key was not a string".fmt(f), - Error::ValueAfterTable => "values must be emitted before tables".fmt(f), - Error::DateInvalid => "a serialized date was invalid".fmt(f), - Error::NumberInvalid => "a serialized number was invalid".fmt(f), - Error::UnsupportedNone => "unsupported None value".fmt(f), - Error::Custom(ref s) => s.fmt(f), - Error::KeyNewline => unreachable!(), - Error::ArrayMixedType => unreachable!(), - Error::__Nonexhaustive => panic!(), - } - } -} - -impl error::Error for Error {} - -impl ser::Error for Error { - fn custom<T: fmt::Display>(msg: T) -> Error { - Error::Custom(msg.to_string()) - } -} - -enum Category { - Primitive, - Array, - Table, -} - -/// Convenience function to serialize items in a map in an order valid with -/// TOML. -/// -/// TOML carries the restriction that keys in a table must be serialized last if -/// their value is a table itself. This isn't always easy to guarantee, so this -/// helper can be used like so: -/// -/// ```rust -/// # use serde_derive::Serialize; -/// # use std::collections::HashMap; -/// #[derive(Serialize)] -/// struct Manifest { -/// package: Package, -/// #[serde(serialize_with = "toml::ser::tables_last")] -/// dependencies: HashMap<String, Dependency>, -/// } -/// # type Package = String; -/// # type Dependency = String; -/// # fn main() {} -/// ``` -pub fn tables_last<'a, I, K, V, S>(data: &'a I, serializer: S) -> Result<S::Ok, S::Error> -where - &'a I: IntoIterator<Item = (K, V)>, - K: ser::Serialize, - V: ser::Serialize, - S: ser::Serializer, -{ - use serde::ser::SerializeMap; - - let mut map = serializer.serialize_map(None)?; - for (k, v) in data { - if let Category::Primitive = v.serialize(Categorize::new())? { - map.serialize_entry(&k, &v)?; - } - } - for (k, v) in data { - if let Category::Array = v.serialize(Categorize::new())? { - map.serialize_entry(&k, &v)?; - } - } - for (k, v) in data { - if let Category::Table = v.serialize(Categorize::new())? { - map.serialize_entry(&k, &v)?; - } - } - map.end() -} - -struct Categorize<E>(marker::PhantomData<E>); - -impl<E> Categorize<E> { - fn new() -> Self { - Categorize(marker::PhantomData) - } -} - -impl<E: ser::Error> ser::Serializer for Categorize<E> { - type Ok = Category; - type Error = E; - type SerializeSeq = Self; - type SerializeTuple = Self; - type SerializeTupleStruct = Self; - type SerializeTupleVariant = Self; - type SerializeMap = Self; - type SerializeStruct = Self; - type SerializeStructVariant = ser::Impossible<Category, E>; - - fn serialize_bool(self, _: bool) -> Result<Self::Ok, Self::Error> { - Ok(Category::Primitive) - } - - fn serialize_i8(self, _: i8) -> Result<Self::Ok, Self::Error> { - Ok(Category::Primitive) - } - - fn serialize_i16(self, _: i16) -> Result<Self::Ok, Self::Error> { - Ok(Category::Primitive) - } - - fn serialize_i32(self, _: i32) -> Result<Self::Ok, Self::Error> { - Ok(Category::Primitive) - } - - fn serialize_i64(self, _: i64) -> Result<Self::Ok, Self::Error> { - Ok(Category::Primitive) - } - - fn serialize_u8(self, _: u8) -> Result<Self::Ok, Self::Error> { - Ok(Category::Primitive) - } - - fn serialize_u16(self, _: u16) -> Result<Self::Ok, Self::Error> { - Ok(Category::Primitive) - } - - fn serialize_u32(self, _: u32) -> Result<Self::Ok, Self::Error> { - Ok(Category::Primitive) - } - - fn serialize_u64(self, _: u64) -> Result<Self::Ok, Self::Error> { - Ok(Category::Primitive) - } - - fn serialize_f32(self, _: f32) -> Result<Self::Ok, Self::Error> { - Ok(Category::Primitive) - } - - fn serialize_f64(self, _: f64) -> Result<Self::Ok, Self::Error> { - Ok(Category::Primitive) - } - - fn serialize_char(self, _: char) -> Result<Self::Ok, Self::Error> { - Ok(Category::Primitive) - } - - fn serialize_str(self, _: &str) -> Result<Self::Ok, Self::Error> { - Ok(Category::Primitive) - } - - fn serialize_bytes(self, _: &[u8]) -> Result<Self::Ok, Self::Error> { - Ok(Category::Array) - } - - fn serialize_none(self) -> Result<Self::Ok, Self::Error> { - Err(ser::Error::custom("unsupported")) - } - - fn serialize_some<T: ?Sized + ser::Serialize>(self, v: &T) -> Result<Self::Ok, Self::Error> { - v.serialize(self) - } - - fn serialize_unit(self) -> Result<Self::Ok, Self::Error> { - Err(ser::Error::custom("unsupported")) - } - - fn serialize_unit_struct(self, _: &'static str) -> Result<Self::Ok, Self::Error> { - Err(ser::Error::custom("unsupported")) - } - - fn serialize_unit_variant( - self, - _: &'static str, - _: u32, - _: &'static str, - ) -> Result<Self::Ok, Self::Error> { - Err(ser::Error::custom("unsupported")) - } - - fn serialize_newtype_struct<T: ?Sized + ser::Serialize>( - self, - _: &'static str, - v: &T, - ) -> Result<Self::Ok, Self::Error> { - v.serialize(self) - } - - fn serialize_newtype_variant<T: ?Sized + ser::Serialize>( - self, - _: &'static str, - _: u32, - _: &'static str, - _: &T, - ) -> Result<Self::Ok, Self::Error> { - Err(ser::Error::custom("unsupported")) - } - - fn serialize_seq(self, _: Option<usize>) -> Result<Self, Self::Error> { - Ok(self) - } - - fn serialize_tuple(self, _: usize) -> Result<Self::SerializeTuple, Self::Error> { - Ok(self) - } - - fn serialize_tuple_struct( - self, - _: &'static str, - _: usize, - ) -> Result<Self::SerializeTupleStruct, Self::Error> { - Ok(self) - } - - fn serialize_tuple_variant( - self, - _: &'static str, - _: u32, - _: &'static str, - _: usize, - ) -> Result<Self::SerializeTupleVariant, Self::Error> { - Ok(self) - } - - fn serialize_map(self, _: Option<usize>) -> Result<Self, Self::Error> { - Ok(self) - } - - fn serialize_struct(self, _: &'static str, _: usize) -> Result<Self, Self::Error> { - Ok(self) - } - - fn serialize_struct_variant( - self, - _: &'static str, - _: u32, - _: &'static str, - _: usize, - ) -> Result<Self::SerializeStructVariant, Self::Error> { - Err(ser::Error::custom("unsupported")) - } -} - -impl<E: ser::Error> ser::SerializeSeq for Categorize<E> { - type Ok = Category; - type Error = E; - - fn serialize_element<T: ?Sized + ser::Serialize>(&mut self, _: &T) -> Result<(), Self::Error> { - Ok(()) - } - - fn end(self) -> Result<Self::Ok, Self::Error> { - Ok(Category::Array) - } -} - -impl<E: ser::Error> ser::SerializeTuple for Categorize<E> { - type Ok = Category; - type Error = E; - - fn serialize_element<T: ?Sized + ser::Serialize>(&mut self, _: &T) -> Result<(), Self::Error> { - Ok(()) - } - - fn end(self) -> Result<Self::Ok, Self::Error> { - Ok(Category::Array) - } -} - -impl<E: ser::Error> ser::SerializeTupleVariant for Categorize<E> { - type Ok = Category; - type Error = E; - - fn serialize_field<T: ?Sized + ser::Serialize>(&mut self, _: &T) -> Result<(), Self::Error> { - Ok(()) - } - - fn end(self) -> Result<Self::Ok, Self::Error> { - Ok(Category::Array) - } -} - -impl<E: ser::Error> ser::SerializeTupleStruct for Categorize<E> { - type Ok = Category; - type Error = E; - - fn serialize_field<T: ?Sized + ser::Serialize>(&mut self, _: &T) -> Result<(), Self::Error> { - Ok(()) - } - - fn end(self) -> Result<Self::Ok, Self::Error> { - Ok(Category::Array) - } -} - -impl<E: ser::Error> ser::SerializeMap for Categorize<E> { - type Ok = Category; - type Error = E; - - fn serialize_key<T: ?Sized + ser::Serialize>(&mut self, _: &T) -> Result<(), Self::Error> { - Ok(()) - } - - fn serialize_value<T: ?Sized + ser::Serialize>(&mut self, _: &T) -> Result<(), Self::Error> { - Ok(()) - } - - fn end(self) -> Result<Self::Ok, Self::Error> { - Ok(Category::Table) - } -} - -impl<E: ser::Error> ser::SerializeStruct for Categorize<E> { - type Ok = Category; - type Error = E; - - fn serialize_field<T: ?Sized>(&mut self, _: &'static str, _: &T) -> Result<(), Self::Error> - where - T: ser::Serialize, - { - Ok(()) - } - - fn end(self) -> Result<Self::Ok, Self::Error> { - Ok(Category::Table) - } -} diff --git a/vendor/toml-0.5.9/src/spanned.rs b/vendor/toml-0.5.9/src/spanned.rs deleted file mode 100644 index 9ee56ae6d..000000000 --- a/vendor/toml-0.5.9/src/spanned.rs +++ /dev/null @@ -1,168 +0,0 @@ -use serde::{de, ser}; -use std::borrow::Borrow; -use std::cmp::Ordering; -use std::fmt; -use std::hash::{Hash, Hasher}; - -pub(crate) const NAME: &str = "$__toml_private_Spanned"; -pub(crate) const START: &str = "$__toml_private_start"; -pub(crate) const END: &str = "$__toml_private_end"; -pub(crate) const VALUE: &str = "$__toml_private_value"; - -/// A spanned value, indicating the range at which it is defined in the source. -/// -/// ``` -/// use serde_derive::Deserialize; -/// use toml::Spanned; -/// -/// #[derive(Deserialize)] -/// struct Value { -/// s: Spanned<String>, -/// } -/// -/// fn main() { -/// let t = "s = \"value\"\n"; -/// -/// let u: Value = toml::from_str(t).unwrap(); -/// -/// assert_eq!(u.s.start(), 4); -/// assert_eq!(u.s.end(), 11); -/// assert_eq!(u.s.get_ref(), "value"); -/// assert_eq!(u.s.into_inner(), String::from("value")); -/// } -/// ``` -#[derive(Clone, Debug)] -pub struct Spanned<T> { - /// The start range. - start: usize, - /// The end range (exclusive). - end: usize, - /// The spanned value. - value: T, -} - -impl<T> Spanned<T> { - /// Access the start of the span of the contained value. - pub fn start(&self) -> usize { - self.start - } - - /// Access the end of the span of the contained value. - pub fn end(&self) -> usize { - self.end - } - - /// Get the span of the contained value. - pub fn span(&self) -> (usize, usize) { - (self.start, self.end) - } - - /// Consumes the spanned value and returns the contained value. - pub fn into_inner(self) -> T { - self.value - } - - /// Returns a reference to the contained value. - pub fn get_ref(&self) -> &T { - &self.value - } - - /// Returns a mutable reference to the contained value. - pub fn get_mut(&mut self) -> &mut T { - &mut self.value - } -} - -impl Borrow<str> for Spanned<String> { - fn borrow(&self) -> &str { - &self.get_ref() - } -} - -impl<T: PartialEq> PartialEq for Spanned<T> { - fn eq(&self, other: &Self) -> bool { - self.value.eq(&other.value) - } -} - -impl<T: Eq> Eq for Spanned<T> {} - -impl<T: Hash> Hash for Spanned<T> { - fn hash<H: Hasher>(&self, state: &mut H) { - self.value.hash(state); - } -} - -impl<T: PartialOrd> PartialOrd for Spanned<T> { - fn partial_cmp(&self, other: &Self) -> Option<Ordering> { - self.value.partial_cmp(&other.value) - } -} - -impl<T: Ord> Ord for Spanned<T> { - fn cmp(&self, other: &Self) -> Ordering { - self.value.cmp(&other.value) - } -} - -impl<'de, T> de::Deserialize<'de> for Spanned<T> -where - T: de::Deserialize<'de>, -{ - fn deserialize<D>(deserializer: D) -> Result<Spanned<T>, D::Error> - where - D: de::Deserializer<'de>, - { - struct SpannedVisitor<T>(::std::marker::PhantomData<T>); - - impl<'de, T> de::Visitor<'de> for SpannedVisitor<T> - where - T: de::Deserialize<'de>, - { - type Value = Spanned<T>; - - fn expecting(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result { - formatter.write_str("a TOML spanned") - } - - fn visit_map<V>(self, mut visitor: V) -> Result<Spanned<T>, V::Error> - where - V: de::MapAccess<'de>, - { - if visitor.next_key()? != Some(START) { - return Err(de::Error::custom("spanned start key not found")); - } - - let start: usize = visitor.next_value()?; - - if visitor.next_key()? != Some(END) { - return Err(de::Error::custom("spanned end key not found")); - } - - let end: usize = visitor.next_value()?; - - if visitor.next_key()? != Some(VALUE) { - return Err(de::Error::custom("spanned value key not found")); - } - - let value: T = visitor.next_value()?; - - Ok(Spanned { start, end, value }) - } - } - - let visitor = SpannedVisitor(::std::marker::PhantomData); - - static FIELDS: [&str; 3] = [START, END, VALUE]; - deserializer.deserialize_struct(NAME, &FIELDS, visitor) - } -} - -impl<T: ser::Serialize> ser::Serialize for Spanned<T> { - fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error> - where - S: ser::Serializer, - { - self.value.serialize(serializer) - } -} diff --git a/vendor/toml-0.5.9/src/tokens.rs b/vendor/toml-0.5.9/src/tokens.rs deleted file mode 100644 index c2422828e..000000000 --- a/vendor/toml-0.5.9/src/tokens.rs +++ /dev/null @@ -1,740 +0,0 @@ -use std::borrow::Cow; -use std::char; -use std::str; -use std::string; -use std::string::String as StdString; - -use self::Token::*; - -/// A span, designating a range of bytes where a token is located. -#[derive(Eq, PartialEq, Debug, Clone, Copy)] -pub struct Span { - /// The start of the range. - pub start: usize, - /// The end of the range (exclusive). - pub end: usize, -} - -impl From<Span> for (usize, usize) { - fn from(Span { start, end }: Span) -> (usize, usize) { - (start, end) - } -} - -#[derive(Eq, PartialEq, Debug)] -pub enum Token<'a> { - Whitespace(&'a str), - Newline, - Comment(&'a str), - - Equals, - Period, - Comma, - Colon, - Plus, - LeftBrace, - RightBrace, - LeftBracket, - RightBracket, - - Keylike(&'a str), - String { - src: &'a str, - val: Cow<'a, str>, - multiline: bool, - }, -} - -#[derive(Eq, PartialEq, Debug)] -pub enum Error { - InvalidCharInString(usize, char), - InvalidEscape(usize, char), - InvalidHexEscape(usize, char), - InvalidEscapeValue(usize, u32), - NewlineInString(usize), - Unexpected(usize, char), - UnterminatedString(usize), - NewlineInTableKey(usize), - MultilineStringKey(usize), - Wanted { - at: usize, - expected: &'static str, - found: &'static str, - }, -} - -#[derive(Clone)] -pub struct Tokenizer<'a> { - input: &'a str, - chars: CrlfFold<'a>, -} - -#[derive(Clone)] -struct CrlfFold<'a> { - chars: str::CharIndices<'a>, -} - -#[derive(Debug)] -enum MaybeString { - NotEscaped(usize), - Owned(string::String), -} - -impl<'a> Tokenizer<'a> { - pub fn new(input: &'a str) -> Tokenizer<'a> { - let mut t = Tokenizer { - input, - chars: CrlfFold { - chars: input.char_indices(), - }, - }; - // Eat utf-8 BOM - t.eatc('\u{feff}'); - t - } - - pub fn next(&mut self) -> Result<Option<(Span, Token<'a>)>, Error> { - let (start, token) = match self.one() { - Some((start, '\n')) => (start, Newline), - Some((start, ' ')) => (start, self.whitespace_token(start)), - Some((start, '\t')) => (start, self.whitespace_token(start)), - Some((start, '#')) => (start, self.comment_token(start)), - Some((start, '=')) => (start, Equals), - Some((start, '.')) => (start, Period), - Some((start, ',')) => (start, Comma), - Some((start, ':')) => (start, Colon), - Some((start, '+')) => (start, Plus), - Some((start, '{')) => (start, LeftBrace), - Some((start, '}')) => (start, RightBrace), - Some((start, '[')) => (start, LeftBracket), - Some((start, ']')) => (start, RightBracket), - Some((start, '\'')) => { - return self - .literal_string(start) - .map(|t| Some((self.step_span(start), t))) - } - Some((start, '"')) => { - return self - .basic_string(start) - .map(|t| Some((self.step_span(start), t))) - } - Some((start, ch)) if is_keylike(ch) => (start, self.keylike(start)), - - Some((start, ch)) => return Err(Error::Unexpected(start, ch)), - None => return Ok(None), - }; - - let span = self.step_span(start); - Ok(Some((span, token))) - } - - pub fn peek(&mut self) -> Result<Option<(Span, Token<'a>)>, Error> { - self.clone().next() - } - - pub fn eat(&mut self, expected: Token<'a>) -> Result<bool, Error> { - self.eat_spanned(expected).map(|s| s.is_some()) - } - - /// Eat a value, returning it's span if it was consumed. - pub fn eat_spanned(&mut self, expected: Token<'a>) -> Result<Option<Span>, Error> { - let span = match self.peek()? { - Some((span, ref found)) if expected == *found => span, - Some(_) => return Ok(None), - None => return Ok(None), - }; - - drop(self.next()); - Ok(Some(span)) - } - - pub fn expect(&mut self, expected: Token<'a>) -> Result<(), Error> { - // ignore span - let _ = self.expect_spanned(expected)?; - Ok(()) - } - - /// Expect the given token returning its span. - pub fn expect_spanned(&mut self, expected: Token<'a>) -> Result<Span, Error> { - let current = self.current(); - match self.next()? { - Some((span, found)) => { - if expected == found { - Ok(span) - } else { - Err(Error::Wanted { - at: current, - expected: expected.describe(), - found: found.describe(), - }) - } - } - None => Err(Error::Wanted { - at: self.input.len(), - expected: expected.describe(), - found: "eof", - }), - } - } - - pub fn table_key(&mut self) -> Result<(Span, Cow<'a, str>), Error> { - let current = self.current(); - match self.next()? { - Some((span, Token::Keylike(k))) => Ok((span, k.into())), - Some(( - span, - Token::String { - src, - val, - multiline, - }, - )) => { - let offset = self.substr_offset(src); - if multiline { - return Err(Error::MultilineStringKey(offset)); - } - match src.find('\n') { - None => Ok((span, val)), - Some(i) => Err(Error::NewlineInTableKey(offset + i)), - } - } - Some((_, other)) => Err(Error::Wanted { - at: current, - expected: "a table key", - found: other.describe(), - }), - None => Err(Error::Wanted { - at: self.input.len(), - expected: "a table key", - found: "eof", - }), - } - } - - pub fn eat_whitespace(&mut self) -> Result<(), Error> { - while self.eatc(' ') || self.eatc('\t') { - // ... - } - Ok(()) - } - - pub fn eat_comment(&mut self) -> Result<bool, Error> { - if !self.eatc('#') { - return Ok(false); - } - drop(self.comment_token(0)); - self.eat_newline_or_eof().map(|()| true) - } - - pub fn eat_newline_or_eof(&mut self) -> Result<(), Error> { - let current = self.current(); - match self.next()? { - None | Some((_, Token::Newline)) => Ok(()), - Some((_, other)) => Err(Error::Wanted { - at: current, - expected: "newline", - found: other.describe(), - }), - } - } - - pub fn skip_to_newline(&mut self) { - loop { - match self.one() { - Some((_, '\n')) | None => break, - _ => {} - } - } - } - - fn eatc(&mut self, ch: char) -> bool { - match self.chars.clone().next() { - Some((_, ch2)) if ch == ch2 => { - self.one(); - true - } - _ => false, - } - } - - pub fn current(&mut self) -> usize { - self.chars - .clone() - .next() - .map(|i| i.0) - .unwrap_or_else(|| self.input.len()) - } - - pub fn input(&self) -> &'a str { - self.input - } - - fn whitespace_token(&mut self, start: usize) -> Token<'a> { - while self.eatc(' ') || self.eatc('\t') { - // ... - } - Whitespace(&self.input[start..self.current()]) - } - - fn comment_token(&mut self, start: usize) -> Token<'a> { - while let Some((_, ch)) = self.chars.clone().next() { - if ch != '\t' && (ch < '\u{20}' || ch > '\u{10ffff}') { - break; - } - self.one(); - } - Comment(&self.input[start..self.current()]) - } - - fn read_string( - &mut self, - delim: char, - start: usize, - new_ch: &mut dyn FnMut( - &mut Tokenizer<'_>, - &mut MaybeString, - bool, - usize, - char, - ) -> Result<(), Error>, - ) -> Result<Token<'a>, Error> { - let mut multiline = false; - if self.eatc(delim) { - if self.eatc(delim) { - multiline = true; - } else { - return Ok(String { - src: &self.input[start..start + 2], - val: Cow::Borrowed(""), - multiline: false, - }); - } - } - let mut val = MaybeString::NotEscaped(self.current()); - let mut n = 0; - 'outer: loop { - n += 1; - match self.one() { - Some((i, '\n')) => { - if multiline { - if self.input.as_bytes()[i] == b'\r' { - val.to_owned(&self.input[..i]); - } - if n == 1 { - val = MaybeString::NotEscaped(self.current()); - } else { - val.push('\n'); - } - continue; - } else { - return Err(Error::NewlineInString(i)); - } - } - Some((mut i, ch)) if ch == delim => { - if multiline { - if !self.eatc(delim) { - val.push(delim); - continue 'outer; - } - if !self.eatc(delim) { - val.push(delim); - val.push(delim); - continue 'outer; - } - if self.eatc(delim) { - val.push(delim); - i += 1; - } - if self.eatc(delim) { - val.push(delim); - i += 1; - } - } - return Ok(String { - src: &self.input[start..self.current()], - val: val.into_cow(&self.input[..i]), - multiline, - }); - } - Some((i, c)) => new_ch(self, &mut val, multiline, i, c)?, - None => return Err(Error::UnterminatedString(start)), - } - } - } - - fn literal_string(&mut self, start: usize) -> Result<Token<'a>, Error> { - self.read_string('\'', start, &mut |_me, val, _multi, i, ch| { - if ch == '\u{09}' || ('\u{20}' <= ch && ch <= '\u{10ffff}' && ch != '\u{7f}') { - val.push(ch); - Ok(()) - } else { - Err(Error::InvalidCharInString(i, ch)) - } - }) - } - - fn basic_string(&mut self, start: usize) -> Result<Token<'a>, Error> { - self.read_string('"', start, &mut |me, val, multi, i, ch| match ch { - '\\' => { - val.to_owned(&me.input[..i]); - match me.chars.next() { - Some((_, '"')) => val.push('"'), - Some((_, '\\')) => val.push('\\'), - Some((_, 'b')) => val.push('\u{8}'), - Some((_, 'f')) => val.push('\u{c}'), - Some((_, 'n')) => val.push('\n'), - Some((_, 'r')) => val.push('\r'), - Some((_, 't')) => val.push('\t'), - Some((i, c @ 'u')) | Some((i, c @ 'U')) => { - let len = if c == 'u' { 4 } else { 8 }; - val.push(me.hex(start, i, len)?); - } - Some((i, c @ ' ')) | Some((i, c @ '\t')) | Some((i, c @ '\n')) if multi => { - if c != '\n' { - while let Some((_, ch)) = me.chars.clone().next() { - match ch { - ' ' | '\t' => { - me.chars.next(); - continue; - } - '\n' => { - me.chars.next(); - break; - } - _ => return Err(Error::InvalidEscape(i, c)), - } - } - } - while let Some((_, ch)) = me.chars.clone().next() { - match ch { - ' ' | '\t' | '\n' => { - me.chars.next(); - } - _ => break, - } - } - } - Some((i, c)) => return Err(Error::InvalidEscape(i, c)), - None => return Err(Error::UnterminatedString(start)), - } - Ok(()) - } - ch if ch == '\u{09}' || ('\u{20}' <= ch && ch <= '\u{10ffff}' && ch != '\u{7f}') => { - val.push(ch); - Ok(()) - } - _ => Err(Error::InvalidCharInString(i, ch)), - }) - } - - fn hex(&mut self, start: usize, i: usize, len: usize) -> Result<char, Error> { - let mut buf = StdString::with_capacity(len); - for _ in 0..len { - match self.one() { - Some((_, ch)) if ch as u32 <= 0x7F && ch.is_digit(16) => buf.push(ch), - Some((i, ch)) => return Err(Error::InvalidHexEscape(i, ch)), - None => return Err(Error::UnterminatedString(start)), - } - } - let val = u32::from_str_radix(&buf, 16).unwrap(); - match char::from_u32(val) { - Some(ch) => Ok(ch), - None => Err(Error::InvalidEscapeValue(i, val)), - } - } - - fn keylike(&mut self, start: usize) -> Token<'a> { - while let Some((_, ch)) = self.peek_one() { - if !is_keylike(ch) { - break; - } - self.one(); - } - Keylike(&self.input[start..self.current()]) - } - - pub fn substr_offset(&self, s: &'a str) -> usize { - assert!(s.len() <= self.input.len()); - let a = self.input.as_ptr() as usize; - let b = s.as_ptr() as usize; - assert!(a <= b); - b - a - } - - /// Calculate the span of a single character. - fn step_span(&mut self, start: usize) -> Span { - let end = self - .peek_one() - .map(|t| t.0) - .unwrap_or_else(|| self.input.len()); - Span { start, end } - } - - /// Peek one char without consuming it. - fn peek_one(&mut self) -> Option<(usize, char)> { - self.chars.clone().next() - } - - /// Take one char. - pub fn one(&mut self) -> Option<(usize, char)> { - self.chars.next() - } -} - -impl<'a> Iterator for CrlfFold<'a> { - type Item = (usize, char); - - fn next(&mut self) -> Option<(usize, char)> { - self.chars.next().map(|(i, c)| { - if c == '\r' { - let mut attempt = self.chars.clone(); - if let Some((_, '\n')) = attempt.next() { - self.chars = attempt; - return (i, '\n'); - } - } - (i, c) - }) - } -} - -impl MaybeString { - fn push(&mut self, ch: char) { - match *self { - MaybeString::NotEscaped(..) => {} - MaybeString::Owned(ref mut s) => s.push(ch), - } - } - - fn to_owned(&mut self, input: &str) { - match *self { - MaybeString::NotEscaped(start) => { - *self = MaybeString::Owned(input[start..].to_owned()); - } - MaybeString::Owned(..) => {} - } - } - - fn into_cow(self, input: &str) -> Cow<'_, str> { - match self { - MaybeString::NotEscaped(start) => Cow::Borrowed(&input[start..]), - MaybeString::Owned(s) => Cow::Owned(s), - } - } -} - -fn is_keylike(ch: char) -> bool { - ('A' <= ch && ch <= 'Z') - || ('a' <= ch && ch <= 'z') - || ('0' <= ch && ch <= '9') - || ch == '-' - || ch == '_' -} - -impl<'a> Token<'a> { - pub fn describe(&self) -> &'static str { - match *self { - Token::Keylike(_) => "an identifier", - Token::Equals => "an equals", - Token::Period => "a period", - Token::Comment(_) => "a comment", - Token::Newline => "a newline", - Token::Whitespace(_) => "whitespace", - Token::Comma => "a comma", - Token::RightBrace => "a right brace", - Token::LeftBrace => "a left brace", - Token::RightBracket => "a right bracket", - Token::LeftBracket => "a left bracket", - Token::String { multiline, .. } => { - if multiline { - "a multiline string" - } else { - "a string" - } - } - Token::Colon => "a colon", - Token::Plus => "a plus", - } - } -} - -#[cfg(test)] -mod tests { - use super::{Error, Token, Tokenizer}; - use std::borrow::Cow; - - fn err(input: &str, err: Error) { - let mut t = Tokenizer::new(input); - let token = t.next().unwrap_err(); - assert_eq!(token, err); - assert!(t.next().unwrap().is_none()); - } - - #[test] - fn literal_strings() { - fn t(input: &str, val: &str, multiline: bool) { - let mut t = Tokenizer::new(input); - let (_, token) = t.next().unwrap().unwrap(); - assert_eq!( - token, - Token::String { - src: input, - val: Cow::Borrowed(val), - multiline: multiline, - } - ); - assert!(t.next().unwrap().is_none()); - } - - t("''", "", false); - t("''''''", "", true); - t("'''\n'''", "", true); - t("'a'", "a", false); - t("'\"a'", "\"a", false); - t("''''a'''", "'a", true); - t("'''\n'a\n'''", "'a\n", true); - t("'''a\n'a\r\n'''", "a\n'a\n", true); - } - - #[test] - fn basic_strings() { - fn t(input: &str, val: &str, multiline: bool) { - let mut t = Tokenizer::new(input); - let (_, token) = t.next().unwrap().unwrap(); - assert_eq!( - token, - Token::String { - src: input, - val: Cow::Borrowed(val), - multiline: multiline, - } - ); - assert!(t.next().unwrap().is_none()); - } - - t(r#""""#, "", false); - t(r#""""""""#, "", true); - t(r#""a""#, "a", false); - t(r#""""a""""#, "a", true); - t(r#""\t""#, "\t", false); - t(r#""\u0000""#, "\0", false); - t(r#""\U00000000""#, "\0", false); - t(r#""\U000A0000""#, "\u{A0000}", false); - t(r#""\\t""#, "\\t", false); - t("\"\t\"", "\t", false); - t("\"\"\"\n\t\"\"\"", "\t", true); - t("\"\"\"\\\n\"\"\"", "", true); - t( - "\"\"\"\\\n \t \t \\\r\n \t \n \t \r\n\"\"\"", - "", - true, - ); - t(r#""\r""#, "\r", false); - t(r#""\n""#, "\n", false); - t(r#""\b""#, "\u{8}", false); - t(r#""a\fa""#, "a\u{c}a", false); - t(r#""\"a""#, "\"a", false); - t("\"\"\"\na\"\"\"", "a", true); - t("\"\"\"\n\"\"\"", "", true); - t(r#""""a\"""b""""#, "a\"\"\"b", true); - err(r#""\a"#, Error::InvalidEscape(2, 'a')); - err("\"\\\n", Error::InvalidEscape(2, '\n')); - err("\"\\\r\n", Error::InvalidEscape(2, '\n')); - err("\"\\", Error::UnterminatedString(0)); - err("\"\u{0}", Error::InvalidCharInString(1, '\u{0}')); - err(r#""\U00""#, Error::InvalidHexEscape(5, '"')); - err(r#""\U00"#, Error::UnterminatedString(0)); - err(r#""\uD800"#, Error::InvalidEscapeValue(2, 0xd800)); - err(r#""\UFFFFFFFF"#, Error::InvalidEscapeValue(2, 0xffff_ffff)); - } - - #[test] - fn keylike() { - fn t(input: &str) { - let mut t = Tokenizer::new(input); - let (_, token) = t.next().unwrap().unwrap(); - assert_eq!(token, Token::Keylike(input)); - assert!(t.next().unwrap().is_none()); - } - t("foo"); - t("0bar"); - t("bar0"); - t("1234"); - t("a-b"); - t("a_B"); - t("-_-"); - t("___"); - } - - #[test] - fn all() { - fn t(input: &str, expected: &[((usize, usize), Token<'_>, &str)]) { - let mut tokens = Tokenizer::new(input); - let mut actual: Vec<((usize, usize), Token<'_>, &str)> = Vec::new(); - while let Some((span, token)) = tokens.next().unwrap() { - actual.push((span.into(), token, &input[span.start..span.end])); - } - for (a, b) in actual.iter().zip(expected) { - assert_eq!(a, b); - } - assert_eq!(actual.len(), expected.len()); - } - - t( - " a ", - &[ - ((0, 1), Token::Whitespace(" "), " "), - ((1, 2), Token::Keylike("a"), "a"), - ((2, 3), Token::Whitespace(" "), " "), - ], - ); - - t( - " a\t [[]] \t [] {} , . =\n# foo \r\n#foo \n ", - &[ - ((0, 1), Token::Whitespace(" "), " "), - ((1, 2), Token::Keylike("a"), "a"), - ((2, 4), Token::Whitespace("\t "), "\t "), - ((4, 5), Token::LeftBracket, "["), - ((5, 6), Token::LeftBracket, "["), - ((6, 7), Token::RightBracket, "]"), - ((7, 8), Token::RightBracket, "]"), - ((8, 11), Token::Whitespace(" \t "), " \t "), - ((11, 12), Token::LeftBracket, "["), - ((12, 13), Token::RightBracket, "]"), - ((13, 14), Token::Whitespace(" "), " "), - ((14, 15), Token::LeftBrace, "{"), - ((15, 16), Token::RightBrace, "}"), - ((16, 17), Token::Whitespace(" "), " "), - ((17, 18), Token::Comma, ","), - ((18, 19), Token::Whitespace(" "), " "), - ((19, 20), Token::Period, "."), - ((20, 21), Token::Whitespace(" "), " "), - ((21, 22), Token::Equals, "="), - ((22, 23), Token::Newline, "\n"), - ((23, 29), Token::Comment("# foo "), "# foo "), - ((29, 31), Token::Newline, "\r\n"), - ((31, 36), Token::Comment("#foo "), "#foo "), - ((36, 37), Token::Newline, "\n"), - ((37, 38), Token::Whitespace(" "), " "), - ], - ); - } - - #[test] - fn bare_cr_bad() { - err("\r", Error::Unexpected(0, '\r')); - err("'\n", Error::NewlineInString(1)); - err("'\u{0}", Error::InvalidCharInString(1, '\u{0}')); - err("'", Error::UnterminatedString(0)); - err("\u{0}", Error::Unexpected(0, '\u{0}')); - } - - #[test] - fn bad_comment() { - let mut t = Tokenizer::new("#\u{0}"); - t.next().unwrap().unwrap(); - assert_eq!(t.next(), Err(Error::Unexpected(1, '\u{0}'))); - assert!(t.next().unwrap().is_none()); - } -} diff --git a/vendor/toml-0.5.9/src/value.rs b/vendor/toml-0.5.9/src/value.rs deleted file mode 100644 index 1a1756d10..000000000 --- a/vendor/toml-0.5.9/src/value.rs +++ /dev/null @@ -1,1081 +0,0 @@ -//! Definition of a TOML value - -use std::collections::{BTreeMap, HashMap}; -use std::fmt; -use std::hash::Hash; -use std::mem::discriminant; -use std::ops; -use std::str::FromStr; -use std::vec; - -use serde::de; -use serde::de::IntoDeserializer; -use serde::ser; - -use crate::datetime::{self, DatetimeFromString}; -pub use crate::datetime::{Date, Datetime, DatetimeParseError, Offset, Time}; - -pub use crate::map::{Entry, Map}; - -/// Representation of a TOML value. -#[derive(PartialEq, Clone, Debug)] -pub enum Value { - /// Represents a TOML string - String(String), - /// Represents a TOML integer - Integer(i64), - /// Represents a TOML float - Float(f64), - /// Represents a TOML boolean - Boolean(bool), - /// Represents a TOML datetime - Datetime(Datetime), - /// Represents a TOML array - Array(Array), - /// Represents a TOML table - Table(Table), -} - -/// Type representing a TOML array, payload of the `Value::Array` variant -pub type Array = Vec<Value>; - -/// Type representing a TOML table, payload of the `Value::Table` variant. -/// By default it is backed by a BTreeMap, enable the `preserve_order` feature -/// to use a LinkedHashMap instead. -pub type Table = Map<String, Value>; - -impl Value { - /// Convert a `T` into `toml::Value` which is an enum that can represent - /// any valid TOML data. - /// - /// This conversion can fail if `T`'s implementation of `Serialize` decides to - /// fail, or if `T` contains a map with non-string keys. - pub fn try_from<T>(value: T) -> Result<Value, crate::ser::Error> - where - T: ser::Serialize, - { - value.serialize(Serializer) - } - - /// Interpret a `toml::Value` as an instance of type `T`. - /// - /// This conversion can fail if the structure of the `Value` does not match the - /// structure expected by `T`, for example if `T` is a struct type but the - /// `Value` contains something other than a TOML table. It can also fail if the - /// structure is correct but `T`'s implementation of `Deserialize` decides that - /// something is wrong with the data, for example required struct fields are - /// missing from the TOML map or some number is too big to fit in the expected - /// primitive type. - pub fn try_into<'de, T>(self) -> Result<T, crate::de::Error> - where - T: de::Deserialize<'de>, - { - de::Deserialize::deserialize(self) - } - - /// Index into a TOML array or map. A string index can be used to access a - /// value in a map, and a usize index can be used to access an element of an - /// array. - /// - /// Returns `None` if the type of `self` does not match the type of the - /// index, for example if the index is a string and `self` is an array or a - /// number. Also returns `None` if the given key does not exist in the map - /// or the given index is not within the bounds of the array. - pub fn get<I: Index>(&self, index: I) -> Option<&Value> { - index.index(self) - } - - /// Mutably index into a TOML array or map. A string index can be used to - /// access a value in a map, and a usize index can be used to access an - /// element of an array. - /// - /// Returns `None` if the type of `self` does not match the type of the - /// index, for example if the index is a string and `self` is an array or a - /// number. Also returns `None` if the given key does not exist in the map - /// or the given index is not within the bounds of the array. - pub fn get_mut<I: Index>(&mut self, index: I) -> Option<&mut Value> { - index.index_mut(self) - } - - /// Extracts the integer value if it is an integer. - pub fn as_integer(&self) -> Option<i64> { - match *self { - Value::Integer(i) => Some(i), - _ => None, - } - } - - /// Tests whether this value is an integer. - pub fn is_integer(&self) -> bool { - self.as_integer().is_some() - } - - /// Extracts the float value if it is a float. - pub fn as_float(&self) -> Option<f64> { - match *self { - Value::Float(f) => Some(f), - _ => None, - } - } - - /// Tests whether this value is a float. - pub fn is_float(&self) -> bool { - self.as_float().is_some() - } - - /// Extracts the boolean value if it is a boolean. - pub fn as_bool(&self) -> Option<bool> { - match *self { - Value::Boolean(b) => Some(b), - _ => None, - } - } - - /// Tests whether this value is a boolean. - pub fn is_bool(&self) -> bool { - self.as_bool().is_some() - } - - /// Extracts the string of this value if it is a string. - pub fn as_str(&self) -> Option<&str> { - match *self { - Value::String(ref s) => Some(&**s), - _ => None, - } - } - - /// Tests if this value is a string. - pub fn is_str(&self) -> bool { - self.as_str().is_some() - } - - /// Extracts the datetime value if it is a datetime. - /// - /// Note that a parsed TOML value will only contain ISO 8601 dates. An - /// example date is: - /// - /// ```notrust - /// 1979-05-27T07:32:00Z - /// ``` - pub fn as_datetime(&self) -> Option<&Datetime> { - match *self { - Value::Datetime(ref s) => Some(s), - _ => None, - } - } - - /// Tests whether this value is a datetime. - pub fn is_datetime(&self) -> bool { - self.as_datetime().is_some() - } - - /// Extracts the array value if it is an array. - pub fn as_array(&self) -> Option<&Vec<Value>> { - match *self { - Value::Array(ref s) => Some(s), - _ => None, - } - } - - /// Extracts the array value if it is an array. - pub fn as_array_mut(&mut self) -> Option<&mut Vec<Value>> { - match *self { - Value::Array(ref mut s) => Some(s), - _ => None, - } - } - - /// Tests whether this value is an array. - pub fn is_array(&self) -> bool { - self.as_array().is_some() - } - - /// Extracts the table value if it is a table. - pub fn as_table(&self) -> Option<&Table> { - match *self { - Value::Table(ref s) => Some(s), - _ => None, - } - } - - /// Extracts the table value if it is a table. - pub fn as_table_mut(&mut self) -> Option<&mut Table> { - match *self { - Value::Table(ref mut s) => Some(s), - _ => None, - } - } - - /// Tests whether this value is a table. - pub fn is_table(&self) -> bool { - self.as_table().is_some() - } - - /// Tests whether this and another value have the same type. - pub fn same_type(&self, other: &Value) -> bool { - discriminant(self) == discriminant(other) - } - - /// Returns a human-readable representation of the type of this value. - pub fn type_str(&self) -> &'static str { - match *self { - Value::String(..) => "string", - Value::Integer(..) => "integer", - Value::Float(..) => "float", - Value::Boolean(..) => "boolean", - Value::Datetime(..) => "datetime", - Value::Array(..) => "array", - Value::Table(..) => "table", - } - } -} - -impl<I> ops::Index<I> for Value -where - I: Index, -{ - type Output = Value; - - fn index(&self, index: I) -> &Value { - self.get(index).expect("index not found") - } -} - -impl<I> ops::IndexMut<I> for Value -where - I: Index, -{ - fn index_mut(&mut self, index: I) -> &mut Value { - self.get_mut(index).expect("index not found") - } -} - -impl<'a> From<&'a str> for Value { - #[inline] - fn from(val: &'a str) -> Value { - Value::String(val.to_string()) - } -} - -impl<V: Into<Value>> From<Vec<V>> for Value { - fn from(val: Vec<V>) -> Value { - Value::Array(val.into_iter().map(|v| v.into()).collect()) - } -} - -impl<S: Into<String>, V: Into<Value>> From<BTreeMap<S, V>> for Value { - fn from(val: BTreeMap<S, V>) -> Value { - let table = val.into_iter().map(|(s, v)| (s.into(), v.into())).collect(); - - Value::Table(table) - } -} - -impl<S: Into<String> + Hash + Eq, V: Into<Value>> From<HashMap<S, V>> for Value { - fn from(val: HashMap<S, V>) -> Value { - let table = val.into_iter().map(|(s, v)| (s.into(), v.into())).collect(); - - Value::Table(table) - } -} - -macro_rules! impl_into_value { - ($variant:ident : $T:ty) => { - impl From<$T> for Value { - #[inline] - fn from(val: $T) -> Value { - Value::$variant(val.into()) - } - } - }; -} - -impl_into_value!(String: String); -impl_into_value!(Integer: i64); -impl_into_value!(Integer: i32); -impl_into_value!(Integer: i8); -impl_into_value!(Integer: u8); -impl_into_value!(Integer: u32); -impl_into_value!(Float: f64); -impl_into_value!(Float: f32); -impl_into_value!(Boolean: bool); -impl_into_value!(Datetime: Datetime); -impl_into_value!(Table: Table); - -/// Types that can be used to index a `toml::Value` -/// -/// Currently this is implemented for `usize` to index arrays and `str` to index -/// tables. -/// -/// This trait is sealed and not intended for implementation outside of the -/// `toml` crate. -pub trait Index: Sealed { - #[doc(hidden)] - fn index<'a>(&self, val: &'a Value) -> Option<&'a Value>; - #[doc(hidden)] - fn index_mut<'a>(&self, val: &'a mut Value) -> Option<&'a mut Value>; -} - -/// An implementation detail that should not be implemented, this will change in -/// the future and break code otherwise. -#[doc(hidden)] -pub trait Sealed {} -impl Sealed for usize {} -impl Sealed for str {} -impl Sealed for String {} -impl<'a, T: Sealed + ?Sized> Sealed for &'a T {} - -impl Index for usize { - fn index<'a>(&self, val: &'a Value) -> Option<&'a Value> { - match *val { - Value::Array(ref a) => a.get(*self), - _ => None, - } - } - - fn index_mut<'a>(&self, val: &'a mut Value) -> Option<&'a mut Value> { - match *val { - Value::Array(ref mut a) => a.get_mut(*self), - _ => None, - } - } -} - -impl Index for str { - fn index<'a>(&self, val: &'a Value) -> Option<&'a Value> { - match *val { - Value::Table(ref a) => a.get(self), - _ => None, - } - } - - fn index_mut<'a>(&self, val: &'a mut Value) -> Option<&'a mut Value> { - match *val { - Value::Table(ref mut a) => a.get_mut(self), - _ => None, - } - } -} - -impl Index for String { - fn index<'a>(&self, val: &'a Value) -> Option<&'a Value> { - self[..].index(val) - } - - fn index_mut<'a>(&self, val: &'a mut Value) -> Option<&'a mut Value> { - self[..].index_mut(val) - } -} - -impl<'s, T: ?Sized> Index for &'s T -where - T: Index, -{ - fn index<'a>(&self, val: &'a Value) -> Option<&'a Value> { - (**self).index(val) - } - - fn index_mut<'a>(&self, val: &'a mut Value) -> Option<&'a mut Value> { - (**self).index_mut(val) - } -} - -impl fmt::Display for Value { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { - crate::ser::to_string(self) - .expect("Unable to represent value as string") - .fmt(f) - } -} - -impl FromStr for Value { - type Err = crate::de::Error; - fn from_str(s: &str) -> Result<Value, Self::Err> { - crate::from_str(s) - } -} - -impl ser::Serialize for Value { - fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error> - where - S: ser::Serializer, - { - use serde::ser::SerializeMap; - - match *self { - Value::String(ref s) => serializer.serialize_str(s), - Value::Integer(i) => serializer.serialize_i64(i), - Value::Float(f) => serializer.serialize_f64(f), - Value::Boolean(b) => serializer.serialize_bool(b), - Value::Datetime(ref s) => s.serialize(serializer), - Value::Array(ref a) => a.serialize(serializer), - Value::Table(ref t) => { - let mut map = serializer.serialize_map(Some(t.len()))?; - // Be sure to visit non-tables first (and also non - // array-of-tables) as all keys must be emitted first. - for (k, v) in t { - if !v.is_table() && !v.is_array() - || (v - .as_array() - .map(|a| !a.iter().any(|v| v.is_table())) - .unwrap_or(false)) - { - map.serialize_entry(k, v)?; - } - } - for (k, v) in t { - if v.as_array() - .map(|a| a.iter().any(|v| v.is_table())) - .unwrap_or(false) - { - map.serialize_entry(k, v)?; - } - } - for (k, v) in t { - if v.is_table() { - map.serialize_entry(k, v)?; - } - } - map.end() - } - } - } -} - -impl<'de> de::Deserialize<'de> for Value { - fn deserialize<D>(deserializer: D) -> Result<Value, D::Error> - where - D: de::Deserializer<'de>, - { - struct ValueVisitor; - - impl<'de> de::Visitor<'de> for ValueVisitor { - type Value = Value; - - fn expecting(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result { - formatter.write_str("any valid TOML value") - } - - fn visit_bool<E>(self, value: bool) -> Result<Value, E> { - Ok(Value::Boolean(value)) - } - - fn visit_i64<E>(self, value: i64) -> Result<Value, E> { - Ok(Value::Integer(value)) - } - - fn visit_u64<E: de::Error>(self, value: u64) -> Result<Value, E> { - if value <= i64::max_value() as u64 { - Ok(Value::Integer(value as i64)) - } else { - Err(de::Error::custom("u64 value was too large")) - } - } - - fn visit_u32<E>(self, value: u32) -> Result<Value, E> { - Ok(Value::Integer(value.into())) - } - - fn visit_i32<E>(self, value: i32) -> Result<Value, E> { - Ok(Value::Integer(value.into())) - } - - fn visit_f64<E>(self, value: f64) -> Result<Value, E> { - Ok(Value::Float(value)) - } - - fn visit_str<E>(self, value: &str) -> Result<Value, E> { - Ok(Value::String(value.into())) - } - - fn visit_string<E>(self, value: String) -> Result<Value, E> { - Ok(Value::String(value)) - } - - fn visit_some<D>(self, deserializer: D) -> Result<Value, D::Error> - where - D: de::Deserializer<'de>, - { - de::Deserialize::deserialize(deserializer) - } - - fn visit_seq<V>(self, mut visitor: V) -> Result<Value, V::Error> - where - V: de::SeqAccess<'de>, - { - let mut vec = Vec::new(); - while let Some(elem) = visitor.next_element()? { - vec.push(elem); - } - Ok(Value::Array(vec)) - } - - fn visit_map<V>(self, mut visitor: V) -> Result<Value, V::Error> - where - V: de::MapAccess<'de>, - { - let mut key = String::new(); - let datetime = visitor.next_key_seed(DatetimeOrTable { key: &mut key })?; - match datetime { - Some(true) => { - let date: DatetimeFromString = visitor.next_value()?; - return Ok(Value::Datetime(date.value)); - } - None => return Ok(Value::Table(Map::new())), - Some(false) => {} - } - let mut map = Map::new(); - map.insert(key, visitor.next_value()?); - while let Some(key) = visitor.next_key::<String>()? { - if let Entry::Vacant(vacant) = map.entry(&key) { - vacant.insert(visitor.next_value()?); - } else { - let msg = format!("duplicate key: `{}`", key); - return Err(de::Error::custom(msg)); - } - } - Ok(Value::Table(map)) - } - } - - deserializer.deserialize_any(ValueVisitor) - } -} - -impl<'de> de::Deserializer<'de> for Value { - type Error = crate::de::Error; - - fn deserialize_any<V>(self, visitor: V) -> Result<V::Value, crate::de::Error> - where - V: de::Visitor<'de>, - { - match self { - Value::Boolean(v) => visitor.visit_bool(v), - Value::Integer(n) => visitor.visit_i64(n), - Value::Float(n) => visitor.visit_f64(n), - Value::String(v) => visitor.visit_string(v), - Value::Datetime(v) => visitor.visit_string(v.to_string()), - Value::Array(v) => { - let len = v.len(); - let mut deserializer = SeqDeserializer::new(v); - let seq = visitor.visit_seq(&mut deserializer)?; - let remaining = deserializer.iter.len(); - if remaining == 0 { - Ok(seq) - } else { - Err(de::Error::invalid_length(len, &"fewer elements in array")) - } - } - Value::Table(v) => { - let len = v.len(); - let mut deserializer = MapDeserializer::new(v); - let map = visitor.visit_map(&mut deserializer)?; - let remaining = deserializer.iter.len(); - if remaining == 0 { - Ok(map) - } else { - Err(de::Error::invalid_length(len, &"fewer elements in map")) - } - } - } - } - - #[inline] - fn deserialize_enum<V>( - self, - _name: &str, - _variants: &'static [&'static str], - visitor: V, - ) -> Result<V::Value, crate::de::Error> - where - V: de::Visitor<'de>, - { - match self { - Value::String(variant) => visitor.visit_enum(variant.into_deserializer()), - _ => Err(de::Error::invalid_type( - de::Unexpected::UnitVariant, - &"string only", - )), - } - } - - // `None` is interpreted as a missing field so be sure to implement `Some` - // as a present field. - fn deserialize_option<V>(self, visitor: V) -> Result<V::Value, crate::de::Error> - where - V: de::Visitor<'de>, - { - visitor.visit_some(self) - } - - fn deserialize_newtype_struct<V>( - self, - _name: &'static str, - visitor: V, - ) -> Result<V::Value, crate::de::Error> - where - V: de::Visitor<'de>, - { - visitor.visit_newtype_struct(self) - } - - serde::forward_to_deserialize_any! { - bool u8 u16 u32 u64 i8 i16 i32 i64 f32 f64 char str string unit seq - bytes byte_buf map unit_struct tuple_struct struct - tuple ignored_any identifier - } -} - -struct SeqDeserializer { - iter: vec::IntoIter<Value>, -} - -impl SeqDeserializer { - fn new(vec: Vec<Value>) -> Self { - SeqDeserializer { - iter: vec.into_iter(), - } - } -} - -impl<'de> de::SeqAccess<'de> for SeqDeserializer { - type Error = crate::de::Error; - - fn next_element_seed<T>(&mut self, seed: T) -> Result<Option<T::Value>, crate::de::Error> - where - T: de::DeserializeSeed<'de>, - { - match self.iter.next() { - Some(value) => seed.deserialize(value).map(Some), - None => Ok(None), - } - } - - fn size_hint(&self) -> Option<usize> { - match self.iter.size_hint() { - (lower, Some(upper)) if lower == upper => Some(upper), - _ => None, - } - } -} - -struct MapDeserializer { - iter: <Map<String, Value> as IntoIterator>::IntoIter, - value: Option<(String, Value)>, -} - -impl MapDeserializer { - fn new(map: Map<String, Value>) -> Self { - MapDeserializer { - iter: map.into_iter(), - value: None, - } - } -} - -impl<'de> de::MapAccess<'de> for MapDeserializer { - type Error = crate::de::Error; - - fn next_key_seed<T>(&mut self, seed: T) -> Result<Option<T::Value>, crate::de::Error> - where - T: de::DeserializeSeed<'de>, - { - match self.iter.next() { - Some((key, value)) => { - self.value = Some((key.clone(), value)); - seed.deserialize(Value::String(key)).map(Some) - } - None => Ok(None), - } - } - - fn next_value_seed<T>(&mut self, seed: T) -> Result<T::Value, crate::de::Error> - where - T: de::DeserializeSeed<'de>, - { - let (key, res) = match self.value.take() { - Some((key, value)) => (key, seed.deserialize(value)), - None => return Err(de::Error::custom("value is missing")), - }; - res.map_err(|mut error| { - error.add_key_context(&key); - error - }) - } - - fn size_hint(&self) -> Option<usize> { - match self.iter.size_hint() { - (lower, Some(upper)) if lower == upper => Some(upper), - _ => None, - } - } -} - -impl<'de> de::IntoDeserializer<'de, crate::de::Error> for Value { - type Deserializer = Self; - - fn into_deserializer(self) -> Self { - self - } -} - -struct Serializer; - -impl ser::Serializer for Serializer { - type Ok = Value; - type Error = crate::ser::Error; - - type SerializeSeq = SerializeVec; - type SerializeTuple = SerializeVec; - type SerializeTupleStruct = SerializeVec; - type SerializeTupleVariant = SerializeVec; - type SerializeMap = SerializeMap; - type SerializeStruct = SerializeMap; - type SerializeStructVariant = ser::Impossible<Value, crate::ser::Error>; - - fn serialize_bool(self, value: bool) -> Result<Value, crate::ser::Error> { - Ok(Value::Boolean(value)) - } - - fn serialize_i8(self, value: i8) -> Result<Value, crate::ser::Error> { - self.serialize_i64(value.into()) - } - - fn serialize_i16(self, value: i16) -> Result<Value, crate::ser::Error> { - self.serialize_i64(value.into()) - } - - fn serialize_i32(self, value: i32) -> Result<Value, crate::ser::Error> { - self.serialize_i64(value.into()) - } - - fn serialize_i64(self, value: i64) -> Result<Value, crate::ser::Error> { - Ok(Value::Integer(value)) - } - - fn serialize_u8(self, value: u8) -> Result<Value, crate::ser::Error> { - self.serialize_i64(value.into()) - } - - fn serialize_u16(self, value: u16) -> Result<Value, crate::ser::Error> { - self.serialize_i64(value.into()) - } - - fn serialize_u32(self, value: u32) -> Result<Value, crate::ser::Error> { - self.serialize_i64(value.into()) - } - - fn serialize_u64(self, value: u64) -> Result<Value, crate::ser::Error> { - if value <= i64::max_value() as u64 { - self.serialize_i64(value as i64) - } else { - Err(ser::Error::custom("u64 value was too large")) - } - } - - fn serialize_f32(self, value: f32) -> Result<Value, crate::ser::Error> { - self.serialize_f64(value.into()) - } - - fn serialize_f64(self, value: f64) -> Result<Value, crate::ser::Error> { - Ok(Value::Float(value)) - } - - fn serialize_char(self, value: char) -> Result<Value, crate::ser::Error> { - let mut s = String::new(); - s.push(value); - self.serialize_str(&s) - } - - fn serialize_str(self, value: &str) -> Result<Value, crate::ser::Error> { - Ok(Value::String(value.to_owned())) - } - - fn serialize_bytes(self, value: &[u8]) -> Result<Value, crate::ser::Error> { - let vec = value.iter().map(|&b| Value::Integer(b.into())).collect(); - Ok(Value::Array(vec)) - } - - fn serialize_unit(self) -> Result<Value, crate::ser::Error> { - Err(crate::ser::Error::UnsupportedType) - } - - fn serialize_unit_struct(self, _name: &'static str) -> Result<Value, crate::ser::Error> { - Err(crate::ser::Error::UnsupportedType) - } - - fn serialize_unit_variant( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - ) -> Result<Value, crate::ser::Error> { - self.serialize_str(_variant) - } - - fn serialize_newtype_struct<T: ?Sized>( - self, - _name: &'static str, - value: &T, - ) -> Result<Value, crate::ser::Error> - where - T: ser::Serialize, - { - value.serialize(self) - } - - fn serialize_newtype_variant<T: ?Sized>( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - _value: &T, - ) -> Result<Value, crate::ser::Error> - where - T: ser::Serialize, - { - Err(crate::ser::Error::UnsupportedType) - } - - fn serialize_none(self) -> Result<Value, crate::ser::Error> { - Err(crate::ser::Error::UnsupportedNone) - } - - fn serialize_some<T: ?Sized>(self, value: &T) -> Result<Value, crate::ser::Error> - where - T: ser::Serialize, - { - value.serialize(self) - } - - fn serialize_seq(self, len: Option<usize>) -> Result<Self::SerializeSeq, crate::ser::Error> { - Ok(SerializeVec { - vec: Vec::with_capacity(len.unwrap_or(0)), - }) - } - - fn serialize_tuple(self, len: usize) -> Result<Self::SerializeTuple, crate::ser::Error> { - self.serialize_seq(Some(len)) - } - - fn serialize_tuple_struct( - self, - _name: &'static str, - len: usize, - ) -> Result<Self::SerializeTupleStruct, crate::ser::Error> { - self.serialize_seq(Some(len)) - } - - fn serialize_tuple_variant( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - len: usize, - ) -> Result<Self::SerializeTupleVariant, crate::ser::Error> { - self.serialize_seq(Some(len)) - } - - fn serialize_map(self, _len: Option<usize>) -> Result<Self::SerializeMap, crate::ser::Error> { - Ok(SerializeMap { - map: Map::new(), - next_key: None, - }) - } - - fn serialize_struct( - self, - _name: &'static str, - len: usize, - ) -> Result<Self::SerializeStruct, crate::ser::Error> { - self.serialize_map(Some(len)) - } - - fn serialize_struct_variant( - self, - _name: &'static str, - _variant_index: u32, - _variant: &'static str, - _len: usize, - ) -> Result<Self::SerializeStructVariant, crate::ser::Error> { - Err(crate::ser::Error::UnsupportedType) - } -} - -struct SerializeVec { - vec: Vec<Value>, -} - -struct SerializeMap { - map: Map<String, Value>, - next_key: Option<String>, -} - -impl ser::SerializeSeq for SerializeVec { - type Ok = Value; - type Error = crate::ser::Error; - - fn serialize_element<T: ?Sized>(&mut self, value: &T) -> Result<(), crate::ser::Error> - where - T: ser::Serialize, - { - self.vec.push(Value::try_from(value)?); - Ok(()) - } - - fn end(self) -> Result<Value, crate::ser::Error> { - Ok(Value::Array(self.vec)) - } -} - -impl ser::SerializeTuple for SerializeVec { - type Ok = Value; - type Error = crate::ser::Error; - - fn serialize_element<T: ?Sized>(&mut self, value: &T) -> Result<(), crate::ser::Error> - where - T: ser::Serialize, - { - ser::SerializeSeq::serialize_element(self, value) - } - - fn end(self) -> Result<Value, crate::ser::Error> { - ser::SerializeSeq::end(self) - } -} - -impl ser::SerializeTupleStruct for SerializeVec { - type Ok = Value; - type Error = crate::ser::Error; - - fn serialize_field<T: ?Sized>(&mut self, value: &T) -> Result<(), crate::ser::Error> - where - T: ser::Serialize, - { - ser::SerializeSeq::serialize_element(self, value) - } - - fn end(self) -> Result<Value, crate::ser::Error> { - ser::SerializeSeq::end(self) - } -} - -impl ser::SerializeTupleVariant for SerializeVec { - type Ok = Value; - type Error = crate::ser::Error; - - fn serialize_field<T: ?Sized>(&mut self, value: &T) -> Result<(), crate::ser::Error> - where - T: ser::Serialize, - { - ser::SerializeSeq::serialize_element(self, value) - } - - fn end(self) -> Result<Value, crate::ser::Error> { - ser::SerializeSeq::end(self) - } -} - -impl ser::SerializeMap for SerializeMap { - type Ok = Value; - type Error = crate::ser::Error; - - fn serialize_key<T: ?Sized>(&mut self, key: &T) -> Result<(), crate::ser::Error> - where - T: ser::Serialize, - { - match Value::try_from(key)? { - Value::String(s) => self.next_key = Some(s), - _ => return Err(crate::ser::Error::KeyNotString), - }; - Ok(()) - } - - fn serialize_value<T: ?Sized>(&mut self, value: &T) -> Result<(), crate::ser::Error> - where - T: ser::Serialize, - { - let key = self.next_key.take(); - let key = key.expect("serialize_value called before serialize_key"); - match Value::try_from(value) { - Ok(value) => { - self.map.insert(key, value); - } - Err(crate::ser::Error::UnsupportedNone) => {} - Err(e) => return Err(e), - } - Ok(()) - } - - fn end(self) -> Result<Value, crate::ser::Error> { - Ok(Value::Table(self.map)) - } -} - -impl ser::SerializeStruct for SerializeMap { - type Ok = Value; - type Error = crate::ser::Error; - - fn serialize_field<T: ?Sized>( - &mut self, - key: &'static str, - value: &T, - ) -> Result<(), crate::ser::Error> - where - T: ser::Serialize, - { - ser::SerializeMap::serialize_key(self, key)?; - ser::SerializeMap::serialize_value(self, value) - } - - fn end(self) -> Result<Value, crate::ser::Error> { - ser::SerializeMap::end(self) - } -} - -struct DatetimeOrTable<'a> { - key: &'a mut String, -} - -impl<'a, 'de> de::DeserializeSeed<'de> for DatetimeOrTable<'a> { - type Value = bool; - - fn deserialize<D>(self, deserializer: D) -> Result<Self::Value, D::Error> - where - D: de::Deserializer<'de>, - { - deserializer.deserialize_any(self) - } -} - -impl<'a, 'de> de::Visitor<'de> for DatetimeOrTable<'a> { - type Value = bool; - - fn expecting(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result { - formatter.write_str("a string key") - } - - fn visit_str<E>(self, s: &str) -> Result<bool, E> - where - E: de::Error, - { - if s == datetime::FIELD { - Ok(true) - } else { - self.key.push_str(s); - Ok(false) - } - } - - fn visit_string<E>(self, s: String) -> Result<bool, E> - where - E: de::Error, - { - if s == datetime::FIELD { - Ok(true) - } else { - *self.key = s; - Ok(false) - } - } -} |