1*0583cff8SDavid Pedersen use super::*;
2*0583cff8SDavid Pedersen use http_body::Body as _;
3*0583cff8SDavid Pedersen 
4*0583cff8SDavid Pedersen #[tokio::test(flavor = "multi_thread")]
5*0583cff8SDavid Pedersen async fn client_enabled_server_enabled() {
6*0583cff8SDavid Pedersen     let (client, server) = tokio::io::duplex(UNCOMPRESSED_MIN_BODY_SIZE * 10);
7*0583cff8SDavid Pedersen 
8*0583cff8SDavid Pedersen     let svc = test_server::TestServer::new(Svc::default()).accept_gzip();
9*0583cff8SDavid Pedersen 
10*0583cff8SDavid Pedersen     let request_bytes_counter = Arc::new(AtomicUsize::new(0));
11*0583cff8SDavid Pedersen 
12*0583cff8SDavid Pedersen     fn assert_right_encoding<B>(req: http::Request<B>) -> http::Request<B> {
13*0583cff8SDavid Pedersen         assert_eq!(req.headers().get("grpc-encoding").unwrap(), "gzip");
14*0583cff8SDavid Pedersen         req
15*0583cff8SDavid Pedersen     }
16*0583cff8SDavid Pedersen 
17*0583cff8SDavid Pedersen     tokio::spawn({
18*0583cff8SDavid Pedersen         let request_bytes_counter = request_bytes_counter.clone();
19*0583cff8SDavid Pedersen         async move {
20*0583cff8SDavid Pedersen             Server::builder()
21*0583cff8SDavid Pedersen                 .layer(
22*0583cff8SDavid Pedersen                     ServiceBuilder::new()
23*0583cff8SDavid Pedersen                         .map_request(assert_right_encoding)
24*0583cff8SDavid Pedersen                         .layer(measure_request_body_size_layer(
25*0583cff8SDavid Pedersen                             request_bytes_counter.clone(),
26*0583cff8SDavid Pedersen                         ))
27*0583cff8SDavid Pedersen                         .into_inner(),
28*0583cff8SDavid Pedersen                 )
29*0583cff8SDavid Pedersen                 .add_service(svc)
30*0583cff8SDavid Pedersen                 .serve_with_incoming(futures::stream::iter(vec![Ok::<_, std::io::Error>(
31*0583cff8SDavid Pedersen                     MockStream(server),
32*0583cff8SDavid Pedersen                 )]))
33*0583cff8SDavid Pedersen                 .await
34*0583cff8SDavid Pedersen                 .unwrap();
35*0583cff8SDavid Pedersen         }
36*0583cff8SDavid Pedersen     });
37*0583cff8SDavid Pedersen 
38*0583cff8SDavid Pedersen     let mut client = test_client::TestClient::new(mock_io_channel(client).await).send_gzip();
39*0583cff8SDavid Pedersen 
40*0583cff8SDavid Pedersen     let data = [0_u8; UNCOMPRESSED_MIN_BODY_SIZE].to_vec();
41*0583cff8SDavid Pedersen     let stream = futures::stream::iter(vec![SomeData { data: data.clone() }, SomeData { data }]);
42*0583cff8SDavid Pedersen     let req = Request::new(Box::pin(stream));
43*0583cff8SDavid Pedersen 
44*0583cff8SDavid Pedersen     client.compress_input_client_stream(req).await.unwrap();
45*0583cff8SDavid Pedersen 
46*0583cff8SDavid Pedersen     let bytes_sent = request_bytes_counter.load(SeqCst);
47*0583cff8SDavid Pedersen     assert!(bytes_sent < UNCOMPRESSED_MIN_BODY_SIZE);
48*0583cff8SDavid Pedersen }
49*0583cff8SDavid Pedersen 
50*0583cff8SDavid Pedersen #[tokio::test(flavor = "multi_thread")]
51*0583cff8SDavid Pedersen async fn client_disabled_server_enabled() {
52*0583cff8SDavid Pedersen     let (client, server) = tokio::io::duplex(UNCOMPRESSED_MIN_BODY_SIZE * 10);
53*0583cff8SDavid Pedersen 
54*0583cff8SDavid Pedersen     let svc = test_server::TestServer::new(Svc::default()).accept_gzip();
55*0583cff8SDavid Pedersen 
56*0583cff8SDavid Pedersen     let request_bytes_counter = Arc::new(AtomicUsize::new(0));
57*0583cff8SDavid Pedersen 
58*0583cff8SDavid Pedersen     fn assert_right_encoding<B>(req: http::Request<B>) -> http::Request<B> {
59*0583cff8SDavid Pedersen         assert!(req.headers().get("grpc-encoding").is_none());
60*0583cff8SDavid Pedersen         req
61*0583cff8SDavid Pedersen     }
62*0583cff8SDavid Pedersen 
63*0583cff8SDavid Pedersen     tokio::spawn({
64*0583cff8SDavid Pedersen         let request_bytes_counter = request_bytes_counter.clone();
65*0583cff8SDavid Pedersen         async move {
66*0583cff8SDavid Pedersen             Server::builder()
67*0583cff8SDavid Pedersen                 .layer(
68*0583cff8SDavid Pedersen                     ServiceBuilder::new()
69*0583cff8SDavid Pedersen                         .map_request(assert_right_encoding)
70*0583cff8SDavid Pedersen                         .layer(measure_request_body_size_layer(
71*0583cff8SDavid Pedersen                             request_bytes_counter.clone(),
72*0583cff8SDavid Pedersen                         ))
73*0583cff8SDavid Pedersen                         .into_inner(),
74*0583cff8SDavid Pedersen                 )
75*0583cff8SDavid Pedersen                 .add_service(svc)
76*0583cff8SDavid Pedersen                 .serve_with_incoming(futures::stream::iter(vec![Ok::<_, std::io::Error>(
77*0583cff8SDavid Pedersen                     MockStream(server),
78*0583cff8SDavid Pedersen                 )]))
79*0583cff8SDavid Pedersen                 .await
80*0583cff8SDavid Pedersen                 .unwrap();
81*0583cff8SDavid Pedersen         }
82*0583cff8SDavid Pedersen     });
83*0583cff8SDavid Pedersen 
84*0583cff8SDavid Pedersen     let mut client = test_client::TestClient::new(mock_io_channel(client).await);
85*0583cff8SDavid Pedersen 
86*0583cff8SDavid Pedersen     let data = [0_u8; UNCOMPRESSED_MIN_BODY_SIZE].to_vec();
87*0583cff8SDavid Pedersen     let stream = futures::stream::iter(vec![SomeData { data: data.clone() }, SomeData { data }]);
88*0583cff8SDavid Pedersen     let req = Request::new(Box::pin(stream));
89*0583cff8SDavid Pedersen 
90*0583cff8SDavid Pedersen     client.compress_input_client_stream(req).await.unwrap();
91*0583cff8SDavid Pedersen 
92*0583cff8SDavid Pedersen     let bytes_sent = request_bytes_counter.load(SeqCst);
93*0583cff8SDavid Pedersen     assert!(bytes_sent > UNCOMPRESSED_MIN_BODY_SIZE);
94*0583cff8SDavid Pedersen }
95*0583cff8SDavid Pedersen 
96*0583cff8SDavid Pedersen #[tokio::test(flavor = "multi_thread")]
97*0583cff8SDavid Pedersen async fn client_enabled_server_disabled() {
98*0583cff8SDavid Pedersen     let (client, server) = tokio::io::duplex(UNCOMPRESSED_MIN_BODY_SIZE * 10);
99*0583cff8SDavid Pedersen 
100*0583cff8SDavid Pedersen     let svc = test_server::TestServer::new(Svc::default());
101*0583cff8SDavid Pedersen 
102*0583cff8SDavid Pedersen     tokio::spawn(async move {
103*0583cff8SDavid Pedersen         Server::builder()
104*0583cff8SDavid Pedersen             .add_service(svc)
105*0583cff8SDavid Pedersen             .serve_with_incoming(futures::stream::iter(vec![Ok::<_, std::io::Error>(
106*0583cff8SDavid Pedersen                 MockStream(server),
107*0583cff8SDavid Pedersen             )]))
108*0583cff8SDavid Pedersen             .await
109*0583cff8SDavid Pedersen             .unwrap();
110*0583cff8SDavid Pedersen     });
111*0583cff8SDavid Pedersen 
112*0583cff8SDavid Pedersen     let mut client = test_client::TestClient::new(mock_io_channel(client).await).send_gzip();
113*0583cff8SDavid Pedersen 
114*0583cff8SDavid Pedersen     let data = [0_u8; UNCOMPRESSED_MIN_BODY_SIZE].to_vec();
115*0583cff8SDavid Pedersen     let stream = futures::stream::iter(vec![SomeData { data: data.clone() }, SomeData { data }]);
116*0583cff8SDavid Pedersen     let req = Request::new(Box::pin(stream));
117*0583cff8SDavid Pedersen 
118*0583cff8SDavid Pedersen     let status = client.compress_input_client_stream(req).await.unwrap_err();
119*0583cff8SDavid Pedersen 
120*0583cff8SDavid Pedersen     assert_eq!(status.code(), tonic::Code::Unimplemented);
121*0583cff8SDavid Pedersen     assert_eq!(
122*0583cff8SDavid Pedersen         status.message(),
123*0583cff8SDavid Pedersen         "Content is compressed with `gzip` which isn't supported"
124*0583cff8SDavid Pedersen     );
125*0583cff8SDavid Pedersen }
126*0583cff8SDavid Pedersen 
127*0583cff8SDavid Pedersen #[tokio::test(flavor = "multi_thread")]
128*0583cff8SDavid Pedersen async fn compressing_response_from_client_stream() {
129*0583cff8SDavid Pedersen     let (client, server) = tokio::io::duplex(UNCOMPRESSED_MIN_BODY_SIZE * 10);
130*0583cff8SDavid Pedersen 
131*0583cff8SDavid Pedersen     let svc = test_server::TestServer::new(Svc::default()).send_gzip();
132*0583cff8SDavid Pedersen 
133*0583cff8SDavid Pedersen     let response_bytes_counter = Arc::new(AtomicUsize::new(0));
134*0583cff8SDavid Pedersen 
135*0583cff8SDavid Pedersen     tokio::spawn({
136*0583cff8SDavid Pedersen         let response_bytes_counter = response_bytes_counter.clone();
137*0583cff8SDavid Pedersen         async move {
138*0583cff8SDavid Pedersen             Server::builder()
139*0583cff8SDavid Pedersen                 .layer(
140*0583cff8SDavid Pedersen                     ServiceBuilder::new()
141*0583cff8SDavid Pedersen                         .layer(MapResponseBodyLayer::new(move |body| {
142*0583cff8SDavid Pedersen                             util::CountBytesBody {
143*0583cff8SDavid Pedersen                                 inner: body,
144*0583cff8SDavid Pedersen                                 counter: response_bytes_counter.clone(),
145*0583cff8SDavid Pedersen                             }
146*0583cff8SDavid Pedersen                         }))
147*0583cff8SDavid Pedersen                         .into_inner(),
148*0583cff8SDavid Pedersen                 )
149*0583cff8SDavid Pedersen                 .add_service(svc)
150*0583cff8SDavid Pedersen                 .serve_with_incoming(futures::stream::iter(vec![Ok::<_, std::io::Error>(
151*0583cff8SDavid Pedersen                     MockStream(server),
152*0583cff8SDavid Pedersen                 )]))
153*0583cff8SDavid Pedersen                 .await
154*0583cff8SDavid Pedersen                 .unwrap();
155*0583cff8SDavid Pedersen         }
156*0583cff8SDavid Pedersen     });
157*0583cff8SDavid Pedersen 
158*0583cff8SDavid Pedersen     let mut client = test_client::TestClient::new(mock_io_channel(client).await).accept_gzip();
159*0583cff8SDavid Pedersen 
160*0583cff8SDavid Pedersen     let stream = futures::stream::iter(vec![]);
161*0583cff8SDavid Pedersen     let req = Request::new(Box::pin(stream));
162*0583cff8SDavid Pedersen 
163*0583cff8SDavid Pedersen     let res = client.compress_output_client_stream(req).await.unwrap();
164*0583cff8SDavid Pedersen     assert_eq!(res.metadata().get("grpc-encoding").unwrap(), "gzip");
165*0583cff8SDavid Pedersen     let bytes_sent = response_bytes_counter.load(SeqCst);
166*0583cff8SDavid Pedersen     assert!(bytes_sent < UNCOMPRESSED_MIN_BODY_SIZE);
167*0583cff8SDavid Pedersen }
168