stats_accounting

This commit is contained in:
John Smith 2022-03-19 18:19:40 -04:00
parent babe176747
commit 3888a832a0
19 changed files with 285 additions and 67 deletions

3
.gitmodules vendored
View File

@ -25,3 +25,6 @@
[submodule "external/mdns"]
path = external/mdns
url = ../mdns.git
[submodule "external/hashlink"]
path = external/hashlink
url = ../hashlink.git

1
Cargo.lock generated
View File

@ -4201,6 +4201,7 @@ dependencies = [
"generic-array 0.14.5",
"getrandom 0.2.5",
"hashbrown 0.12.0",
"hashlink",
"hex",
"ifstructs",
"jni",

1
external/hashlink vendored Submodule

@ -0,0 +1 @@
Subproject commit f5846ec3ff06865a204114bd710253e7e67e4498

View File

@ -26,6 +26,7 @@ generic-array = "^0"
secrecy = "^0"
chacha20poly1305 = "^0"
uluru = "^3"
hashlink = "^0"
serde-big-array = "^0"
futures-util = { version = "^0", default_features = false, features = ["alloc"] }
parking_lot = "^0"

View File

@ -4,8 +4,8 @@ use crate::network_connection::*;
use crate::network_manager::*;
use crate::xx::*;
use crate::*;
use futures_util::future::{select, Either};
use futures_util::stream::{FuturesUnordered, StreamExt};
use futures_util::{select, FutureExt};
const CONNECTION_PROCESSOR_CHANNEL_SIZE: usize = 128usize;
@ -162,12 +162,28 @@ impl ConnectionManager {
Box::pin(async move {
//
let descriptor = conn.connection_descriptor();
let inactivity_timeout = this
.network_manager()
.config()
.get()
.network
.connection_inactivity_timeout_ms;
loop {
let res = conn.clone().recv().await;
let message = match res {
Ok(v) => v,
Err(e) => {
log_net!(error e);
// process inactivity timeout on receives only
// if you want a keepalive, it has to be requested from the other side
let message = select! {
res = conn.recv().fuse() => {
match res {
Ok(v) => v,
Err(e) => {
log_net!(error e);
break;
}
}
}
_ = intf::sleep(inactivity_timeout).fuse()=> {
// timeout
log_net!("connection timeout on {:?}", descriptor);
break;
}
};
@ -201,8 +217,8 @@ impl ConnectionManager {
FuturesUnordered::new();
loop {
// Either process an existing connection, or receive a new one to add to our list
match select(connection_futures.next(), Box::pin(rx.recv_async())).await {
Either::Left((x, _)) => {
select! {
x = connection_futures.next().fuse() => {
// Processed some connection to completion, or there are none left
match x {
Some(()) => {
@ -222,7 +238,7 @@ impl ConnectionManager {
}
}
}
Either::Right((x, _)) => {
x = rx.recv_async().fuse() => {
// Got a new connection future
match x {
Ok(v) => {

View File

@ -8,7 +8,6 @@ use core::convert::TryInto;
use curve25519_dalek as cd;
use ed25519_dalek as ed;
use serde::{Deserialize, Serialize};
use serde_big_array::*;
use uluru;
use x25519_dalek as xd;
@ -18,11 +17,6 @@ pub type Nonce = [u8; 24];
const DH_CACHE_SIZE: usize = 1024;
pub const ENCRYPTION_OVERHEAD: usize = 16;
big_array! {
BigArray;
DH_CACHE_SIZE
}
type DHCache = uluru::LRUCache<DHCacheEntry, DH_CACHE_SIZE>;
#[derive(Serialize, Deserialize)]

View File

@ -55,16 +55,21 @@ impl DummyNetworkConnection {
///////////////////////////////////////////////////////////
// Top-level protocol independent network connection object
#[derive(Debug)]
struct NetworkConnectionInner {
#[derive(Debug, Clone)]
pub struct NetworkConnectionStats {
last_message_sent_time: Option<u64>,
last_message_recv_time: Option<u64>,
established_time: u64,
}
#[derive(Debug)]
struct NetworkConnectionInner {
stats: NetworkConnectionStats,
}
#[derive(Debug)]
struct NetworkConnectionArc {
descriptor: ConnectionDescriptor,
established_time: u64,
protocol_connection: ProtocolNetworkConnection,
inner: Mutex<NetworkConnectionInner>,
}
@ -84,8 +89,11 @@ impl Eq for NetworkConnection {}
impl NetworkConnection {
fn new_inner() -> NetworkConnectionInner {
NetworkConnectionInner {
last_message_sent_time: None,
last_message_recv_time: None,
stats: NetworkConnectionStats {
last_message_sent_time: None,
last_message_recv_time: None,
established_time: intf::get_timestamp(),
},
}
}
fn new_arc(
@ -94,7 +102,6 @@ impl NetworkConnection {
) -> NetworkConnectionArc {
NetworkConnectionArc {
descriptor,
established_time: intf::get_timestamp(),
protocol_connection,
inner: Mutex::new(Self::new_inner()),
}
@ -136,7 +143,7 @@ impl NetworkConnection {
let out = self.arc.protocol_connection.send(message).await;
if out.is_ok() {
let mut inner = self.arc.inner.lock();
inner.last_message_sent_time.max_assign(Some(ts));
inner.stats.last_message_sent_time.max_assign(Some(ts));
}
out
}
@ -145,8 +152,13 @@ impl NetworkConnection {
let out = self.arc.protocol_connection.recv().await;
if out.is_ok() {
let mut inner = self.arc.inner.lock();
inner.last_message_recv_time.max_assign(Some(ts));
inner.stats.last_message_recv_time.max_assign(Some(ts));
}
out
}
pub fn stats(&self) -> NetworkConnectionStats {
let inner = self.arc.inner.lock();
inner.stats.clone()
}
}

View File

@ -11,6 +11,8 @@ use xx::*;
////////////////////////////////////////////////////////////////////////////////////////
pub const MAX_MESSAGE_SIZE: usize = MAX_ENVELOPE_SIZE;
pub const IPADDR_TABLE_SIZE: usize = 1024;
pub const IPADDR_MAX_INACTIVE_DURATION_US: u64 = 300_000_000u64; // 5 minutes
#[derive(Copy, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
pub enum NetworkClass {
@ -79,11 +81,33 @@ struct NetworkComponents {
receipt_manager: ReceiptManager,
}
// Statistics per address
#[derive(Clone, Default)]
pub struct PerAddressStats {
last_seen_ts: u64,
transfer_stats_accounting: TransferStatsAccounting,
transfer_stats: TransferStatsDownUp,
}
// Statistics about the low-level network
#[derive(Clone, Default)]
pub struct NetworkManagerStats {
self_stats: PerAddressStats,
per_address_stats: HashMap<IpAddr, PerAddressStats>,
recent_addresses: VecDeque<IpAddr>,
}
// The mutable state of the network manager
pub struct NetworkManagerInner {
struct NetworkManagerInner {
routing_table: Option<RoutingTable>,
components: Option<NetworkComponents>,
network_class: Option<NetworkClass>,
stats: NetworkManagerStats,
}
struct NetworkManagerUnlockedInner {
// Background processes
rolling_transfers_task: TickTask,
}
#[derive(Clone)]
@ -92,6 +116,7 @@ pub struct NetworkManager {
table_store: TableStore,
crypto: Crypto,
inner: Arc<Mutex<NetworkManagerInner>>,
unlocked_inner: Arc<NetworkManagerUnlockedInner>,
}
impl NetworkManager {
@ -100,16 +125,34 @@ impl NetworkManager {
routing_table: None,
components: None,
network_class: None,
stats: NetworkManagerStats::default(),
}
}
fn new_unlocked_inner(_config: VeilidConfig) -> NetworkManagerUnlockedInner {
//let c = config.get();
NetworkManagerUnlockedInner {
rolling_transfers_task: TickTask::new(ROLLING_TRANSFERS_INTERVAL_SECS),
}
}
pub fn new(config: VeilidConfig, table_store: TableStore, crypto: Crypto) -> Self {
Self {
config,
let this = Self {
config: config.clone(),
table_store,
crypto,
inner: Arc::new(Mutex::new(Self::new_inner())),
unlocked_inner: Arc::new(Self::new_unlocked_inner(config)),
};
// Set rolling transfers tick task
{
let this2 = this.clone();
this.unlocked_inner
.rolling_transfers_task
.set_routine(move |l, t| {
Box::pin(this2.clone().rolling_transfers_task_routine(l, t))
});
}
this
}
pub fn config(&self) -> VeilidConfig {
self.config.clone()
@ -546,4 +589,76 @@ impl NetworkManager {
// Inform caller that we dealt with the envelope locally
Ok(true)
}
// Compute transfer statistics for the low level network
async fn rolling_transfers_task_routine(self, last_ts: u64, cur_ts: u64) -> Result<(), String> {
log_net!("--- network manager rolling_transfers task");
let inner = &mut *self.inner.lock();
// Roll the low level network transfer stats for our address
inner
.stats
.self_stats
.transfer_stats_accounting
.roll_transfers(last_ts, cur_ts, &mut inner.stats.self_stats.transfer_stats);
// Roll all per-address transfers
let mut dead_addrs: HashSet<IpAddr> = HashSet::new();
for (addr, stats) in &mut inner.stats.per_address_stats {
stats.transfer_stats_accounting.roll_transfers(
last_ts,
cur_ts,
&mut stats.transfer_stats,
);
// While we're here, lets see if this address has timed out
if cur_ts - stats.last_seen_ts >= IPADDR_MAX_INACTIVE_DURATION_US {
// it's dead, put it in the dead list
dead_addrs.insert(*addr);
}
}
// Remove the dead addresses from our tables
for da in &dead_addrs {
inner.stats.per_address_stats.remove(da);
}
inner
.stats
.recent_addresses
.retain(|a| !dead_addrs.contains(a));
Ok(())
}
// Callbacks from low level network for statistics gathering
fn packet_sent(&self, addr: IpAddr, bytes: u64) {
let inner = &mut *self.inner.lock();
inner
.stats
.self_stats
.transfer_stats_accounting
.add_up(bytes);
inner
.stats
.per_address_stats
.entry(addr)
.or_default()
.transfer_stats_accounting
.add_up(bytes);
}
fn packet_rcvd(&self, addr: IpAddr, bytes: u64) {
let inner = &mut *self.inner.lock();
inner
.stats
.self_stats
.transfer_stats_accounting
.add_down(bytes);
inner
.stats
.per_address_stats
.entry(addr)
.or_default()
.transfer_stats_accounting
.add_down(bytes);
}
}

View File

@ -32,7 +32,8 @@ pub struct BucketEntry {
min_max_version: Option<(u8, u8)>,
last_connection: Option<(ConnectionDescriptor, u64)>,
dial_infos: Vec<DialInfo>,
stats_accounting: StatsAccounting,
latency_stats_accounting: LatencyStatsAccounting,
transfer_stats_accounting: TransferStatsAccounting,
peer_stats: PeerStats,
}
@ -44,7 +45,8 @@ impl BucketEntry {
min_max_version: None,
last_connection: None,
dial_infos: Vec::new(),
stats_accounting: StatsAccounting::new(),
latency_stats_accounting: LatencyStatsAccounting::new(),
transfer_stats_accounting: TransferStatsAccounting::new(),
peer_stats: PeerStats {
time_added: now,
last_seen: None,
@ -133,13 +135,16 @@ impl BucketEntry {
///// stats methods
// called every ROLLING_TRANSFERS_INTERVAL_SECS seconds
pub(super) fn roll_transfers(&mut self, last_ts: u64, cur_ts: u64) {
self.stats_accounting
.roll_transfers(last_ts, cur_ts, &mut self.peer_stats.transfer);
self.transfer_stats_accounting.roll_transfers(
last_ts,
cur_ts,
&mut self.peer_stats.transfer,
);
}
// Called for every round trip packet we receive
fn record_latency(&mut self, latency: u64) {
self.peer_stats.latency = Some(self.stats_accounting.record_latency(latency));
self.peer_stats.latency = Some(self.latency_stats_accounting.record_latency(latency));
}
///// state machine handling
@ -255,7 +260,7 @@ impl BucketEntry {
pub(super) fn ping_sent(&mut self, ts: u64, bytes: u64) {
self.peer_stats.ping_stats.total_sent += 1;
self.stats_accounting.add_up(bytes);
self.transfer_stats_accounting.add_up(bytes);
self.peer_stats.ping_stats.in_flight += 1;
self.peer_stats.ping_stats.last_pinged = Some(ts);
// if we haven't heard from this node yet and it's our first attempt at contacting it
@ -265,14 +270,14 @@ impl BucketEntry {
}
}
pub(super) fn ping_rcvd(&mut self, ts: u64, bytes: u64) {
self.stats_accounting.add_down(bytes);
self.transfer_stats_accounting.add_down(bytes);
self.touch_last_seen(ts);
}
pub(super) fn pong_sent(&mut self, _ts: u64, bytes: u64) {
self.stats_accounting.add_up(bytes);
self.transfer_stats_accounting.add_up(bytes);
}
pub(super) fn pong_rcvd(&mut self, send_ts: u64, recv_ts: u64, bytes: u64) {
self.stats_accounting.add_down(bytes);
self.transfer_stats_accounting.add_down(bytes);
self.peer_stats.ping_stats.in_flight -= 1;
self.peer_stats.ping_stats.total_returned += 1;
self.peer_stats.ping_stats.consecutive_pongs += 1;
@ -294,7 +299,7 @@ impl BucketEntry {
self.peer_stats.ping_stats.first_consecutive_pong_time = None;
}
pub(super) fn question_sent(&mut self, ts: u64, bytes: u64) {
self.stats_accounting.add_up(bytes);
self.transfer_stats_accounting.add_up(bytes);
// if we haven't heard from this node yet and it's our first attempt at contacting it
// then we set the last_seen time
if self.peer_stats.last_seen.is_none() {
@ -302,14 +307,14 @@ impl BucketEntry {
}
}
pub(super) fn question_rcvd(&mut self, ts: u64, bytes: u64) {
self.stats_accounting.add_down(bytes);
self.transfer_stats_accounting.add_down(bytes);
self.touch_last_seen(ts);
}
pub(super) fn answer_sent(&mut self, _ts: u64, bytes: u64) {
self.stats_accounting.add_up(bytes);
self.transfer_stats_accounting.add_up(bytes);
}
pub(super) fn answer_rcvd(&mut self, send_ts: u64, recv_ts: u64, bytes: u64) {
self.stats_accounting.add_down(bytes);
self.transfer_stats_accounting.add_down(bytes);
self.record_latency(recv_ts - send_ts);
self.touch_last_seen(recv_ts);
}

View File

@ -7,8 +7,14 @@ impl RoutingTable {
out += "Routing Table Info:\n";
out += &format!(" Node Id: {}\n", inner.node_id.encode());
out += &format!(" Stats Accounting: {:#?}\n\n", inner.stats_accounting);
out += &format!(" Transfer Stats: {:#?}\n\n", inner.transfer_stats);
out += &format!(
" Self Transfer Stats Accounting: {:#?}\n\n",
inner.self_transfer_stats_accounting
);
out += &format!(
" Self Transfer Stats: {:#?}\n\n",
inner.self_transfer_stats
);
out
}

View File

@ -50,12 +50,14 @@ struct RoutingTableInner {
buckets: Vec<Bucket>,
dial_info_details: Vec<DialInfoDetail>,
bucket_entry_count: usize,
// Waiters
eventual_changed_dial_info: Eventual,
// Transfer stats for this node
stats_accounting: StatsAccounting,
// latency: Option<LatencyStats>,
transfer_stats: TransferStatsDownUp,
self_latency_stats_accounting: LatencyStatsAccounting,
self_transfer_stats_accounting: TransferStatsAccounting,
self_transfer_stats: TransferStatsDownUp,
}
struct RoutingTableUnlockedInner {
@ -83,8 +85,9 @@ impl RoutingTable {
dial_info_details: Vec::new(),
bucket_entry_count: 0,
eventual_changed_dial_info: Eventual::new(),
stats_accounting: StatsAccounting::new(),
transfer_stats: TransferStatsDownUp::default(),
self_latency_stats_accounting: LatencyStatsAccounting::new(),
self_transfer_stats_accounting: TransferStatsAccounting::new(),
self_transfer_stats: TransferStatsDownUp::default(),
}
}
fn new_unlocked_inner(config: VeilidConfig) -> RoutingTableUnlockedInner {
@ -609,9 +612,11 @@ impl RoutingTable {
let inner = &mut *self.inner.lock();
// Roll our own node's transfers
inner
.stats_accounting
.roll_transfers(last_ts, cur_ts, &mut inner.transfer_stats);
inner.self_transfer_stats_accounting.roll_transfers(
last_ts,
cur_ts,
&mut inner.self_transfer_stats,
);
// Roll all bucket entry transfers
for b in &mut inner.buckets {
@ -649,25 +654,37 @@ impl RoutingTable {
// Stats Accounting
pub fn ping_sent(&self, node_ref: NodeRef, ts: u64, bytes: u64) {
self.inner.lock().stats_accounting.add_up(bytes);
self.inner
.lock()
.self_transfer_stats_accounting
.add_up(bytes);
node_ref.operate(|e| {
e.ping_sent(ts, bytes);
})
}
pub fn ping_rcvd(&self, node_ref: NodeRef, ts: u64, bytes: u64) {
self.inner.lock().stats_accounting.add_down(bytes);
self.inner
.lock()
.self_transfer_stats_accounting
.add_down(bytes);
node_ref.operate(|e| {
e.ping_rcvd(ts, bytes);
})
}
pub fn pong_sent(&self, node_ref: NodeRef, ts: u64, bytes: u64) {
self.inner.lock().stats_accounting.add_up(bytes);
self.inner
.lock()
.self_transfer_stats_accounting
.add_up(bytes);
node_ref.operate(|e| {
e.pong_sent(ts, bytes);
})
}
pub fn pong_rcvd(&self, node_ref: NodeRef, send_ts: u64, recv_ts: u64, bytes: u64) {
self.inner.lock().stats_accounting.add_down(bytes);
self.inner
.lock()
.self_transfer_stats_accounting
.add_down(bytes);
node_ref.operate(|e| {
e.pong_rcvd(send_ts, recv_ts, bytes);
})
@ -678,25 +695,37 @@ impl RoutingTable {
})
}
pub fn question_sent(&self, node_ref: NodeRef, ts: u64, bytes: u64) {
self.inner.lock().stats_accounting.add_up(bytes);
self.inner
.lock()
.self_transfer_stats_accounting
.add_up(bytes);
node_ref.operate(|e| {
e.question_sent(ts, bytes);
})
}
pub fn question_rcvd(&self, node_ref: NodeRef, ts: u64, bytes: u64) {
self.inner.lock().stats_accounting.add_down(bytes);
self.inner
.lock()
.self_transfer_stats_accounting
.add_down(bytes);
node_ref.operate(|e| {
e.question_rcvd(ts, bytes);
})
}
pub fn answer_sent(&self, node_ref: NodeRef, ts: u64, bytes: u64) {
self.inner.lock().stats_accounting.add_up(bytes);
self.inner
.lock()
.self_transfer_stats_accounting
.add_up(bytes);
node_ref.operate(|e| {
e.answer_sent(ts, bytes);
})
}
pub fn answer_rcvd(&self, node_ref: NodeRef, send_ts: u64, recv_ts: u64, bytes: u64) {
self.inner.lock().stats_accounting.add_down(bytes);
self.inner
.lock()
.self_transfer_stats_accounting
.add_down(bytes);
node_ref.operate(|e| {
e.answer_rcvd(send_ts, recv_ts, bytes);
})

View File

@ -19,16 +19,14 @@ pub struct TransferCount {
}
#[derive(Debug, Clone, Default)]
pub struct StatsAccounting {
rolling_latencies: VecDeque<u64>,
pub struct TransferStatsAccounting {
rolling_transfers: VecDeque<TransferCount>,
current_transfer: TransferCount,
}
impl StatsAccounting {
impl TransferStatsAccounting {
pub fn new() -> Self {
Self {
rolling_latencies: VecDeque::new(),
rolling_transfers: VecDeque::new(),
current_transfer: TransferCount::default(),
}
@ -79,6 +77,19 @@ impl StatsAccounting {
transfer_stats.down.average /= len;
transfer_stats.up.average /= len;
}
}
#[derive(Debug, Clone, Default)]
pub struct LatencyStatsAccounting {
rolling_latencies: VecDeque<u64>,
}
impl LatencyStatsAccounting {
pub fn new() -> Self {
Self {
rolling_latencies: VecDeque::new(),
}
}
pub fn record_latency(&mut self, latency: u64) -> veilid_api::LatencyStats {
while self.rolling_latencies.len() >= ROLLING_LATENCIES_SIZE {

View File

@ -187,6 +187,7 @@ fn config_callback(key: String) -> ConfigCallbackReturn {
"protected_store.delete" => Ok(Box::new(false)),
"network.max_connections" => Ok(Box::new(16u32)),
"network.connection_initial_timeout_ms" => Ok(Box::new(2_000u32)),
"network.connection_inactivity_timeout_ms" => Ok(Box::new(60_000u32)),
"network.node_id" => Ok(Box::new(dht::key::DHTKey::default())),
"network.node_id_secret" => Ok(Box::new(dht::key::DHTKeySecret::default())),
"network.bootstrap" => Ok(Box::new(Vec::<String>::new())),
@ -291,6 +292,7 @@ pub async fn test_config() {
assert_eq!(inner.protected_store.delete, false);
assert_eq!(inner.network.max_connections, 16);
assert_eq!(inner.network.connection_initial_timeout_ms, 2_000u32);
assert_eq!(inner.network.connection_inactivity_timeout_ms, 60_000u32);
assert!(!inner.network.node_id.valid);
assert!(!inner.network.node_id_secret.valid);
assert_eq!(inner.network.bootstrap, Vec::<String>::new());

View File

@ -880,12 +880,6 @@ pub struct LatencyStats {
pub slowest: u64, // slowest latency in the ROLLING_LATENCIES_SIZE last latencies
}
#[derive(Clone, Debug, Default, Serialize, Deserialize)]
pub struct TransferStatsDownUp {
pub down: TransferStats,
pub up: TransferStats,
}
#[derive(Clone, Debug, Default, Serialize, Deserialize)]
pub struct TransferStats {
pub total: u64, // total amount transferred ever
@ -894,6 +888,12 @@ pub struct TransferStats {
pub minimum: u64, // minimum rate over the ROLLING_TRANSFERS_SIZE last amounts
}
#[derive(Clone, Debug, Default, Serialize, Deserialize)]
pub struct TransferStatsDownUp {
pub down: TransferStats,
pub up: TransferStats,
}
#[derive(Clone, Debug, Default, Serialize, Deserialize)]
pub struct PingStats {
pub in_flight: u32, // number of pings issued that have yet to be answered

View File

@ -128,6 +128,7 @@ pub struct VeilidConfigLeases {
pub struct VeilidConfigNetwork {
pub max_connections: u32,
pub connection_initial_timeout_ms: u32,
pub connection_inactivity_timeout_ms: u32,
pub node_id: key::DHTKey,
pub node_id_secret: key::DHTKeySecret,
pub bootstrap: Vec<String>,
@ -282,6 +283,7 @@ impl VeilidConfig {
get_config!(inner.network.node_id_secret);
get_config!(inner.network.max_connections);
get_config!(inner.network.connection_initial_timeout_ms);
get_config!(inner.network.connection_inactivity_timeout_ms);
get_config!(inner.network.bootstrap);
get_config!(inner.network.dht.resolve_node_timeout_ms);
get_config!(inner.network.dht.resolve_node_count);

View File

@ -31,8 +31,12 @@ cfg_if! {
if #[cfg(target_arch = "wasm32")] {
pub use alloc::string::String;
pub use alloc::vec::Vec;
pub use alloc::collections::LinkedList;
pub use alloc::collections::VecDeque;
pub use alloc::collections::btree_map::BTreeMap;
pub use alloc::collections::btree_set::BTreeSet;
pub use hashbrown::hash_map::HashMap;
pub use hashbrown::hash_set::HashSet;
pub use alloc::boxed::Box;
pub use alloc::borrow::{Cow, ToOwned};
pub use wasm_bindgen::prelude::*;
@ -54,8 +58,12 @@ cfg_if! {
} else {
pub use std::string::String;
pub use std::vec::Vec;
pub use std::collections::LinkedList;
pub use std::collections::VecDeque;
pub use std::collections::btree_map::BTreeMap;
pub use std::collections::btree_set::BTreeSet;
pub use std::collections::hash_map::HashMap;
pub use std::collections::hash_set::HashSet;
pub use std::boxed::Box;
pub use std::borrow::{Cow, ToOwned};
pub use std::cmp;

View File

@ -40,6 +40,7 @@ Future<VeilidConfig> getDefaultVeilidConfig() async {
network: VeilidConfigNetwork(
maxConnections: 16,
connectionInitialTimeoutMs: 2000,
connectionInactivityTimeoutMs: 60000,
nodeId: "",
nodeIdSecret: "",
bootstrap: [],

View File

@ -516,6 +516,7 @@ class VeilidConfigLeases {
class VeilidConfigNetwork {
int maxConnections;
int connectionInitialTimeoutMs;
int connectionInactivityTimeoutMs;
String nodeId;
String nodeIdSecret;
List<String> bootstrap;
@ -533,6 +534,7 @@ class VeilidConfigNetwork {
VeilidConfigNetwork({
required this.maxConnections,
required this.connectionInitialTimeoutMs,
required this.connectionInactivityTimeoutMs,
required this.nodeId,
required this.nodeIdSecret,
required this.bootstrap,
@ -552,6 +554,7 @@ class VeilidConfigNetwork {
return {
'max_connections': maxConnections,
'connection_initial_timeout_ms': connectionInitialTimeoutMs,
'connection_inactivity_timeout_ms': connectionInactivityTimeoutMs,
'node_id': nodeId,
'node_id_secret': nodeIdSecret,
'bootstrap': bootstrap,
@ -571,6 +574,8 @@ class VeilidConfigNetwork {
VeilidConfigNetwork.fromJson(Map<String, dynamic> json)
: maxConnections = json['max_connections'],
connectionInitialTimeoutMs = json['connection_initial_timeout_ms'],
connectionInactivityTimeoutMs =
json['connection_inactivity_timeout_ms'],
nodeId = json['node_id'],
nodeIdSecret = json['node_id_secret'],
bootstrap = json['bootstrap'],

View File

@ -50,6 +50,7 @@ core:
network:
max_connections: 16
connection_initial_timeout_ms: 2000
connection_inactivity_timeout_ms: 60000
node_id: ''
node_id_secret: ''
bootstrap: []
@ -523,6 +524,7 @@ pub struct Leases {
pub struct Network {
pub max_connections: u32,
pub connection_initial_timeout_ms: u32,
pub connection_inactivity_timeout_ms: u32,
pub node_id: veilid_core::DHTKey,
pub node_id_secret: veilid_core::DHTKeySecret,
pub bootstrap: Vec<ParsedNodeDialInfo>,
@ -794,6 +796,9 @@ impl Settings {
"network.connection_initial_timeout_ms" => {
Ok(Box::new(inner.core.network.connection_initial_timeout_ms))
}
"network.connection_inactivity_timeout_ms" => Ok(Box::new(
inner.core.network.connection_inactivity_timeout_ms,
)),
"network.node_id" => Ok(Box::new(inner.core.network.node_id)),
"network.node_id_secret" => Ok(Box::new(inner.core.network.node_id_secret)),
"network.bootstrap" => Ok(Box::new(
@ -1131,6 +1136,7 @@ mod tests {
assert_eq!(s.core.network.max_connections, 16);
assert_eq!(s.core.network.connection_initial_timeout_ms, 2_000u32);
assert_eq!(s.core.network.connection_inactivity_timeout_ms, 60_000u32);
assert_eq!(s.core.network.node_id, veilid_core::DHTKey::default());
assert_eq!(
s.core.network.node_id_secret,