gear_common/storage/complex/
waitlist.rs1use crate::storage::{
25 Callback, CountedByKey, DoubleMapStorage, GetCallback, Interval, IterableByKeyMap, IterableMap,
26 KeyFor,
27};
28use core::marker::PhantomData;
29
30pub type ValueWithInterval<T, B> = (T, Interval<B>);
31
32pub trait Waitlist {
34 type Key1;
36 type Key2;
38 type Value;
40 type BlockNumber;
44 type Error: WaitlistError;
46 type OutputError: From<Self::Error>;
48
49 fn contains(key1: &Self::Key1, key2: &Self::Key2) -> bool;
51
52 fn insert(value: Self::Value, bn: Self::BlockNumber) -> Result<(), Self::OutputError>;
54
55 fn remove(
58 key1: Self::Key1,
59 key2: Self::Key2,
60 ) -> Result<ValueWithInterval<Self::Value, Self::BlockNumber>, Self::OutputError>;
61
62 fn clear();
64}
65
66pub trait WaitlistCallbacks {
68 type Value;
73 type BlockNumber;
78
79 type GetBlockNumber: GetCallback<Self::BlockNumber>;
81 type OnInsert: Callback<ValueWithInterval<Self::Value, Self::BlockNumber>>;
83 type OnRemove: Callback<ValueWithInterval<Self::Value, Self::BlockNumber>>;
85}
86
87pub trait WaitlistError {
91 fn duplicate_key() -> Self;
93
94 fn element_not_found() -> Self;
96}
97
98pub struct WaitlistImpl<T, Value, BlockNumber, Error, OutputError, Callbacks, KeyGen>(
105 PhantomData<(T, Error, OutputError, Callbacks, KeyGen)>,
106)
107where
108 T: DoubleMapStorage<Value = (Value, Interval<BlockNumber>)>,
109 Error: WaitlistError,
110 OutputError: From<Error>,
111 Callbacks: WaitlistCallbacks<Value = Value, BlockNumber = BlockNumber>,
112 KeyGen: KeyFor<Key = (T::Key1, T::Key2), Value = Value>;
113
114impl<T, Value, BlockNumber, Error, OutputError, Callbacks, KeyGen> Waitlist
116 for WaitlistImpl<T, Value, BlockNumber, Error, OutputError, Callbacks, KeyGen>
117where
118 T: DoubleMapStorage<Value = (Value, Interval<BlockNumber>)>,
119 Error: WaitlistError,
120 OutputError: From<Error>,
121 Callbacks: WaitlistCallbacks<Value = Value, BlockNumber = BlockNumber>,
122 KeyGen: KeyFor<Key = (T::Key1, T::Key2), Value = Value>,
123{
124 type Key1 = T::Key1;
125 type Key2 = T::Key2;
126 type Value = Value;
127 type BlockNumber = BlockNumber;
128 type Error = Error;
129 type OutputError = OutputError;
130
131 fn contains(program_id: &Self::Key1, message_id: &Self::Key2) -> bool {
132 T::contains_keys(program_id, message_id)
133 }
134
135 fn insert(
136 message: Self::Value,
137 scheduled_at: Self::BlockNumber,
138 ) -> Result<(), Self::OutputError> {
139 let (key1, key2) = KeyGen::key_for(&message);
140
141 if Self::contains(&key1, &key2) {
142 return Err(Self::Error::duplicate_key().into());
143 }
144
145 let block_number = Callbacks::GetBlockNumber::call();
146 let message_with_bn = (
147 message,
148 Interval {
149 start: block_number,
150 finish: scheduled_at,
151 },
152 );
153
154 Callbacks::OnInsert::call(&message_with_bn);
155 T::insert(key1, key2, message_with_bn);
156 Ok(())
157 }
158
159 fn remove(
160 program_id: Self::Key1,
161 message_id: Self::Key2,
162 ) -> Result<ValueWithInterval<Self::Value, Self::BlockNumber>, Self::OutputError> {
163 if let Some(message_with_bn) = T::take(program_id, message_id) {
164 Callbacks::OnRemove::call(&message_with_bn);
165 Ok(message_with_bn)
166 } else {
167 Err(Self::Error::element_not_found().into())
168 }
169 }
170
171 fn clear() {
172 T::clear()
173 }
174}
175
176impl<T, Value, BlockNumber, Error, OutputError, Callbacks, KeyGen> CountedByKey
179 for WaitlistImpl<T, Value, BlockNumber, Error, OutputError, Callbacks, KeyGen>
180where
181 T: DoubleMapStorage<Value = (Value, Interval<BlockNumber>)> + CountedByKey<Key = T::Key1>,
182 Error: WaitlistError,
183 OutputError: From<Error>,
184 Callbacks: WaitlistCallbacks<Value = Value, BlockNumber = BlockNumber>,
185 KeyGen: KeyFor<Key = (T::Key1, T::Key2), Value = Value>,
186{
187 type Key = T::Key1;
188 type Length = T::Length;
189
190 fn len(key: &Self::Key) -> Self::Length {
191 T::len(key)
192 }
193}
194
195impl<T, Value, BlockNumber, Error, OutputError, Callbacks, KeyGen> IterableByKeyMap<T::Value>
198 for WaitlistImpl<T, Value, BlockNumber, Error, OutputError, Callbacks, KeyGen>
199where
200 T: DoubleMapStorage<Value = (Value, Interval<BlockNumber>)>
201 + IterableByKeyMap<T::Value, Key = T::Key1>,
202 Error: WaitlistError,
203 OutputError: From<Error>,
204 Callbacks: WaitlistCallbacks<Value = Value, BlockNumber = BlockNumber>,
205 KeyGen: KeyFor<Key = (T::Key1, T::Key2), Value = Value>,
206{
207 type Key = T::Key1;
208 type DrainIter = T::DrainIter;
209 type Iter = T::Iter;
210
211 fn drain_key(key: Self::Key) -> Self::DrainIter {
212 T::drain_key(key)
213 }
214
215 fn iter_key(key: Self::Key) -> Self::Iter {
216 T::iter_key(key)
217 }
218}
219
220impl<T, Value, BlockNumber, Error, OutputError, Callbacks, KeyGen> IterableMap<T::Value>
223 for WaitlistImpl<T, Value, BlockNumber, Error, OutputError, Callbacks, KeyGen>
224where
225 T: DoubleMapStorage<Value = (Value, Interval<BlockNumber>)> + IterableMap<T::Value>,
226 Error: WaitlistError,
227 OutputError: From<Error>,
228 Callbacks: WaitlistCallbacks<Value = Value, BlockNumber = BlockNumber>,
229 KeyGen: KeyFor<Key = (T::Key1, T::Key2), Value = Value>,
230{
231 type DrainIter = T::DrainIter;
232 type Iter = T::Iter;
233
234 fn drain() -> Self::DrainIter {
235 T::drain()
236 }
237
238 fn iter() -> Self::Iter {
239 T::iter()
240 }
241}