@@ -88,6 +88,7 @@ impl StatusLine {
8888pub struct ResponseHeaders {
8989 content_length : i32 ,
9090 content_type : MediaType ,
91+ deprecation : bool ,
9192 server : String ,
9293 allow : Vec < Method > ,
9394 accept_encoding : bool ,
@@ -98,6 +99,7 @@ impl Default for ResponseHeaders {
9899 Self {
99100 content_length : Default :: default ( ) ,
100101 content_type : Default :: default ( ) ,
102+ deprecation : false ,
101103 server : String :: from ( "Firecracker API" ) ,
102104 allow : Vec :: new ( ) ,
103105 accept_encoding : false ,
@@ -126,6 +128,16 @@ impl ResponseHeaders {
126128 buf. write_all ( & [ CR , LF ] )
127129 }
128130
131+ // The logic pertaining to `Deprecation` header writing.
132+ fn write_deprecation_header < T : Write > ( & self , buf : & mut T ) -> Result < ( ) , WriteError > {
133+ if !self . deprecation {
134+ return Ok ( ( ) ) ;
135+ }
136+
137+ buf. write_all ( b"Deprecation: true" ) ?;
138+ buf. write_all ( & [ CR , LF ] )
139+ }
140+
129141 /// Writes the headers to `buf` using the HTTP specification.
130142 pub fn write_all < T : Write > ( & self , buf : & mut T ) -> Result < ( ) , WriteError > {
131143 buf. write_all ( Header :: Server . raw ( ) ) ?;
@@ -137,6 +149,7 @@ impl ResponseHeaders {
137149 buf. write_all ( & [ CR , LF ] ) ?;
138150
139151 self . write_allow_header ( buf) ?;
152+ self . write_deprecation_header ( buf) ?;
140153
141154 if self . content_length != 0 {
142155 buf. write_all ( Header :: ContentType . raw ( ) ) ?;
@@ -175,6 +188,13 @@ impl ResponseHeaders {
175188 self . content_type = content_type;
176189 }
177190
191+ /// Sets the `Deprecation` header to be written in the HTTP response.
192+ /// https://tools.ietf.org/id/draft-dalal-deprecation-header-03.html
193+ #[ allow( unused) ]
194+ pub fn set_deprecation ( & mut self ) {
195+ self . deprecation = true ;
196+ }
197+
178198 /// Sets the encoding type to be written in the HTTP response.
179199 #[ allow( unused) ]
180200 pub fn set_encoding ( & mut self ) {
@@ -219,6 +239,11 @@ impl Response {
219239 self . headers . set_content_type ( content_type) ;
220240 }
221241
242+ /// Marks the `Response` as deprecated.
243+ pub fn set_deprecation ( & mut self ) {
244+ self . headers . set_deprecation ( ) ;
245+ }
246+
222247 /// Updates the encoding type of `Response`.
223248 pub fn set_encoding ( & mut self ) {
224249 self . headers . set_encoding ( ) ;
@@ -279,6 +304,11 @@ impl Response {
279304 self . headers . content_type
280305 }
281306
307+ /// Returns the deprecation status of the response.
308+ pub fn deprecation ( & self ) -> bool {
309+ self . headers . deprecation
310+ }
311+
282312 /// Returns the HTTP Version of the response.
283313 pub fn http_version ( & self ) -> Version {
284314 self . status_line . http_version
@@ -392,6 +422,54 @@ mod tests {
392422 assert_eq ! ( response. allow( ) , vec![ Method :: Get , Method :: Put ] ) ;
393423 }
394424
425+ #[ test]
426+ fn test_deprecation ( ) {
427+ // Test a deprecated response with body.
428+ let mut response = Response :: new ( Version :: Http10 , StatusCode :: OK ) ;
429+ let body = "This is a test" ;
430+ response. set_body ( Body :: new ( body) ) ;
431+ response. set_content_type ( MediaType :: PlainText ) ;
432+ response. set_encoding ( ) ;
433+ response. set_deprecation ( ) ;
434+
435+ assert_eq ! ( response. status( ) , StatusCode :: OK ) ;
436+ assert_eq ! ( response. body( ) . unwrap( ) , Body :: new( body) ) ;
437+ assert_eq ! ( response. http_version( ) , Version :: Http10 ) ;
438+ assert_eq ! ( response. content_length( ) , 14 ) ;
439+ assert_eq ! ( response. content_type( ) , MediaType :: PlainText ) ;
440+ assert ! ( response. deprecation( ) ) ;
441+
442+ let expected_response: & ' static [ u8 ] = b"HTTP/1.0 200 \r \n \
443+ Server: Firecracker API\r \n \
444+ Connection: keep-alive\r \n \
445+ Deprecation: true\r \n \
446+ Content-Type: text/plain\r \n \
447+ Content-Length: 14\r \n \
448+ Accept-Encoding: identity\r \n \r \n \
449+ This is a test";
450+
451+ let mut response_buf: [ u8 ; 172 ] = [ 0 ; 172 ] ;
452+ assert ! ( response. write_all( & mut response_buf. as_mut( ) ) . is_ok( ) ) ;
453+ assert_eq ! ( response_buf. as_ref( ) , expected_response) ;
454+
455+ // Test a deprecated response without a body.
456+ let mut response = Response :: new ( Version :: Http10 , StatusCode :: NoContent ) ;
457+ response. set_deprecation ( ) ;
458+
459+ assert_eq ! ( response. status( ) , StatusCode :: NoContent ) ;
460+ assert_eq ! ( response. http_version( ) , Version :: Http10 ) ;
461+ assert ! ( response. deprecation( ) ) ;
462+
463+ let expected_response: & ' static [ u8 ] = b"HTTP/1.0 204 \r \n \
464+ Server: Firecracker API\r \n \
465+ Connection: keep-alive\r \n \
466+ Deprecation: true\r \n \r \n ";
467+
468+ let mut response_buf: [ u8 ; 85 ] = [ 0 ; 85 ] ;
469+ assert ! ( response. write_all( & mut response_buf. as_mut( ) ) . is_ok( ) ) ;
470+ assert_eq ! ( response_buf. as_ref( ) , expected_response) ;
471+ }
472+
395473 #[ test]
396474 fn test_equal ( ) {
397475 let response = Response :: new ( Version :: Http10 , StatusCode :: MethodNotAllowed ) ;
0 commit comments