diff --git a/src/test/agent_test.rs b/src/test/agent_test.rs index f1e4920..fe9a9ee 100644 --- a/src/test/agent_test.rs +++ b/src/test/agent_test.rs @@ -1,6 +1,7 @@ use crate::test; use super::super::*; +use std::thread; #[test] fn agent_reuse_headers() { @@ -56,24 +57,61 @@ fn agent_cookies() { #[test] #[cfg(feature = "tls")] fn connection_reuse() { - use std::io::Read; + use std::io::{BufRead, BufReader, Read, Write}; use std::time::Duration; + // Start a test server on an available port, that times out idle connections at 2 seconds. + let listener = std::net::TcpListener::bind("localhost:0").unwrap(); + let port = listener.local_addr().unwrap().port(); + let url = format!("http://localhost:{}", port); + thread::spawn(move || { + for stream in listener.incoming() { + thread::spawn(move || { + let stream = stream.unwrap(); + stream + .set_read_timeout(Some(Duration::from_millis(2000))) + .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(); + } + } + }); + } + }); + let agent = Agent::default().build(); - let resp = agent.get("https://fau.xxx/").call(); + let resp = agent.get(&url).call(); // use up the connection so it gets returned to the pool assert_eq!(resp.status(), 200); - resp.into_reader().read_to_end(&mut vec![]).unwrap(); + let mut buf = vec![]; + resp.into_reader().read_to_end(&mut buf).unwrap(); - // wait for the server to close the connection. fau.xxx has a - // 2 second connection keep-alive. then it closes. + { + let mut guard_state = agent.state().lock().unwrap(); + let mut state = guard_state.take().unwrap(); + assert!(state.pool().len() > 0); + } + + // wait for the server to close the connection. std::thread::sleep(Duration::from_secs(3)); // try and make a new request on the pool. this fails // when we discover that the TLS connection is dead // first when attempting to read from it. - let resp = agent.get("https://fau.xxx/").call(); + // Note: This test assumes the second .call() actually + // pulls from the pool. If for some reason the timed-out + // connection wasn't in the pool, we won't be testing what + // we thought we were testing. + let resp = agent.get(&url).call(); if let Some(err) = resp.synthetic_error() { panic!("Pooled connection failed! {:?}", err); }