1 use std::borrow::Borrow;
2 use std::str::FromStr;
3 
4 /// Opaque string storage internal to `toml_edit`
5 #[derive(Default, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
6 pub struct InternalString(Inner);
7 
8 #[cfg(feature = "kstring")]
9 type Inner = kstring::KString;
10 #[cfg(not(feature = "kstring"))]
11 type Inner = String;
12 
13 impl InternalString {
14     /// Create an empty string
new() -> Self15     pub fn new() -> Self {
16         InternalString(Inner::new())
17     }
18 
19     /// Access the underlying string
20     #[inline]
as_str(&self) -> &str21     pub fn as_str(&self) -> &str {
22         self.0.as_str()
23     }
24 }
25 
26 impl std::fmt::Debug for InternalString {
27     #[inline]
fmt(&self, formatter: &mut std::fmt::Formatter<'_>) -> Result<(), std::fmt::Error>28     fn fmt(&self, formatter: &mut std::fmt::Formatter<'_>) -> Result<(), std::fmt::Error> {
29         self.0.fmt(formatter)
30     }
31 }
32 
33 impl std::ops::Deref for InternalString {
34     type Target = str;
35 
36     #[inline]
deref(&self) -> &str37     fn deref(&self) -> &str {
38         self.as_str()
39     }
40 }
41 
42 impl Borrow<str> for InternalString {
43     #[inline]
borrow(&self) -> &str44     fn borrow(&self) -> &str {
45         self.as_str()
46     }
47 }
48 
49 impl AsRef<str> for InternalString {
50     #[inline]
as_ref(&self) -> &str51     fn as_ref(&self) -> &str {
52         self.as_str()
53     }
54 }
55 
56 impl From<&str> for InternalString {
57     #[inline]
from(s: &str) -> Self58     fn from(s: &str) -> Self {
59         #[cfg(feature = "kstring")]
60         let inner = kstring::KString::from_ref(s);
61         #[cfg(not(feature = "kstring"))]
62         let inner = String::from(s);
63 
64         InternalString(inner)
65     }
66 }
67 
68 impl From<String> for InternalString {
69     #[inline]
from(s: String) -> Self70     fn from(s: String) -> Self {
71         #[allow(clippy::useless_conversion)] // handle any string type
72         InternalString(s.into())
73     }
74 }
75 
76 impl From<&String> for InternalString {
77     #[inline]
from(s: &String) -> Self78     fn from(s: &String) -> Self {
79         InternalString(s.into())
80     }
81 }
82 
83 impl From<&InternalString> for InternalString {
84     #[inline]
from(s: &InternalString) -> Self85     fn from(s: &InternalString) -> Self {
86         s.clone()
87     }
88 }
89 
90 impl From<Box<str>> for InternalString {
91     #[inline]
from(s: Box<str>) -> Self92     fn from(s: Box<str>) -> Self {
93         InternalString(s.into())
94     }
95 }
96 
97 impl FromStr for InternalString {
98     type Err = core::convert::Infallible;
99     #[inline]
from_str(s: &str) -> Result<Self, Self::Err>100     fn from_str(s: &str) -> Result<Self, Self::Err> {
101         Ok(Self::from(s))
102     }
103 }
104 
105 impl std::fmt::Display for InternalString {
106     #[inline]
fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result107     fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
108         self.as_str().fmt(f)
109     }
110 }
111 
112 #[cfg(feature = "serde")]
113 impl serde::Serialize for InternalString {
114     #[inline]
serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error> where S: serde::Serializer,115     fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
116     where
117         S: serde::Serializer,
118     {
119         serializer.serialize_str(self.as_str())
120     }
121 }
122 
123 #[cfg(feature = "serde")]
124 impl<'de> serde::Deserialize<'de> for InternalString {
deserialize<D>(deserializer: D) -> Result<Self, D::Error> where D: serde::Deserializer<'de>,125     fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
126     where
127         D: serde::Deserializer<'de>,
128     {
129         deserializer.deserialize_string(StringVisitor)
130     }
131 }
132 
133 #[cfg(feature = "serde")]
134 struct StringVisitor;
135 
136 #[cfg(feature = "serde")]
137 impl<'de> serde::de::Visitor<'de> for StringVisitor {
138     type Value = InternalString;
139 
expecting(&self, formatter: &mut std::fmt::Formatter<'_>) -> std::fmt::Result140     fn expecting(&self, formatter: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
141         formatter.write_str("a string")
142     }
143 
visit_str<E>(self, v: &str) -> Result<Self::Value, E> where E: serde::de::Error,144     fn visit_str<E>(self, v: &str) -> Result<Self::Value, E>
145     where
146         E: serde::de::Error,
147     {
148         Ok(InternalString::from(v))
149     }
150 
visit_string<E>(self, v: String) -> Result<Self::Value, E> where E: serde::de::Error,151     fn visit_string<E>(self, v: String) -> Result<Self::Value, E>
152     where
153         E: serde::de::Error,
154     {
155         Ok(InternalString::from(v))
156     }
157 
visit_bytes<E>(self, v: &[u8]) -> Result<Self::Value, E> where E: serde::de::Error,158     fn visit_bytes<E>(self, v: &[u8]) -> Result<Self::Value, E>
159     where
160         E: serde::de::Error,
161     {
162         match std::str::from_utf8(v) {
163             Ok(s) => Ok(InternalString::from(s)),
164             Err(_) => Err(serde::de::Error::invalid_value(
165                 serde::de::Unexpected::Bytes(v),
166                 &self,
167             )),
168         }
169     }
170 
visit_byte_buf<E>(self, v: Vec<u8>) -> Result<Self::Value, E> where E: serde::de::Error,171     fn visit_byte_buf<E>(self, v: Vec<u8>) -> Result<Self::Value, E>
172     where
173         E: serde::de::Error,
174     {
175         match String::from_utf8(v) {
176             Ok(s) => Ok(InternalString::from(s)),
177             Err(e) => Err(serde::de::Error::invalid_value(
178                 serde::de::Unexpected::Bytes(&e.into_bytes()),
179                 &self,
180             )),
181         }
182     }
183 }
184