abi_stable/std_types/cow.rs
1//! Contains the ffi-safe equivalent of `std::borrow::Cow`, and related items.
2
3use std::{
4 borrow::{Borrow, Cow},
5 cmp::{Eq, Ord, Ordering, PartialEq, PartialOrd},
6 fmt::{self, Debug},
7 hash::{Hash, Hasher},
8 ops::Deref,
9};
10
11use serde::{Deserialize, Deserializer, Serialize, Serializer};
12
13#[allow(unused_imports)]
14use core_extensions::{matches, SelfOps};
15
16use crate::{
17 std_types::{RSlice, RStr, RString, RVec},
18 traits::{IntoOwned, IntoReprC, IntoReprRust},
19 StableAbi,
20};
21
22// #[cfg(test)]
23#[cfg(all(test, not(feature = "only_new_tests")))]
24mod tests;
25
26////////////////////////////////////////////////////////////////////
27
28/// For making a `Cow<'a, Self>` convertible into an `RCow`.
29pub trait RCowCompatibleRef<'a>: ToOwned {
30 /// The (preferably) ffi-safe equivalent of `&Self`.
31 type RefC: IntoOwned<ROwned = Self::ROwned, Target = Self>;
32
33 /// The owned version of `Self::RefC`.
34 type ROwned: Borrow<Self> + Into<Self::Owned> + From<Self::Owned>;
35
36 /// Converts a reference to an FFI-safe type
37 fn as_c_ref(from: &'a Self) -> Self::RefC;
38
39 /// Converts an FFI-safe type to a reference
40 fn as_rust_ref(from: Self::RefC) -> &'a Self;
41}
42
43impl<'a> RCowCompatibleRef<'a> for str {
44 type RefC = RStr<'a>;
45 type ROwned = RString;
46
47 fn as_c_ref(from: &'a Self) -> Self::RefC {
48 RStr::from_str(from)
49 }
50 fn as_rust_ref(from: Self::RefC) -> &'a Self {
51 from.as_str()
52 }
53}
54
55impl<'a, T: Clone + 'a> RCowCompatibleRef<'a> for [T] {
56 type RefC = RSlice<'a, T>;
57 type ROwned = RVec<T>;
58
59 fn as_c_ref(from: &'a Self) -> Self::RefC {
60 RSlice::from_slice(from)
61 }
62 fn as_rust_ref(from: Self::RefC) -> &'a Self {
63 from.into()
64 }
65}
66
67impl<'a, T: Clone + 'a> RCowCompatibleRef<'a> for T {
68 type RefC = &'a T;
69 type ROwned = T;
70
71 fn as_c_ref(from: &'a Self) -> Self::RefC {
72 from
73 }
74 fn as_rust_ref(from: Self::RefC) -> &'a Self {
75 from
76 }
77}
78
79////////////////////////////////////////////////////////////////////
80
81/// Ffi-safe equivalent of `std::borrow::Cow`.
82///
83/// This has type aliases for the three most common usecases:
84///
85/// - [`RCowStr`]: contains an `RStr<'_>` or an `RString`.
86///
87/// - [`RCowSlice`]: contains an `RSlice<'_, T>` or an `RVec<T>`.
88///
89/// - [`RCowVal`]: contains a `&T` or a `T`.
90///
91/// # Example
92///
93/// ### Using a `RCowStr<'a>`.
94///
95/// This implements a solution to the well known fizzbuzz problem.
96///
97/// ```
98/// use abi_stable::std_types::{RCow, RCowStr};
99///
100/// fn fizzbuzz(n: u32) -> RCowStr<'static> {
101/// match (n % 3, n % 5) {
102/// (0, 0) => RCow::from("FizzBuzz"),
103/// (0, _) => RCow::from("Fizz"),
104/// (_, 0) => RCow::from("Buzz"),
105/// (_, _) => RCow::from(n.to_string()),
106/// }
107/// }
108///
109/// for n in 1..=100 {
110/// println!("{}", fizzbuzz(n));
111/// }
112/// ```
113///
114/// Note: this example allocates when the number is neither a multiple of 5 or 3.
115///
116#[repr(C)]
117#[derive(StableAbi)]
118pub enum RCow<B, O> {
119 ///
120 Borrowed(B),
121 ///
122 Owned(O),
123}
124
125use self::RCow::{Borrowed, Owned};
126
127/// Ffi-safe equivalent of `Cow<'a, T>`, either a `&T` or `T`.
128///
129/// # Example
130///
131/// ```rust
132/// use abi_stable::std_types::{RCow, RCowVal};
133///
134/// fn foo(x: u8) -> RCowVal<'static, u8> {
135/// if x % 2 == 0 {
136/// RCow::Borrowed(&1)
137/// } else {
138/// RCow::Owned(x * 2)
139/// }
140/// }
141///
142/// assert_eq!(*foo(3), 6);
143/// assert_eq!(*foo(4), 1);
144/// assert_eq!(*foo(5), 10);
145/// assert_eq!(*foo(6), 1);
146/// assert_eq!(*foo(7), 14);
147///
148/// ```
149pub type RCowVal<'a, T> = RCow<&'a T, T>;
150
151/// Ffi-safe equivalent of `Cow<'a, str>`, either an [`RStr`] or [`RString`].
152///
153/// # Example
154///
155/// ```rust
156/// use abi_stable::std_types::{RCow, RCowStr};
157///
158/// fn foo(x: &str) -> RCowStr<'_> {
159/// if let Some(x) = x.strip_prefix("tri") {
160/// RCow::from(x.repeat(3))
161/// } else {
162/// RCow::from(x)
163/// }
164/// }
165///
166/// assert_eq!(foo("foo"), "foo");
167/// assert_eq!(foo("bar"), "bar");
168/// assert_eq!(foo("tribaz"), "bazbazbaz");
169/// assert_eq!(foo("triqux"), "quxquxqux");
170///
171/// ```
172///
173pub type RCowStr<'a> = RCow<RStr<'a>, RString>;
174
175/// Ffi-safe equivalent of `Cow<'a, [T]>`, either an [`RSlice`] or [`RVec`].
176///
177/// # Example
178///
179/// ```rust
180/// use abi_stable::std_types::{RCow, RCowSlice, RVec};
181///
182/// use std::iter::once;
183///
184/// fn foo(x: &[u32]) -> RCowSlice<'_, u32> {
185/// match x {
186/// [prev @ .., x] if *x == 5 => RCow::from(RVec::from(prev)),
187/// _ => RCow::from(x),
188/// }
189/// }
190///
191/// assert_eq!(foo(&[3, 4]), &[3, 4][..]);
192/// assert_eq!(foo(&[3, 4, 5]), &[3, 4][..]);
193/// assert_eq!(foo(&[3, 4, 5, 6]), &[3, 4, 5, 6][..]);
194/// assert_eq!(foo(&[3, 4, 5, 6, 7]), &[3, 4, 5, 6, 7][..]);
195///
196/// ```
197///
198pub type RCowSlice<'a, T> = RCow<RSlice<'a, T>, RVec<T>>;
199
200// ///////////////////////////////////////////////////////////////////////////
201
202impl<B> RCow<B, B::ROwned>
203where
204 B: IntoOwned,
205{
206 /// Get a mutable reference to the owned form of RCow,
207 /// converting to the owned form if it is currently the borrowed form.
208 ///
209 /// # Examples
210 ///
211 /// ```
212 /// use abi_stable::std_types::{RCow, RCowStr};
213 ///
214 /// let mut cow: RCowStr<'_> = RCow::from("Hello");
215 ///
216 /// assert_eq!(&*cow, "Hello");
217 /// assert!(cow.is_borrowed());
218 ///
219 /// cow.to_mut().push_str(", world!");
220 ///
221 /// assert!(cow.is_owned());
222 /// assert_eq!(cow, RCow::from("Hello, world!"));
223 ///
224 /// ```
225 pub fn to_mut(&mut self) -> &mut B::ROwned {
226 if let Borrowed(v) = *self {
227 let owned = B::into_owned(v);
228 *self = Owned(owned)
229 }
230 match self {
231 Borrowed(_) => unreachable!(),
232 Owned(v) => v,
233 }
234 }
235 /// Unwraps into the owned owner form of RCow,
236 /// converting to the owned form if it is currently the borrowed form.
237 ///
238 /// # Examples
239 ///
240 /// ```
241 /// use abi_stable::std_types::{RCow, RCowStr};
242 ///
243 /// let mut cow: RCowStr<'_> = RCow::from("Hello");
244 ///
245 /// assert_eq!(&*cow, "Hello");
246 ///
247 /// let mut buff = cow.into_owned();
248 /// buff.push_str(", world!");
249 ///
250 /// assert_eq!(&*buff, "Hello, world!");
251 ///
252 /// ```
253 pub fn into_owned(self) -> B::ROwned {
254 match self {
255 Borrowed(x) => B::into_owned(x),
256 Owned(x) => x,
257 }
258 }
259
260 /// Gets the contents of the RCow casted to the borrowed variant.
261 ///
262 /// # Examples
263 ///
264 /// ```
265 /// use abi_stable::std_types::{RCow, RCowSlice, RSlice};
266 /// {
267 /// let cow: RCowSlice<'_, u8> = RCow::from(&[0, 1, 2, 3][..]);
268 /// assert_eq!(cow.borrowed(), RSlice::from_slice(&[0, 1, 2, 3]));
269 /// }
270 /// {
271 /// let cow: RCowSlice<'_, u8> = RCow::from(vec![0, 1, 2, 3]);
272 /// assert_eq!(cow.borrowed(), RSlice::from_slice(&[0, 1, 2, 3]));
273 /// }
274 /// ```
275 pub fn borrowed(&self) -> &<B as Deref>::Target {
276 match self {
277 Borrowed(x) => x,
278 Owned(x) => x.borrow(),
279 }
280 }
281}
282
283impl<B, O> RCow<B, O> {
284 /// Whether this is a borrowing RCow.
285 ///
286 /// # Examples
287 ///
288 /// ```
289 /// use abi_stable::std_types::{RCow, RCowSlice};
290 ///
291 /// {
292 /// let cow: RCowSlice<'_, u8> = RCow::from(&[0, 1, 2, 3][..]);
293 /// assert!(cow.is_borrowed());
294 /// }
295 /// {
296 /// let cow: RCowSlice<'_, u8> = RCow::from(vec![0, 1, 2, 3]);
297 /// assert!(!cow.is_borrowed());
298 /// }
299 ///
300 /// ```
301 pub const fn is_borrowed(&self) -> bool {
302 matches!(self, Borrowed { .. })
303 }
304
305 /// Whether this is an owning RCow.
306 ///
307 /// # Examples
308 ///
309 /// ```
310 /// use abi_stable::std_types::{RCow, RCowSlice};
311 ///
312 /// let cow: RCowSlice<'_, u8> = RCow::from(&[0, 1, 2, 3][..]);
313 /// assert!(!cow.is_owned());
314 ///
315 /// let cow: RCowSlice<'_, u8> = RCow::from(vec![0, 1, 2, 3]);
316 /// assert!(cow.is_owned());
317 ///
318 /// ```
319 pub const fn is_owned(&self) -> bool {
320 matches!(self, Owned { .. })
321 }
322}
323
324#[allow(dead_code)]
325#[cfg(test)]
326impl<B> RCow<B, B::ROwned>
327where
328 B: IntoOwned,
329{
330 /// Access this as a borrowing RCow.Returns None if it's not a borrowing one.
331 fn as_borrowed(&self) -> Option<B> {
332 match *self {
333 Borrowed(x) => Some(x),
334 Owned(_) => None,
335 }
336 }
337
338 /// Access this as an owned RCow.Returns None if it's not an owned one.
339 fn as_owned(&self) -> Option<&B::ROwned> {
340 match self {
341 Borrowed(_) => None,
342 Owned(x) => Some(x),
343 }
344 }
345}
346
347impl<B> Copy for RCow<B, B::ROwned>
348where
349 B: IntoOwned,
350 B::ROwned: Copy,
351{
352}
353
354impl<B> Clone for RCow<B, B::ROwned>
355where
356 B: IntoOwned,
357 B::ROwned: Clone,
358{
359 fn clone(&self) -> Self {
360 match self {
361 Borrowed(x) => Borrowed(*x),
362 Owned(x) => Owned((*x).clone()),
363 }
364 }
365}
366
367impl<B> Deref for RCow<B, B::ROwned>
368where
369 B: IntoOwned,
370{
371 type Target = B::Target;
372
373 #[inline]
374 fn deref(&self) -> &Self::Target {
375 match self {
376 Borrowed(x) => x,
377 Owned(x) => x.borrow(),
378 }
379 }
380}
381
382////////////////////
383
384macro_rules! impl_borrow_asref {
385 (impl[$($impl_p:tt)*] $ty:ty, $target:ty) => {
386 impl<$($impl_p)*> Borrow<$target> for $ty {
387 fn borrow(&self) -> &$target {
388 self
389 }
390 }
391
392 impl<$($impl_p)*> AsRef<$target> for $ty {
393 fn as_ref(&self) -> &$target {
394 self
395 }
396 }
397 };
398}
399
400impl_borrow_asref! {impl[T: Clone] RCowVal<'_, T>, T}
401impl_borrow_asref! {impl[] RCowStr<'_>, str}
402impl_borrow_asref! {impl[T: Clone] RCowSlice<'_, T>, [T]}
403
404////////////////////////////////////////////////////////////
405
406impl<B> Debug for RCow<B, B::ROwned>
407where
408 B: IntoOwned,
409 B::Target: Debug,
410{
411 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
412 <B::Target as Debug>::fmt(&**self, f)
413 }
414}
415
416impl<B> fmt::Display for RCow<B, B::ROwned>
417where
418 B: IntoOwned,
419 B::Target: fmt::Display,
420{
421 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
422 <B::Target as fmt::Display>::fmt(&**self, f)
423 }
424}
425
426////////////////////////////
427
428slice_like_impl_cmp_traits! {
429 impl[] RCowSlice<'_, T>,
430 where[T: Clone];
431 Vec<U>,
432 [U],
433 &[U],
434}
435
436slice_like_impl_cmp_traits! {
437 impl[const N: usize] RCowSlice<'_, T>,
438 where[T: Clone];
439 [U; N],
440}
441
442slice_like_impl_cmp_traits! {
443 impl[] RCowSlice<'_, T>,
444 where[T: Clone, U: Clone];
445 Cow<'_, [U]>,
446}
447
448deref_coerced_impl_cmp_traits! {
449 RCowStr<'_>;
450 coerce_to = str,
451 [
452 String,
453 str,
454 &str,
455 Cow<'_, str>,
456 ]
457}
458
459impl<B> Eq for RCow<B, B::ROwned>
460where
461 B: IntoOwned,
462 B::Target: Eq,
463{
464}
465
466impl<B, V> PartialEq<RCow<V, V::ROwned>> for RCow<B, B::ROwned>
467where
468 B: IntoOwned,
469 V: IntoOwned,
470 B::Target: PartialEq<V::Target>,
471{
472 fn eq(&self, other: &RCow<V, V::ROwned>) -> bool {
473 **self == **other
474 }
475}
476
477impl<B> Ord for RCow<B, B::ROwned>
478where
479 B: IntoOwned,
480 B::Target: Ord,
481{
482 fn cmp(&self, other: &Self) -> Ordering {
483 (**self).cmp(&**other)
484 }
485}
486
487impl<B, V> PartialOrd<RCow<V, V::ROwned>> for RCow<B, B::ROwned>
488where
489 B: IntoOwned,
490 V: IntoOwned,
491 B::Target: PartialOrd<V::Target>,
492{
493 fn partial_cmp(&self, other: &RCow<V, V::ROwned>) -> Option<Ordering> {
494 (**self).partial_cmp(&**other)
495 }
496}
497
498impl<B> Hash for RCow<B, B::ROwned>
499where
500 B: IntoOwned,
501 B::Target: Hash,
502{
503 fn hash<H>(&self, state: &mut H)
504 where
505 H: Hasher,
506 {
507 (**self).hash(state)
508 }
509}
510
511////////////////////////////////////////////////////////////
512
513impl<'a, T, B> From<RCow<B, T::ROwned>> for Cow<'a, T>
514where
515 T: ?Sized + RCowCompatibleRef<'a, RefC = B>,
516 B: IntoOwned<ROwned = T::ROwned, Target = T>,
517{
518 fn from(this: RCow<B, T::ROwned>) -> Cow<'a, T> {
519 match this {
520 RCow::Borrowed(x) => Cow::Borrowed(T::as_rust_ref(x)),
521 RCow::Owned(x) => Cow::Owned(x.into()),
522 }
523 }
524}
525
526macro_rules! impl_into_repr_rust {
527 (impl[$($impl_params:tt)*] $rcow:ty, $cow_param:ty) => {
528 impl<'a, $($impl_params)*> IntoReprRust for $rcow {
529 type ReprRust = Cow<'a, $cow_param>;
530
531 fn into_rust(self) -> Self::ReprRust {
532 self.into()
533 }
534 }
535 };
536}
537impl_into_repr_rust! {impl[T: Clone] RCowSlice<'a, T>, [T]}
538impl_into_repr_rust! {impl[T: Clone] RCowVal<'a, T>, T}
539impl_into_repr_rust! {impl[] RCowStr<'a>, str}
540
541impl_from_rust_repr! {
542 impl['a, T] From<Cow<'a, T>> for RCow<T::RefC, T::ROwned>
543 where [
544 T: ?Sized + RCowCompatibleRef<'a>
545 ]{
546 fn(this){
547 match this {
548 Cow::Borrowed(x) => RCow::Borrowed(T::as_c_ref(x)),
549 Cow::Owned(x) => RCow::Owned(x.into()),
550 }
551 }
552 }
553}
554
555////////////////////////////////////////////////////////////
556
557impl<'a> RCowStr<'a> {
558 /// For converting a `&'a [T]` to an `RCowSlice<'a, T>`,
559 /// most useful when converting from `&'a [T;N]` because it coerces the array to a slice.
560 ///
561 /// # Example
562 ///
563 /// ```rust
564 /// use abi_stable::std_types::{RCow, RCowStr};
565 ///
566 /// const C: RCowStr<'_> = RCow::from_str("hello");
567 ///
568 /// assert_eq!(C, "hello");
569 ///
570 /// ```
571 #[inline]
572 pub const fn from_str(this: &'a str) -> Self {
573 RCow::Borrowed(RStr::from_str(this))
574 }
575
576 conditionally_const! {
577 feature = "rust_1_64"
578 /// Borrows this RCow as a str.
579 ///
580 ;
581 ///
582 /// # Example
583 ///
584 /// ```rust
585 /// use abi_stable::std_types::RCow;
586 ///
587 /// let cow = RCow::from_str("world");
588 ///
589 /// assert_eq!(cow.as_str(), "world")
590 ///
591 /// ```
592 ///
593 pub fn as_str(&self) -> &str {
594 match self {
595 RCow::Borrowed(x) => x.as_str(),
596 RCow::Owned(x) => x.as_str(),
597 }
598 }
599 }
600}
601
602impl<'a> From<&'a str> for RCowStr<'a> {
603 #[inline]
604 fn from(this: &'a str) -> Self {
605 RCow::Borrowed(this.into_c())
606 }
607}
608
609impl<'a> From<RStr<'a>> for RCowStr<'a> {
610 #[inline]
611 fn from(this: RStr<'a>) -> Self {
612 RCow::Borrowed(this)
613 }
614}
615
616impl<'a> From<String> for RCowStr<'a> {
617 #[inline]
618 fn from(this: String) -> Self {
619 RCow::Owned(this.into())
620 }
621}
622
623impl<'a> From<&'a String> for RCowStr<'a> {
624 #[inline]
625 fn from(this: &'a String) -> Self {
626 RCow::Borrowed(this.as_str().into())
627 }
628}
629
630impl<'a> From<RString> for RCowStr<'a> {
631 #[inline]
632 fn from(this: RString) -> Self {
633 RCow::Owned(this)
634 }
635}
636
637impl<'a> From<&'a RString> for RCowStr<'a> {
638 #[inline]
639 fn from(this: &'a RString) -> Self {
640 RCow::Borrowed(this.as_rstr())
641 }
642}
643
644impl<'a, T> From<&'a [T]> for RCowSlice<'a, T>
645where
646 T: Clone,
647{
648 #[inline]
649 fn from(this: &'a [T]) -> Self {
650 RCow::Borrowed(RSlice::from(this))
651 }
652}
653
654impl<'a, T> From<&'a Vec<T>> for RCowSlice<'a, T>
655where
656 T: Clone,
657{
658 #[inline]
659 fn from(this: &'a Vec<T>) -> Self {
660 RCow::Borrowed(RSlice::from_slice(this))
661 }
662}
663
664impl<'a, T> From<&'a RVec<T>> for RCowSlice<'a, T>
665where
666 T: Clone,
667{
668 #[inline]
669 fn from(this: &'a RVec<T>) -> Self {
670 RCow::Borrowed(RSlice::from_slice(this))
671 }
672}
673
674impl<'a, T> RCowSlice<'a, T> {
675 /// For converting a `&'a [T]` to an `RCowSlice<'a, T>`,
676 /// most useful when converting from `&'a [T;N]` because it coerces the array to a slice.
677 ///
678 /// # Example
679 ///
680 /// ```rust
681 /// use abi_stable::std_types::{RCow, RCowSlice};
682 ///
683 /// const C: RCowSlice<'_, u8> = RCow::from_slice(&[3, 5, 8]);
684 ///
685 /// assert_eq!(C, [3, 5, 8]);
686 ///
687 /// ```
688 #[inline]
689 pub const fn from_slice(this: &'a [T]) -> Self {
690 RCow::Borrowed(RSlice::from_slice(this))
691 }
692
693 conditionally_const! {
694 feature = "rust_1_64"
695 /// Borrows this RCow as a slice.
696 ///
697 ;
698 ///
699 /// # Example
700 ///
701 /// ```rust
702 /// use abi_stable::std_types::RCow;
703 ///
704 /// let cow = RCow::from_slice(&[3, 5, 8]);
705 ///
706 /// assert_eq!(cow.as_slice(), [3, 5, 8])
707 ///
708 /// ```
709 ///
710 pub fn as_slice(&self) -> &[T] {
711 match self {
712 RCow::Borrowed(x) => x.as_slice(),
713 RCow::Owned(x) => x.as_slice(),
714 }
715 }
716 }
717}
718
719impl<'a, T> From<RSlice<'a, T>> for RCowSlice<'a, T>
720where
721 T: Clone,
722{
723 #[inline]
724 fn from(this: RSlice<'a, T>) -> Self {
725 RCow::Borrowed(this)
726 }
727}
728
729impl<'a, T> From<Vec<T>> for RCowSlice<'a, T>
730where
731 T: Clone,
732{
733 #[inline]
734 fn from(this: Vec<T>) -> Self {
735 RCow::Owned(RVec::from(this))
736 }
737}
738
739impl<'a, T> From<RVec<T>> for RCowSlice<'a, T>
740where
741 T: Clone,
742{
743 #[inline]
744 fn from(this: RVec<T>) -> Self {
745 RCow::Owned(this)
746 }
747}
748
749////////////////////////////////////////////////////////////
750
751/// Deserializes an `RCow<'a, [u8]>` that borrows the slice from the deserializer
752/// whenever possible.
753///
754/// # Example
755///
756/// Defining a type containing an `RCow<'a, [u8]>` which borrows from the deserializer.
757///
758/// ```
759/// use abi_stable::std_types::cow::{deserialize_borrowed_bytes, RCow, RCowSlice};
760///
761/// use serde::{Deserialize, Serialize};
762///
763/// #[derive(Debug, Deserialize, Serialize, PartialEq)]
764/// pub struct TheSlice<'a> {
765/// #[serde(borrow, deserialize_with = "deserialize_borrowed_bytes")]
766/// slice: RCowSlice<'a, u8>,
767/// }
768///
769/// let the_slice = TheSlice {
770/// slice: RCow::from(vec![0, 1, 2, 3, 4, 5]),
771/// };
772///
773/// let vec = bincode::serialize(&the_slice).unwrap();
774///
775/// let deserialized_slice = bincode::deserialize(&vec).unwrap();
776///
777/// assert_eq!(the_slice, deserialized_slice);
778///
779/// assert!(deserialized_slice.slice.is_borrowed());
780///
781/// ```
782///
783pub fn deserialize_borrowed_bytes<'de, 'a, D>(
784 deserializer: D,
785) -> Result<RCowSlice<'a, u8>, D::Error>
786where
787 D: Deserializer<'de>,
788 'de: 'a,
789{
790 #[derive(Deserialize)]
791 struct BorrowingCowSlice<'a> {
792 #[serde(borrow)]
793 cow: Cow<'a, [u8]>,
794 }
795
796 <BorrowingCowSlice<'de> as Deserialize<'de>>::deserialize(deserializer).map(|x| match x.cow {
797 Cow::Borrowed(y) => RCow::Borrowed(y.into()),
798 Cow::Owned(y) => RCow::Owned(y.into()),
799 })
800}
801
802/// Deserializes an `RCowStr<'a>` that borrows the string from the deserializer
803/// whenever possible.
804///
805///
806/// # Example
807///
808/// Defining a type containing an `RCowStr<'a>` which borrows from the deserializer.
809///
810/// ```
811/// use abi_stable::std_types::cow::{deserialize_borrowed_str, RCow, RCowStr};
812///
813/// use serde::{Deserialize, Serialize};
814///
815/// #[derive(Debug, Deserialize, Serialize, PartialEq)]
816/// pub struct TheSlice<'a> {
817/// #[serde(borrow, deserialize_with = "deserialize_borrowed_str")]
818/// slice: RCowStr<'a>,
819/// }
820///
821/// let the_slice = TheSlice {
822/// slice: RCow::from("That's a lot of fish."),
823/// };
824///
825/// let string = serde_json::to_string(&the_slice).unwrap();
826///
827/// let deserialized_slice = serde_json::from_str::<TheSlice<'_>>(&string).unwrap();
828///
829/// assert_eq!(the_slice, deserialized_slice);
830///
831/// assert!(deserialized_slice.slice.is_borrowed());
832///
833/// ```
834///
835pub fn deserialize_borrowed_str<'de, 'a, D>(deserializer: D) -> Result<RCowStr<'a>, D::Error>
836where
837 D: Deserializer<'de>,
838 'de: 'a,
839{
840 #[derive(Deserialize)]
841 struct BorrowingCowStr<'a>(#[serde(borrow)] Cow<'a, str>);
842
843 <BorrowingCowStr<'de> as Deserialize<'de>>::deserialize(deserializer)
844 .map(|x| RCowStr::from(x.0))
845}
846
847impl<'de, 'a, T> Deserialize<'de> for RCowSlice<'a, T>
848where
849 T: Clone + Deserialize<'de>,
850{
851 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
852 where
853 D: Deserializer<'de>,
854 {
855 <RVec<T>>::deserialize(deserializer).map(RCowSlice::<'a, T>::Owned)
856 }
857}
858
859impl<'de, 'a> Deserialize<'de> for RCowStr<'a> {
860 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
861 where
862 D: Deserializer<'de>,
863 {
864 <Cow<'a, str> as Deserialize<'de>>::deserialize(deserializer).map(RCow::from)
865 }
866}
867
868impl<'de, 'a, T> Deserialize<'de> for RCowVal<'a, T>
869where
870 T: Clone + Deserialize<'de>,
871{
872 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
873 where
874 D: Deserializer<'de>,
875 {
876 <T as Deserialize<'de>>::deserialize(deserializer).map(RCow::Owned)
877 }
878}
879
880impl<B> Serialize for RCow<B, B::ROwned>
881where
882 B: IntoOwned,
883 B::Target: Serialize,
884{
885 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
886 where
887 S: Serializer,
888 {
889 (**self).serialize(serializer)
890 }
891}
892
893/// A helper type, to deserialize an `RCow<'a, [u8]>` which borrows from the deserializer.
894///
895/// # Example
896///
897/// ```
898/// use abi_stable::std_types::cow::{
899/// deserialize_borrowed_bytes, BorrowingRCowU8Slice,
900/// };
901///
902/// let the_slice: Vec<u8> = vec![0, 1, 2, 3, 4, 5];
903///
904/// let vec = bincode::serialize(&the_slice).unwrap();
905///
906/// let deserialized_slice =
907/// bincode::deserialize::<BorrowingRCowU8Slice<'_>>(&vec).unwrap();
908///
909/// assert_eq!(&*deserialized_slice.cow, &*the_slice);
910///
911/// assert!(deserialized_slice.cow.is_borrowed());
912///
913/// ```
914///
915#[derive(Deserialize)]
916#[serde(transparent)]
917pub struct BorrowingRCowU8Slice<'a> {
918 /// The deserialized `Cow`.
919 #[serde(borrow, deserialize_with = "deserialize_borrowed_bytes")]
920 pub cow: RCowSlice<'a, u8>,
921}
922
923/// A helper type, to deserialize a `RCowStr<'a>` which borrows from the deserializer.
924///
925/// # Example
926///
927/// Defining a type containing an `RCowStr<'a>` borrowing from the deserializer,
928/// serializing it, and then deserializing it.
929///
930/// ```
931/// use abi_stable::std_types::cow::{deserialize_borrowed_str, BorrowingRCowStr};
932///
933/// let json = r##""W____ of S____""##;
934///
935/// let deserialized_slice =
936/// serde_json::from_str::<BorrowingRCowStr<'_>>(json).unwrap();
937///
938/// assert_eq!(&*deserialized_slice.cow, json.trim_matches('"'));
939///
940/// assert!(deserialized_slice.cow.is_borrowed());
941///
942/// ```
943///
944#[derive(Deserialize)]
945#[serde(transparent)]
946pub struct BorrowingRCowStr<'a> {
947 /// The deserialized `Cow`.
948 #[serde(borrow, deserialize_with = "deserialize_borrowed_str")]
949 pub cow: RCowStr<'a>,
950}
951
952//////////////////////////////////////////////////////////////////////////////////////