Radish alpha
h
Radicle Heartwood Protocol & Stack
Radicle
Git (anonymous pull)
Log in to clone via SSH
node: Allow rate-limitting to be configurable
Alexis Sellier committed 2 years ago
commit a7cd7b25f56ccef812b40f64d31e2565adfc1f4f
parent af724eeb0dde8836bbc610424cf661d41746fa98
3 files changed +48 -12
modified radicle-node/src/service.rs
@@ -738,7 +738,10 @@ where
        }
        let host: HostName = addr.into();

-
        if self.limiter.limit(host.clone(), &Link::Inbound, self.clock) {
+
        if self
+
            .limiter
+
            .limit(host.clone(), &self.config.limits.rate.inbound, self.clock)
+
        {
            trace!(target: "service", "Rate limitting inbound connection from {host}..");
            return false;
        }
@@ -1132,9 +1135,13 @@ where
            warn!(target: "service", "Session not found for {remote}");
            return Ok(());
        };
+
        let limit = match peer.link {
+
            Link::Outbound => &self.config.limits.rate.outbound,
+
            Link::Inbound => &self.config.limits.rate.inbound,
+
        };
        if self
            .limiter
-
            .limit(peer.addr.clone().into(), &peer.link, self.clock)
+
            .limit(peer.addr.clone().into(), limit, self.clock)
        {
            trace!(target: "service", "Rate limiting message from {remote} ({})", peer.addr);
            return Ok(());
modified radicle-node/src/service/limitter.rs
@@ -1,7 +1,7 @@
use std::collections::HashMap;

use localtime::LocalTime;
-
use radicle::node::HostName;
+
use radicle::node::{config, HostName};

/// Peer rate limitter.
///
@@ -38,19 +38,13 @@ pub trait AsTokens {
    fn rate(&self) -> f64;
}

-
impl AsTokens for crate::Link {
+
impl AsTokens for config::RateLimit {
    fn rate(&self) -> f64 {
-
        match self {
-
            Self::Inbound => 0.1,
-
            Self::Outbound => 1.0,
-
        }
+
        self.fill_rate
    }

    fn capacity(&self) -> usize {
-
        match self {
-
            Self::Inbound => 16,
-
            Self::Outbound => 64,
-
        }
+
        self.capacity
    }
}

modified radicle/src/node/config.rs
@@ -57,6 +57,9 @@ pub struct Limits {
    pub routing_max_age: LocalDuration,
    /// Maximum number of concurrent fetches per per connection.
    pub fetch_concurrency: usize,
+
    /// Rate limitter settings.
+
    #[serde(default)]
+
    pub rate: RateLimits,
}

impl Default for Limits {
@@ -65,6 +68,38 @@ impl Default for Limits {
            routing_max_size: 1000,
            routing_max_age: LocalDuration::from_mins(7 * 24 * 60),
            fetch_concurrency: 1,
+
            rate: RateLimits::default(),
+
        }
+
    }
+
}
+

+
/// Rate limts for a single connection.
+
#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
+
#[serde(rename_all = "camelCase")]
+
pub struct RateLimit {
+
    pub fill_rate: f64,
+
    pub capacity: usize,
+
}
+

+
/// Rate limits for inbound and outbound connections.
+
#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
+
#[serde(rename_all = "camelCase")]
+
pub struct RateLimits {
+
    pub inbound: RateLimit,
+
    pub outbound: RateLimit,
+
}
+

+
impl Default for RateLimits {
+
    fn default() -> Self {
+
        Self {
+
            inbound: RateLimit {
+
                fill_rate: 0.1,
+
                capacity: 16,
+
            },
+
            outbound: RateLimit {
+
                fill_rate: 1.0,
+
                capacity: 64,
+
            },
        }
    }
}