ab_farmer_rpc_primitives/
lib.rs

1//! Primitives for the farmer
2
3use ab_core_primitives::block::BlockRoot;
4use ab_core_primitives::block::header::OwnedBlockHeaderSeal;
5use ab_core_primitives::hashes::Blake3Hash;
6use ab_core_primitives::pot::SlotNumber;
7use ab_core_primitives::solutions::{Solution, SolutionRange};
8use ab_farmer_components::FarmerProtocolInfo;
9use ab_networking::libp2p::Multiaddr;
10use parity_scale_codec::{Decode, Encode, EncodeLike, Input, Output};
11use serde::{Deserialize, Serialize};
12use std::time::Duration;
13
14/// Defines a limit for number of segments that can be requested over RPC
15pub const MAX_SEGMENT_HEADERS_PER_REQUEST: usize = 1000;
16
17/// Information necessary for farmer application
18#[derive(Debug, Clone, Serialize, Deserialize)]
19#[serde(rename_all = "camelCase")]
20pub struct FarmerAppInfo {
21    /// Genesis root of the beacon chain
22    pub genesis_root: BlockRoot,
23    /// Bootstrap nodes for DSN
24    pub dsn_bootstrap_nodes: Vec<Multiaddr>,
25    /// Whether node is syncing right now
26    pub syncing: bool,
27    /// How much time farmer has to audit sectors and generate a solution
28    pub farming_timeout: Duration,
29    /// Protocol info for farmer
30    pub protocol_info: FarmerProtocolInfo,
31}
32
33impl Encode for FarmerAppInfo {
34    fn size_hint(&self) -> usize {
35        0_usize
36            .saturating_add(Encode::size_hint(&self.genesis_root))
37            .saturating_add(Encode::size_hint(
38                &self
39                    .dsn_bootstrap_nodes
40                    .iter()
41                    .map(|addr| addr.as_ref())
42                    .collect::<Vec<_>>(),
43            ))
44            .saturating_add(Encode::size_hint(&self.syncing))
45            .saturating_add(Encode::size_hint(&self.farming_timeout))
46            .saturating_add(Encode::size_hint(&self.protocol_info))
47    }
48
49    fn encode_to<O: Output + ?Sized>(&self, output: &mut O) {
50        Encode::encode_to(&self.genesis_root, output);
51        Encode::encode_to(
52            &self
53                .dsn_bootstrap_nodes
54                .iter()
55                .map(|addr| addr.as_ref())
56                .collect::<Vec<_>>(),
57            output,
58        );
59        Encode::encode_to(&self.syncing, output);
60        Encode::encode_to(&self.farming_timeout, output);
61        Encode::encode_to(&self.protocol_info, output);
62    }
63}
64
65impl EncodeLike for FarmerAppInfo {}
66
67impl Decode for FarmerAppInfo {
68    fn decode<I: Input>(input: &mut I) -> Result<Self, parity_scale_codec::Error> {
69        Ok(FarmerAppInfo {
70            genesis_root: BlockRoot::decode(input)
71                .map_err(|error| error.chain("Could not decode `FarmerAppInfo::genesis_root`"))?,
72            dsn_bootstrap_nodes: Vec::<Vec<u8>>::decode(input)
73                .map_err(|error| {
74                    error.chain("Could not decode `FarmerAppInfo::dsn_bootstrap_nodes`")
75                })?
76                .into_iter()
77                .map(Multiaddr::try_from)
78                .collect::<Result<Vec<_>, _>>()
79                .map_err(|error| {
80                    parity_scale_codec::Error::from("Failed to decode bytes as Multiaddr")
81                        .chain(error.to_string())
82                        .chain("Could not decode `FarmerAppInfo::dsn_bootstrap_nodes`")
83                })?,
84            syncing: bool::decode(input)
85                .map_err(|error| error.chain("Could not decode `FarmerAppInfo::syncing`"))?,
86            farming_timeout: Duration::decode(input).map_err(|error| {
87                error.chain("Could not decode `FarmerAppInfo::farming_timeout`")
88            })?,
89            protocol_info: FarmerProtocolInfo::decode(input)
90                .map_err(|error| error.chain("Could not decode `FarmerAppInfo::protocol_info`"))?,
91        })
92    }
93}
94
95/// Information about new slot that just arrived
96#[derive(Debug, Copy, Clone, Eq, PartialEq, Encode, Decode, Serialize, Deserialize)]
97#[serde(rename_all = "camelCase")]
98pub struct SlotInfo {
99    /// Slot number
100    pub slot_number: SlotNumber,
101    /// Global slot challenge
102    pub global_challenge: Blake3Hash,
103    /// Acceptable solution range for block authoring
104    pub solution_range: SolutionRange,
105}
106
107/// Response of a slot challenge consisting of an optional solution and
108/// the submitter(farmer)'s secret key for block signing.
109#[derive(Clone, Debug, Encode, Decode, Serialize, Deserialize)]
110#[serde(rename_all = "camelCase")]
111pub struct SolutionResponse {
112    /// Slot number.
113    pub slot_number: SlotNumber,
114    /// Solution farmer has for the challenge.
115    ///
116    /// Corresponds to `slot_number` above.
117    pub solution: Solution,
118}
119
120/// Block sealing info
121#[derive(Clone, Copy, Debug, Encode, Decode, Serialize, Deserialize)]
122#[serde(rename_all = "camelCase")]
123pub struct BlockSealInfo {
124    /// Block pre-seal hash to be signed
125    pub pre_seal_hash: Blake3Hash,
126    /// Public key hash of the plot identity that should create signature
127    pub public_key_hash: Blake3Hash,
128}
129
130/// Block sealing response
131#[derive(Clone, Copy, Debug, Encode, Decode, Serialize, Deserialize)]
132#[serde(rename_all = "camelCase")]
133pub struct BlockSealResponse {
134    /// Block pre-seal hash that was signed
135    pub pre_seal_hash: Blake3Hash,
136    /// The seal itself
137    pub seal: OwnedBlockHeaderSeal,
138}