Skip to content

Commit 7e2cd97

Browse files
authored
Fix sam local support for missing headers (#38) (#332)
* Added unit tests for TryFrom<HeaderMap> for Context
1 parent 797f0ab commit 7e2cd97

File tree

1 file changed

+92
-13
lines changed

1 file changed

+92
-13
lines changed

lambda-runtime/src/types.rs

+92-13
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
use crate::{Config, Error};
2-
use http::HeaderMap;
2+
use http::{HeaderMap, HeaderValue};
33
use serde::{Deserialize, Serialize};
44
use std::{collections::HashMap, convert::TryFrom};
55

@@ -120,28 +120,107 @@ impl TryFrom<HeaderMap> for Context {
120120
type Error = Error;
121121
fn try_from(headers: HeaderMap) -> Result<Self, Self::Error> {
122122
let ctx = Context {
123-
request_id: headers["lambda-runtime-aws-request-id"]
124-
.to_str()
125-
.expect("Missing Request ID")
123+
request_id: headers
124+
.get("lambda-runtime-aws-request-id")
125+
.expect("missing lambda-runtime-aws-request-id header")
126+
.to_str()?
126127
.to_owned(),
127-
deadline: headers["lambda-runtime-deadline-ms"]
128+
deadline: headers
129+
.get("lambda-runtime-deadline-ms")
130+
.expect("missing lambda-runtime-deadline-ms header")
131+
.to_str()?
132+
.parse::<u64>()?,
133+
invoked_function_arn: headers
134+
.get("lambda-runtime-invoked-function-arn")
135+
.unwrap_or(&HeaderValue::from_static(
136+
"No header lambda-runtime-invoked-function-arn found.",
137+
))
128138
.to_str()?
129-
.parse()
130-
.expect("Missing deadline"),
131-
invoked_function_arn: headers["lambda-runtime-invoked-function-arn"]
132-
.to_str()
133-
.expect("Missing arn; this is a bug")
134139
.to_owned(),
135-
xray_trace_id: headers["lambda-runtime-trace-id"]
136-
.to_str()
137-
.expect("Invalid XRayTraceID sent by Lambda; this is a bug")
140+
xray_trace_id: headers
141+
.get("lambda-runtime-trace-id")
142+
.unwrap_or(&HeaderValue::from_static("No header lambda-runtime-trace-id found."))
143+
.to_str()?
138144
.to_owned(),
139145
..Default::default()
140146
};
141147
Ok(ctx)
142148
}
143149
}
144150

151+
#[cfg(test)]
152+
mod test {
153+
use super::*;
154+
155+
#[test]
156+
fn context_with_expected_values_and_types_resolves() {
157+
let mut headers = HeaderMap::new();
158+
headers.insert("lambda-runtime-aws-request-id", HeaderValue::from_static("my-id"));
159+
headers.insert("lambda-runtime-deadline-ms", HeaderValue::from_static("123"));
160+
headers.insert(
161+
"lambda-runtime-invoked-function-arn",
162+
HeaderValue::from_static("arn::myarn"),
163+
);
164+
headers.insert("lambda-runtime-trace-id", HeaderValue::from_static("arn::myarn"));
165+
let tried = Context::try_from(headers);
166+
assert!(tried.is_ok());
167+
}
168+
169+
#[test]
170+
fn context_with_certain_missing_headers_still_resolves() {
171+
let mut headers = HeaderMap::new();
172+
headers.insert("lambda-runtime-aws-request-id", HeaderValue::from_static("my-id"));
173+
headers.insert("lambda-runtime-deadline-ms", HeaderValue::from_static("123"));
174+
let tried = Context::try_from(headers);
175+
assert!(tried.is_ok());
176+
}
177+
178+
#[test]
179+
fn context_with_bad_deadline_type_is_err() {
180+
let mut headers = HeaderMap::new();
181+
headers.insert("lambda-runtime-aws-request-id", HeaderValue::from_static("my-id"));
182+
headers.insert(
183+
"lambda-runtime-deadline-ms",
184+
HeaderValue::from_static("BAD-Type,not <u64>"),
185+
);
186+
headers.insert(
187+
"lambda-runtime-invoked-function-arn",
188+
HeaderValue::from_static("arn::myarn"),
189+
);
190+
headers.insert("lambda-runtime-trace-id", HeaderValue::from_static("arn::myarn"));
191+
let tried = Context::try_from(headers);
192+
assert!(tried.is_err());
193+
}
194+
195+
#[test]
196+
#[should_panic]
197+
#[allow(unused_must_use)]
198+
fn context_with_missing_request_id_should_panic() {
199+
let mut headers = HeaderMap::new();
200+
headers.insert("lambda-runtime-aws-request-id", HeaderValue::from_static("my-id"));
201+
headers.insert(
202+
"lambda-runtime-invoked-function-arn",
203+
HeaderValue::from_static("arn::myarn"),
204+
);
205+
headers.insert("lambda-runtime-trace-id", HeaderValue::from_static("arn::myarn"));
206+
Context::try_from(headers);
207+
}
208+
209+
#[test]
210+
#[should_panic]
211+
#[allow(unused_must_use)]
212+
fn context_with_missing_deadline_should_panic() {
213+
let mut headers = HeaderMap::new();
214+
headers.insert("lambda-runtime-deadline-ms", HeaderValue::from_static("123"));
215+
headers.insert(
216+
"lambda-runtime-invoked-function-arn",
217+
HeaderValue::from_static("arn::myarn"),
218+
);
219+
headers.insert("lambda-runtime-trace-id", HeaderValue::from_static("arn::myarn"));
220+
Context::try_from(headers);
221+
}
222+
}
223+
145224
impl Context {
146225
/// Add environment details to the context by setting `env_config`.
147226
pub fn with_config(self, config: &Config) -> Self {

0 commit comments

Comments
 (0)