From ae3b7029a971e94658c46952ed87c3c14b3dd666 Mon Sep 17 00:00:00 2001 From: Trinity Pointard Date: Thu, 18 Mar 2021 03:12:27 +0100 Subject: [PATCH 1/4] add support for using domain name in configuration --- src/util/config.rs | 53 +++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 52 insertions(+), 1 deletion(-) diff --git a/src/util/config.rs b/src/util/config.rs index cd65e009..fe6ab979 100644 --- a/src/util/config.rs +++ b/src/util/config.rs @@ -1,8 +1,9 @@ +use std::fmt; use std::io::Read; use std::net::SocketAddr; use std::path::PathBuf; -use serde::Deserialize; +use serde::{de, Deserialize}; use crate::error::Error; @@ -11,8 +12,10 @@ pub struct Config { pub metadata_dir: PathBuf, pub data_dir: PathBuf, + #[serde(deserialize_with = "deserialize_addr")] pub rpc_bind_addr: SocketAddr, + #[serde(deserialize_with = "deserialize_vec_addr")] pub bootstrap_peers: Vec, pub consul_host: Option, pub consul_service_name: Option, @@ -48,12 +51,14 @@ pub struct TlsConfig { #[derive(Deserialize, Debug, Clone)] pub struct ApiConfig { + #[serde(deserialize_with = "deserialize_addr")] pub api_bind_addr: SocketAddr, pub s3_region: String, } #[derive(Deserialize, Debug, Clone)] pub struct WebConfig { + #[serde(deserialize_with = "deserialize_addr")] pub bind_addr: SocketAddr, pub root_domain: String, pub index: String, @@ -82,3 +87,49 @@ pub fn read_config(config_file: PathBuf) -> Result { Ok(toml::from_str(&config)?) } + +fn deserialize_addr<'de, D>(deserializer: D) -> Result +where + D: de::Deserializer<'de>, +{ + struct AddrVisitor; + + impl<'de> de::Visitor<'de> for AddrVisitor { + type Value = SocketAddr; + + fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result { + formatter.write_str("a string representing a socket address") + } + + fn visit_str(self, s: &str) -> Result + where + E: de::Error, + { + use std::net::ToSocketAddrs; + s.to_socket_addrs() + .map_err(|_| de::Error::custom("could not resolve to a socket address"))? + .next() + .ok_or(de::Error::custom("could not resolve to a socket address")) + } + } + + deserializer.deserialize_any(AddrVisitor) +} + +fn deserialize_vec_addr<'de, D>(deserializer: D) -> Result, D::Error> +where + D: de::Deserializer<'de>, +{ + use std::net::ToSocketAddrs; + + let mut res = vec![]; + for s in >::deserialize(deserializer)? { + res.push( + s.to_socket_addrs() + .map_err(|_| de::Error::custom("could not resolve to a socket address"))? + .next() + .ok_or(de::Error::custom("could not resolve to a socket address"))?, + ); + } + Ok(res) +} From 81e9db783fd7f104ad3d15d60436a8767172e0df Mon Sep 17 00:00:00 2001 From: Trinity Pointard Date: Thu, 18 Mar 2021 03:44:00 +0100 Subject: [PATCH 2/4] simplify addresse deserialialiser and limit allocations --- src/util/config.rs | 30 +++++++----------------------- 1 file changed, 7 insertions(+), 23 deletions(-) diff --git a/src/util/config.rs b/src/util/config.rs index fe6ab979..313692fc 100644 --- a/src/util/config.rs +++ b/src/util/config.rs @@ -1,4 +1,3 @@ -use std::fmt; use std::io::Read; use std::net::SocketAddr; use std::path::PathBuf; @@ -92,28 +91,13 @@ fn deserialize_addr<'de, D>(deserializer: D) -> Result where D: de::Deserializer<'de>, { - struct AddrVisitor; + use std::net::ToSocketAddrs; - impl<'de> de::Visitor<'de> for AddrVisitor { - type Value = SocketAddr; - - fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result { - formatter.write_str("a string representing a socket address") - } - - fn visit_str(self, s: &str) -> Result - where - E: de::Error, - { - use std::net::ToSocketAddrs; - s.to_socket_addrs() - .map_err(|_| de::Error::custom("could not resolve to a socket address"))? - .next() - .ok_or(de::Error::custom("could not resolve to a socket address")) - } - } - - deserializer.deserialize_any(AddrVisitor) + <&str>::deserialize(deserializer)? + .to_socket_addrs() + .map_err(|_| de::Error::custom("could not resolve to a socket address"))? + .next() + .ok_or(de::Error::custom("could not resolve to a socket address")) } fn deserialize_vec_addr<'de, D>(deserializer: D) -> Result, D::Error> @@ -123,7 +107,7 @@ where use std::net::ToSocketAddrs; let mut res = vec![]; - for s in >::deserialize(deserializer)? { + for s in >::deserialize(deserializer)? { res.push( s.to_socket_addrs() .map_err(|_| de::Error::custom("could not resolve to a socket address"))? From c8a7ce5cdf8deb376752588ba1fd99675d8587e7 Mon Sep 17 00:00:00 2001 From: Trinity Pointard Date: Thu, 18 Mar 2021 19:46:35 +0100 Subject: [PATCH 3/4] remove domain resolution for *_bind_addr --- src/util/config.rs | 16 ---------------- 1 file changed, 16 deletions(-) diff --git a/src/util/config.rs b/src/util/config.rs index 313692fc..6b449459 100644 --- a/src/util/config.rs +++ b/src/util/config.rs @@ -11,7 +11,6 @@ pub struct Config { pub metadata_dir: PathBuf, pub data_dir: PathBuf, - #[serde(deserialize_with = "deserialize_addr")] pub rpc_bind_addr: SocketAddr, #[serde(deserialize_with = "deserialize_vec_addr")] @@ -50,14 +49,12 @@ pub struct TlsConfig { #[derive(Deserialize, Debug, Clone)] pub struct ApiConfig { - #[serde(deserialize_with = "deserialize_addr")] pub api_bind_addr: SocketAddr, pub s3_region: String, } #[derive(Deserialize, Debug, Clone)] pub struct WebConfig { - #[serde(deserialize_with = "deserialize_addr")] pub bind_addr: SocketAddr, pub root_domain: String, pub index: String, @@ -87,19 +84,6 @@ pub fn read_config(config_file: PathBuf) -> Result { Ok(toml::from_str(&config)?) } -fn deserialize_addr<'de, D>(deserializer: D) -> Result -where - D: de::Deserializer<'de>, -{ - use std::net::ToSocketAddrs; - - <&str>::deserialize(deserializer)? - .to_socket_addrs() - .map_err(|_| de::Error::custom("could not resolve to a socket address"))? - .next() - .ok_or(de::Error::custom("could not resolve to a socket address")) -} - fn deserialize_vec_addr<'de, D>(deserializer: D) -> Result, D::Error> where D: de::Deserializer<'de>, From f17cb6c969121d12937409f9ec0d204cad4a841c Mon Sep 17 00:00:00 2001 From: Trinity Pointard Date: Thu, 18 Mar 2021 21:04:30 +0100 Subject: [PATCH 4/4] resolve domain to multiple addresses And warn instead of failling when a domain can't be resolved --- src/util/config.rs | 27 +++++++++++++++++---------- 1 file changed, 17 insertions(+), 10 deletions(-) diff --git a/src/util/config.rs b/src/util/config.rs index 6b449459..9ff67711 100644 --- a/src/util/config.rs +++ b/src/util/config.rs @@ -90,14 +90,21 @@ where { use std::net::ToSocketAddrs; - let mut res = vec![]; - for s in >::deserialize(deserializer)? { - res.push( - s.to_socket_addrs() - .map_err(|_| de::Error::custom("could not resolve to a socket address"))? - .next() - .ok_or(de::Error::custom("could not resolve to a socket address"))?, - ); - } - Ok(res) + Ok(>::deserialize(deserializer)? + .iter() + .filter_map(|&name| { + name.to_socket_addrs() + .map(|iter| (name, iter)) + .map_err(|_| warn!("Error resolving \"{}\"", name)) + .ok() + }) + .map(|(name, iter)| { + let v = iter.collect::>(); + if v.is_empty() { + warn!("Error resolving \"{}\"", name) + } + v + }) + .flatten() + .collect()) }