dip/src/service.rs

85 lines
2.7 KiB
Rust
Raw Normal View History

2018-08-16 15:05:58 +00:00
use std::collections::HashMap;
2018-08-16 21:06:23 +00:00
use std::thread;
2018-08-16 15:05:58 +00:00
use futures::{future, Future, Stream};
use hyper::{Body, Error, Request, Response, StatusCode};
use mktemp::Temp;
2018-08-16 15:05:58 +00:00
use {HOOKS, URIPATTERN};
2018-08-16 15:05:58 +00:00
pub fn dip_service(req: Request<Body>) -> Box<Future<Item = Response<Body>, Error = Error> + Send> {
2018-08-16 15:05:58 +00:00
let path = req.uri().path().to_owned();
let captures = match URIPATTERN.captures(path.as_ref()) {
Some(value) => value,
None => {
return Box::new(future::ok(
Response::builder()
.status(StatusCode::NOT_FOUND)
.body(Body::from("not found"))
.unwrap(),
))
}
};
let name = match captures.name("name") {
Some(value) => value.as_str().to_owned(),
None => {
return Box::new(future::ok(
Response::builder()
.status(StatusCode::NOT_FOUND)
.body(Body::from("not found"))
.unwrap(),
))
}
2018-08-16 15:05:58 +00:00
};
// TODO: filter by method as well
let headers = req.headers()
.clone()
.into_iter()
.filter_map(|(k, v)| {
let key = k.unwrap().as_str().to_owned();
v.to_str().map(|value| (key, value.to_owned())).ok()
2018-08-16 15:05:58 +00:00
})
.collect::<HashMap<_, _>>();
let method = req.method().as_str().to_owned();
2018-08-16 21:06:23 +00:00
// spawn job
thread::spawn(move || {
req.into_body().concat2().map(move |body| {
let body = String::from_utf8(body.to_vec()).unwrap();
let req_obj = json!({
"body": body,
"headers": headers,
"method": method,
});
let hooks = HOOKS.lock().unwrap();
{
let mut temp_dir = Temp::new_dir().unwrap();
let temp_path = temp_dir.to_path_buf();
assert!(temp_path.exists());
let hook = hooks.get(&name).unwrap();
2018-08-17 02:04:52 +00:00
let (code, msg) = match hook.handle(req_obj, temp_path) {
2018-08-17 01:06:35 +00:00
Ok(msg) => (StatusCode::ACCEPTED, msg),
Err(msg) => (StatusCode::BAD_REQUEST, msg),
};
2018-08-16 21:06:23 +00:00
temp_dir.release();
Response::builder()
.status(code)
.body(Body::from(msg))
.unwrap_or_else(|err| Response::new(Body::from(format!("{}", err))))
}
})
});
2018-08-16 15:05:58 +00:00
2018-08-16 21:06:23 +00:00
Box::new(future::ok(
2018-08-16 15:05:58 +00:00
Response::builder()
2018-08-16 21:06:23 +00:00
.status(StatusCode::ACCEPTED)
// TODO: assign job a uuid and do some logging
.body(Body::from(format!("job {} started", -1)))
.unwrap(),
))
2018-08-16 15:05:58 +00:00
}