fix(server): error if Response code is 1xx

Returning a Response from a Service with a 1xx StatusCode is not
currently supported in hyper. It has always resulted in broken
semantics. This patch simply errors better.

- A Response with 1xx status is converted into a 500 response with no body.
- An error is returned from the `server::Connection` to alert about the
  bad response.
This commit is contained in:
Sean McArthur
2018-01-23 13:02:44 -08:00
parent 227742221f
commit 44c34ce9ad
5 changed files with 80 additions and 13 deletions

View File

@@ -22,7 +22,8 @@ use std::sync::{Arc, Mutex};
use std::thread;
use std::time::Duration;
use hyper::server::{Http, Request, Response, Service, NewService};
use hyper::StatusCode;
use hyper::server::{Http, Request, Response, Service, NewService, service_fn};
#[test]
@@ -867,6 +868,38 @@ fn nonempty_parse_eof_returns_error() {
core.run(fut).unwrap_err();
}
#[test]
fn returning_1xx_response_is_error() {
let mut core = Core::new().unwrap();
let listener = TcpListener::bind(&"127.0.0.1:0".parse().unwrap(), &core.handle()).unwrap();
let addr = listener.local_addr().unwrap();
thread::spawn(move || {
let mut tcp = connect(&addr);
tcp.write_all(b"GET / HTTP/1.1\r\n\r\n").unwrap();
let mut buf = [0; 256];
tcp.read(&mut buf).unwrap();
let expected = "HTTP/1.1 500 ";
assert_eq!(s(&buf[..expected.len()]), expected);
});
let fut = listener.incoming()
.into_future()
.map_err(|_| unreachable!())
.and_then(|(item, _incoming)| {
let (socket, _) = item.unwrap();
Http::<hyper::Chunk>::new()
.serve_connection(socket, service_fn(|_| {
Ok(Response::<hyper::Body>::new()
.with_status(StatusCode::Continue))
}))
.map(|_| ())
});
core.run(fut).unwrap_err();
}
#[test]
fn remote_addr() {
let server = serve();
@@ -1191,3 +1224,4 @@ impl Drop for Dropped {
self.0.store(true, Ordering::SeqCst);
}
}