@@ -16,13 +16,17 @@ pub struct XMetadataToken(pub Option<String>);
1616
1717// Defined in lowercase since HTTP headers are case-insensitive.
1818const X_METADATA_TOKEN_HEADER : & str = "x-metadata-token" ;
19+ const X_AWS_EC2_METADATA_TOKEN_HEADER : & str = "x-aws-ec2-metadata-token" ;
1920
2021impl From < & HashMap < String , String > > for XMetadataToken {
2122 fn from ( custom_headers : & HashMap < String , String > ) -> Self {
2223 Self (
2324 custom_headers
2425 . iter ( )
25- . find ( |( k, _) | k. to_lowercase ( ) == X_METADATA_TOKEN_HEADER )
26+ . find ( |( k, _) | {
27+ let k = k. to_lowercase ( ) ;
28+ k == X_METADATA_TOKEN_HEADER || k == X_AWS_EC2_METADATA_TOKEN_HEADER
29+ } )
2630 . map ( |( _, v) | v. to_string ( ) ) ,
2731 )
2832 }
@@ -35,14 +39,19 @@ pub struct XMetadataTokenTtlSeconds(pub Option<u32>);
3539
3640// Defined in lowercase since HTTP headers are case-insensitive.
3741const X_METADATA_TOKEN_TTL_SECONDS_HEADER : & str = "x-metadata-token-ttl-seconds" ;
42+ const X_AWS_EC2_METADATA_TOKEN_SSL_SECONDS_HEADER : & str = "x-aws-ec2-metadata-token-ttl-seconds" ;
3843
3944impl TryFrom < & HashMap < String , String > > for XMetadataTokenTtlSeconds {
4045 type Error = RequestError ;
4146
4247 fn try_from ( custom_headers : & HashMap < String , String > ) -> Result < Self , RequestError > {
4348 let seconds = custom_headers
4449 . iter ( )
45- . find ( |( k, _) | k. to_lowercase ( ) == X_METADATA_TOKEN_TTL_SECONDS_HEADER )
50+ . find ( |( k, _) | {
51+ let k = k. to_lowercase ( ) ;
52+ k == X_METADATA_TOKEN_TTL_SECONDS_HEADER
53+ || k == X_AWS_EC2_METADATA_TOKEN_SSL_SECONDS_HEADER
54+ } )
4655 . map ( |( k, v) | {
4756 v. parse :: < u32 > ( ) . map_err ( |_| {
4857 RequestError :: HeaderError ( HttpHeaderError :: InvalidValue (
@@ -89,26 +98,36 @@ mod tests {
8998 let x_metadata_token = XMetadataToken :: from ( & custom_headers) ;
9099 assert ! ( x_metadata_token. 0 . is_none( ) ) ;
91100
92- // Valid header
93- let token = "THIS_IS_TOKEN" ;
94- let custom_headers = HashMap :: from ( [ ( X_METADATA_TOKEN_HEADER . into ( ) , token. into ( ) ) ] ) ;
95- let x_metadata_token = XMetadataToken :: from ( & custom_headers) ;
96- assert_eq ! ( & x_metadata_token. 0 . unwrap( ) , token) ;
97-
98- // Valid header in unrelated custom headers
101+ for header in [ X_METADATA_TOKEN_HEADER , X_AWS_EC2_METADATA_TOKEN_HEADER ] {
102+ let token = "THIS_IS_TOKEN" ;
103+
104+ // Valid header
105+ let custom_headers = HashMap :: from ( [ ( header. into ( ) , token. into ( ) ) ] ) ;
106+ let x_metadata_token = XMetadataToken :: from ( & custom_headers) ;
107+ assert_eq ! ( & x_metadata_token. 0 . unwrap( ) , token) ;
108+
109+ // Valid header in unrelated custom headers
110+ let custom_headers = HashMap :: from ( [
111+ ( "Some-Header" . into ( ) , "10" . into ( ) ) ,
112+ ( "Another-Header" . into ( ) , "value" . into ( ) ) ,
113+ ( header. into ( ) , token. into ( ) ) ,
114+ ] ) ;
115+ let x_metadata_token = XMetadataToken :: from ( & custom_headers) ;
116+ assert_eq ! ( & x_metadata_token. 0 . unwrap( ) , token) ;
117+
118+ // Test case-insensitiveness
119+ let custom_headers = HashMap :: from ( [ ( to_mixed_case ( header) , token. into ( ) ) ] ) ;
120+ let x_metadata_token = XMetadataToken :: from ( & custom_headers) ;
121+ assert_eq ! ( & x_metadata_token. 0 . unwrap( ) , token) ;
122+ }
123+
124+ // The first one should be used when multiple valid headers are included.
99125 let custom_headers = HashMap :: from ( [
100- ( "Some-Header" . into ( ) , "10" . into ( ) ) ,
101- ( "Another-Header" . into ( ) , "value" . into ( ) ) ,
102- ( X_METADATA_TOKEN_HEADER . into ( ) , token. into ( ) ) ,
126+ ( X_METADATA_TOKEN_HEADER . into ( ) , "first" . into ( ) ) ,
127+ ( X_AWS_EC2_METADATA_TOKEN_HEADER . into ( ) , "second" . into ( ) ) ,
103128 ] ) ;
104129 let x_metadata_token = XMetadataToken :: from ( & custom_headers) ;
105- assert_eq ! ( & x_metadata_token. 0 . unwrap( ) , token) ;
106-
107- // Test case-insensitiveness
108- let custom_headers =
109- HashMap :: from ( [ ( to_mixed_case ( X_METADATA_TOKEN_HEADER ) , token. into ( ) ) ] ) ;
110- let x_metadata_token = XMetadataToken :: from ( & custom_headers) ;
111- assert_eq ! ( & x_metadata_token. 0 . unwrap( ) , token) ;
130+ assert_eq ! ( & x_metadata_token. 0 . unwrap( ) , "first" ) ;
112131 }
113132
114133 #[ test]
@@ -128,48 +147,58 @@ mod tests {
128147 XMetadataTokenTtlSeconds :: try_from ( & custom_headers) . unwrap ( ) ;
129148 assert ! ( x_metadata_token_ttl_seconds. 0 . is_none( ) ) ;
130149
131- // Valid header
132- let seconds = 60 ;
133- let custom_headers = HashMap :: from ( [ (
134- X_METADATA_TOKEN_TTL_SECONDS_HEADER . into ( ) ,
135- seconds. to_string ( ) ,
136- ) ] ) ;
137- let x_metadata_token_ttl_seconds =
138- XMetadataTokenTtlSeconds :: try_from ( & custom_headers) . unwrap ( ) ;
139- assert_eq ! ( x_metadata_token_ttl_seconds. 0 . unwrap( ) , seconds) ;
140-
141- // Valid header in unrelated custom headers
150+ for header in [
151+ X_METADATA_TOKEN_TTL_SECONDS_HEADER ,
152+ X_AWS_EC2_METADATA_TOKEN_SSL_SECONDS_HEADER ,
153+ ] {
154+ let seconds = 60 ;
155+
156+ // Valid header
157+ let custom_headers = HashMap :: from ( [ ( header. into ( ) , seconds. to_string ( ) ) ] ) ;
158+ let x_metadata_token_ttl_seconds =
159+ XMetadataTokenTtlSeconds :: try_from ( & custom_headers) . unwrap ( ) ;
160+ assert_eq ! ( x_metadata_token_ttl_seconds. 0 . unwrap( ) , seconds) ;
161+
162+ // Valid header in unrelated custom headers
163+ let custom_headers = HashMap :: from ( [
164+ ( "Some-Header" . into ( ) , "10" . into ( ) ) ,
165+ ( "Another-Header" . into ( ) , "value" . into ( ) ) ,
166+ ( header. into ( ) , seconds. to_string ( ) ) ,
167+ ] ) ;
168+ let x_metadata_token_ttl_seconds =
169+ XMetadataTokenTtlSeconds :: try_from ( & custom_headers) . unwrap ( ) ;
170+ assert_eq ! ( x_metadata_token_ttl_seconds. 0 . unwrap( ) , seconds) ;
171+
172+ // Test case-insensitiveness
173+ let custom_headers = HashMap :: from ( [ ( to_mixed_case ( header) , seconds. to_string ( ) ) ] ) ;
174+ let x_metadata_token_ttl_seconds =
175+ XMetadataTokenTtlSeconds :: try_from ( & custom_headers) . unwrap ( ) ;
176+ assert_eq ! ( x_metadata_token_ttl_seconds. 0 . unwrap( ) , seconds) ;
177+
178+ // Invalid value
179+ let mixed_case_header = to_mixed_case ( header) ;
180+ let invalid_seconds = "-60" ;
181+ let custom_headers =
182+ HashMap :: from ( [ ( mixed_case_header. clone ( ) , invalid_seconds. to_string ( ) ) ] ) ;
183+ assert_eq ! (
184+ XMetadataTokenTtlSeconds :: try_from( & custom_headers) . unwrap_err( ) ,
185+ RequestError :: HeaderError ( HttpHeaderError :: InvalidValue (
186+ mixed_case_header,
187+ invalid_seconds. to_string( )
188+ ) )
189+ ) ;
190+ }
191+
192+ // The first one should be used when multiple valid headers are included.
142193 let custom_headers = HashMap :: from ( [
143- ( "Some-Header" . into ( ) , "10" . into ( ) ) ,
144- ( "Another-Header" . into ( ) , "value" . into ( ) ) ,
194+ ( X_METADATA_TOKEN_TTL_SECONDS_HEADER . into ( ) , 1 . to_string ( ) ) ,
145195 (
146- X_METADATA_TOKEN_TTL_SECONDS_HEADER . into ( ) ,
147- seconds . to_string ( ) ,
196+ X_AWS_EC2_METADATA_TOKEN_SSL_SECONDS_HEADER . into ( ) ,
197+ 2 . to_string ( ) ,
148198 ) ,
149199 ] ) ;
150200 let x_metadata_token_ttl_seconds =
151201 XMetadataTokenTtlSeconds :: try_from ( & custom_headers) . unwrap ( ) ;
152- assert_eq ! ( x_metadata_token_ttl_seconds. 0 . unwrap( ) , seconds) ;
153-
154- // Test case-insensitiveness
155- let custom_headers = HashMap :: from ( [ (
156- to_mixed_case ( X_METADATA_TOKEN_TTL_SECONDS_HEADER ) ,
157- seconds. to_string ( ) ,
158- ) ] ) ;
159- let x_metadata_token_ttl_seconds =
160- XMetadataTokenTtlSeconds :: try_from ( & custom_headers) . unwrap ( ) ;
161- assert_eq ! ( x_metadata_token_ttl_seconds. 0 . unwrap( ) , seconds) ;
162-
163- // Invalid value
164- let header_name = "X-metadata-token-ttl-seconds" ;
165- let invalid_seconds = "-60" ;
166- let custom_headers = HashMap :: from ( [ ( header_name. into ( ) , invalid_seconds. to_string ( ) ) ] ) ;
167- assert_eq ! (
168- XMetadataTokenTtlSeconds :: try_from( & custom_headers) . unwrap_err( ) ,
169- RequestError :: HeaderError ( HttpHeaderError :: InvalidValue (
170- header_name. into( ) ,
171- invalid_seconds. to_string( )
172- ) )
173- ) ;
202+ assert_eq ! ( x_metadata_token_ttl_seconds. 0 . unwrap( ) , 1 ) ;
174203 }
175204}
0 commit comments