Skip to main content

hopr_lib/
config.rs

1use hopr_api::types::primitive::prelude::*;
2pub use hopr_transport::{
3    TagAllocatorConfig,
4    config::{
5        HoprPacketPipelineConfig, HoprProtocolConfig, HostConfig, HostType, ProbeConfig, SessionGlobalConfig,
6        TransportConfig, looks_like_domain,
7    },
8};
9use validator::{Validate, ValidationError};
10
11pub const DEFAULT_HOST: &str = "0.0.0.0";
12pub const DEFAULT_PORT: u16 = 9091;
13
14#[inline]
15fn default_invalid_address() -> Address {
16    Address::default()
17}
18
19#[cfg_attr(feature = "serde", cfg_eval::cfg_eval, serde_with::serde_as)]
20#[derive(Debug, Clone, PartialEq, smart_default::SmartDefault, Validate)]
21#[cfg_attr(
22    feature = "serde",
23    derive(serde::Serialize, serde::Deserialize),
24    serde(deny_unknown_fields)
25)]
26pub struct SafeModule {
27    #[cfg_attr(
28        feature = "serde",
29        serde_as(as = "serde_with::DisplayFromStr"),
30        serde(default = "default_invalid_address")
31    )]
32    #[default(default_invalid_address())]
33    pub safe_address: Address,
34    #[cfg_attr(
35        feature = "serde",
36        serde_as(as = "serde_with::DisplayFromStr"),
37        serde(default = "default_invalid_address")
38    )]
39    #[default(default_invalid_address())]
40    pub module_address: Address,
41}
42
43#[allow(dead_code)]
44fn validate_directory_exists(s: &str) -> Result<(), ValidationError> {
45    if std::path::Path::new(s).is_dir() {
46        Ok(())
47    } else {
48        Err(ValidationError::new("Invalid directory path specified"))
49    }
50}
51
52#[derive(Debug, Clone, PartialEq, smart_default::SmartDefault, Validate)]
53#[cfg_attr(
54    feature = "serde",
55    derive(serde::Serialize, serde::Deserialize),
56    serde(deny_unknown_fields)
57)]
58pub struct HoprLibConfig {
59    /// Configuration related to host specifics
60    #[validate(nested)]
61    #[default(default_host())]
62    #[cfg_attr(feature = "serde", serde(default = "default_host"))]
63    pub host: HostConfig,
64    /// Determines whether the node should be advertised publicly on-chain.
65    #[cfg_attr(feature = "serde", serde(default))]
66    pub publish: bool,
67    /// Configuration of the HOPR protocol.
68    #[validate(nested)]
69    #[cfg_attr(feature = "serde", serde(default))]
70    pub protocol: HoprProtocolConfig,
71    /// Configuration of the node Safe and Module.
72    #[validate(nested)]
73    #[cfg_attr(feature = "serde", serde(default))]
74    pub safe_module: SafeModule,
75}
76
77// NOTE: this intentionally does not validate (0.0.0.0) to force user to specify
78// their external IP.
79#[inline]
80fn default_host() -> HostConfig {
81    HostConfig {
82        address: HostType::IPv4(DEFAULT_HOST.to_owned()),
83        port: DEFAULT_PORT,
84    }
85}
86
87#[cfg(test)]
88mod tests {
89    #[cfg(feature = "serde")]
90    #[test]
91    fn test_config_should_be_serializable_using_serde() -> Result<(), Box<dyn std::error::Error>> {
92        let cfg = super::HoprLibConfig::default();
93
94        let yaml = serde_saphyr::to_string(&cfg)?;
95        let cfg_after_serde: super::HoprLibConfig = serde_saphyr::from_str(&yaml)?;
96        assert_eq!(cfg, cfg_after_serde);
97
98        Ok(())
99    }
100}