casper_types/
peers_map.rs1use alloc::collections::BTreeMap;
2
3use crate::bytesrepr::{self, FromBytes, ToBytes};
4use alloc::{
5 string::{String, ToString},
6 vec::Vec,
7};
8#[cfg(feature = "json-schema")]
9use schemars::JsonSchema;
10use serde::{Deserialize, Serialize};
11
12#[cfg(any(feature = "testing", test))]
13use crate::testing::TestRng;
14#[cfg(any(feature = "testing", test))]
15use core::iter;
16#[cfg(any(feature = "testing", test))]
17use rand::Rng;
18
19#[derive(Clone, PartialEq, Eq, Serialize, Deserialize, Debug)]
21#[cfg_attr(feature = "json-schema", derive(JsonSchema))]
22#[serde(deny_unknown_fields)]
23pub struct PeerEntry {
24 pub node_id: String,
26 pub address: String,
28}
29
30impl PeerEntry {
31 #[cfg(any(feature = "testing", test))]
32 pub(crate) fn random(rng: &mut TestRng) -> Self {
33 Self {
34 node_id: rng.random_string(10..20),
35 address: rng.random_string(10..20),
36 }
37 }
38}
39
40impl ToBytes for PeerEntry {
41 fn to_bytes(&self) -> Result<Vec<u8>, bytesrepr::Error> {
42 let mut buffer = bytesrepr::allocate_buffer(self)?;
43 self.write_bytes(&mut buffer)?;
44 Ok(buffer)
45 }
46
47 fn write_bytes(&self, writer: &mut Vec<u8>) -> Result<(), bytesrepr::Error> {
48 self.node_id.write_bytes(writer)?;
49 self.address.write_bytes(writer)
50 }
51
52 fn serialized_length(&self) -> usize {
53 self.node_id.serialized_length() + self.address.serialized_length()
54 }
55}
56
57impl FromBytes for PeerEntry {
58 fn from_bytes(bytes: &[u8]) -> Result<(Self, &[u8]), bytesrepr::Error> {
59 let (node_id, remainder) = String::from_bytes(bytes)?;
60 let (address, remainder) = String::from_bytes(remainder)?;
61 Ok((PeerEntry { node_id, address }, remainder))
62 }
63}
64
65#[derive(Clone, PartialEq, Eq, Serialize, Deserialize, Debug)]
67#[cfg_attr(feature = "json-schema", derive(JsonSchema))]
68#[serde(deny_unknown_fields)]
69pub struct Peers(Vec<PeerEntry>);
70
71impl Peers {
72 pub fn into_inner(self) -> Vec<PeerEntry> {
74 self.0
75 }
76
77 #[cfg(any(feature = "testing", test))]
79 pub fn random(rng: &mut TestRng) -> Self {
80 let count = rng.gen_range(0..10);
81 let peers = iter::repeat(())
82 .map(|_| PeerEntry::random(rng))
83 .take(count)
84 .collect();
85 Self(peers)
86 }
87}
88
89impl<Id: ToString> From<BTreeMap<Id, String>> for Peers {
90 fn from(input: BTreeMap<Id, String>) -> Self {
91 let ret = input
92 .into_iter()
93 .map(|(node_id, address)| PeerEntry {
94 node_id: node_id.to_string(),
95 address,
96 })
97 .collect();
98 Peers(ret)
99 }
100}
101
102impl ToBytes for Peers {
103 fn to_bytes(&self) -> Result<Vec<u8>, bytesrepr::Error> {
104 let mut buffer = bytesrepr::allocate_buffer(self)?;
105 self.write_bytes(&mut buffer)?;
106 Ok(buffer)
107 }
108
109 fn write_bytes(&self, writer: &mut Vec<u8>) -> Result<(), bytesrepr::Error> {
110 self.0.write_bytes(writer)
111 }
112
113 fn serialized_length(&self) -> usize {
114 self.0.serialized_length()
115 }
116}
117
118impl FromBytes for Peers {
119 fn from_bytes(bytes: &[u8]) -> Result<(Self, &[u8]), bytesrepr::Error> {
120 let (inner, remainder) = Vec::<PeerEntry>::from_bytes(bytes)?;
121 Ok((Peers(inner), remainder))
122 }
123}
124
125#[cfg(test)]
126mod tests {
127 use super::*;
128 use crate::testing::TestRng;
129
130 #[test]
131 fn bytesrepr_roundtrip() {
132 let rng = &mut TestRng::new();
133
134 let val = Peers::random(rng);
135 bytesrepr::test_serialization_roundtrip(&val);
136 }
137
138 #[test]
139 fn bytesrepr_empty_roundtrip() {
140 let val = Peers(vec![]);
141 bytesrepr::test_serialization_roundtrip(&val);
142 }
143
144 #[test]
145 fn bytesrepr_empty_vec_should_have_count_0() {
146 let val = Peers(vec![]);
147 let x = Peers::to_bytes(&val).expect("should have vec");
148 let (count, _) = u32::from_bytes(&x).expect("should have count");
149 assert!(count == 0, "count should be 0");
150 }
151}