use embedded_io_adapters::tokio_1::FromTokio; use hyper::service::{make_service_fn, service_fn}; use hyper::{Body, Server}; use reqwless::client::HttpConnection; use reqwless::request::RequestBuilder; use reqwless::Error; use reqwless::{headers::ContentType, request::Request}; use std::str::from_utf8; use std::sync::Once; use tokio::net::TcpStream; use tokio::sync::oneshot; mod connection; use connection::*; static INIT: Once = Once::new(); fn setup() { INIT.call_once(|| { env_logger::init(); }); } #[tokio::test] async fn test_request_response() { setup(); let addr = ([127, 0, 0, 1], 0).into(); let service = make_service_fn(|_| async { Ok::<_, hyper::Error>(service_fn(echo)) }); let server = Server::bind(&addr).serve(service); let addr = server.local_addr(); let (tx, rx) = oneshot::channel(); let t = tokio::spawn(async move { tokio::select! { _ = server => {} _ = rx => {} } }); let stream = TcpStream::connect(addr).await.unwrap(); let mut stream = HttpConnection::Plain(TokioStream(FromTokio::new(stream))); let request = Request::post("/") .body(b"PING".as_slice()) .content_type(ContentType::TextPlain) .build(); let mut rx_buf = [0; 4096]; let response = stream.send(request, &mut rx_buf).await.unwrap(); let body = response.body().read_to_end().await; assert_eq!(body.unwrap(), b"PING"); tx.send(()).unwrap(); t.await.unwrap(); } async fn echo(req: hyper::Request) -> Result, hyper::Error> { match (req.method(), req.uri().path()) { _ => Ok(hyper::Response::new(req.into_body())), } } #[tokio::test] async fn write_without_base_path() { let request = Request::get("/hello").build(); let mut buf = Vec::new(); request.write_header(&mut buf).await.unwrap(); assert!(from_utf8(&buf).unwrap().starts_with("GET /hello HTTP/1.1")); } #[tokio::test] async fn google_panic() { use std::net::SocketAddr; let google_ip = [142, 250, 74, 110]; let addr = SocketAddr::from((google_ip, 80)); let conn = tokio::net::TcpStream::connect(addr).await.unwrap(); let mut conn = HttpConnection::Plain(TokioStream(FromTokio::new(conn))); let request = Request::get("/") .host("www.google.com") .content_type(ContentType::TextPlain) .build(); let mut rx_buf = [0; 8 * 1024]; let resp = conn.send(request, &mut rx_buf).await.unwrap(); let result = resp.body().read_to_end().await; match result { Ok(body) => { println!("{} -> {}", body.len(), core::str::from_utf8(&body).unwrap()); } Err(Error::BufferTooSmall) => println!("Buffer too small"), Err(e) => panic!("Unexpected error: {e:?}"), } }