use std::path::Path;
use derive_builder::Builder;
use derive_more::AsRef;
use fs_mistrust::{Mistrust, MistrustBuilder};
use serde::{Deserialize, Serialize};
use tor_config::{impl_standard_builder, mistrust::BuilderExt, CfgPath};
use tor_keymgr::config::arti::{ArtiNativeKeystoreConfig, ArtiNativeKeystoreConfigBuilder};
pub use tor_config::ConfigBuildError;
#[derive(Clone, Builder, Debug, Eq, PartialEq, AsRef)]
#[builder(build_fn(error = "ConfigBuildError"))]
#[builder(derive(Serialize, Deserialize, Debug))]
#[non_exhaustive]
pub struct TorRelayConfig {
#[builder(sub_builder)]
#[builder_field_attr(serde(default))]
pub(crate) storage: StorageConfig,
}
impl_standard_builder! { TorRelayConfig }
impl TorRelayConfigBuilder {
#[allow(unused)] pub fn from_directories<P, Q>(state_dir: P, cache_dir: Q) -> Self
where
P: AsRef<Path>,
Q: AsRef<Path>,
{
let mut builder = Self::default();
builder
.storage()
.cache_dir(CfgPath::new_literal(cache_dir.as_ref()))
.state_dir(CfgPath::new_literal(state_dir.as_ref()));
builder
}
}
#[derive(Debug, Clone, Builder, Eq, PartialEq)]
#[builder(build_fn(error = "ConfigBuildError"))]
#[builder(derive(Debug, Serialize, Deserialize))]
#[non_exhaustive]
pub struct StorageConfig {
#[builder(setter(into), default = "default_cache_dir()")]
cache_dir: CfgPath,
#[builder(setter(into), default = "default_state_dir()")]
state_dir: CfgPath,
#[builder(sub_builder)]
#[builder_field_attr(serde(default))]
keystore: ArtiNativeKeystoreConfig,
#[builder(sub_builder(fn_name = "build_for_arti"))]
#[builder_field_attr(serde(default))]
permissions: Mistrust,
}
impl_standard_builder! { StorageConfig }
fn default_cache_dir() -> CfgPath {
CfgPath::new("${ARTI_RELAY_CACHE}".to_owned())
}
fn default_state_dir() -> CfgPath {
CfgPath::new("${ARTI_RELAY_LOCAL_DATA}".to_owned())
}
#[cfg(test)]
mod test {
use super::*;
#[test]
fn defaults() {
let dflt = TorRelayConfig::default();
let b2 = TorRelayConfigBuilder::default();
let dflt2 = b2.build().unwrap();
assert_eq!(&dflt, &dflt2);
}
#[test]
fn builder() {
let mut bld = TorRelayConfigBuilder::default();
bld.storage()
.cache_dir(CfgPath::new("/var/tmp/foo".to_owned()))
.state_dir(CfgPath::new("/var/tmp/bar".to_owned()));
let val = bld.build().unwrap();
assert_ne!(val, TorRelayConfig::default());
}
}