diff --git a/templates/account_summary.html b/templates/account_summary.html index 9d208fe..06b000a 100644 --- a/templates/account_summary.html +++ b/templates/account_summary.html @@ -22,7 +22,6 @@

Last transactions

- More @@ -57,13 +56,6 @@ - {% endblock body %} diff --git a/templates/classifiers.html b/templates/classifiers.html index 194e289..8fc4780 100644 --- a/templates/classifiers.html +++ b/templates/classifiers.html @@ -3,7 +3,7 @@ {% block body %}
- New + New
@@ -27,7 +27,7 @@
- New + New
diff --git a/webserver/src/main.rs b/webserver/src/main.rs index 2100794..25c2f98 100644 --- a/webserver/src/main.rs +++ b/webserver/src/main.rs @@ -38,37 +38,30 @@ async fn main() { .route("/accounts/id/:id", get(routes::ui::account::show)) .route( "/accounts/id/:id/transactions/add", - get(routes::ui::account::add_transactions_view), - ) - .route( - "/accounts/id/:id/transactions/add", - post(routes::ui::account::add_transactions_action), + get(routes::ui::account::add_transactions_view) + .post(routes::ui::account::add_transactions_action), ) .route( "/accounts/id/:id/transactions", get(routes::ui::account::list_transactions), ) - .route("/transaction/:id", get(routes::ui::transaction::view)) - .route("/transaction/:id", post(routes::ui::transaction::update)) + .route( + "/transaction/:id", + get(routes::ui::transaction::view).post(routes::ui::transaction::update), + ) .route( "/classifiers", get(routes::ui::classifier::view_classifiers), ) .route( "/classifiers/new_rule", - get(routes::ui::classifier::rules_new_view), - ) - .route( - "/classifiers/new_rule", - post(routes::ui::classifier::rules_new_action), + get(routes::ui::classifier::rules_new_view) + .post(routes::ui::classifier::rules_new_action), ) .route( "/classifiers/new_category", - get(routes::ui::classifier::category_new_view), - ) - .route( - "/classifiers/new_category", - post(routes::ui::classifier::category_new_action), + get(routes::ui::classifier::category_new_view) + .post(routes::ui::classifier::category_new_action), ) .nest( "/static", @@ -115,6 +108,7 @@ async fn main() { web_view::builder() .title("Test") .content(web_view::Content::Url("http://localhost:3000")) + .size(1024, 600) .user_data(()) .invoke_handler(|_wv, _arg| Ok(())) .run() diff --git a/webserver/src/routes/ui.rs b/webserver/src/routes/ui.rs index 4d1eaad..cb61e2c 100644 --- a/webserver/src/routes/ui.rs +++ b/webserver/src/routes/ui.rs @@ -1,7 +1,7 @@ use std::{borrow::BorrowMut, collections::HashMap, sync::Arc}; use axum::{extract::State, response::IntoResponse}; -use chrono::{DateTime, Utc}; +use chrono::Utc; use hyper::{header::CONTENT_TYPE, StatusCode}; use serde::Serialize; use sqlx::SqlitePool; @@ -11,9 +11,7 @@ use crate::users::UserToken; use accounters::models::{account::Account, categories::Category, transaction::Transaction}; pub mod account; -pub mod categories; pub mod classifier; -pub mod rules; pub mod transaction; #[derive(Serialize)] diff --git a/webserver/src/routes/ui/account.rs b/webserver/src/routes/ui/account.rs index 854a14b..1b5e221 100644 --- a/webserver/src/routes/ui/account.rs +++ b/webserver/src/routes/ui/account.rs @@ -134,6 +134,14 @@ pub async fn list_transactions( ); } + let categories: HashMap = Category::list(db.as_ref()) + .await + .unwrap() + .iter() + .map(|x| (x.category_id, x.name.clone())) + .collect(); + ctx.insert("categories", &categories); + let n_entries = entries.unwrap_or(10).max(10); let page = page.unwrap_or(0).max(0); diff --git a/webserver/src/routes/ui/categories.rs b/webserver/src/routes/ui/categories.rs deleted file mode 100644 index 7d6eb30..0000000 --- a/webserver/src/routes/ui/categories.rs +++ /dev/null @@ -1,72 +0,0 @@ -use std::sync::Arc; - -use accounters::models::categories::Category; -use axum::{ - extract::{Form, State}, - response::IntoResponse, -}; -use hyper::{header::CONTENT_TYPE, StatusCode}; -use serde::Deserialize; -use sqlx::SqlitePool; -use tera::{Context, Tera}; - -use crate::users::UserToken; - -pub async fn list( - State(db): State>, - State(tmpl): State>, - uid: UserToken, -) -> impl IntoResponse { - match Category::list(db.as_ref()).await { - Ok(categories) => { - let mut ctx = Context::new(); - ctx.insert("categories", &categories); - ( - StatusCode::OK, - [(CONTENT_TYPE, "text/html;charset=utf-8")], - tmpl.render("categories_list.html", &ctx).unwrap(), - ) - } - Err(e) => ( - StatusCode::INTERNAL_SERVER_ERROR, - [(CONTENT_TYPE, "text/plain;charset=utf-8")], - format!("{e}"), - ), - } -} - -pub async fn new_view(State(tmpl): State>, uid: UserToken) -> impl IntoResponse { - ( - StatusCode::OK, - [(CONTENT_TYPE, "text/html;charset=utf-8")], - tmpl.render("categories_new.html", &Context::new()).unwrap(), - ) -} - -#[derive(Deserialize)] -pub struct NewRuleParams { - pub name: String, - pub description: String, -} - -pub async fn new_action( - State(db): State>, - State(tmpls): State>, - uid: UserToken, - Form(params): Form, -) -> impl IntoResponse { - match Category::new(db.as_ref(), ¶ms.name, ¶ms.description).await { - Ok(_) => ( - StatusCode::OK, - [(CONTENT_TYPE, "text/html;charset=utf-8")], - tmpls - .render("rules_new_success.html", &Context::new()) - .unwrap(), - ), - Err(e) => ( - StatusCode::INTERNAL_SERVER_ERROR, - [(CONTENT_TYPE, "text/plain;charset=utf-8")], - format!("{e}"), - ), - } -} diff --git a/webserver/src/routes/ui/classifier.rs b/webserver/src/routes/ui/classifier.rs index 3fb91c3..89ec53d 100644 --- a/webserver/src/routes/ui/classifier.rs +++ b/webserver/src/routes/ui/classifier.rs @@ -5,7 +5,10 @@ use axum::{ extract::{Form, State}, response::IntoResponse, }; -use hyper::{header::CONTENT_TYPE, StatusCode}; +use hyper::{ + header::{CONTENT_TYPE, LOCATION}, + StatusCode, +}; use serde::Deserialize; use sqlx::SqlitePool; use tera::{Context, Tera}; @@ -75,17 +78,14 @@ pub struct NewRuleParams { pub async fn rules_new_action( State(db): State>, - State(tmpls): State>, uid: UserToken, Form(params): Form, ) -> impl IntoResponse { match Rule::new(db.as_ref(), uid.user_id, params.regex, params.category).await { Ok(_) => ( - StatusCode::OK, - [(CONTENT_TYPE, "text/html;charset=utf-8")], - tmpls - .render("rules_new_success.html", &Context::new()) - .unwrap(), + StatusCode::MOVED_PERMANENTLY, + [(LOCATION, "/classifiers")], + String::new(), ), Err(e) => ( StatusCode::INTERNAL_SERVER_ERROR, @@ -95,29 +95,6 @@ pub async fn rules_new_action( } } -pub async fn category_list( - State(db): State>, - State(tmpl): State>, - uid: UserToken, -) -> impl IntoResponse { - match Category::list(db.as_ref()).await { - Ok(categories) => { - let mut ctx = Context::new(); - ctx.insert("categories", &categories); - ( - StatusCode::OK, - [(CONTENT_TYPE, "text/html;charset=utf-8")], - tmpl.render("categories_list.html", &ctx).unwrap(), - ) - } - Err(e) => ( - StatusCode::INTERNAL_SERVER_ERROR, - [(CONTENT_TYPE, "text/plain;charset=utf-8")], - format!("{e}"), - ), - } -} - pub async fn category_new_view(State(tmpl): State>, uid: UserToken) -> impl IntoResponse { ( StatusCode::OK, @@ -134,17 +111,14 @@ pub struct CategoryNewRuleParams { pub async fn category_new_action( State(db): State>, - State(tmpls): State>, uid: UserToken, Form(params): Form, ) -> impl IntoResponse { match Category::new(db.as_ref(), ¶ms.name, ¶ms.description).await { Ok(_) => ( - StatusCode::OK, - [(CONTENT_TYPE, "text/html;charset=utf-8")], - tmpls - .render("rules_new_success.html", &Context::new()) - .unwrap(), + StatusCode::MOVED_PERMANENTLY, + [(LOCATION, "/classifiers")], + String::new(), ), Err(e) => ( StatusCode::INTERNAL_SERVER_ERROR, diff --git a/webserver/src/routes/ui/rules.rs b/webserver/src/routes/ui/rules.rs deleted file mode 100644 index 44e8cc1..0000000 --- a/webserver/src/routes/ui/rules.rs +++ /dev/null @@ -1,84 +0,0 @@ -use std::sync::Arc; - -use accounters::models::{categories::Category, rules::Rule}; -use axum::{ - extract::{Form, State}, - response::IntoResponse, -}; -use hyper::{header::CONTENT_TYPE, StatusCode}; -use serde::Deserialize; -use sqlx::SqlitePool; -use tera::{Context, Tera}; - -use crate::users::UserToken; - -pub async fn list( - State(db): State>, - State(tmpls): State>, - uid: UserToken, -) -> impl IntoResponse { - let rules = match Rule::list_by_user(db.as_ref(), uid.user_id).await { - Ok(r) => r, - Err(e) => { - return ( - StatusCode::INTERNAL_SERVER_ERROR, - [(CONTENT_TYPE, "text/plain")], - format!("{e:?}"), - ); - } - }; - - let mut ctx = Context::new(); - - ctx.insert("rules", &rules); - - ( - StatusCode::OK, - [(CONTENT_TYPE, "text/html;charset=utf-8")], - tmpls.render("rules_list.html", &ctx).unwrap(), - ) -} - -pub async fn new_view( - State(db): State>, - State(tmpls): State>, - uid: UserToken, -) -> impl IntoResponse { - let categories = Category::list(db.as_ref()).await.unwrap(); - let mut ctx = Context::new(); - ctx.insert("categories", &categories); - ( - StatusCode::OK, - [(CONTENT_TYPE, "text/html;charset=utf-8")], - tmpls.render("rules_new.html", &ctx).unwrap(), - ) -} - -#[derive(Deserialize)] -pub struct NewRuleParams { - pub description: String, - pub regex: String, - pub category: i32, -} - -pub async fn new_action( - State(db): State>, - State(tmpls): State>, - uid: UserToken, - Form(params): Form, -) -> impl IntoResponse { - match Rule::new(db.as_ref(), uid.user_id, params.regex, params.category).await { - Ok(_) => ( - StatusCode::OK, - [(CONTENT_TYPE, "text/html;charset=utf-8")], - tmpls - .render("rules_new_success.html", &Context::new()) - .unwrap(), - ), - Err(e) => ( - StatusCode::INTERNAL_SERVER_ERROR, - [(CONTENT_TYPE, "text/plain;charset=utf-8")], - format!("{e}"), - ), - } -}