10583cff8SDavid Pedersen use super::*;
20583cff8SDavid Pedersen use http_body::Body as _;
3a585a722SMarcus Griep use tonic::codec::CompressionEncoding;
40583cff8SDavid Pedersen 
50583cff8SDavid Pedersen #[tokio::test(flavor = "multi_thread")]
60583cff8SDavid Pedersen async fn client_enabled_server_enabled() {
70583cff8SDavid Pedersen     let (client, server) = tokio::io::duplex(UNCOMPRESSED_MIN_BODY_SIZE * 10);
80583cff8SDavid Pedersen 
9a585a722SMarcus Griep     let svc =
10a585a722SMarcus Griep         test_server::TestServer::new(Svc::default()).accept_compressed(CompressionEncoding::Gzip);
110583cff8SDavid Pedersen 
120583cff8SDavid Pedersen     let request_bytes_counter = Arc::new(AtomicUsize::new(0));
130583cff8SDavid Pedersen 
140583cff8SDavid Pedersen     fn assert_right_encoding<B>(req: http::Request<B>) -> http::Request<B> {
150583cff8SDavid Pedersen         assert_eq!(req.headers().get("grpc-encoding").unwrap(), "gzip");
160583cff8SDavid Pedersen         req
170583cff8SDavid Pedersen     }
180583cff8SDavid Pedersen 
190583cff8SDavid Pedersen     tokio::spawn({
200583cff8SDavid Pedersen         let request_bytes_counter = request_bytes_counter.clone();
210583cff8SDavid Pedersen         async move {
220583cff8SDavid Pedersen             Server::builder()
230583cff8SDavid Pedersen                 .layer(
240583cff8SDavid Pedersen                     ServiceBuilder::new()
250583cff8SDavid Pedersen                         .map_request(assert_right_encoding)
260583cff8SDavid Pedersen                         .layer(measure_request_body_size_layer(
270583cff8SDavid Pedersen                             request_bytes_counter.clone(),
280583cff8SDavid Pedersen                         ))
290583cff8SDavid Pedersen                         .into_inner(),
300583cff8SDavid Pedersen                 )
310583cff8SDavid Pedersen                 .add_service(svc)
32*23602b47Stottoto                 .serve_with_incoming(tokio_stream::iter(vec![Ok::<_, std::io::Error>(server)]))
330583cff8SDavid Pedersen                 .await
340583cff8SDavid Pedersen                 .unwrap();
350583cff8SDavid Pedersen         }
360583cff8SDavid Pedersen     });
370583cff8SDavid Pedersen 
38a585a722SMarcus Griep     let mut client = test_client::TestClient::new(mock_io_channel(client).await)
39a585a722SMarcus Griep         .send_compressed(CompressionEncoding::Gzip);
400583cff8SDavid Pedersen 
410583cff8SDavid Pedersen     let data = [0_u8; UNCOMPRESSED_MIN_BODY_SIZE].to_vec();
42*23602b47Stottoto     let stream = tokio_stream::iter(vec![SomeData { data: data.clone() }, SomeData { data }]);
430583cff8SDavid Pedersen     let req = Request::new(Box::pin(stream));
440583cff8SDavid Pedersen 
450583cff8SDavid Pedersen     client.compress_input_client_stream(req).await.unwrap();
460583cff8SDavid Pedersen 
470583cff8SDavid Pedersen     let bytes_sent = request_bytes_counter.load(SeqCst);
480583cff8SDavid Pedersen     assert!(bytes_sent < UNCOMPRESSED_MIN_BODY_SIZE);
490583cff8SDavid Pedersen }
500583cff8SDavid Pedersen 
510583cff8SDavid Pedersen #[tokio::test(flavor = "multi_thread")]
520583cff8SDavid Pedersen async fn client_disabled_server_enabled() {
530583cff8SDavid Pedersen     let (client, server) = tokio::io::duplex(UNCOMPRESSED_MIN_BODY_SIZE * 10);
540583cff8SDavid Pedersen 
55a585a722SMarcus Griep     let svc =
56a585a722SMarcus Griep         test_server::TestServer::new(Svc::default()).accept_compressed(CompressionEncoding::Gzip);
570583cff8SDavid Pedersen 
580583cff8SDavid Pedersen     let request_bytes_counter = Arc::new(AtomicUsize::new(0));
590583cff8SDavid Pedersen 
600583cff8SDavid Pedersen     fn assert_right_encoding<B>(req: http::Request<B>) -> http::Request<B> {
610583cff8SDavid Pedersen         assert!(req.headers().get("grpc-encoding").is_none());
620583cff8SDavid Pedersen         req
630583cff8SDavid Pedersen     }
640583cff8SDavid Pedersen 
650583cff8SDavid Pedersen     tokio::spawn({
660583cff8SDavid Pedersen         let request_bytes_counter = request_bytes_counter.clone();
670583cff8SDavid Pedersen         async move {
680583cff8SDavid Pedersen             Server::builder()
690583cff8SDavid Pedersen                 .layer(
700583cff8SDavid Pedersen                     ServiceBuilder::new()
710583cff8SDavid Pedersen                         .map_request(assert_right_encoding)
720583cff8SDavid Pedersen                         .layer(measure_request_body_size_layer(
730583cff8SDavid Pedersen                             request_bytes_counter.clone(),
740583cff8SDavid Pedersen                         ))
750583cff8SDavid Pedersen                         .into_inner(),
760583cff8SDavid Pedersen                 )
770583cff8SDavid Pedersen                 .add_service(svc)
78*23602b47Stottoto                 .serve_with_incoming(tokio_stream::iter(vec![Ok::<_, std::io::Error>(server)]))
790583cff8SDavid Pedersen                 .await
800583cff8SDavid Pedersen                 .unwrap();
810583cff8SDavid Pedersen         }
820583cff8SDavid Pedersen     });
830583cff8SDavid Pedersen 
840583cff8SDavid Pedersen     let mut client = test_client::TestClient::new(mock_io_channel(client).await);
850583cff8SDavid Pedersen 
860583cff8SDavid Pedersen     let data = [0_u8; UNCOMPRESSED_MIN_BODY_SIZE].to_vec();
87*23602b47Stottoto     let stream = tokio_stream::iter(vec![SomeData { data: data.clone() }, SomeData { data }]);
880583cff8SDavid Pedersen     let req = Request::new(Box::pin(stream));
890583cff8SDavid Pedersen 
900583cff8SDavid Pedersen     client.compress_input_client_stream(req).await.unwrap();
910583cff8SDavid Pedersen 
920583cff8SDavid Pedersen     let bytes_sent = request_bytes_counter.load(SeqCst);
930583cff8SDavid Pedersen     assert!(bytes_sent > UNCOMPRESSED_MIN_BODY_SIZE);
940583cff8SDavid Pedersen }
950583cff8SDavid Pedersen 
960583cff8SDavid Pedersen #[tokio::test(flavor = "multi_thread")]
970583cff8SDavid Pedersen async fn client_enabled_server_disabled() {
980583cff8SDavid Pedersen     let (client, server) = tokio::io::duplex(UNCOMPRESSED_MIN_BODY_SIZE * 10);
990583cff8SDavid Pedersen 
1000583cff8SDavid Pedersen     let svc = test_server::TestServer::new(Svc::default());
1010583cff8SDavid Pedersen 
1020583cff8SDavid Pedersen     tokio::spawn(async move {
1030583cff8SDavid Pedersen         Server::builder()
1040583cff8SDavid Pedersen             .add_service(svc)
105*23602b47Stottoto             .serve_with_incoming(tokio_stream::iter(vec![Ok::<_, std::io::Error>(server)]))
1060583cff8SDavid Pedersen             .await
1070583cff8SDavid Pedersen             .unwrap();
1080583cff8SDavid Pedersen     });
1090583cff8SDavid Pedersen 
110a585a722SMarcus Griep     let mut client = test_client::TestClient::new(mock_io_channel(client).await)
111a585a722SMarcus Griep         .send_compressed(CompressionEncoding::Gzip);
1120583cff8SDavid Pedersen 
1130583cff8SDavid Pedersen     let data = [0_u8; UNCOMPRESSED_MIN_BODY_SIZE].to_vec();
114*23602b47Stottoto     let stream = tokio_stream::iter(vec![SomeData { data: data.clone() }, SomeData { data }]);
1150583cff8SDavid Pedersen     let req = Request::new(Box::pin(stream));
1160583cff8SDavid Pedersen 
1170583cff8SDavid Pedersen     let status = client.compress_input_client_stream(req).await.unwrap_err();
1180583cff8SDavid Pedersen 
1190583cff8SDavid Pedersen     assert_eq!(status.code(), tonic::Code::Unimplemented);
1200583cff8SDavid Pedersen     assert_eq!(
1210583cff8SDavid Pedersen         status.message(),
1220583cff8SDavid Pedersen         "Content is compressed with `gzip` which isn't supported"
1230583cff8SDavid Pedersen     );
1240583cff8SDavid Pedersen }
1250583cff8SDavid Pedersen 
1260583cff8SDavid Pedersen #[tokio::test(flavor = "multi_thread")]
1270583cff8SDavid Pedersen async fn compressing_response_from_client_stream() {
1280583cff8SDavid Pedersen     let (client, server) = tokio::io::duplex(UNCOMPRESSED_MIN_BODY_SIZE * 10);
1290583cff8SDavid Pedersen 
130a585a722SMarcus Griep     let svc =
131a585a722SMarcus Griep         test_server::TestServer::new(Svc::default()).send_compressed(CompressionEncoding::Gzip);
1320583cff8SDavid Pedersen 
1330583cff8SDavid Pedersen     let response_bytes_counter = Arc::new(AtomicUsize::new(0));
1340583cff8SDavid Pedersen 
1350583cff8SDavid Pedersen     tokio::spawn({
1360583cff8SDavid Pedersen         let response_bytes_counter = response_bytes_counter.clone();
1370583cff8SDavid Pedersen         async move {
1380583cff8SDavid Pedersen             Server::builder()
1390583cff8SDavid Pedersen                 .layer(
1400583cff8SDavid Pedersen                     ServiceBuilder::new()
1410583cff8SDavid Pedersen                         .layer(MapResponseBodyLayer::new(move |body| {
1420583cff8SDavid Pedersen                             util::CountBytesBody {
1430583cff8SDavid Pedersen                                 inner: body,
1440583cff8SDavid Pedersen                                 counter: response_bytes_counter.clone(),
1450583cff8SDavid Pedersen                             }
1460583cff8SDavid Pedersen                         }))
1470583cff8SDavid Pedersen                         .into_inner(),
1480583cff8SDavid Pedersen                 )
1490583cff8SDavid Pedersen                 .add_service(svc)
150*23602b47Stottoto                 .serve_with_incoming(tokio_stream::iter(vec![Ok::<_, std::io::Error>(server)]))
1510583cff8SDavid Pedersen                 .await
1520583cff8SDavid Pedersen                 .unwrap();
1530583cff8SDavid Pedersen         }
1540583cff8SDavid Pedersen     });
1550583cff8SDavid Pedersen 
156a585a722SMarcus Griep     let mut client = test_client::TestClient::new(mock_io_channel(client).await)
157a585a722SMarcus Griep         .accept_compressed(CompressionEncoding::Gzip);
1580583cff8SDavid Pedersen 
159*23602b47Stottoto     let stream = tokio_stream::iter(vec![]);
1600583cff8SDavid Pedersen     let req = Request::new(Box::pin(stream));
1610583cff8SDavid Pedersen 
1620583cff8SDavid Pedersen     let res = client.compress_output_client_stream(req).await.unwrap();
1630583cff8SDavid Pedersen     assert_eq!(res.metadata().get("grpc-encoding").unwrap(), "gzip");
1640583cff8SDavid Pedersen     let bytes_sent = response_bytes_counter.load(SeqCst);
1650583cff8SDavid Pedersen     assert!(bytes_sent < UNCOMPRESSED_MIN_BODY_SIZE);
1660583cff8SDavid Pedersen }
167