aboutsummaryrefslogtreecommitdiff
path: root/src/controller/utils.rs
diff options
context:
space:
mode:
authorJoris2021-01-03 13:40:40 +0100
committerJoris2021-01-03 13:54:20 +0100
commit11052951b74b9ad4b6a9412ae490086235f9154b (patch)
tree64526ac926c1bf470ea113f6cac8a33158684e8d /src/controller/utils.rs
parent371449b0e312a03162b78797b83dee9d81706669 (diff)
downloadbudget-11052951b74b9ad4b6a9412ae490086235f9154b.tar.gz
budget-11052951b74b9ad4b6a9412ae490086235f9154b.tar.bz2
budget-11052951b74b9ad4b6a9412ae490086235f9154b.zip
Rewrite in Rust
Diffstat (limited to 'src/controller/utils.rs')
-rw-r--r--src/controller/utils.rs119
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()
+ }
+}