#rust #hyper
#Ржавчина #hyper
Вопрос:
Hyper HttpConnector
и hyper_tls HttpsConnector
явно реализуют общую черту (или черты). Я изучил их реализации и не смог подобрать правильный тип (или псевдоним), который позволил бы мне передавать экземпляры любой структуры функции, как в программе ниже. Похоже, что Tower::Service<Url>
это правильная черта, но я не смог найти правильный ответ и действительно мог бы воспользоваться помощью.
use hyper::{client::connect::HttpConnector, service::Service, Uri};
use hyper_tls::HttpsConnector;
// What type should param c have here for this program to compile?
fn with_connector(c: ????) {}
fn main() {
with_connector(HttpConnector::new());
with_connector(HttpsConnector::new());
}
Соответствующие реализации для:
[dependencies]
hyper = "0.13"
hyper-tls = "0.4.3"
Вариант использования заключается в том, что я пишу собственный соединитель, который будет содержать экземпляр любого из них в качестве делегата. Заранее спасибо.
Комментарии:
1. Он использует
tower_service::Service
underneath, но он реэкспортируется какhyper::service::Service
, так что, может быть, использовать это?2. Проблема, с которой я сталкиваюсь, связана с дженериками и связанными типами для этой функции сервиса, это довольно безумно. Я не знаю, как указать тип, чтобы охватить оба
HttpConnector
иHttpsConnector
.3. Что вы пробовали, что не работает?
4. Я нашел исправление, которое нравится компилятору. Смотрите решение этого вопроса. Это немного некрасиво и не очевидно, но я изучаю Rust и, возможно, это мое незнание. Спасибо за вашу помощь.
Ответ №1:
Я смог решить эту проблему, скопировав определения универсального типа, общие для обоих соединителей. На мой взгляд, результат все еще безумно уродлив: трудно поверить, что кто-то мог придумать это без копирования / вставки, как я. Но, может быть, у кого-то, кто хорошо знаком с различными задействованными функциями, не возникнет проблем?
use hyper::{client::connect::HttpConnector, service::Service, Uri};
use hyper_tls::HttpsConnector;
use tokio::io::{AsyncRead, AsyncWrite};
type BoxError = Box<dyn std::error::Error Send Sync>;
fn with_connector<T>(conn: T)
where
T: Service<Uri>,
T::Response: AsyncRead AsyncWrite Send Unpin,
T::Future: Send 'static,
T::Error: Into<BoxError>,
{
// do something with conn
}
fn main() {
let http = HttpConnector::new();
with_connector(http);
let https = HttpsConnector::new();
with_connector(https);
}
[dependencies]
hyper = "0.13"
hyper-tls = "0.4.3"
tokio = { version = "0.2", features = ["full"] }