1pub mod chain_sync;
14mod disconnected_peers;
15pub mod polkadot;
16pub mod state;
17pub mod state_sync;
18pub mod warp;
19
20use crate::sync::{
21 pending_responses::ResponseFuture,
22 service::network::NetworkServiceHandle,
23 types::{BadPeer, SyncStatus},
24};
25use soil_client::blockchain::Error as ClientError;
26use soil_client::consensus::BlockOrigin;
27use soil_client::import::{BlockImportError, BlockImportStatus, IncomingBlock};
28use soil_network::common::sync::message::BlockAnnounce;
29use soil_network::types::PeerId;
30use soil_network::ProtocolName;
31use std::any::Any;
32use subsoil::runtime::{
33 traits::{Block as BlockT, NumberFor},
34 Justifications,
35};
36
37pub trait SyncingStrategy<B: BlockT>: Send
39where
40 B: BlockT,
41{
42 fn add_peer(&mut self, peer_id: PeerId, best_hash: B::Hash, best_number: NumberFor<B>);
44
45 fn remove_peer(&mut self, peer_id: &PeerId);
47
48 #[must_use]
52 fn on_validated_block_announce(
53 &mut self,
54 is_best: bool,
55 peer_id: PeerId,
56 announce: &BlockAnnounce<B::Header>,
57 ) -> Option<(B::Hash, NumberFor<B>)>;
58
59 fn set_sync_fork_request(&mut self, peers: Vec<PeerId>, hash: &B::Hash, number: NumberFor<B>);
67
68 fn request_justification(&mut self, hash: &B::Hash, number: NumberFor<B>);
70
71 fn clear_justification_requests(&mut self);
73
74 fn on_justification_import(&mut self, hash: B::Hash, number: NumberFor<B>, success: bool);
76
77 fn on_generic_response(
82 &mut self,
83 peer_id: &PeerId,
84 key: StrategyKey,
85 protocol_name: ProtocolName,
86 response: Box<dyn Any + Send>,
87 );
88
89 fn on_blocks_processed(
94 &mut self,
95 imported: usize,
96 count: usize,
97 results: Vec<(Result<BlockImportStatus<NumberFor<B>>, BlockImportError>, B::Hash)>,
98 );
99
100 fn on_block_finalized(&mut self, hash: &B::Hash, number: NumberFor<B>);
102
103 fn update_chain_info(&mut self, best_hash: &B::Hash, best_number: NumberFor<B>);
105
106 fn is_major_syncing(&self) -> bool;
108
109 fn num_peers(&self) -> usize;
111
112 fn status(&self) -> SyncStatus<B>;
114
115 fn num_downloaded_blocks(&self) -> usize;
117
118 fn num_sync_requests(&self) -> usize;
120
121 #[must_use]
123 fn actions(
124 &mut self,
125 network_service: &NetworkServiceHandle,
127 ) -> Result<Vec<SyncingAction<B>>, ClientError>;
128}
129
130#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
132pub struct StrategyKey(&'static str);
133
134impl StrategyKey {
135 pub const fn new(key: &'static str) -> Self {
137 Self(key)
138 }
139}
140
141pub enum SyncingAction<B: BlockT> {
142 StartRequest {
144 peer_id: PeerId,
145 key: StrategyKey,
146 request: ResponseFuture,
147 remove_obsolete: bool,
149 },
150 CancelRequest { peer_id: PeerId, key: StrategyKey },
152 DropPeer(BadPeer),
154 ImportBlocks { origin: BlockOrigin, blocks: Vec<IncomingBlock<B>> },
156 ImportJustifications {
158 peer_id: PeerId,
159 hash: B::Hash,
160 number: NumberFor<B>,
161 justifications: Justifications,
162 },
163 Finished,
165}
166
167impl<B> std::fmt::Debug for SyncingAction<B>
170where
171 B: BlockT,
172{
173 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
174 match &self {
175 Self::StartRequest { peer_id, key, remove_obsolete, .. } => {
176 write!(
177 f,
178 "StartRequest {{ peer_id: {:?}, key: {:?}, remove_obsolete: {:?} }}",
179 peer_id, key, remove_obsolete
180 )
181 },
182 Self::CancelRequest { peer_id, key } => {
183 write!(f, "CancelRequest {{ peer_id: {:?}, key: {:?} }}", peer_id, key)
184 },
185 Self::DropPeer(peer) => write!(f, "DropPeer({:?})", peer),
186 Self::ImportBlocks { blocks, .. } => write!(f, "ImportBlocks({:?})", blocks),
187 Self::ImportJustifications { hash, number, .. } => {
188 write!(f, "ImportJustifications({:?}, {:?})", hash, number)
189 },
190 Self::Finished => write!(f, "Finished"),
191 }
192 }
193}
194
195impl<B: BlockT> SyncingAction<B> {
196 pub fn is_finished(&self) -> bool {
198 matches!(self, SyncingAction::Finished)
199 }
200
201 #[cfg(test)]
202 pub(crate) fn name(&self) -> &'static str {
203 match self {
204 Self::StartRequest { .. } => "StartRequest",
205 Self::CancelRequest { .. } => "CancelRequest",
206 Self::DropPeer(_) => "DropPeer",
207 Self::ImportBlocks { .. } => "ImportBlocks",
208 Self::ImportJustifications { .. } => "ImportJustifications",
209 Self::Finished => "Finished",
210 }
211 }
212}