Group transactions by date to simplify grouping in UI
This commit is contained in:
parent
777520e9df
commit
44254ed4d0
@ -21,19 +21,6 @@ const Reconciling = computed(() => useTransactionsStore().Reconciling);
|
|||||||
const transactionsStore = useTransactionsStore();
|
const transactionsStore = useTransactionsStore();
|
||||||
const TX = transactionsStore.Transactions.get(props.transactionid)!;
|
const TX = transactionsStore.Transactions.get(props.transactionid)!;
|
||||||
|
|
||||||
function dateChanged() {
|
|
||||||
const currentAccount = useAccountStore().CurrentAccount;
|
|
||||||
if (currentAccount == null)
|
|
||||||
return true;
|
|
||||||
const transactionIndex = currentAccount.Transactions.indexOf(props.transactionid);
|
|
||||||
if(transactionIndex<=0)
|
|
||||||
return true;
|
|
||||||
|
|
||||||
const previousTransactionId = currentAccount.Transactions[transactionIndex-1];
|
|
||||||
const previousTransaction = transactionsStore.Transactions.get(previousTransactionId);
|
|
||||||
return TX.Date.getTime() != previousTransaction?.Date.getTime();
|
|
||||||
}
|
|
||||||
|
|
||||||
function getStatusSymbol() {
|
function getStatusSymbol() {
|
||||||
if(TX.Status == "Reconciled")
|
if(TX.Status == "Reconciled")
|
||||||
return "✔";
|
return "✔";
|
||||||
@ -46,13 +33,6 @@ function getStatusSymbol() {
|
|||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
<tr v-if="dateChanged()" class="table-row md:hidden">
|
|
||||||
<td class="py-2" colspan="5">
|
|
||||||
<span class="bg-gray-400 dark:bg-slate-600 rounded-lg p-1 px-2 w-full block">
|
|
||||||
{{ formatDate(TX.Date) }}
|
|
||||||
</span>
|
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
<tr
|
<tr
|
||||||
v-if="!edit"
|
v-if="!edit"
|
||||||
class="{{new Date(TX.Date) > new Date() ? 'future' : ''}}"
|
class="{{new Date(TX.Date) > new Date() ? 'future' : ''}}"
|
||||||
|
@ -6,3 +6,12 @@ export function formatDate(date: Date): string {
|
|||||||
day: "2-digit",
|
day: "2-digit",
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export function groupBy<T, K extends keyof any>(list: T[], getKey: (item: T) => K) {
|
||||||
|
return list.reduce((previous, currentItem) => {
|
||||||
|
const group = getKey(currentItem);
|
||||||
|
if (!previous[group]) previous[group] = [];
|
||||||
|
previous[group].push(currentItem);
|
||||||
|
return previous;
|
||||||
|
}, {} as Record<K, T[]>);
|
||||||
|
}
|
@ -10,6 +10,7 @@ import { useTransactionsStore } from "../stores/transactions";
|
|||||||
import Modal from "../components/Modal.vue";
|
import Modal from "../components/Modal.vue";
|
||||||
import Input from "../components/Input.vue";
|
import Input from "../components/Input.vue";
|
||||||
import Checkbox from "../components/Checkbox.vue";
|
import Checkbox from "../components/Checkbox.vue";
|
||||||
|
import { formatDate } from "../date";
|
||||||
|
|
||||||
defineProps<{
|
defineProps<{
|
||||||
budgetid: string
|
budgetid: string
|
||||||
@ -144,12 +145,21 @@ function createReconcilationTransaction() {
|
|||||||
:budgetid="budgetid"
|
:budgetid="budgetid"
|
||||||
:accountid="accountid"
|
:accountid="accountid"
|
||||||
/>
|
/>
|
||||||
|
<template v-for="(dayTransactions, index) in transactions.TransactionsByDate">
|
||||||
|
<tr class="table-row md:hidden">
|
||||||
|
<td class="py-2" colspan="5">
|
||||||
|
<span class="bg-gray-400 dark:bg-slate-600 rounded-lg p-1 px-2 w-full block">
|
||||||
|
{{ index }}
|
||||||
|
</span>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
<TransactionRow
|
<TransactionRow
|
||||||
v-for="(transaction, index) in transactions.TransactionsList"
|
v-for="(transaction, index) in dayTransactions"
|
||||||
:key="transaction.ID"
|
:key="transaction.ID"
|
||||||
:transactionid="transaction.ID"
|
:transactionid="transaction.ID"
|
||||||
:index="index"
|
:index="index"
|
||||||
/>
|
/>
|
||||||
|
</template>
|
||||||
</table>
|
</table>
|
||||||
<div class="md:hidden">
|
<div class="md:hidden">
|
||||||
<Modal @submit="submitModal">
|
<Modal @submit="submitModal">
|
||||||
|
@ -201,10 +201,9 @@ export const useAccountStore = defineStore("budget/account", {
|
|||||||
);
|
);
|
||||||
const response = await result.json();
|
const response = await result.json();
|
||||||
const transactionsStore = useTransactionsStore();
|
const transactionsStore = useTransactionsStore();
|
||||||
const transactions = transactionsStore.AddTransactions(
|
transactionsStore.AddTransactions(
|
||||||
response.Transactions
|
response.Transactions
|
||||||
);
|
);
|
||||||
account.Transactions = transactions;
|
|
||||||
},
|
},
|
||||||
async FetchMonthBudget(budgetid: string, year: number, month: number) {
|
async FetchMonthBudget(budgetid: string, year: number, month: number) {
|
||||||
const result = await GET(
|
const result = await GET(
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import { defineStore } from "pinia";
|
import { defineStore } from "pinia";
|
||||||
import { POST } from "../api";
|
import { POST } from "../api";
|
||||||
|
import { formatDate, groupBy } from "../date";
|
||||||
import { useAccountStore } from "./budget-account";
|
import { useAccountStore } from "./budget-account";
|
||||||
|
|
||||||
interface State {
|
interface State {
|
||||||
@ -21,6 +22,7 @@ export interface Transaction {
|
|||||||
PayeeID: string | undefined;
|
PayeeID: string | undefined;
|
||||||
Amount: number;
|
Amount: number;
|
||||||
Reconciled: boolean;
|
Reconciled: boolean;
|
||||||
|
AccountID: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export const useTransactionsStore = defineStore("budget/transactions", {
|
export const useTransactionsStore = defineStore("budget/transactions", {
|
||||||
@ -39,24 +41,27 @@ export const useTransactionsStore = defineStore("budget/transactions", {
|
|||||||
}
|
}
|
||||||
return reconciledBalance;
|
return reconciledBalance;
|
||||||
},
|
},
|
||||||
|
TransactionsByDate(state) : Record<string, Transaction[]> {
|
||||||
|
const accountsStore = useAccountStore();
|
||||||
|
const accountID = accountsStore.CurrentAccountID;
|
||||||
|
const allTransactions = [...this.Transactions.values()];
|
||||||
|
return groupBy(allTransactions.filter(x => x.AccountID == accountID), x => formatDate(x.Date));
|
||||||
|
},
|
||||||
TransactionsList(state) : Transaction[] {
|
TransactionsList(state) : Transaction[] {
|
||||||
const accountsStore = useAccountStore();
|
const accountsStore = useAccountStore();
|
||||||
return accountsStore.CurrentAccount!.Transactions.map((x) => {
|
const accountID = accountsStore.CurrentAccountID;
|
||||||
return this.Transactions.get(x)!;
|
const allTransactions = [...this.Transactions.values()];
|
||||||
});
|
return allTransactions.filter(x => x.AccountID == accountID);
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
actions: {
|
actions: {
|
||||||
AddTransactions(transactions: Array<Transaction>) {
|
AddTransactions(transactions: Array<Transaction>) {
|
||||||
const transactionIds = [] as Array<string>;
|
|
||||||
this.$patch(() => {
|
this.$patch(() => {
|
||||||
for (const transaction of transactions) {
|
for (const transaction of transactions) {
|
||||||
transaction.Date = new Date(transaction.Date);
|
transaction.Date = new Date(transaction.Date);
|
||||||
this.Transactions.set(transaction.ID, transaction);
|
this.Transactions.set(transaction.ID, transaction);
|
||||||
transactionIds.push(transaction.ID);
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
return transactionIds;
|
|
||||||
},
|
},
|
||||||
SetReconciledForAllTransactions(value: boolean) {
|
SetReconciledForAllTransactions(value: boolean) {
|
||||||
for (const transaction of this.TransactionsList) {
|
for (const transaction of this.TransactionsList) {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user