Working well enough
This commit is contained in:
@ -96,12 +96,14 @@ export async function getBudgetTransactions(id) {
|
|||||||
from budget_transaction
|
from budget_transaction
|
||||||
join transaction on budget_transaction.transaction_id = transaction.id
|
join transaction on budget_transaction.transaction_id = transaction.id
|
||||||
where budget_transaction.budget_id = ${id}
|
where budget_transaction.budget_id = ${id}
|
||||||
order by transaction.posted desc
|
order by transaction.date desc
|
||||||
`;
|
`;
|
||||||
console.log(`Fetched ${transactions.length} transactions for budget ${id}`);
|
console.log(`Fetched ${transactions.length} transactions for budget ${id}`);
|
||||||
// transactions = Result [{ id: 1, posted: 1633036800, amount: 50.00, description: "Grocery Store", pending: false, notes: "Weekly groceries" }, ...]
|
// transactions = Result [{ id: 1, posted: 1633036800, amount: 50.00, description: "Grocery Store", pending: false, notes: "Weekly groceries" }, ...]
|
||||||
return { transactions };
|
return { transactions };
|
||||||
} catch {
|
} catch (error) {
|
||||||
|
console.error(`Error fetching transactions for budget ${id}`);
|
||||||
|
console.error(error);
|
||||||
return [];
|
return [];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -109,9 +111,9 @@ export async function getBudgetTransactions(id) {
|
|||||||
export async function updateBudgetTransaction(id, amount, notes) {
|
export async function updateBudgetTransaction(id, amount, notes) {
|
||||||
// Delete a transaction from a budget
|
// Delete a transaction from a budget
|
||||||
const result = await db`
|
const result = await db`
|
||||||
update from budget_transaction
|
update budget_transaction
|
||||||
where id= ${id}
|
|
||||||
SET amount = ${amount}, notes = ${notes}
|
SET amount = ${amount}, notes = ${notes}
|
||||||
|
where id= ${id}
|
||||||
`;
|
`;
|
||||||
// result = Result [{ id: 1 }]
|
// result = Result [{ id: 1 }]
|
||||||
return result;
|
return result;
|
||||||
|
|||||||
@ -19,11 +19,11 @@ export async function PATCH({ params, request }) {
|
|||||||
const { slug } = params;
|
const { slug } = params;
|
||||||
let body = await request.json();
|
let body = await request.json();
|
||||||
|
|
||||||
const { amount, notes } = body;
|
const { amount, notes, transactionId } = body;
|
||||||
console.log({ slug, transactionId, amount });
|
console.log({ slug, transactionId, amount });
|
||||||
|
|
||||||
// Call the deleteBudget function from db.js (budgetId, transactionId, amount)
|
// Call the deleteBudget function from db.js (budgetId, transactionId, amount)
|
||||||
return updateBudgetTransaction(slug, amount, notes)
|
return updateBudgetTransaction(transactionId, amount, notes)
|
||||||
.then(() => new Response(`Budget transaction updated successfully`, { status: 200 }))
|
.then(() => new Response(`Budget transaction updated successfully`, { status: 200 }))
|
||||||
.catch(
|
.catch(
|
||||||
(err) => new Response(`Error updating transaction in budget ${err.message}`, { status: 500 })
|
(err) => new Response(`Error updating transaction in budget ${err.message}`, { status: 500 })
|
||||||
|
|||||||
@ -1,18 +1,27 @@
|
|||||||
<script>
|
<script>
|
||||||
import { EditSymbol } from '$lib/editSymbol.svelte';
|
import { EditSymbol } from '$lib/editSymbol.svelte';
|
||||||
import { TrashBin } from '$lib/trashbin.svelte';
|
import { TrashBin } from '$lib/trashbin.svelte';
|
||||||
|
import { loadingModal } from '$lib/loadingModal.svelte';
|
||||||
|
import { getContext } from 'svelte';
|
||||||
|
import { invalidate, invalidateAll } from '$app/navigation';
|
||||||
|
|
||||||
let { data } = $props();
|
let { data } = $props();
|
||||||
|
const addToast = getContext('addToast');
|
||||||
let budget = $derived(data.budget);
|
let budget = $derived(data.budget);
|
||||||
let transactions = $derived(data.transactions.transactions || []);
|
let transactions = $derived(data.transactions.transactions || []);
|
||||||
let newData = $state({
|
let newData = $state({
|
||||||
amount: 0,
|
amount: 0,
|
||||||
notes: ''
|
notes: '',
|
||||||
|
name: '',
|
||||||
|
id: null
|
||||||
});
|
});
|
||||||
let toDelete = $state(null);
|
let toDelete = $state('');
|
||||||
let toDeleteName = $state('');
|
let toDeleteName = $state('');
|
||||||
|
let loading = $state(false);
|
||||||
|
|
||||||
async function saveTransaction() {
|
async function saveTransaction() {
|
||||||
|
loading = true;
|
||||||
|
EditBudgetTransactionModal.close();
|
||||||
let res = await fetch(`/api/budget/${budget.id}/transaction`, {
|
let res = await fetch(`/api/budget/${budget.id}/transaction`, {
|
||||||
method: 'PATCH',
|
method: 'PATCH',
|
||||||
headers: {
|
headers: {
|
||||||
@ -20,14 +29,27 @@
|
|||||||
},
|
},
|
||||||
body: JSON.stringify({
|
body: JSON.stringify({
|
||||||
amount: $state.snapshot(newData.amount),
|
amount: $state.snapshot(newData.amount),
|
||||||
notes: $state.snapshot(newData.notes)
|
notes: $state.snapshot(newData.notes),
|
||||||
|
transactionId: $state.snapshot(newData.id)
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
|
loading = false;
|
||||||
|
console.log(res.ok);
|
||||||
|
if (res.ok) {
|
||||||
|
// Optionally, you can refresh the UI or show a success message
|
||||||
|
addToast('Transaction updated successfully', 'success');
|
||||||
|
invalidateAll();
|
||||||
|
} else {
|
||||||
|
console.error('Failed to update transaction');
|
||||||
|
addToast('Failed to update transaction', 'error');
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function edit(transaction) {
|
function edit(transaction) {
|
||||||
newData.amount = transaction.budget_amount;
|
newData.amount = transaction.budget_amount;
|
||||||
|
newData.name = transaction.description;
|
||||||
newData.notes = transaction.notes || '';
|
newData.notes = transaction.notes || '';
|
||||||
|
newData.id = transaction.budget_transaction_id;
|
||||||
EditBudgetTransactionModal.showModal();
|
EditBudgetTransactionModal.showModal();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -42,7 +64,7 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
function deleteTransaction(transaction) {
|
function deleteTransaction(transaction) {
|
||||||
toDelete = transaction;
|
toDelete = transaction.budget_transaction_id;
|
||||||
DeleteTransactionModal.showModal();
|
DeleteTransactionModal.showModal();
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
@ -71,56 +93,36 @@
|
|||||||
<div class="w-64 grow">{budget.amount}</div>
|
<div class="w-64 grow">{budget.amount}</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="">
|
<ul class="list bg-base-100 rounded-box shadow-md">
|
||||||
<h2>Notes:</h2>
|
{#each transactions as tras}
|
||||||
<p>{budget.notes}</p>
|
<li class="list-row">
|
||||||
</div>
|
<div>
|
||||||
|
<div>{tras.description}</div>
|
||||||
|
<div class="text-xs uppercase font-semibold opacity-60">
|
||||||
|
{tras.date.toDateString()}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<table class="overflow-x-auto rounded-box border border-base-content/5 bg-base-100">
|
<div class="text-center">{tras.notes}</div>
|
||||||
<thead>
|
|
||||||
<tr class="">
|
|
||||||
<th>Date</th>
|
|
||||||
<th>Description</th>
|
|
||||||
<th>Amount</th>
|
|
||||||
<th>Notes</th>
|
|
||||||
<th></th>
|
|
||||||
</tr>
|
|
||||||
</thead>
|
|
||||||
<tbody>
|
|
||||||
{#each transactions as txn}
|
|
||||||
<tr>
|
|
||||||
<td>{txn.date.toDateString()}</td>
|
|
||||||
<td>{txn.description}</td>
|
|
||||||
<td>${txn.budget_amount}</td>
|
|
||||||
<td>
|
|
||||||
{#if txn.notes}
|
|
||||||
<span>{txn.notes}</span>
|
|
||||||
{:else}
|
|
||||||
<span class="text-gray-500">No notes</span>
|
|
||||||
{/if}
|
|
||||||
</td>
|
|
||||||
|
|
||||||
<td
|
<div class="text-lg uppercase font-semibold text-right w-32">{tras.budget_amount}</div>
|
||||||
><button class="btn btn-square btn-ghost" onclick={() => edit(txn)}
|
<div>
|
||||||
|
<button class="btn btn-square btn-ghost" onclick={() => edit(tras)}
|
||||||
>{@render EditSymbol()}</button
|
>{@render EditSymbol()}</button
|
||||||
></td
|
|
||||||
><td
|
|
||||||
><button class="btn btn-square btn-ghost" onclick={() => deleteTransaction(txn)}
|
|
||||||
>{@render TrashBin()}</button
|
|
||||||
></td
|
|
||||||
></tr
|
|
||||||
>
|
>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<button class="btn btn-square btn-ghost" onclick={() => deleteTransaction(tras)}
|
||||||
|
>{@render TrashBin()}</button
|
||||||
|
>
|
||||||
|
</div>
|
||||||
|
</li>
|
||||||
{/each}
|
{/each}
|
||||||
{#if transactions.length === 0}
|
</ul>
|
||||||
<tr>
|
|
||||||
<td colspan="3">No transactions found.</td>
|
|
||||||
</tr>
|
|
||||||
{/if}
|
|
||||||
</tbody>
|
|
||||||
</table>
|
|
||||||
|
|
||||||
<dialog id="EditBudgetTransactionModal" class="modal">
|
<dialog id="EditBudgetTransactionModal" class="modal">
|
||||||
<div class="modal-box">
|
<div class="modal-box">
|
||||||
|
<h1>{newData.name}</h1>
|
||||||
<fieldset class="fieldset bg-base-200 border-base-300 rounded-box w-xs border p-4">
|
<fieldset class="fieldset bg-base-200 border-base-300 rounded-box w-xs border p-4">
|
||||||
<legend class="fieldset-legend">Edit</legend>
|
<legend class="fieldset-legend">Edit</legend>
|
||||||
|
|
||||||
@ -159,7 +161,8 @@
|
|||||||
|
|
||||||
<dialog id="DeleteTransactionModal" class="modal">
|
<dialog id="DeleteTransactionModal" class="modal">
|
||||||
<div class="modal-box">
|
<div class="modal-box">
|
||||||
<h1>Are you sure you want to delete {toDelete?.description}?</h1>
|
<p>Are you sure you want to delete</p>
|
||||||
|
<span>{toDelete}</span>
|
||||||
<p>Type it in the box to confirm</p>
|
<p>Type it in the box to confirm</p>
|
||||||
<input
|
<input
|
||||||
bind:value={toDeleteName}
|
bind:value={toDeleteName}
|
||||||
@ -170,19 +173,22 @@
|
|||||||
<button
|
<button
|
||||||
class="btn btn-error mt-4"
|
class="btn btn-error mt-4"
|
||||||
onclick={async () => {
|
onclick={async () => {
|
||||||
if (toDelete.description === toDeleteName) {
|
if (toDelete == toDeleteName) {
|
||||||
let res = await fetch(`/api/budget/${toDelete.budget_transaction_id}/transaction/`, {
|
let res = await fetch(`/api/budget/${toDelete}/transaction/`, {
|
||||||
method: 'DELETE'
|
method: 'DELETE'
|
||||||
});
|
});
|
||||||
if (res.ok) {
|
if (res.ok) {
|
||||||
console.log('Rule deleted successfully');
|
console.log('Rule deleted successfully');
|
||||||
DeleteTransactionModal.close();
|
DeleteTransactionModal.close();
|
||||||
location.reload();
|
invalidateAll();
|
||||||
|
addToast('Transaction deleted successfully', 'success');
|
||||||
} else {
|
} else {
|
||||||
console.error('Failed to delete transaction');
|
console.error('Failed to delete transaction');
|
||||||
|
addToast('Failed to delete transaction', 'error');
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
console.error('Name does not match');
|
console.error('Name does not match');
|
||||||
|
addToast('Name does not match', 'warning');
|
||||||
}
|
}
|
||||||
}}>Delete</button
|
}}>Delete</button
|
||||||
>
|
>
|
||||||
@ -191,3 +197,7 @@
|
|||||||
<button>close</button>
|
<button>close</button>
|
||||||
</form>
|
</form>
|
||||||
</dialog>
|
</dialog>
|
||||||
|
|
||||||
|
{#if loading}
|
||||||
|
{@render loadingModal()}
|
||||||
|
{/if}
|
||||||
|
|||||||
Reference in New Issue
Block a user