time/format_description/
owned_format_item.rs1use alloc::boxed::Box;
4use alloc::string::String;
5use alloc::vec::Vec;
6use core::fmt;
7
8use crate::error;
9use crate::format_description::{BorrowedFormatItem, Component};
10
11#[non_exhaustive]
13#[derive(Clone, Eq)]
14pub enum OwnedFormatItem {
15 #[deprecated(
20 since = "0.3.48",
21 note = "use `StringLiteral` instead; raw bytes are not recommended"
22 )]
23 Literal(Box<[u8]>),
24 StringLiteral(Box<str>),
26 Component(Component),
28 Compound(Box<[Self]>),
31 Optional(Box<Self>),
36 First(Box<[Self]>),
40}
41
42impl fmt::Debug for OwnedFormatItem {
43 #[inline]
44 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
45 match self {
46 #[expect(deprecated)]
47 Self::Literal(literal) => f.write_str(&String::from_utf8_lossy(literal)),
48 Self::StringLiteral(literal) => f.write_str(literal),
49 Self::Component(component) => component.fmt(f),
50 Self::Compound(compound) => compound.fmt(f),
51 Self::Optional(item) => f.debug_tuple("Optional").field(item).finish(),
52 Self::First(items) => f.debug_tuple("First").field(items).finish(),
53 }
54 }
55}
56
57impl PartialEq for OwnedFormatItem {
58 fn eq(&self, other: &Self) -> bool {
59 match (self, other) {
60 #[expect(deprecated)]
62 (Self::Literal(a), Self::Literal(b)) => a == b,
63 (Self::StringLiteral(a), Self::StringLiteral(b)) => a == b,
64 (Self::Component(a), Self::Component(b)) => a == b,
65 (Self::Compound(a), Self::Compound(b)) => a == b,
66 (Self::Optional(a), Self::Optional(b)) => a == b,
67 (Self::First(a), Self::First(b)) => a == b,
68 #[expect(deprecated)]
70 (Self::Literal(a), Self::StringLiteral(b)) => &**a == b.as_bytes(),
71 #[expect(deprecated)]
72 (Self::StringLiteral(a), Self::Literal(b)) => a.as_bytes() == &**b,
73 _ => false,
74 }
75 }
76}
77
78impl From<BorrowedFormatItem<'_>> for OwnedFormatItem {
79 #[inline]
80 fn from(item: BorrowedFormatItem<'_>) -> Self {
81 (&item).into()
82 }
83}
84
85impl From<&BorrowedFormatItem<'_>> for OwnedFormatItem {
86 #[inline]
87 fn from(item: &BorrowedFormatItem<'_>) -> Self {
88 match item {
89 #[expect(deprecated)]
90 BorrowedFormatItem::Literal(literal) => {
91 Self::Literal(literal.to_vec().into_boxed_slice())
92 }
93 BorrowedFormatItem::StringLiteral(literal) => {
94 use alloc::borrow::ToOwned as _;
95 Self::StringLiteral((*literal).to_owned().into_boxed_str())
96 }
97 BorrowedFormatItem::Component(component) => Self::Component(*component),
98 BorrowedFormatItem::Compound(compound) => {
99 Self::Compound(compound.iter().cloned().map(Into::into).collect())
100 }
101 BorrowedFormatItem::Optional(item) => Self::Optional(Box::new((*item).into())),
102 BorrowedFormatItem::First(items) => {
103 Self::First(items.iter().cloned().map(Into::into).collect())
104 }
105 }
106 }
107}
108
109impl From<Vec<BorrowedFormatItem<'_>>> for OwnedFormatItem {
110 #[inline]
111 fn from(items: Vec<BorrowedFormatItem<'_>>) -> Self {
112 items.as_slice().into()
113 }
114}
115
116impl<'a, T> From<&T> for OwnedFormatItem
117where
118 T: AsRef<[BorrowedFormatItem<'a>]> + ?Sized,
119{
120 #[inline]
121 fn from(items: &T) -> Self {
122 Self::Compound(items.as_ref().iter().cloned().map(Into::into).collect())
123 }
124}
125
126impl From<Component> for OwnedFormatItem {
127 #[inline]
128 fn from(component: Component) -> Self {
129 Self::Component(component)
130 }
131}
132
133impl TryFrom<OwnedFormatItem> for Component {
134 type Error = error::DifferentVariant;
135
136 #[inline]
137 fn try_from(value: OwnedFormatItem) -> Result<Self, Self::Error> {
138 match value {
139 OwnedFormatItem::Component(component) => Ok(component),
140 _ => Err(error::DifferentVariant),
141 }
142 }
143}
144
145impl From<Vec<Self>> for OwnedFormatItem {
146 #[inline]
147 fn from(items: Vec<Self>) -> Self {
148 Self::Compound(items.into_boxed_slice())
149 }
150}
151
152impl TryFrom<OwnedFormatItem> for Vec<OwnedFormatItem> {
153 type Error = error::DifferentVariant;
154
155 #[inline]
156 fn try_from(value: OwnedFormatItem) -> Result<Self, Self::Error> {
157 match value {
158 OwnedFormatItem::Compound(items) => Ok(items.into_vec()),
159 _ => Err(error::DifferentVariant),
160 }
161 }
162}
163
164impl PartialEq<Component> for OwnedFormatItem {
165 #[inline]
166 fn eq(&self, rhs: &Component) -> bool {
167 matches!(self, Self::Component(component) if component == rhs)
168 }
169}
170
171impl PartialEq<OwnedFormatItem> for Component {
172 #[inline]
173 fn eq(&self, rhs: &OwnedFormatItem) -> bool {
174 rhs == self
175 }
176}
177
178impl PartialEq<&[Self]> for OwnedFormatItem {
179 #[inline]
180 fn eq(&self, rhs: &&[Self]) -> bool {
181 matches!(self, Self::Compound(compound) if &&**compound == rhs)
182 }
183}
184
185impl PartialEq<OwnedFormatItem> for &[OwnedFormatItem] {
186 #[inline]
187 fn eq(&self, rhs: &OwnedFormatItem) -> bool {
188 rhs == self
189 }
190}