2个不稳定版本
使用旧的Rust 2015
0.2.0 | 2017年5月7日 |
---|---|
0.1.0 | 2017年5月6日 |
在 HTTP客户端 中出现 503
每月下载量 23
在 bouncer 中使用
12KB
158 行
api
api
为定义客户端端的HTTP API提供了一组实用工具,无需担心实际的HTTP客户端(直到发送请求!)。
Api trait
api::Api
是一个用于定义远程API的trait。开发者必须为表示API端点的 struct
实现它。
对于我们的示例,我们将创建一个针对 httpbin 及其端点 /delay:n
的简单客户端(响应延迟n秒并返回有关请求的一些信息)。
Api
有三个关联类型
-
Body
用于生成请求体,它必须实现std::io::Read
trait。如果端点不需要体,应使用std::io::Empty
。 -
Reply
定义我们期望从API收到的响应。 -
Error
定义在收到响应时可能遇到的全部预期错误。
首先,我们需要定义请求和响应。 /delay/:n
在路径中只有一个参数,我们只关心JSON响应中的 origin
和 headers
字段(我们将使用 serde_json
来解析响应体)。
extern crate api;
#[macro_use]
extern crate serde_derive;
extern crate serde;
extern crate serde_json;
// request for /delay/:n
struct Delay {
delay: u8
}
// it's a subset of the available data
#[derive(Deserialize)]
struct Info {
origin: String, // ip address
headers: BTreeMap<String, String>, // headers received by the server
}
impl api::Api for Delay {
type Reply = Info;
type Body = io::Empty;
type Error = serde_json::Error;
...
}
然后,我们可以开始定义HTTP请求的外观,为 Delay
实现 Api
trait。我们将向 /delay/:n
发送 GET
请求,其中 :n
将被 Delay.delay
中的值替换。
impl api::Api for Delay {
type Reply = Info;
type Body = io::Empty;
type Error = serde_json::Error;
fn method(&self) -> api::Method {
api::Method::Get
}
fn path(&self) -> String {
// use a safe joiner to create the path!
format!("/delay/{}", self.delay)
}
fn query(&self) -> api::Query {
// we'll send any parameter in the query
Query::new()
}
fn headers(&self) -> api::Header {
let mut headers = api::Header::new();
headers.insert("X-Request-ID", "abcde");
headers
}
fn body(&self) -> std::io::Empty {
std::io::empty()
}
}
现在,我们需要从代表HTTP响应的 HttpResponse
trait 创建回复 Info
。
impl api::Api for Delay {
type Reply = Info;
type Body = io::Empty;
type Error = serde_json::Error;
...
fn parse<R: HttpResponse>(&self, resp: &mut R) -> Result<Info, serde_json::Error> {
serde_json::from_reader(resp.body())
}
}
api
具有一个特质 Client
,用于为实际的 HTTP 客户端创建适配器,并且为 hyper::Client
实现了它。 Client
有一个方法 send
,它接受 API 的基本 URL 和请求。
extern crate hyper;
use api::Client;
...
fn main() {
let mut client = hyper::Client::new();
let resp = client.send("http://httpbin.org/", Delay { delay: 1 });
println!("{:?}", resp);
}
完整代码在 examples/httpbin.rs
中(运行 cargo run --example=httpbin --features=use-hyper
)。
依赖项
~0–1MB
~19K SLoC