mod message_stream;
mod reactor;
pub mod connector;
use std::{io, net::SocketAddr, num::NonZeroUsize};
use crate::connector::Target;
pub use message_stream::StreamConfig;
pub use reactor::{Handle, run, run_with_connector};
#[cfg(feature = "socks")]
pub use reactor::run_with_socks5_proxy;
#[cfg(not(feature = "async"))]
pub use crossbeam_channel;
#[cfg(feature = "async")]
pub use async_channel;
#[derive(Debug, Clone)]
pub struct Config {
pub bind_addr: Vec<std::net::SocketAddr>,
pub stream_config: StreamConfig,
pub receive_buffer_size: usize,
pub receive_channel_size: Option<NonZeroUsize>,
}
impl Default for Config {
fn default() -> Self {
Self {
bind_addr: Default::default(),
stream_config: Default::default(),
receive_buffer_size: 1024 * 1024,
receive_channel_size: None,
}
}
}
pub trait Message: std::fmt::Debug + Sized + Send + Sync + 'static {
const MAX_SIZE: usize;
fn encode(&self, sink: &mut impl std::io::Write) -> usize;
fn decode(buffer: &[u8]) -> Result<(Self, usize), DecodeError>;
fn size_hint(&self) -> Option<usize> {
None
}
}
pub enum DecodeError {
NotEnoughData,
MalformedMessage,
}
#[derive(Debug, Clone, Hash, Copy, PartialEq, Eq, PartialOrd, Ord)]
pub struct PeerId(u64);
impl PeerId {
pub fn set_raw(value: u64) -> Self {
Self(value)
}
pub fn next(&self) -> Self {
Self(self.0 + 1)
}
pub fn inner(&self) -> u64 {
self.0
}
}
impl std::fmt::Display for PeerId {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(f, "{}", self.0)
}
}
#[derive(Debug)]
pub enum Command<M: Message> {
Connect(Target),
Disconnect(PeerId),
Message(PeerId, M),
}
impl<M: Message> Command<M> {
pub fn connect(target: impl Into<Target>) -> Self {
Self::Connect(target.into())
}
}
#[derive(Debug)]
pub enum Event<M: Message> {
ConnectedTo {
target: Target,
result: io::Result<PeerId>,
},
ConnectedFrom {
peer: PeerId,
addr: SocketAddr,
interface: SocketAddr,
},
Disconnected {
peer: PeerId,
reason: DisconnectReason,
},
Message {
peer: PeerId,
message: M,
size: usize,
},
NoPeer(PeerId),
SendBufferFull {
peer: PeerId,
message: M,
},
}
#[derive(Debug)]
pub enum DisconnectReason {
Requested,
Left,
CodecViolation,
WriteStale,
Error(io::Error),
}