From 787157455e1ba1eaa9adcdbf8d662222eec4aee9 Mon Sep 17 00:00:00 2001 From: "Konni (im Schloss)" Date: Thu, 18 May 2023 12:25:22 +0200 Subject: [PATCH] Balance and trx prep --- api/src/db_types.rs | 2 ++ api/src/routes.rs | 6 ++++ api/todo.md | 10 +++++++ app/src/main.rs | 2 ++ app/src/screens/costs.rs | 65 ++++++++++++++++++++++++++++++++++++++++ 5 files changed, 85 insertions(+) diff --git a/api/src/db_types.rs b/api/src/db_types.rs index fd599af..f9fa8c2 100644 --- a/api/src/db_types.rs +++ b/api/src/db_types.rs @@ -165,6 +165,8 @@ impl UserDebtExt for UserDebt { finally, they are both joined. */ + + // TODO Migration strategy: UNION the trx table to the debt table (debtor_id, creditor_id, owed) let dtrs: Vec = sqlx::query_as!( DebtTableRecord , r#" WITH debt_table AS ( SELECT debtor_id, creditor_id, (amount/nr_shares)::NUMERIC(16,2) as owed diff --git a/api/src/routes.rs b/api/src/routes.rs index 175d58a..9fdad81 100644 --- a/api/src/routes.rs +++ b/api/src/routes.rs @@ -213,6 +213,8 @@ async fn get_wg_users_public(params: web::Path<(i32,)>) -> Result) -> Result { + // TODO MIGRATION STRAT: Dings endpunkt mit enum CostOrTrx rückgabe + // er fetched von beiden tabellen und mischt die dann hier in die richtige reihenfolge! let cost = Cost::get_all_balance(member.identity.id, member.wg_id, query.balance.unwrap_or(0)).await?; Ok( HttpResponse::Ok() @@ -347,6 +349,9 @@ async fn post_wg_costs_balance(WGMemberIdentity{identity, wg_id} : WGMemberIdent async fn get_wg_costs_balance(identity: Identity) -> Result { let costs_opt = if let Some(wg_id) = identity.wg { + /// TODO Migration Strat: rename to "i_paid_cost, i_recieved_cost" and add "i_paid_trx, i_recieved_trx" + /// This will make sure that info is there + let balances = sqlx::query_as!(Balance, r#" SELECT equal_balances.id, equal_balances.balanced_on, equal_balances.initiator_id, equal_balances.wg_id, coalesce( sum(costs.amount), 0) as total_unified_spending, @@ -388,6 +393,7 @@ async fn get_wg_costs_over_time(member: WGMemberIdentity, params: web::Path<(Str my_total_spending: Option } + // needs no modification for trx let balances = sqlx::query_as!(DBRegularSpending, r#" SELECT date_trunc($3, added_on) as time_bucket , diff --git a/api/todo.md b/api/todo.md index 0924898..b982208 100644 --- a/api/todo.md +++ b/api/todo.md @@ -4,6 +4,16 @@ - add FromRequest for WGIdentity (requires WG) ✔ - DELETE cost ✔ +*** +### Priority +* Add trx table +* Change GEt /my_wg/costs or add another to take enum +* Change GET /my_wg/costs/stats (tally) to union trxs +* Change GET /my_wg/costs/balances to also aggregate trxs +* make no changes to over_time, that shit is fine +* add endpoints to add and remove trxs + +*** - continue refactoring backend: balance and stats - Add cost_shares.amount field, and update POST cost (and in future POST shares) accordingly, to guard that all shares add up exactly to costs.amount - The result will allow for far more flexible and inexpensive querying of data diff --git a/app/src/main.rs b/app/src/main.rs index c3aa615..b405471 100644 --- a/app/src/main.rs +++ b/app/src/main.rs @@ -119,6 +119,7 @@ pub fn LoggedInApp<'a>(cx: Scope, member: &'a WGMember) -> Element { Route { to: "/costs/detail", Layout { CostDetailScreen {} } } Route { to: "/costs/tally", Layout { TopTabs {} CostTallyScreen {} } } Route { to: "/costs/balance", Layout { CostBalanceDetailScreen {} } } + Route { to: "/costs/balance/confirm", CostBalanceConfirmScreen {} } Route { to: "/costs/stats", Layout { TopTabs {} CostStatScreen {} } } Route { to: "/settings", Layout { SettingScreen {} } } @@ -128,6 +129,7 @@ pub fn LoggedInApp<'a>(cx: Scope, member: &'a WGMember) -> Element { } + fn TopTabs(cx: Scope) -> Element { cx.render(rsx!( nav { diff --git a/app/src/screens/costs.rs b/app/src/screens/costs.rs index 63b635d..94377f0 100644 --- a/app/src/screens/costs.rs +++ b/app/src/screens/costs.rs @@ -261,6 +261,15 @@ pub fn CostTallyScreen(cx: Scope) -> Element { render!( Tallys { } + Link { + to: "/costs/balance/confirm", + + div { + background_color: "green", + color: "white", + "Komplett abrechnen" + } + } //trx_obj h3 { class: "cost_seperator", @@ -534,6 +543,62 @@ pub fn CostBalanceDetailScreen(cx: Scope) -> Element { ) } +pub fn CostBalanceConfirmScreen(cx: Scope) -> Element { + let router = use_router(cx); + let http = use_context::(cx)?; + + let send_balance = move |evt: Event| { + evt.stop_propagation(); + cx.spawn({ + to_owned![router, http]; + + async move { + let req = http.post(format!("{API_URL}/api/my_wg/costs/balance")); + let result = req.send().await; + match result.map(|res| res.error_for_status()) { + Ok(res) => { + trace!("SUCCESSFULLY ADDED BALANCE!"); + router.pop_route(); + }, + Err(err) => { + error!("Couldn't add entry!! {err}"); + } + } + } + }) + //evt.values + }; + + render!( + div { + background_color: "crimson", + position: "fixed", + top: "0", + left: "0", + right: "0", + bottom: "0", + text_align: "center", + color: "white", + + h2 { "Willst du wirklich alles abrechnen?" } + h4 { "Der aktuelle Unterschied wird auf 0 gesetzt." } + + button { + value: "JA", + onclick: send_balance, + + "JA" + } + button { + value: "Nein", + onclick: move |_| {router.pop_route();}, + + "Nein" + } + } + ) +} + // ========== Components #[inline_props] fn TransactionEntry(cx: Scope, trx: BalancingTransaction) -> Element {