iddqd/id_ord_map/
proptest_impls.rs1use crate::{IdOrdItem, id_ord_map::IdOrdMap};
4use core::fmt;
5use proptest::{
6 arbitrary::{Arbitrary, StrategyFor, any_with},
7 collection::{SizeRange, VecStrategy, VecValueTree},
8 strategy::{NewTree, Strategy, ValueTree},
9 test_runner::TestRunner,
10};
11
12#[must_use = "strategies do nothing unless used"]
16#[derive(Clone)]
17pub struct IdOrdMapStrategy<T>
18where
19 T: Strategy,
20{
21 inner: VecStrategy<T>,
22}
23
24impl<T> fmt::Debug for IdOrdMapStrategy<T>
25where
26 T: Strategy,
27{
28 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
29 f.debug_struct("IdOrdMapStrategy")
30 .field("inner", &self.inner)
31 .finish_non_exhaustive()
32 }
33}
34
35pub fn prop_strategy<T: Strategy>(
73 element: T,
74 size: impl Into<SizeRange>,
75) -> IdOrdMapStrategy<T> {
76 IdOrdMapStrategy { inner: proptest::collection::vec(element, size) }
77}
78
79impl<'a, T> Strategy for IdOrdMapStrategy<T>
80where
81 T: Strategy,
82 T::Value: 'a + IdOrdItem,
83 <T::Value as IdOrdItem>::Key<'a>: fmt::Debug,
84{
85 type Tree = IdOrdMapValueTree<T::Tree>;
86 type Value = IdOrdMap<T::Value>;
87
88 fn new_tree(&self, runner: &mut TestRunner) -> NewTree<Self> {
89 let inner = self.inner.new_tree(runner)?;
90
91 Ok(IdOrdMapValueTree { inner })
92 }
93}
94
95#[derive(Clone)]
97pub struct IdOrdMapValueTree<T>
98where
99 T: ValueTree,
100{
101 inner: VecValueTree<T>,
102}
103
104impl<T> fmt::Debug for IdOrdMapValueTree<T>
105where
106 T: ValueTree + fmt::Debug,
107{
108 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
109 f.debug_struct("IdOrdMapValueTree")
110 .field("inner", &self.inner)
111 .finish_non_exhaustive()
112 }
113}
114
115impl<'a, T> ValueTree for IdOrdMapValueTree<T>
116where
117 T: ValueTree,
118 T::Value: 'a + IdOrdItem,
119 <T::Value as IdOrdItem>::Key<'a>: fmt::Debug,
120{
121 type Value = IdOrdMap<T::Value>;
122
123 fn current(&self) -> Self::Value {
124 let items = self.inner.current();
125 let mut map = IdOrdMap::new();
126
127 for item in items {
128 map.insert_overwrite(item);
130 }
131
132 map
133 }
134
135 fn simplify(&mut self) -> bool {
136 self.inner.simplify()
137 }
138
139 fn complicate(&mut self) -> bool {
140 self.inner.complicate()
141 }
142}
143
144impl<'a, T> Arbitrary for IdOrdMap<T>
145where
146 T: 'a + IdOrdItem + Arbitrary,
147 <T as IdOrdItem>::Key<'a>: fmt::Debug,
148{
149 type Parameters = (SizeRange, T::Parameters);
150 type Strategy = IdOrdMapStrategy<StrategyFor<T>>;
151
152 fn arbitrary_with(args: Self::Parameters) -> Self::Strategy {
153 let (size, element_args) = args;
154 prop_strategy(any_with::<T>(element_args), size)
155 }
156}