Skip to content

Commit 4ca8d42

Browse files
committed
Merge branch 'release/v0.1.1'
2 parents f7f1233 + fbb4811 commit 4ca8d42

File tree

4 files changed

+50
-2
lines changed

4 files changed

+50
-2
lines changed

Cargo.toml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
11
[package]
22
name = "stream-body"
3-
version = "0.1.0"
3+
version = "0.1.1"
44
description = "An HttpBody implementation with efficient streaming support for the Rust HTTP library hyper"
55
homepage = "https://github.com/rousan/stream-body"
66
repository = "https://github.com/rousan/stream-body"
7-
keywords = ["rust", "hyper", "asynchronous", "stream", "writer", "channel"]
7+
keywords = ["rust", "hyper", "asynchronous", "stream", "writer"]
88
categories = ["asynchronous"]
99
authors = ["Rousan Ali <[email protected]>"]
1010
readme = "README.md"

examples/from-reader.rs

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
use hyper::service::{make_service_fn, service_fn};
2+
use hyper::{Body, Request, Response, Server};
3+
use std::{convert::Infallible, net::SocketAddr};
4+
use stream_body::StreamBody;
5+
use tokio::fs::File;
6+
7+
async fn handle(_: Request<Body>) -> Result<Response<StreamBody>, Infallible> {
8+
let f = File::open("large-file.pdf").await.unwrap();
9+
let file_size = f.metadata().await.unwrap().len();
10+
11+
Ok(Response::builder()
12+
.header("Content-Type", "application/pdf")
13+
.header("Content-Length", file_size.to_string())
14+
.body(StreamBody::from_reader(f))
15+
.unwrap())
16+
}
17+
18+
#[tokio::main]
19+
async fn main() {
20+
let addr = SocketAddr::from(([127, 0, 0, 1], 3000));
21+
22+
let make_svc = make_service_fn(|_conn| async { Ok::<_, Infallible>(service_fn(handle)) });
23+
24+
let server = Server::bind(&addr).serve(make_svc);
25+
26+
if let Err(e) = server.await {
27+
eprintln!("server error: {}", e);
28+
}
29+
}

src/body.rs

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ use http::{HeaderMap, HeaderValue};
66
use http_body::{Body, SizeHint};
77
use pin_project_lite::pin_project;
88
use std::borrow::Cow;
9+
use std::marker::Unpin;
910
use std::mem::MaybeUninit;
1011
use std::pin::Pin;
1112
use std::sync::{Arc, Mutex};
@@ -94,6 +95,24 @@ impl StreamBody {
9495

9596
(w, body)
9697
}
98+
99+
/// A helper method to convert an [AsyncRead](https://docs.rs/tokio/0.2.16/tokio/io/trait.AsyncRead.html) to a `StreamBody`. If there is any error
100+
/// thrown during the reading/writing, it will be logged via [log::error!](https://docs.rs/log/0.4.10/log/macro.error.html).
101+
pub fn from_reader<R: AsyncRead + Unpin + Send + 'static>(mut r: R) -> StreamBody {
102+
let (mut w, body) = StreamBody::channel();
103+
104+
tokio::spawn(async move {
105+
if let Err(err) = io::copy(&mut r, &mut w).await {
106+
log::error!(
107+
"{}: StreamBody: Something went wrong while piping the provided reader to the body: {}",
108+
env!("CARGO_PKG_NAME"),
109+
err
110+
)
111+
}
112+
});
113+
114+
body
115+
}
97116
}
98117

99118
impl Body for StreamBody {

0 commit comments

Comments
 (0)