diff options
author | Joris | 2021-01-03 13:40:40 +0100 |
---|---|---|
committer | Joris | 2021-01-03 13:54:20 +0100 |
commit | 11052951b74b9ad4b6a9412ae490086235f9154b (patch) | |
tree | 64526ac926c1bf470ea113f6cac8a33158684e8d /src/controller/utils.rs | |
parent | 371449b0e312a03162b78797b83dee9d81706669 (diff) |
Rewrite in Rust
Diffstat (limited to 'src/controller/utils.rs')
-rw-r--r-- | src/controller/utils.rs | 119 |
1 files changed, 119 insertions, 0 deletions
diff --git a/src/controller/utils.rs b/src/controller/utils.rs new file mode 100644 index 0000000..225f8a4 --- /dev/null +++ b/src/controller/utils.rs @@ -0,0 +1,119 @@ +use hyper::header::{ + HeaderName, HeaderValue, CACHE_CONTROL, CONTENT_TYPE, LOCATION, SET_COOKIE, +}; +use hyper::{Body, Response, StatusCode}; +use std::collections::HashMap; +use tera::{Context, Tera}; +use tokio::fs::File; +use tokio_util::codec::{BytesCodec, FramedRead}; +use uuid::Uuid; + +use crate::controller::error; +use crate::model::config::Config; + +pub fn with_header( + response: Response<Body>, + name: HeaderName, + value: &str, +) -> Response<Body> { + with_headers(response, vec![(name, value)]) +} + +pub fn with_headers( + response: Response<Body>, + headers: Vec<(HeaderName, &str)>, +) -> Response<Body> { + let mut response = response; + let response_headers = response.headers_mut(); + for (name, value) in headers { + response_headers.insert(name, HeaderValue::from_str(value).unwrap()); + } + response +} + +pub fn with_login_cookie( + config: Config, + login_token: Uuid, + response: Response<Body>, +) -> Response<Body> { + let cookie = format!( + "TOKEN={}; SameSite=Strict; HttpOnly; Max-Age=86400{}", + login_token, + if config.secure_cookies { + "; Secure" + } else { + "" + } + ); + + with_header(response, SET_COOKIE, &cookie) +} + +pub fn with_logout_cookie( + config: Config, + response: Response<Body>, +) -> Response<Body> { + let cookie = format!( + "TOKEN=; SameSite=Strict; HttpOnly; Max-Age=0{}", + if config.secure_cookies { + "; Secure" + } else { + "" + } + ); + + with_header(response, SET_COOKIE, &cookie) +} + +pub fn template( + assets: &HashMap<String, String>, + templates: &Tera, + path: &str, + context: Context, +) -> Response<Body> { + let mut context = context.clone(); + context.insert("assets", assets); + + let response = match templates.render(path, &context) { + Ok(template) => Response::new(template.into()), + Err(err) => Response::new( + error::template( + assets, + templates, + "Erreur serveur", + &format!( + "Erreur lors de la préparation de la page : {:?}", + err + ), + ) + .into(), + ), + }; + + with_headers( + response, + vec![(CONTENT_TYPE, "text/html"), (CACHE_CONTROL, "no-cache")], + ) +} + +pub fn redirect(uri: &str) -> Response<Body> { + let mut response = Response::default(); + *response.status_mut() = StatusCode::MOVED_PERMANENTLY; + with_headers(response, vec![(LOCATION, uri), (CACHE_CONTROL, "no-cache")]) +} + +pub fn not_found() -> Response<Body> { + let mut response = Response::default(); + *response.status_mut() = StatusCode::NOT_FOUND; + response +} + +pub async fn file(filename: &str) -> Response<Body> { + if let Ok(file) = File::open(filename).await { + let stream = FramedRead::new(file, BytesCodec::new()); + let body = Body::wrap_stream(stream); + with_header(Response::new(body), CACHE_CONTROL, "max-age=3153600000") + } else { + not_found() + } +} |