Rust回调:错误:生存期';静态要求

Rust回调:错误:生存期';静态要求,rust,lifetime,Rust,Lifetime,我正在尝试编写一个将回调作为参数的泛型函数。但是,我始终会收到以下错误消息: extern crate futures; extern crate gotham; extern crate hyper; extern crate mime; extern crate serde; extern crate serde_json; use futures::{future, Future, Stream}; use gotham::handler::{HandlerFuture, IntoHan

我正在尝试编写一个将回调作为参数的泛型函数。但是,我始终会收到以下错误消息:

extern crate futures;
extern crate gotham;
extern crate hyper;
extern crate mime;
extern crate serde;
extern crate serde_json;

use futures::{future, Future, Stream};
use gotham::handler::{HandlerFuture, IntoHandlerError};
use gotham::http::response::create_response;
use gotham::state::{FromState, State};
use hyper::{Body, StatusCode};
use mime::APPLICATION_JSON;
use serde::{Deserialize, Serialize};
use serde_json::{from_str, to_string};

pub fn helper<'de, Q, S, C>(mut state : State, callback : C) -> Box<HandlerFuture>
    where Q : Deserialize<'de>,
          S : Serialize,
          C : Fn(Q) -> S
{
    let f = Body::take_from(&mut state)
        .concat2()
        .then(|full_body| match full_body {
            Ok(valid_body) => {
                let body_content = String::from_utf8(valid_body.to_vec()).unwrap();
                let body_json = from_str::<Q>(&body_content).unwrap();
                let resp_json = callback(body_json);
                let resp_content = to_string(&resp_json).unwrap().into_bytes();
                let res = create_response(&state, StatusCode::Ok, Some((resp_content, APPLICATION_JSON)));
                future::ok((state, res))
            }
            Err(e) => return future::err((state, e.into_handler_error()))
        });

    Box::new(f)
}
error[E0310]:参数类型'C'可能寿命不够长
-->src/lib.rs:36:5
|
17 | pub fn helper src/lib.rs:36:5
|
36 |盒子::新(f)
|     ^^^^^^^^^^^
这是一个生成错误消息的最小可编译示例:

extern crate futures;
extern crate gotham;
extern crate hyper;
extern crate mime;
extern crate serde;
extern crate serde_json;

use futures::{future, Future, Stream};
use gotham::handler::{HandlerFuture, IntoHandlerError};
use gotham::http::response::create_response;
use gotham::state::{FromState, State};
use hyper::{Body, StatusCode};
use mime::APPLICATION_JSON;
use serde::{Deserialize, Serialize};
use serde_json::{from_str, to_string};

pub fn helper<'de, Q, S, C>(mut state : State, callback : C) -> Box<HandlerFuture>
    where Q : Deserialize<'de>,
          S : Serialize,
          C : Fn(Q) -> S
{
    let f = Body::take_from(&mut state)
        .concat2()
        .then(|full_body| match full_body {
            Ok(valid_body) => {
                let body_content = String::from_utf8(valid_body.to_vec()).unwrap();
                let body_json = from_str::<Q>(&body_content).unwrap();
                let resp_json = callback(body_json);
                let resp_content = to_string(&resp_json).unwrap().into_bytes();
                let res = create_response(&state, StatusCode::Ok, Some((resp_content, APPLICATION_JSON)));
                future::ok((state, res))
            }
            Err(e) => return future::err((state, e.into_handler_error()))
        });

    Box::new(f)
}
这是我的
货物的最小内容。toml

[package]
name = "test"
version = "0.1.0"

[dependencies]
futures = "0.1"
gotham = "0.2"
hyper = "0.11"
mime = "0.3"
serde = "1.0"
serde_json = "1.0"

在rustc的建议和帮助下,我能够解决所有错误:

  • 我在
    where
    子句中添加了
    C:'static
  • 我更改了闭包
    |full|u body
    ,使其
    移动
  • 我将绑定的类型从
    反序列化更改为{
    让body_content=String::from_utf8(有效的_body.to_vec()).unwrap();
    让body_json=from_str::(&body_content).unwrap();
    让resp_json=callback(body_json);
    让resp_content=to_string(&resp_json).unwrap()进入_字节();
    让res=create_response(&state,StatusCode::Ok,Some((resp_content,APPLICATION_JSON));
    未来::ok((状态,res))
    }
    Err(e)=>returnfuture::Err((状态,e.into_handler_error())
    });
    框::新(f)
    }
    
    为什么您认为您的代码应该有效?您的返回值是否捕获了该引用?参考寿命够长吗?编译器将如何验证这一点?你为什么决定首先引用?@Shepmaster我相信我的代码应该可以工作,因为如果我不接受回调,而是调用函数,它确实可以工作。我不知道你在哪里问我为什么要引用,如果它是
    回调
    的参数,将它改为
    Fn(Q)
    ,而不是
    Fn(&Q)
    ,没有任何区别。我在问你为什么要引用
    &Fn
    。那个参考资料能活多久?编译器如何验证它的寿命足够长?@Shepmaster好吧,如果我不引用,我会收到一条错误消息,说明在编译时回调的大小未知(
    S+'static的特征绑定:std::marker::Sized`不满足