|
1 | 1 | //! An HTTP server
|
2 | 2 |
|
3 |
| -use async_std::future::Future; |
4 | 3 | use async_std::io;
|
5 | 4 | use async_std::net::ToSocketAddrs;
|
| 5 | +use async_std::prelude::*; |
6 | 6 | use async_std::sync::Arc;
|
7 |
| -use async_std::task::{Context, Poll}; |
8 |
| -use http_service::HttpService; |
| 7 | +use async_std::task; |
9 | 8 |
|
10 | 9 | use std::fmt::Debug;
|
11 |
| -use std::pin::Pin; |
12 | 10 |
|
13 | 11 | use crate::cookies;
|
14 | 12 | use crate::log;
|
@@ -281,14 +279,31 @@ impl<State: Send + Sync + 'static> Server<State> {
|
281 | 279 |
|
282 | 280 | /// Asynchronously serve the app at the given address.
|
283 | 281 | #[cfg(feature = "h1-server")]
|
284 |
| - pub async fn listen(self, addr: impl ToSocketAddrs) -> std::io::Result<()> { |
| 282 | + pub async fn listen(self, addr: impl ToSocketAddrs) -> io::Result<()> { |
285 | 283 | let listener = async_std::net::TcpListener::bind(addr).await?;
|
286 | 284 |
|
287 | 285 | let addr = format!("http://{}", listener.local_addr()?);
|
288 | 286 | log::info!("Server is listening on: {}", addr);
|
289 |
| - let mut server = http_service_h1::Server::new(addr, listener.incoming(), self); |
| 287 | + let mut incoming = listener.incoming(); |
290 | 288 |
|
291 |
| - server.run().await |
| 289 | + while let Some(stream) = incoming.next().await { |
| 290 | + let stream = stream?; |
| 291 | + let addr = addr.clone(); |
| 292 | + let this = self.clone(); |
| 293 | + task::spawn(async move { |
| 294 | + let res = async_h1::accept(&addr, stream, |req| async { |
| 295 | + let res = this.respond(req).await; |
| 296 | + let res = res.map_err(|_| io::Error::from(io::ErrorKind::Other))?; |
| 297 | + Ok(res) |
| 298 | + }) |
| 299 | + .await; |
| 300 | + |
| 301 | + if let Err(err) = res { |
| 302 | + log::error!("async-h1 error", { error: err.to_string() }); |
| 303 | + } |
| 304 | + }); |
| 305 | + } |
| 306 | + Ok(()) |
292 | 307 | }
|
293 | 308 |
|
294 | 309 | /// Respond to a `Request` with a `Response`.
|
@@ -352,56 +367,6 @@ impl<State> Clone for Server<State> {
|
352 | 367 | }
|
353 | 368 | }
|
354 | 369 |
|
355 |
| -#[derive(Debug)] |
356 |
| -pub struct ReadyFuture; |
357 |
| - |
358 |
| -impl Future for ReadyFuture { |
359 |
| - type Output = io::Result<()>; |
360 |
| - |
361 |
| - fn poll(self: Pin<&mut Self>, _cx: &mut Context<'_>) -> Poll<Self::Output> { |
362 |
| - Poll::Ready(Ok(())) |
363 |
| - } |
364 |
| -} |
365 |
| - |
366 |
| -impl<State: Sync + Send + 'static> HttpService for Server<State> { |
367 |
| - type Connection = (); |
368 |
| - type ConnectionFuture = ReadyFuture; |
369 |
| - type ConnectionError = io::Error; |
370 |
| - type ResponseFuture = BoxFuture<'static, Result<http_service::Response, http_types::Error>>; |
371 |
| - type ResponseError = http_types::Error; |
372 |
| - |
373 |
| - fn connect(&self) -> Self::ConnectionFuture { |
374 |
| - ReadyFuture {} |
375 |
| - } |
376 |
| - |
377 |
| - fn respond(&self, _conn: (), req: http_service::Request) -> Self::ResponseFuture { |
378 |
| - let req = Request::new(self.state.clone(), req, Vec::new()); |
379 |
| - let service = self.clone(); |
380 |
| - Box::pin(async move { |
381 |
| - match service.call(req).await { |
382 |
| - Ok(value) => { |
383 |
| - let res = value.into(); |
384 |
| - // We assume that if an error was manually cast to a |
385 |
| - // Response that we actually want to send the body to the |
386 |
| - // client. At this point we don't scrub the message. |
387 |
| - Ok(res) |
388 |
| - } |
389 |
| - Err(err) => { |
390 |
| - let mut res = http_types::Response::new(err.status()); |
391 |
| - res.set_content_type(http_types::mime::PLAIN); |
392 |
| - // Only send the message if it is a non-500 range error. All |
393 |
| - // errors default to 500 by default, so sending the error |
394 |
| - // body is opt-in at the call site. |
395 |
| - if !res.status().is_server_error() { |
396 |
| - res.set_body(err.to_string()); |
397 |
| - } |
398 |
| - Ok(res) |
399 |
| - } |
400 |
| - } |
401 |
| - }) |
402 |
| - } |
403 |
| -} |
404 |
| - |
405 | 370 | impl<State: Sync + Send + 'static, InnerState: Sync + Send + 'static> Endpoint<State>
|
406 | 371 | for Server<InnerState>
|
407 | 372 | {
|
|
0 commit comments