Provide define_accessor_trait and use it to generate CircMgrConfig
This commit is contained in:
parent
8bde40fdd3
commit
82aa4b902a
|
@ -3129,6 +3129,7 @@ dependencies = [
|
|||
name = "tor-basic-utils"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"derive_more",
|
||||
"educe",
|
||||
"rand 0.8.5",
|
||||
]
|
||||
|
|
|
@ -15,4 +15,5 @@ repository = "https://gitlab.torproject.org/tpo/core/arti.git/"
|
|||
rand = "0.8"
|
||||
|
||||
[dev-dependencies]
|
||||
derive_more = "0.99"
|
||||
educe = "0.4.6"
|
||||
|
|
|
@ -72,3 +72,71 @@ pub fn skip_fmt<T>(_: &T, f: &mut fmt::Formatter) -> fmt::Result {
|
|||
}
|
||||
|
||||
// ----------------------------------------------------------------------
|
||||
|
||||
/// Define an "accessor trait", which describes structs that have fields of certain types
|
||||
///
|
||||
/// This can be useful if a large struct, living high up in the dependency graph,
|
||||
/// contains fields that lower-lever crates want to be able to use without having
|
||||
/// to copy the data about etc.
|
||||
///
|
||||
/// ```
|
||||
/// // imagine this in the lower-level module
|
||||
/// use tor_basic_utils::define_accessor_trait;
|
||||
/// define_accessor_trait! {
|
||||
/// pub trait View {
|
||||
/// lorem: String,
|
||||
/// ipsum: usize,
|
||||
/// }
|
||||
/// }
|
||||
///
|
||||
/// fn test_view<V: View>(v: &V) {
|
||||
/// assert_eq!(v.lorem(), "sit");
|
||||
/// assert_eq!(v.ipsum(), &42);
|
||||
/// }
|
||||
///
|
||||
/// // imagine this in the higher-level module
|
||||
/// use derive_more::AsRef;
|
||||
/// #[derive(AsRef)]
|
||||
/// struct Everything {
|
||||
/// #[as_ref] lorem: String,
|
||||
/// #[as_ref] ipsum: usize,
|
||||
/// dolor: Vec<()>,
|
||||
/// }
|
||||
/// impl View for Everything { }
|
||||
///
|
||||
/// let everything = Everything {
|
||||
/// lorem: "sit".into(),
|
||||
/// ipsum: 42,
|
||||
/// dolor: vec![()],
|
||||
/// };
|
||||
///
|
||||
/// test_view(&everything);
|
||||
/// ```
|
||||
///
|
||||
/// ### Generated code
|
||||
///
|
||||
/// ```
|
||||
/// pub trait View: AsRef<String> + AsRef<usize> {
|
||||
/// fn lorem(&self) -> &String { self.as_ref() }
|
||||
/// fn ipsum(&self) -> &usize { self.as_ref() }
|
||||
/// }
|
||||
/// ```
|
||||
#[macro_export]
|
||||
macro_rules! define_accessor_trait {
|
||||
{
|
||||
$( #[ $attr:meta ])*
|
||||
$vis:vis trait $Trait:ident {
|
||||
$( $accessor:ident: $type:ty, )*
|
||||
}
|
||||
} => {
|
||||
$( #[ $attr ])*
|
||||
$vis trait $Trait: $( core::convert::AsRef<$type> + )* {
|
||||
$(
|
||||
/// Access the field
|
||||
fn $accessor(&self) -> &$type { core::convert::AsRef::as_ref(self) }
|
||||
)*
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
//!
|
||||
//! Most types in this module are re-exported by `arti-client`.
|
||||
|
||||
use tor_basic_utils::define_accessor_trait;
|
||||
use tor_config::ConfigBuildError;
|
||||
|
||||
use derive_builder::Builder;
|
||||
|
@ -248,26 +249,17 @@ impl PreemptiveCircuitConfig {
|
|||
}
|
||||
}
|
||||
|
||||
/// Configuration for a circuit manager
|
||||
///
|
||||
/// If the circuit manager gains new configurabilities, this trait will gain additional
|
||||
/// supertraits, as an API break.
|
||||
///
|
||||
/// Prefer to use `TorClientConfig`, which will always implement this trait.
|
||||
pub trait CircMgrConfig:
|
||||
AsRef<PathConfig> + AsRef<CircuitTiming> + AsRef<PreemptiveCircuitConfig>
|
||||
{
|
||||
/// Get the PathConfig
|
||||
fn path_rules(&self) -> &PathConfig {
|
||||
self.as_ref()
|
||||
}
|
||||
/// Get the CircuitTiming
|
||||
fn circuit_timing(&self) -> &CircuitTiming {
|
||||
self.as_ref()
|
||||
}
|
||||
/// Get the PreemptiveCircuitConfig
|
||||
fn preemptive_circuits(&self) -> &PreemptiveCircuitConfig {
|
||||
self.as_ref()
|
||||
define_accessor_trait! {
|
||||
/// Configuration for a circuit manager
|
||||
///
|
||||
/// If the circuit manager gains new configurabilities, this trait will gain additional
|
||||
/// supertraits, as an API break.
|
||||
///
|
||||
/// Prefer to use [`TorClientConfig`], which will always implement this trait.
|
||||
pub trait CircMgrConfig {
|
||||
path_rules: PathConfig,
|
||||
circuit_timing: CircuitTiming,
|
||||
preemptive_circuits: PreemptiveCircuitConfig,
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue