11use crate :: { metadata:: MetadataValue , Status } ;
22use bytes:: { Buf , BufMut , BytesMut } ;
3+ #[ cfg( feature = "deflate" ) ]
4+ use flate2:: read:: { DeflateDecoder , DeflateEncoder } ;
35#[ cfg( feature = "gzip" ) ]
46use flate2:: read:: { GzDecoder , GzEncoder } ;
57use std:: fmt;
@@ -14,7 +16,7 @@ pub(crate) const ACCEPT_ENCODING_HEADER: &str = "grpc-accept-encoding";
1416/// Represents an ordered list of compression encodings that are enabled.
1517#[ derive( Debug , Default , Clone , Copy ) ]
1618pub struct EnabledCompressionEncodings {
17- inner : [ Option < CompressionEncoding > ; 2 ] ,
19+ inner : [ Option < CompressionEncoding > ; 3 ] ,
1820}
1921
2022impl EnabledCompressionEncodings {
@@ -85,6 +87,9 @@ pub enum CompressionEncoding {
8587 #[ cfg( feature = "gzip" ) ]
8688 Gzip ,
8789 #[ allow( missing_docs) ]
90+ #[ cfg( feature = "deflate" ) ]
91+ Deflate ,
92+ #[ allow( missing_docs) ]
8893 #[ cfg( feature = "zstd" ) ]
8994 Zstd ,
9095}
@@ -93,6 +98,8 @@ impl CompressionEncoding {
9398 pub ( crate ) const ENCODINGS : & ' static [ CompressionEncoding ] = & [
9499 #[ cfg( feature = "gzip" ) ]
95100 CompressionEncoding :: Gzip ,
101+ #[ cfg( feature = "deflate" ) ]
102+ CompressionEncoding :: Deflate ,
96103 #[ cfg( feature = "zstd" ) ]
97104 CompressionEncoding :: Zstd ,
98105 ] ;
@@ -112,6 +119,8 @@ impl CompressionEncoding {
112119 split_by_comma ( header_value_str) . find_map ( |value| match value {
113120 #[ cfg( feature = "gzip" ) ]
114121 "gzip" => Some ( CompressionEncoding :: Gzip ) ,
122+ #[ cfg( feature = "deflate" ) ]
123+ "deflate" => Some ( CompressionEncoding :: Deflate ) ,
115124 #[ cfg( feature = "zstd" ) ]
116125 "zstd" => Some ( CompressionEncoding :: Zstd ) ,
117126 _ => None ,
@@ -132,6 +141,10 @@ impl CompressionEncoding {
132141 b"gzip" if enabled_encodings. is_enabled ( CompressionEncoding :: Gzip ) => {
133142 Ok ( Some ( CompressionEncoding :: Gzip ) )
134143 }
144+ #[ cfg( feature = "deflate" ) ]
145+ b"deflate" if enabled_encodings. is_enabled ( CompressionEncoding :: Deflate ) => {
146+ Ok ( Some ( CompressionEncoding :: Deflate ) )
147+ }
135148 #[ cfg( feature = "zstd" ) ]
136149 b"zstd" if enabled_encodings. is_enabled ( CompressionEncoding :: Zstd ) => {
137150 Ok ( Some ( CompressionEncoding :: Zstd ) )
@@ -170,6 +183,8 @@ impl CompressionEncoding {
170183 match self {
171184 #[ cfg( feature = "gzip" ) ]
172185 CompressionEncoding :: Gzip => "gzip" ,
186+ #[ cfg( feature = "deflate" ) ]
187+ CompressionEncoding :: Deflate => "deflate" ,
173188 #[ cfg( feature = "zstd" ) ]
174189 CompressionEncoding :: Zstd => "zstd" ,
175190 }
@@ -217,6 +232,15 @@ pub(crate) fn compress(
217232 ) ;
218233 std:: io:: copy ( & mut gzip_encoder, & mut out_writer) ?;
219234 }
235+ #[ cfg( feature = "deflate" ) ]
236+ CompressionEncoding :: Deflate => {
237+ let mut deflate_encoder = DeflateEncoder :: new (
238+ & decompressed_buf[ 0 ..len] ,
239+ // FIXME: support customizing the compression level
240+ flate2:: Compression :: new ( 6 ) ,
241+ ) ;
242+ std:: io:: copy ( & mut deflate_encoder, & mut out_writer) ?;
243+ }
220244 #[ cfg( feature = "zstd" ) ]
221245 CompressionEncoding :: Zstd => {
222246 let mut zstd_encoder = Encoder :: new (
@@ -247,7 +271,7 @@ pub(crate) fn decompress(
247271 ( ( estimate_decompressed_len / buffer_growth_interval) + 1 ) * buffer_growth_interval;
248272 out_buf. reserve ( capacity) ;
249273
250- #[ cfg( any( feature = "gzip" , feature = "zstd" ) ) ]
274+ #[ cfg( any( feature = "gzip" , feature = "deflate" , feature = " zstd") ) ]
251275 let mut out_writer = out_buf. writer ( ) ;
252276
253277 match settings. encoding {
@@ -256,6 +280,11 @@ pub(crate) fn decompress(
256280 let mut gzip_decoder = GzDecoder :: new ( & compressed_buf[ 0 ..len] ) ;
257281 std:: io:: copy ( & mut gzip_decoder, & mut out_writer) ?;
258282 }
283+ #[ cfg( feature = "deflate" ) ]
284+ CompressionEncoding :: Deflate => {
285+ let mut deflate_decoder = DeflateDecoder :: new ( & compressed_buf[ 0 ..len] ) ;
286+ std:: io:: copy ( & mut deflate_decoder, & mut out_writer) ?;
287+ }
259288 #[ cfg( feature = "zstd" ) ]
260289 CompressionEncoding :: Zstd => {
261290 let mut zstd_decoder = Decoder :: new ( & compressed_buf[ 0 ..len] ) ?;
@@ -282,7 +311,7 @@ pub enum SingleMessageCompressionOverride {
282311
283312#[ cfg( test) ]
284313mod tests {
285- #[ cfg( any( feature = "gzip" , feature = "zstd" ) ) ]
314+ #[ cfg( any( feature = "gzip" , feature = "deflate" , feature = " zstd") ) ]
286315 use http:: HeaderValue ;
287316
288317 use super :: * ;
@@ -300,13 +329,13 @@ mod tests {
300329 const GZIP : HeaderValue = HeaderValue :: from_static ( "gzip,identity" ) ;
301330
302331 let encodings = EnabledCompressionEncodings {
303- inner : [ Some ( CompressionEncoding :: Gzip ) , None ] ,
332+ inner : [ Some ( CompressionEncoding :: Gzip ) , None , None ] ,
304333 } ;
305334
306335 assert_eq ! ( encodings. into_accept_encoding_header_value( ) . unwrap( ) , GZIP ) ;
307336
308337 let encodings = EnabledCompressionEncodings {
309- inner : [ None , Some ( CompressionEncoding :: Gzip ) ] ,
338+ inner : [ None , None , Some ( CompressionEncoding :: Gzip ) ] ,
310339 } ;
311340
312341 assert_eq ! ( encodings. into_accept_encoding_header_value( ) . unwrap( ) , GZIP ) ;
@@ -318,43 +347,45 @@ mod tests {
318347 const ZSTD : HeaderValue = HeaderValue :: from_static ( "zstd,identity" ) ;
319348
320349 let encodings = EnabledCompressionEncodings {
321- inner : [ Some ( CompressionEncoding :: Zstd ) , None ] ,
350+ inner : [ Some ( CompressionEncoding :: Zstd ) , None , None ] ,
322351 } ;
323352
324353 assert_eq ! ( encodings. into_accept_encoding_header_value( ) . unwrap( ) , ZSTD ) ;
325354
326355 let encodings = EnabledCompressionEncodings {
327- inner : [ None , Some ( CompressionEncoding :: Zstd ) ] ,
356+ inner : [ None , None , Some ( CompressionEncoding :: Zstd ) ] ,
328357 } ;
329358
330359 assert_eq ! ( encodings. into_accept_encoding_header_value( ) . unwrap( ) , ZSTD ) ;
331360 }
332361
333362 #[ test]
334- #[ cfg( all( feature = "gzip" , feature = "zstd" ) ) ]
363+ #[ cfg( all( feature = "gzip" , feature = "deflate" , feature = " zstd") ) ]
335364 fn convert_gzip_and_zstd_into_header_value ( ) {
336365 let encodings = EnabledCompressionEncodings {
337366 inner : [
338367 Some ( CompressionEncoding :: Gzip ) ,
368+ Some ( CompressionEncoding :: Deflate ) ,
339369 Some ( CompressionEncoding :: Zstd ) ,
340370 ] ,
341371 } ;
342372
343373 assert_eq ! (
344374 encodings. into_accept_encoding_header_value( ) . unwrap( ) ,
345- HeaderValue :: from_static( "gzip,zstd,identity" ) ,
375+ HeaderValue :: from_static( "gzip,deflate, zstd,identity" ) ,
346376 ) ;
347377
348378 let encodings = EnabledCompressionEncodings {
349379 inner : [
350380 Some ( CompressionEncoding :: Zstd ) ,
381+ Some ( CompressionEncoding :: Deflate ) ,
351382 Some ( CompressionEncoding :: Gzip ) ,
352383 ] ,
353384 } ;
354385
355386 assert_eq ! (
356387 encodings. into_accept_encoding_header_value( ) . unwrap( ) ,
357- HeaderValue :: from_static( "zstd,gzip,identity" ) ,
388+ HeaderValue :: from_static( "zstd,deflate, gzip,identity" ) ,
358389 ) ;
359390 }
360391}
0 commit comments