From 980488f918a70f24a859f3776f4b4dd947c3758e Mon Sep 17 00:00:00 2001 From: Michael Bryan Date: Sun, 20 Nov 2016 22:26:27 +0800 Subject: [PATCH 1/2] test: Added some trivial tests for the RequestBuilder --- src/client.rs | 146 ++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 146 insertions(+) diff --git a/src/client.rs b/src/client.rs index 8f20346..ac566f1 100644 --- a/src/client.rs +++ b/src/client.rs @@ -283,3 +283,149 @@ impl Read for Response { self.inner.read(buf) } } +#[cfg(test)] +mod tests { + use super::*; + use hyper::method::Method; + use hyper::Url; + use hyper::header::{Host, Headers, ContentType}; + use std::collections::HashMap; + + #[test] + fn basic_get_request() { + let client = Client::new().unwrap(); + let some_url = "https://google.com/"; + let r = client.get(some_url); + + assert_eq!(r.method, Method::Get); + assert_eq!(r.url, Url::parse(some_url)); + } + + #[test] + fn basic_head_request() { + let client = Client::new().unwrap(); + let some_url = "https://google.com/"; + let r = client.head(some_url); + + assert_eq!(r.method, Method::Head); + assert_eq!(r.url, Url::parse(some_url)); + } + + #[test] + fn basic_post_request() { + let client = Client::new().unwrap(); + let some_url = "https://google.com/"; + let r = client.post(some_url); + + assert_eq!(r.method, Method::Post); + assert_eq!(r.url, Url::parse(some_url)); + } + + #[test] + fn add_header() { + let client = Client::new().unwrap(); + let some_url = "https://google.com/"; + let mut r = client.post(some_url); + + let header = Host { + hostname: "google.com".to_string(), + port: None, + }; + + // Add a copy of the header to the request builder + r = r.header(header.clone()); + + // then check it was actually added + assert_eq!(r.headers.get::(), Some(&header)); + } + + #[test] + fn add_headers() { + let client = Client::new().unwrap(); + let some_url = "https://google.com/"; + let mut r = client.post(some_url); + + let header = Host { + hostname: "google.com".to_string(), + port: None, + }; + + let mut headers = Headers::new(); + headers.set(header); + + // Add a copy of the headers to the request builder + r = r.headers(headers.clone()); + + // then make sure they were added correctly + assert_eq!(r.headers, headers); + } + + #[test] + #[ignore] + fn add_body() { + // Currently Body doesn't have an implementation of PartialEq, so you + // can't check whether the body is actually what you set. + // + // This is most probably because Body's reader attribute is anything + // which implements Read, meaning the act of checking the body will + // probably consume it. To get around this, you might want to consider + // restricting Body.reader to something a little more concrete like a + // String. + // + // A basic test is included below, but commented out so the compiler + // won't yell at you. + + + // let client = Client::new().unwrap(); + // let some_url = "https://google.com/"; + // let mut r = client.post(some_url); + // + // let body = "Some interesting content"; + // + // r = r.body(body); + // + //assert_eq!(r.body.unwrap().unwrap(), body); + } + + #[test] + fn add_form() { + let client = Client::new().unwrap(); + let some_url = "https://google.com/"; + let mut r = client.post(some_url); + + let mut form_data = HashMap::new(); + form_data.insert("foo", "bar"); + + r = r.form(&form_data); + + // Make sure the content type was set + assert_eq!(r.headers.get::(), Some(&ContentType::form_url_encoded())); + + // need to check the body is set to the serialized hashmap. Can't + // currently do that because Body doesn't implement PartialEq. + + // let body_should_be: Body = serde_urlencoded::to_string(form).map(|b| b.into()); + // assert_eq!(r.body, Some(body_should_be)); + } + + #[test] + fn add_json() { + let client = Client::new().unwrap(); + let some_url = "https://google.com/"; + let mut r = client.post(some_url); + + let mut form_data = HashMap::new(); + form_data.insert("foo", "bar"); + + r = r.json(&form_data); + + // Make sure the content type was set + assert_eq!(r.headers.get::(), Some(&ContentType::json())); + + // need to check the body is set to the serialized hashmap. Can't + // currently do that because Body doesn't implement PartialEq. + + // let body_should_be: Body = serde_urlencoded::to_string(form).map(|b| b.into()); + // assert_eq!(r.body, Some(body_should_be)); + } +} From 59ba7cf23b48c94c7223cf0f2047e9e7b1e0a275 Mon Sep 17 00:00:00 2001 From: Michael Bryan Date: Mon, 21 Nov 2016 11:45:05 +0800 Subject: [PATCH 2/2] test: Fixed up issue with reading a Body and finished RequestBuilder tests --- src/body.rs | 32 +++++++++++++++++++++++++++-- src/client.rs | 56 ++++++++++++++++++++++----------------------------- 2 files changed, 54 insertions(+), 34 deletions(-) diff --git a/src/body.rs b/src/body.rs index cd5c3cc..7348ac7 100644 --- a/src/body.rs +++ b/src/body.rs @@ -1,4 +1,5 @@ -use std::io::Read; +use std::io::{Cursor, Read}; +use std::io; use std::fs::File; use std::fmt; @@ -27,11 +28,39 @@ impl Body { */ } +impl Read for Body { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + self.reader.read(buf) + } +} + enum Kind { Reader(Box, Option), Bytes(Vec), } +impl Read for Kind { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + match *self { + Kind::Reader(ref mut reader, _) => { + reader.read(buf) + } + Kind::Bytes(ref mut bytes) => { + // To make sure the bytes are removed properly when you read + // them, you need to use `drain()` + // FIXME: this will probably have poor performance for larger + // bodies due to allocating more than necessary. + let drained_bytes: Vec = bytes.drain(..).collect(); + + // then you need a Cursor because a standard Vec doesn't implement + // Read + let mut cursor = Cursor::new(drained_bytes); + cursor.read(buf) + } + } + } +} + impl From> for Body { #[inline] fn from(v: Vec) -> Body { @@ -101,4 +130,3 @@ pub fn as_hyper_body<'a>(body: &'a mut Body) -> ::hyper::client::Body<'a> { } } } - diff --git a/src/client.rs b/src/client.rs index ac566f1..1d8ac5e 100644 --- a/src/client.rs +++ b/src/client.rs @@ -290,6 +290,9 @@ mod tests { use hyper::Url; use hyper::header::{Host, Headers, ContentType}; use std::collections::HashMap; + use std::io::Read; + use serde_urlencoded; + use serde_json; #[test] fn basic_get_request() { @@ -361,30 +364,19 @@ mod tests { } #[test] - #[ignore] fn add_body() { - // Currently Body doesn't have an implementation of PartialEq, so you - // can't check whether the body is actually what you set. - // - // This is most probably because Body's reader attribute is anything - // which implements Read, meaning the act of checking the body will - // probably consume it. To get around this, you might want to consider - // restricting Body.reader to something a little more concrete like a - // String. - // - // A basic test is included below, but commented out so the compiler - // won't yell at you. + let client = Client::new().unwrap(); + let some_url = "https://google.com/"; + let mut r = client.post(some_url); + let body = "Some interesting content"; - // let client = Client::new().unwrap(); - // let some_url = "https://google.com/"; - // let mut r = client.post(some_url); - // - // let body = "Some interesting content"; - // - // r = r.body(body); - // - //assert_eq!(r.body.unwrap().unwrap(), body); + r = r.body(body); + + let mut buf = String::new(); + r.body.unwrap().unwrap().read_to_string(&mut buf).unwrap(); + + assert_eq!(buf, body); } #[test] @@ -401,11 +393,11 @@ mod tests { // Make sure the content type was set assert_eq!(r.headers.get::(), Some(&ContentType::form_url_encoded())); - // need to check the body is set to the serialized hashmap. Can't - // currently do that because Body doesn't implement PartialEq. + let mut buf = String::new(); + r.body.unwrap().unwrap().read_to_string(&mut buf).unwrap(); - // let body_should_be: Body = serde_urlencoded::to_string(form).map(|b| b.into()); - // assert_eq!(r.body, Some(body_should_be)); + let body_should_be = serde_urlencoded::to_string(&form_data).unwrap(); + assert_eq!(buf, body_should_be); } #[test] @@ -414,18 +406,18 @@ mod tests { let some_url = "https://google.com/"; let mut r = client.post(some_url); - let mut form_data = HashMap::new(); - form_data.insert("foo", "bar"); + let mut json_data = HashMap::new(); + json_data.insert("foo", "bar"); - r = r.json(&form_data); + r = r.json(&json_data); // Make sure the content type was set assert_eq!(r.headers.get::(), Some(&ContentType::json())); - // need to check the body is set to the serialized hashmap. Can't - // currently do that because Body doesn't implement PartialEq. + let mut buf = String::new(); + r.body.unwrap().unwrap().read_to_string(&mut buf).unwrap(); - // let body_should_be: Body = serde_urlencoded::to_string(form).map(|b| b.into()); - // assert_eq!(r.body, Some(body_should_be)); + let body_should_be = serde_json::to_string(&json_data).unwrap(); + assert_eq!(buf, body_should_be); } }