use crate::test;
use std::io::{BufRead, BufReader, Read, Write};
use std::thread;
use std::time::Duration;
use super::super::*;
#[test]
fn agent_reuse_headers() {
let agent = agent().set("Authorization", "Foo 12345").build();
test::set_handler("/agent_reuse_headers", |unit| {
assert!(unit.has("Authorization"));
assert_eq!(unit.header("Authorization").unwrap(), "Foo 12345");
test::make_response(200, "OK", vec!["X-Call: 1"], vec![])
});
let resp = agent.get("test://host/agent_reuse_headers").call();
assert_eq!(resp.header("X-Call").unwrap(), "1");
test::set_handler("/agent_reuse_headers", |unit| {
assert!(unit.has("Authorization"));
assert_eq!(unit.header("Authorization").unwrap(), "Foo 12345");
test::make_response(200, "OK", vec!["X-Call: 2"], vec![])
});
let resp = agent.get("test://host/agent_reuse_headers").call();
assert_eq!(resp.header("X-Call").unwrap(), "2");
}
#[cfg(feature = "cookie")]
#[test]
fn agent_cookies() {
let agent = agent();
test::set_handler("/agent_cookies", |_unit| {
test::make_response(
200,
"OK",
vec!["Set-Cookie: foo=bar%20baz; Path=/; HttpOnly"],
vec![],
)
});
agent.get("test://host/agent_cookies").call();
assert!(agent.cookie("foo").is_some());
assert_eq!(agent.cookie("foo").unwrap().value(), "bar baz");
test::set_handler("/agent_cookies", |unit| {
assert!(unit.has("cookie"));
assert_eq!(unit.header("cookie").unwrap(), "foo=bar%20baz");
test::make_response(200, "OK", vec![], vec![])
});
agent.get("test://host/agent_cookies").call();
}
fn start_idle_timeout_server() -> u16 {
let listener = std::net::TcpListener::bind("localhost:0").unwrap();
let port = listener.local_addr().unwrap().port();
thread::spawn(move || {
for stream in listener.incoming() {
thread::spawn(move || {
let stream = stream.unwrap();
stream
.set_read_timeout(Some(Duration::from_secs(2)))
.unwrap();
let mut write_stream = stream.try_clone().unwrap();
for line in BufReader::new(stream).lines() {
let line = match line {
Ok(x) => x,
Err(_) => return,
};
if line == "" {
write_stream
.write_all(b"HTTP/1.1 200 OK\r\nContent-Length: 8\r\n\r\nresponse")
.unwrap();
}
}
});
}
});
port
}
#[test]
fn connection_reuse() {
let port = start_idle_timeout_server();
let url = format!("http://localhost:{}", port);
let agent = Agent::default().build();
let resp = agent.get(&url).call();
assert_eq!(resp.status(), 200);
let mut buf = vec![];
resp.into_reader().read_to_end(&mut buf).unwrap();
{
let mut guard_state = agent.state.lock().unwrap();
let mut state = guard_state.take().unwrap();
assert!(state.pool().len() > 0);
}
std::thread::sleep(Duration::from_secs(3));
let resp = agent.get(&url).call();
if let Some(err) = resp.synthetic_error() {
panic!("Pooled connection failed! {:?}", err);
}
assert_eq!(resp.status(), 200);
}