pub struct DnsCache { /* private fields */ }Expand description
A TTL-cached async DNS resolver for the pooled dial path (PERF-05, #170).
Wraps DnsResolver (a hickory TokioResolver) with two caches
shared across every upstream in a registry:
- Positive cache: a successful lookup is reused until the record
TTL expires (capped at
positive_ttl_cap), so repeated dials to the same host skip both the blockinggetaddrinfopath and the network round-trip. The cap bounds/etc/hostsentries (which carry a near-infinite TTL) and operator-facing staleness. - Negative cache: a failed lookup is cached for
negative_ttl(default 5 s) so a transient resolver failure or NXDOMAIN does not trigger a retry storm on the hottest code path; the cached miss returnsAddrNotAvailableuntil it expires, then re-resolves.
IP-literal hosts skip DNS and the cache entirely (the same
short-circuit getaddrinfo takes). The cache is Send + Sync (one
tokio::sync::Mutex over a HashMap); the critical section holds
only the map read/insert, never the resolver future.
Implementations§
Source§impl DnsCache
impl DnsCache
Sourcepub fn new(name_servers: &[String]) -> Self
pub fn new(name_servers: &[String]) -> Self
Build a cache backed by the given name servers (empty = the
resolver default: system config when readable, else the public
resolvers; see DnsResolver::new) with the
default TTLs and entry cap.
Sourcepub fn with_ttls(
name_servers: &[String],
positive_ttl_cap: Duration,
negative_ttl: Duration,
max_entries: usize,
) -> Self
pub fn with_ttls( name_servers: &[String], positive_ttl_cap: Duration, negative_ttl: Duration, max_entries: usize, ) -> Self
Build a cache with explicit TTL/size knobs. Public so the dial-path cache contract (TTL expiry, negative caching, memory bound) can be pinned deterministically in tests without waiting out the default 5 s negative TTL.
Sourcepub async fn resolve(&self, host: &str, port: u16) -> Result<Vec<SocketAddr>>
pub async fn resolve(&self, host: &str, port: u16) -> Result<Vec<SocketAddr>>
Resolve host to a list of SocketAddrs paired with port,
consulting the cache first. IP-literal hosts skip DNS and the
cache. Hostname hits return the cached address set (positive) or
a cached AddrNotAvailable (negative, within negative_ttl);
misses resolve via hickory and populate the cache.
Trait Implementations§
Auto Trait Implementations§
impl !Freeze for DnsCache
impl !RefUnwindSafe for DnsCache
impl Send for DnsCache
impl Sync for DnsCache
impl Unpin for DnsCache
impl !UnwindSafe for DnsCache
Blanket Implementations§
§impl<T> AnyExt for T
impl<T> AnyExt for T
§fn downcast_ref<T>(this: &Self) -> Option<&T>where
T: Any,
fn downcast_ref<T>(this: &Self) -> Option<&T>where
T: Any,
T behind reference§fn downcast_mut<T>(this: &mut Self) -> Option<&mut T>where
T: Any,
fn downcast_mut<T>(this: &mut Self) -> Option<&mut T>where
T: Any,
T behind mutable reference§fn downcast_rc<T>(this: Rc<Self>) -> Result<Rc<T>, Rc<Self>>where
T: Any,
fn downcast_rc<T>(this: Rc<Self>) -> Result<Rc<T>, Rc<Self>>where
T: Any,
T behind Rc pointer§fn downcast_arc<T>(this: Arc<Self>) -> Result<Arc<T>, Arc<Self>>where
T: Any,
fn downcast_arc<T>(this: Arc<Self>) -> Result<Arc<T>, Arc<Self>>where
T: Any,
T behind Arc pointer§fn downcast_box<T>(this: Box<Self>) -> Result<Box<T>, Box<Self>>where
T: Any,
fn downcast_box<T>(this: Box<Self>) -> Result<Box<T>, Box<Self>>where
T: Any,
T behind Box pointer§fn downcast_move<T>(this: Self) -> Option<T>
fn downcast_move<T>(this: Self) -> Option<T>
Self to T,
useful only in generic context as a workaround for specializationSource§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
§impl<T, X> CoerceTo<T> for Xwhere
T: CoerceFrom<X> + ?Sized,
impl<T, X> CoerceTo<T> for Xwhere
T: CoerceFrom<X> + ?Sized,
fn coerce_rc_to(self: Rc<X>) -> Rc<T>
fn coerce_box_to(self: Box<X>) -> Box<T>
fn coerce_ref_to(&self) -> &T
fn coerce_mut_to(&mut self) -> &mut T
§impl<T> Instrument for T
impl<T> Instrument for T
§fn instrument(self, span: Span) -> Instrumented<Self>
fn instrument(self, span: Span) -> Instrumented<Self>
§fn in_current_span(self) -> Instrumented<Self>
fn in_current_span(self) -> Instrumented<Self>
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read more