pub trait Resolver: DynClone + Debug + Sync + Send {
    fn resolve(&self, domain: &str, opts: ResolveOptions<'_>) -> ResolveResult;

    fn async_resolve<'a>(
        &'a self,
        domain: &'a str,
        opts: ResolveOptions<'a>
    ) -> BoxFuture<'a, ResolveResult> { ... } }
Expand description

域名解析的接口

同时提供阻塞接口和异步接口,异步接口则需要启用 async 功能

Required Methods§

解析域名

该方法的异步版本为 Self::async_resolve

Provided Methods§

Available on crate feature async only.

异步解析域名

Examples found in repository?
src/client/resolver/trust_dns.rs (line 53)
52
53
54
    fn resolve(&self, domain: &str, opts: ResolveOptions) -> ResolveResult {
        block_on(async move { self.async_resolve(domain, opts).await })
    }
More examples
Hide additional examples
src/client/resolver/cache.rs (line 89)
86
87
88
89
90
91
92
    fn async_resolve<'a>(&'a self, domain: &'a str, opts: ResolveOptions<'a>) -> BoxFuture<'a, ResolveResult> {
        Box::pin(async move {
            self.async_cache
                .get(domain, self.resolver.async_resolve(domain, opts))
                .await
        })
    }
src/client/resolver/timeout.rs (line 50)
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
        fn _resolve<R: Resolver + Clone + 'static>(
            resolver: &TimeoutResolver<R>,
            domain: &str,
            opts: ResolveOptions,
        ) -> ResolveResult {
            async_std::task::block_on(async move { resolver.async_resolve(domain, opts).await })
        }

        #[cfg(not(feature = "async"))]
        fn _resolve<R: Resolver + Clone + 'static>(
            resolver: &TimeoutResolver<R>,
            domain: &str,
            opts: ResolveOptions,
        ) -> ResolveResult {
            use super::{super::super::spawn::spawn, owned_resolver_options::OwnedResolveOptions};
            use crossbeam_channel::{bounded, Select, SelectTimeoutError};
            use log::warn;

            let (sender, receiver) = bounded(0);
            {
                let inner = resolver.to_owned();
                let domain = domain.to_owned();
                let opts = OwnedResolveOptions::from(opts);
                if let Err(err) = spawn(
                    "qiniu.rust-sdk.http-client.resolver.TimeoutResolver.resolve".into(),
                    move || {
                        let opts = ResolveOptions::from(&opts);
                        sender.send(inner.resolver.resolve(&domain, opts)).ok();
                    },
                ) {
                    warn!("Timeout Resolver was failed to spawn thread to resolve domain: {}", err);
                }
            }
            let mut sel = Select::new();
            let op1 = sel.recv(&receiver);
            let oper = sel.select_timeout(resolver.timeout);
            return match oper {
                Ok(op) => match op.index() {
                    i if i == op1 => op.recv(&receiver).unwrap(),
                    _ => unreachable!(),
                },
                Err(err) => Err(make_timeout_error(err, opts)),
            };

            fn make_timeout_error(err: SelectTimeoutError, opts: ResolveOptions) -> ResponseError {
                let mut err = ResponseError::new(HttpResponseErrorKind::TimeoutError.into(), err);
                if let Some(retried) = opts.retried() {
                    err = err.retried(retried);
                }
                err
            }
        }
    }

    #[cfg(feature = "async")]
    #[cfg_attr(feature = "docs", doc(cfg(feature = "async")))]
    fn async_resolve<'a>(&'a self, domain: &'a str, opts: ResolveOptions<'a>) -> BoxFuture<'a, ResolveResult> {
        use futures::{pin_mut, select};

        return Box::pin(async move {
            let resolve_task = self.resolver.async_resolve(domain, opts).fuse();
            let timeout_task = AsyncDelay::new(self.timeout).fuse();
            pin_mut!(resolve_task);
            pin_mut!(timeout_task);
            select! {
                resolve_result = resolve_task => resolve_result,
                _ = timeout_task => Err(make_timeout_error(self.timeout, opts)),
            }
        });

        fn make_timeout_error(timeout: Duration, opts: ResolveOptions) -> ResponseError {
            let mut err = ResponseError::new_with_msg(
                HttpResponseErrorKind::TimeoutError.into(),
                format!("Failed to resolve domain in {timeout:?}"),
            );
            if let Some(retried) = opts.retried() {
                err = err.retried(retried);
            }
            err
        }
    }
src/client/resolver/shuffled.rs (line 36)
34
35
36
37
38
39
40
    fn async_resolve<'a>(&'a self, domain: &'a str, opts: ResolveOptions<'a>) -> BoxFuture<'a, ResolveResult> {
        Box::pin(async move {
            let mut answers = self.base_resolver.async_resolve(domain, opts).await?;
            answers.ip_addrs_mut().shuffle(&mut thread_rng());
            Ok(answers)
        })
    }
src/client/resolver/chained.rs (line 44)
40
41
42
43
44
45
46
47
48
49
50
51
    fn async_resolve<'a>(&'a self, domain: &'a str, opts: ResolveOptions<'a>) -> BoxFuture<'a, ResolveResult> {
        Box::pin(async move {
            let mut last_result: Option<ResolveResult> = None;
            for resolver in self.resolvers.iter() {
                match resolver.async_resolve(domain, opts).await {
                    Ok(answers) if !answers.ip_addrs().is_empty() => return Ok(answers),
                    result => last_result = Some(result),
                }
            }
            last_result.unwrap_or_else(|| Err(no_try_error(opts)))
        })
    }
src/client/call/utils.rs (lines 467-470)
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
    pub(in super::super) async fn async_resolve(
        parts: &InnerRequestParts<'_>,
        domain_with_port: &DomainWithPort,
        extensions: &mut Extensions,
        retried: &RetriedStatsInfo,
    ) -> Result<Vec<IpAddrWithPort>, TryError> {
        let answers = with_resolve_domain(parts, domain_with_port.domain(), extensions, retried, || async {
            parts
                .http_client()
                .resolver()
                .async_resolve(
                    domain_with_port.domain(),
                    ResolveOptions::builder().retried(retried).build(),
                )
                .await
        });
        return Ok(answers
            .await?
            .into_ip_addrs()
            .iter()
            .map(|&ip| IpAddrWithPort::new(ip, domain_with_port.port()))
            .collect());

        async fn with_resolve_domain<F: FnOnce() -> Fu, Fu: Future<Output = ResolveResult>>(
            parts: &InnerRequestParts<'_>,
            domain: &str,
            extensions: &mut Extensions,
            retried: &RetriedStatsInfo,
            f: F,
        ) -> Result<ResolveAnswers, TryError> {
            call_to_resolve_domain_callbacks(parts, domain, extensions, retried)?;
            let answers = f()
                .await
                .map_err(|err| TryError::new(err, RetryDecision::TryNextServer.into()))?;
            call_domain_resolved_callbacks(parts, domain, &answers, extensions, retried)?;
            Ok(answers)
        }
    }

Trait Implementations§

Returns a copy of the value. Read more
Performs copy-assignment from source. Read more
Returns a copy of the value. Read more
Performs copy-assignment from source. Read more
Returns a copy of the value. Read more
Performs copy-assignment from source. Read more
Returns a copy of the value. Read more
Performs copy-assignment from source. Read more

Implementations on Foreign Types§

Available on crate feature async only.
Available on crate feature async only.
Available on crate feature async only.
Available on crate feature async only.
Available on crate feature async only.

Implementors§