为什么在我的方法签名中使用 hyper::Client 时会出现错误 "wrong number of type arguments"?
Why do I get the error "wrong number of type arguments" when I use hyper::Client in my method signature?
我想得到一个根据 URL 方案配置的 hyper::Client
。为此,我创建了一个小方法:
extern crate http; // 0.1.8
extern crate hyper; // 0.12.7
extern crate hyper_tls; // 0.1.4
use http::uri::Scheme;
use hyper::{Body, Client, Uri};
use hyper_tls::HttpsConnector;
#[derive(Clone, Debug)]
pub struct Feed;
impl Feed {
fn get_client(uri: Uri) -> Client {
match uri.scheme_part() {
Some(Scheme::HTTP) => Client::new(),
Some(Scheme::HTTPS) => {
let https = HttpsConnector::new(4).expect("TLS initialization failed");
let client = Client::builder().build::<_, Body>(https);
}
_ => panic!("We don't support schemes other than HTTP/HTTPS"),
}
}
}
当我尝试编译它时,我收到此错误消息:
error[E0243]: wrong number of type arguments: expected at least 1, found 0
--> src/main.rs:13:32
|
13 | fn get_client(uri: Uri) -> Client {
| ^^^^^^ expected at least 1 type argument
我不明白为什么它不能编译因为
- 我已经在我的 main.rs
中声明我使用 hyper crate
- 我在文件头声明我的用途
我做错了什么?
hyper::Client
采用类型参数。您可以在关联的函数调用中省略它们 Client::new()
,因为编译器会推导它们,但不会在函数签名中这样做。
您希望 return 类型为 Client<HttpConnector, Body>
。
问题在于您的构建器方法 return 是 Client<HttpsConnector, Body>
,这是不同的。您可能必须定义自己的特征以通过连接器进行抽象。
查看 documentation for Client
: Client
is a generic type,它取决于两个类型参数:连接器类型 C
和可选主体类型 B
。您需要指定哪些类型参数适用于您 return 的 Client
,但在您的特定情况下,您似乎想要 return Client<HttpConnector>
或Client<HttpsConnector>
取决于 URI 方案。你不能那样做,期间。
根据您打算如何使用 get_client
函数,您可以将 return 值包装在 enum
:
中
enum MyClient {
HttpClient (Client<HttpConnector>),
HttpsClient (Client<HttpsConnector>),
}
impl MyClient {
pub fn get(&self, uri: Uri) -> ResponseFuture {
match self {
HttpClient (c) => c.get (uri),
HttpsClient (c) => c.get (uri),
}
}
}
fn get_client(uri: Uri) -> MyClient { /* … */ }
或者你可以定义一个特征,为 Client<HttpConnector>
和 Client<HttpsConnector>
实现它,并有 get_client
return 你的特征的盒装实例,比如:
trait MyClient {
pub fn get(&self, uri: Uri) -> ResponseFuture;
}
impl<C> MyClient for Client<C> {
pub fn get(&self, uri: Uri) -> ResponseFuture {
Client<C>::get (&self, uri)
}
}
fn get_client(uri: Uri) -> Box<MyClient> { /* … */ }
我想得到一个根据 URL 方案配置的 hyper::Client
。为此,我创建了一个小方法:
extern crate http; // 0.1.8
extern crate hyper; // 0.12.7
extern crate hyper_tls; // 0.1.4
use http::uri::Scheme;
use hyper::{Body, Client, Uri};
use hyper_tls::HttpsConnector;
#[derive(Clone, Debug)]
pub struct Feed;
impl Feed {
fn get_client(uri: Uri) -> Client {
match uri.scheme_part() {
Some(Scheme::HTTP) => Client::new(),
Some(Scheme::HTTPS) => {
let https = HttpsConnector::new(4).expect("TLS initialization failed");
let client = Client::builder().build::<_, Body>(https);
}
_ => panic!("We don't support schemes other than HTTP/HTTPS"),
}
}
}
当我尝试编译它时,我收到此错误消息:
error[E0243]: wrong number of type arguments: expected at least 1, found 0
--> src/main.rs:13:32
|
13 | fn get_client(uri: Uri) -> Client {
| ^^^^^^ expected at least 1 type argument
我不明白为什么它不能编译因为
- 我已经在我的 main.rs 中声明我使用 hyper crate
- 我在文件头声明我的用途
我做错了什么?
hyper::Client
采用类型参数。您可以在关联的函数调用中省略它们 Client::new()
,因为编译器会推导它们,但不会在函数签名中这样做。
您希望 return 类型为 Client<HttpConnector, Body>
。
问题在于您的构建器方法 return 是 Client<HttpsConnector, Body>
,这是不同的。您可能必须定义自己的特征以通过连接器进行抽象。
查看 documentation for Client
: Client
is a generic type,它取决于两个类型参数:连接器类型 C
和可选主体类型 B
。您需要指定哪些类型参数适用于您 return 的 Client
,但在您的特定情况下,您似乎想要 return Client<HttpConnector>
或Client<HttpsConnector>
取决于 URI 方案。你不能那样做,期间。
根据您打算如何使用 get_client
函数,您可以将 return 值包装在 enum
:
enum MyClient {
HttpClient (Client<HttpConnector>),
HttpsClient (Client<HttpsConnector>),
}
impl MyClient {
pub fn get(&self, uri: Uri) -> ResponseFuture {
match self {
HttpClient (c) => c.get (uri),
HttpsClient (c) => c.get (uri),
}
}
}
fn get_client(uri: Uri) -> MyClient { /* … */ }
或者你可以定义一个特征,为 Client<HttpConnector>
和 Client<HttpsConnector>
实现它,并有 get_client
return 你的特征的盒装实例,比如:
trait MyClient {
pub fn get(&self, uri: Uri) -> ResponseFuture;
}
impl<C> MyClient for Client<C> {
pub fn get(&self, uri: Uri) -> ResponseFuture {
Client<C>::get (&self, uri)
}
}
fn get_client(uri: Uri) -> Box<MyClient> { /* … */ }