Я пытаюсь использовать Iced (каркас пользовательского интерфейса, основанный на архитектуре Elm) с Reqwest (оболочка над гипер) , который может использовать Serde для JSON десериализации .
Независимо от того, что они работают правильно, но я новичок в Rust, и что-то в моей реализации неверно.
Я начинаю с (в процессе) сетевой функции.
#[derive(Deserialize, Debug, Clone)]
pub(crate) enum Error {
APIError,
ParseError,
}
impl From<reqwest::Error> for Error {
fn from(error: reqwest::Error) -> Self {
Error::APIError
}
}
pub(crate) async fn post<T>(request: Request) -> Result<T, Error>
where
T: DeserializeOwned + Debug + Clone,
{
let headers = standard_headers(request.params);
let response = Client::new()
.post(&format!("{}{}", request.base, request.path))
.json(&request.body)
.headers(headers)
.send()
.await?
.json::<T>()
.await?;
Ok(response)
}
и я пытаюсь использовать его как часть Iced:
fn new() -> (Runner, Command<Message>) {
(
Runner::Loading,
Command::perform(post(Login::request()), Message::Next),
)
}
и получаю ошибку компиляции:
error[E0277]: `*mut (dyn std::ops::Fn() + 'static)` cannot be shared between threads safely
--> src/feature/runner/runner.rs:42:13
|
42 | Command::perform(post(Login::request()), Message::Next),
| ^^^^^^^^^^^^^^^^ `*mut (dyn std::ops::Fn() + 'static)` cannot be shared between threads safely
|
::: <snip>/futures/src/command/native.rs:29:22
|
29 | future: impl Future<Output = T> + 'static + Send,
| ------------------ required by this bound in `iced_futures::command::native::Command::<T>::perform`
|
= help: within `core::fmt::Void`, the trait `std::marker::Sync` is not implemented for `*mut (dyn std::ops::Fn() + 'static)`
Я считаю, что проблема связана с используя T: DeserializeOwned и время жизни в post
, причем владение таково, что тип T
в async fn post
может быть в другом потоке по сравнению с асинхронным вызовом c в Command (отсюда и упоминание о Send
.
. Ответ может быть даже в пожизненной ссылке, но у меня пока недостаточно знаний, чтобы увидеть его или узнать, нахожусь ли я в нужном месте с моими Я вернулся к использованию только конкретного типа вместо T
whi ch работает.
Мне бы очень хотелось понять, почему существует эта проблема и что я могу сделать, чтобы ее решить.
Заранее спасибо!