就是actix
中间件的简化写法wrap_fn
,下面是官方范例。
use actix_web::{dev::Service as _, middleware, web, App};
use actix_web::http::header::{CONTENT_TYPE, HeaderValue};
async fn index() -> &'static str {
"Welcome!"
}
let app = App::new()
.wrap_fn(|req, srv| {
let fut = srv.call(req);
async {
let mut res = fut.await?;
res.headers_mut()
.insert(CONTENT_TYPE, HeaderValue::from_static("text/plain"));
Ok(res)
}
})
.route("/index.html", web::get().to(index));
actix
的中间件实现代码相当冗余,于是盯上了这个API,本来想写成普通函数通过mod引入,但就得精确定义其输入输出类型,结果发现srv
参数的类型是&actix_web::app_service::AppRouting
,是一个私有类型,根本没法定义。
兜兜转转查了下,发现有个issue讨论过,发起者应该也在论坛里面,wrap_fn &AppRouting should use Arc #2681,官方推荐的是actix_web_lab::middleware::from_fn
,倒也不是不行,但一来又引入了新模块,二来其源码展开后就是那种复杂的中间件写法。
是不是这个API目前如果不引入actix_web_lab
的基本是没法不写闭包实现的?
Ext Link: https://docs.rs/actix-web/4.2.1/actix_web/struct.App.html#method.wrap_fn
1
共 2 条评论, 1 页
评论区
写评论谢谢!一到这种时候就脑抽,明明是用泛型函数把这个类型打印出来的,咋就没想到直接泛型函数当做中间件函数就好了。
--
👇
fakeshadow: ```rust fn main() { fn func<S, Req>(req: Req, s: &S) -> S::Future where S: actix_web::dev::Service { s.call(req) }
}
善用泛型来表达,目标库不需要export所有类型。 另外你引用的issue说的完全是另一个问题。