diff options
Diffstat (limited to 'src/controller/incomes.rs')
-rw-r--r-- | src/controller/incomes.rs | 221 |
1 files changed, 221 insertions, 0 deletions
diff --git a/src/controller/incomes.rs b/src/controller/incomes.rs new file mode 100644 index 0000000..ea7f1cf --- /dev/null +++ b/src/controller/incomes.rs @@ -0,0 +1,221 @@ +use chrono::Datelike; +use chrono::Utc; +use hyper::{Body, Response}; +use std::collections::HashMap; +use tera::Context; + +use crate::controller::utils; +use crate::controller::wallet::Wallet; +use crate::db; +use crate::queries; +use crate::templates; +use crate::validation; + +static PER_PAGE: i64 = 10; + +pub async fn table(wallet: &Wallet, query: queries::Incomes) -> Response<Body> { + let page = query.page.unwrap_or(1); + let count = db::incomes::count(&wallet.pool).await; + let incomes = db::incomes::list(&wallet.pool, page, PER_PAGE).await; + let max_page = (count as f32 / PER_PAGE as f32).ceil() as i64; + + let mut context = Context::new(); + context.insert("header", &templates::Header::Incomes); + context.insert("connected_user", &wallet.user); + context.insert("incomes", &incomes); + context.insert("page", &page); + context.insert("max_page", &max_page); + context.insert("highlight", &query.highlight); + + utils::template( + &wallet.assets, + &wallet.templates, + "income/table.html", + context, + ) +} + +static MONTHS: [&str; 12] = [ + "Janvier", + "Février", + "Mars", + "Avril", + "Mai", + "Juin", + "Juillet", + "Août", + "Septembre", + "Octobre", + "Novembre", + "Décembre", +]; + +pub async fn create_form( + wallet: &Wallet, + query: queries::Incomes, +) -> Response<Body> { + create_form_feedback(wallet, query, HashMap::new(), None).await +} + +async fn create_form_feedback( + wallet: &Wallet, + query: queries::Incomes, + form: HashMap<String, String>, + error: Option<String>, +) -> Response<Body> { + let users = db::users::list(&wallet.pool).await; + + let mut context = Context::new(); + context.insert("header", &templates::Header::Incomes); + context.insert("connected_user", &wallet.user); + context.insert("users", &users); + context.insert("query", &query); + context.insert("current_month", &Utc::today().naive_utc().month()); + context.insert("months", &MONTHS); + context.insert("form", &form); + context.insert("error", &error); + + utils::template( + &wallet.assets, + &wallet.templates, + "income/create.html", + context, + ) +} + +pub async fn create( + wallet: &Wallet, + query: queries::Incomes, + form: HashMap<String, String>, +) -> Response<Body> { + let error = |e: &str| { + create_form_feedback(wallet, query, form.clone(), Some(e.to_string())) + }; + + match validation::income::create(&form) { + Some(income) => { + if !db::incomes::defined_at( + &wallet.pool, + income.user_id, + income.month, + income.year, + ) + .await + .is_empty() + { + error("Un revenu est déjà défini à cette date.").await + } else { + match db::incomes::create(&wallet.pool, &income).await { + Some(id) => { + let row = db::incomes::get_row(&wallet.pool, id).await; + let page = (row - 1) / PER_PAGE + 1; + utils::redirect(&format!( + "/incomes?page={}&highlight={}", + page, id + )) + } + None => error("Erreur serveur").await, + } + } + } + None => error("Erreur lors de la validation du formulaire.").await, + } +} + +pub async fn update_form( + id: i64, + wallet: &Wallet, + query: queries::Incomes, +) -> Response<Body> { + update_form_feedback(id, wallet, query, HashMap::new(), None).await +} + +async fn update_form_feedback( + id: i64, + wallet: &Wallet, + query: queries::Incomes, + form: HashMap<String, String>, + error: Option<String>, +) -> Response<Body> { + let users = db::users::list(&wallet.pool).await; + let income = db::incomes::get(&wallet.pool, id).await; + + let mut context = Context::new(); + context.insert("header", &templates::Header::Incomes); + context.insert("connected_user", &wallet.user); + context.insert("users", &users); + context.insert("id", &id); + context.insert("income", &income); + context.insert("query", &query); + context.insert("months", &MONTHS); + context.insert("form", &form); + context.insert("error", &error); + + utils::template( + &wallet.assets, + &wallet.templates, + "income/update.html", + context, + ) +} + +pub async fn update( + id: i64, + wallet: &Wallet, + query: queries::Incomes, + form: HashMap<String, String>, +) -> Response<Body> { + let error = |e: &str| { + update_form_feedback( + id, + wallet, + query, + form.clone(), + Some(e.to_string()), + ) + }; + + match validation::income::update(&form) { + Some(income) => { + let existing_incomes = db::incomes::defined_at( + &wallet.pool, + income.user_id, + income.month, + income.year, + ) + .await; + if existing_incomes.into_iter().any(|eid| eid != id) { + error("Un revenu est déjà défini à cette date.").await + } else if db::incomes::update(&wallet.pool, id, &income).await { + let row = db::incomes::get_row(&wallet.pool, id).await; + let page = (row - 1) / PER_PAGE + 1; + utils::redirect(&format!( + "/incomes?page={}&highlight={}", + page, id + )) + } else { + error("Erreur serveur").await + } + } + None => error("Erreur lors de la validation du formulaire.").await, + } +} + +pub async fn delete( + id: i64, + wallet: &Wallet, + query: queries::Incomes, +) -> Response<Body> { + if db::incomes::delete(&wallet.pool, id).await { + utils::redirect(&format!("/incomes?page={}", query.page.unwrap_or(1))) + } else { + update_form_feedback( + id, + wallet, + query, + HashMap::new(), + Some("Erreur serveur".to_string()), + ) + .await + } +} |