1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40
//! # try_route
//! "tries" to match a route and method to a request, also tries to deserialize inputs if the routes and methods check out.
use lambda_http::{http::Method, RequestExt, RequestPayloadExt};
use serde::de::DeserializeOwned;
use super::error::Error;
/// attemps to match an inbound route to a route given by a handler
/// it is the runtime version of routing for the app! macro
/// it simply checks if the routes are equal as str
/// if they match it then checks that the methods are the same
/// from there it desererializes data either from json or url encoded
/// based on the method, if all goes well, it returns the deserialized type "T"
/// which is later passed to the handler you write
pub fn try_route<T: DeserializeOwned>(
event: &lambda_http::Request,
method: lambda_http::http::Method,
route: &str,
inbound: Option<&str>,
) -> Result<T, Error> {
if inbound.map(|el| el != route).unwrap_or_default() {
return Err(Error::NotFound);
}
if event.method() != method {
return Err(Error::MethodNotAllowed);
}
match event.method() {
&Method::GET | &Method::DELETE => {
let qs = event.query_string_parameters().to_query_string();
Ok(serde_urlencoded::from_str(&qs)?)
}
_ => match event.payload() {
Ok(Some(payload)) => Ok(payload),
Ok(None) => Err(Error::NoPayload),
Err(err) => Err(Error::Payload(err)),
},
}
}