sark_http/field/storage/
mod.rs1use std::{borrow::Cow, marker::PhantomData};
4
5use o3::{
6 alloc::{self, StrExt as _},
7 buffer::storage::Shared,
8};
9
10pub(in crate::field) mod encoded;
11mod lower;
12mod name;
13mod sealed;
14mod value;
15
16pub use lower::Lower;
17pub use name::Name;
18pub(crate) use sealed::Sealed;
19pub use value::Value;
20
21#[derive(Clone, Copy, Debug, PartialEq, Eq)]
23pub enum Error {
24 Syntax(crate::field::Error),
25 Allocation(alloc::Exhausted),
26}
27
28fn try_own(value: Cow<'_, str>) -> Result<String, alloc::Exhausted> {
29 match value {
30 Cow::Borrowed(value) => value.try_to_owned(),
31 Cow::Owned(value) => Ok(value),
32 }
33}
34
35pub trait Bytes: Sealed {
37 fn as_bytes(&self) -> &[u8];
38}
39
40pub trait Text: Bytes {
42 fn as_str(&self) -> &str;
43}
44
45pub trait Constant {
47 const VALUE: &'static str;
48}
49
50#[derive(Clone, Copy, Debug, Default, PartialEq, Eq)]
52pub struct Static<T>(PhantomData<fn() -> T>);
53
54impl<T: Constant> Static<T> {
55 pub const fn new() -> Self {
56 Self(PhantomData)
57 }
58}
59
60impl<T: Constant> Bytes for Static<T> {
61 fn as_bytes(&self) -> &[u8] {
62 T::VALUE.as_bytes()
63 }
64}
65impl<T: Constant> Text for Static<T> {
66 fn as_str(&self) -> &str {
67 T::VALUE
68 }
69}
70
71impl Bytes for str {
72 fn as_bytes(&self) -> &[u8] {
73 str::as_bytes(self)
74 }
75}
76impl Text for str {
77 fn as_str(&self) -> &str {
78 self
79 }
80}
81
82impl Bytes for String {
83 fn as_bytes(&self) -> &[u8] {
84 self.as_str().as_bytes()
85 }
86}
87impl Text for String {
88 fn as_str(&self) -> &str {
89 String::as_str(self)
90 }
91}
92
93impl Bytes for [u8] {
94 fn as_bytes(&self) -> &[u8] {
95 self
96 }
97}
98
99impl<const N: usize> Bytes for [u8; N] {
100 fn as_bytes(&self) -> &[u8] {
101 self
102 }
103}
104
105impl Bytes for Vec<u8> {
106 fn as_bytes(&self) -> &[u8] {
107 self.as_slice()
108 }
109}
110
111impl Bytes for Shared {
112 fn as_bytes(&self) -> &[u8] {
113 self
114 }
115}
116
117impl Bytes for Cow<'_, str> {
118 fn as_bytes(&self) -> &[u8] {
119 self.as_ref().as_bytes()
120 }
121}
122impl Text for Cow<'_, str> {
123 fn as_str(&self) -> &str {
124 self.as_ref()
125 }
126}
127
128impl Bytes for Cow<'_, [u8]> {
129 fn as_bytes(&self) -> &[u8] {
130 self.as_ref()
131 }
132}
133
134impl<T: Bytes + ?Sized> Bytes for &T {
135 fn as_bytes(&self) -> &[u8] {
136 T::as_bytes(self)
137 }
138}
139impl<T: Text + ?Sized> Text for &T {
140 fn as_str(&self) -> &str {
141 T::as_str(self)
142 }
143}
144
145impl<T: Bytes + ?Sized> Bytes for Box<T> {
146 fn as_bytes(&self) -> &[u8] {
147 T::as_bytes(self)
148 }
149}
150impl<T: Text + ?Sized> Text for Box<T> {
151 fn as_str(&self) -> &str {
152 T::as_str(self)
153 }
154}