1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
use cosmwasm_std::{Order, StdError, StdResult, Storage};
use cw_storage_plus::{Bound, IndexList, IndexedMap, KeyDeserialize, Map, PrimaryKey};
use serde::{de::DeserializeOwned, ser::Serialize};
pub const DEFAULT_LIMIT: u32 = 10;
pub const MAX_LIMIT: u32 = 30;
pub fn collect<'a, D, T, R, E, F>(
iter: Box<dyn Iterator<Item = StdResult<(D, T)>> + 'a>,
limit: Option<u32>,
parse_fn: F,
) -> Result<Vec<R>, E>
where
F: Fn(D, T) -> Result<R, E>,
E: From<StdError>,
{
let limit = limit.unwrap_or(DEFAULT_LIMIT).min(MAX_LIMIT) as usize;
iter.take(limit)
.map(|item| {
let (k, v) = item?;
parse_fn(k, v)
})
.collect()
}
pub fn paginate_map<'a, K, T, R, E, F>(
map: &Map<'a, K, T>,
store: &dyn Storage,
start: Option<Bound<'a, K>>,
limit: Option<u32>,
parse_fn: F,
) -> Result<Vec<R>, E>
where
K: PrimaryKey<'a> + KeyDeserialize,
K::Output: 'static,
T: Serialize + DeserializeOwned,
F: Fn(K::Output, T) -> Result<R, E>,
E: From<StdError>,
{
let iter = map.range(store, start, None, Order::Ascending);
collect(iter, limit, parse_fn)
}
pub fn paginate_map_prefix<'a, K, T, R, E, F>(
map: &Map<'a, K, T>,
store: &dyn Storage,
prefix: K::Prefix,
start: Option<Bound<'a, K::Suffix>>,
limit: Option<u32>,
parse_fn: F,
) -> Result<Vec<R>, E>
where
K: PrimaryKey<'a>,
K::Suffix: PrimaryKey<'a> + KeyDeserialize,
<K::Suffix as KeyDeserialize>::Output: 'static,
T: Serialize + DeserializeOwned,
F: Fn(<K::Suffix as KeyDeserialize>::Output, T) -> Result<R, E>,
E: From<StdError>,
{
let iter = map.prefix(prefix).range(store, start, None, Order::Ascending);
collect(iter, limit, parse_fn)
}
pub fn paginate_indexed_map<'a, K, T, I, R, E, F>(
map: &IndexedMap<'a, K, T, I>,
store: &dyn Storage,
start: Option<Bound<'a, K>>,
limit: Option<u32>,
parse_fn: F,
) -> Result<Vec<R>, E>
where
K: PrimaryKey<'a> + KeyDeserialize,
K::Output: 'static,
T: Serialize + DeserializeOwned + Clone,
I: IndexList<T>,
F: Fn(K::Output, T) -> Result<R, E>,
E: From<StdError>,
{
let iter = map.range(store, start, None, Order::Ascending);
collect(iter, limit, parse_fn)
}