Compare commits
No commits in common. "98765a3d2d5f539960bb05ebbd78d875636bc959" and "4cbe3fe0f9adfbdfeb19911bb3da3ad9b171aa8e" have entirely different histories.
98765a3d2d
...
4cbe3fe0f9
|
@ -20,8 +20,6 @@ export interface Card {
|
||||||
name: string;
|
name: string;
|
||||||
last_digits: string;
|
last_digits: string;
|
||||||
currency_id: number;
|
currency_id: number;
|
||||||
currency: Currency;
|
|
||||||
display_name: string;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface Category {
|
export interface Category {
|
||||||
|
@ -52,13 +50,7 @@ export interface Transfer {
|
||||||
from_card_id: number;
|
from_card_id: number;
|
||||||
to_card_id: number;
|
to_card_id: number;
|
||||||
value: number;
|
value: number;
|
||||||
from_value: number;
|
|
||||||
to_value: number;
|
|
||||||
date: string;
|
date: string;
|
||||||
show_value: string;
|
|
||||||
have_diff_currs: boolean;
|
|
||||||
from_card: Card;
|
|
||||||
to_card: Card;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface Payment {
|
export interface Payment {
|
||||||
|
@ -150,8 +142,8 @@ export type EntityType<T extends EntityName> =
|
||||||
//
|
//
|
||||||
|
|
||||||
|
|
||||||
export async function getAll<T>(groupName: string, session?: string, queryParams?: string): Promise<T[] | ErrorMessage> {
|
export async function getAll<T>(groupName: string, session?: string): Promise<T[] | ErrorMessage> {
|
||||||
const url = queryParams ? `${BASE_API_URL}/${groupName}/all?${queryParams}` : `${BASE_API_URL}/${groupName}/all`
|
const url = `${BASE_API_URL}/${groupName}/all`
|
||||||
const defaultHeaders = {
|
const defaultHeaders = {
|
||||||
'Content-Type': 'application/json',
|
'Content-Type': 'application/json',
|
||||||
};
|
};
|
||||||
|
|
|
@ -6,11 +6,10 @@ function isErrorMessage(value: any): value is ErrorMessage {
|
||||||
return value && typeof value.message === 'string';
|
return value && typeof value.message === 'string';
|
||||||
}
|
}
|
||||||
|
|
||||||
export const GET: RequestHandler = async ({ cookies, params, url }): Promise<Response> => {
|
export const GET: RequestHandler = async ({ cookies, params }): Promise<Response> => {
|
||||||
const session = cookies.get('session');
|
const session = cookies.get('session');
|
||||||
const { entity } = params;
|
const { entity } = params;
|
||||||
|
|
||||||
const queryParams = url.searchParams.toString();
|
|
||||||
// Check if the entity is valid
|
// Check if the entity is valid
|
||||||
if (!session) {
|
if (!session) {
|
||||||
return new Response(JSON.stringify("no cookies"), { status: 401 });
|
return new Response(JSON.stringify("no cookies"), { status: 401 });
|
||||||
|
@ -22,7 +21,7 @@ export const GET: RequestHandler = async ({ cookies, params, url }): Promise<Res
|
||||||
|
|
||||||
// TypeScript type inference for entity
|
// TypeScript type inference for entity
|
||||||
const entityName = entity as EntityName
|
const entityName = entity as EntityName
|
||||||
const result = await getAll<EntityType<typeof entityName>>(entityName, session, queryParams);
|
const result = await getAll<EntityType<typeof entityName>>(entityName, session);
|
||||||
|
|
||||||
if (isErrorMessage(result)) {
|
if (isErrorMessage(result)) {
|
||||||
console.log("ERROR");
|
console.log("ERROR");
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
<script lang="ts">
|
<script lang="ts">
|
||||||
import { onMount, tick } from "svelte";
|
import { onMount } from "svelte";
|
||||||
import { type Card, type Currency } from "$lib/entities";
|
import { type Card, type Currency } from "$lib/entities";
|
||||||
import { NumberToFPA } from "$lib/util/fpa";
|
import { NumberToFPA } from "$lib/util/fpa";
|
||||||
|
|
||||||
|
@ -64,18 +64,14 @@
|
||||||
name: "",
|
name: "",
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
if (balanceRef) {
|
|
||||||
balanceRef.value = "";
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async function editCard(card: Card) {
|
function editCard(card: Card) {
|
||||||
editingCard = { ...card };
|
editingCard = { ...card };
|
||||||
if (balanceRef) {
|
if (balanceRef) {
|
||||||
balanceRef.value = NumberToFPA(card.balance);
|
balanceRef.value = NumberToFPA(card.balance);
|
||||||
}
|
}
|
||||||
await tick();
|
|
||||||
if (creditLineRef) {
|
if (creditLineRef) {
|
||||||
creditLineRef.value = NumberToFPA(card.credit_line);
|
creditLineRef.value = NumberToFPA(card.credit_line);
|
||||||
}
|
}
|
||||||
|
|
|
@ -11,25 +11,18 @@
|
||||||
let error: string | null = $state(null);
|
let error: string | null = $state(null);
|
||||||
let editingTransfer: Transfer | null = $state(null);
|
let editingTransfer: Transfer | null = $state(null);
|
||||||
let newTransfer: Partial<Transfer> = $state({
|
let newTransfer: Partial<Transfer> = $state({
|
||||||
from_card_id: 0,
|
|
||||||
to_card_id: 0,
|
|
||||||
card_id: 0,
|
card_id: 0,
|
||||||
value: 0,
|
value: 0,
|
||||||
to_value: 0,
|
|
||||||
from_value: 0,
|
|
||||||
date: "2006-01-02T15:04:05Z",
|
date: "2006-01-02T15:04:05Z",
|
||||||
});
|
});
|
||||||
|
|
||||||
onMount(async () => {
|
onMount(async () => {
|
||||||
await fetchCategories();
|
await fetchCategories();
|
||||||
await fetchCards(true);
|
await fetchCards();
|
||||||
});
|
});
|
||||||
|
|
||||||
async function fetchCards(preloadCurrencies = false) {
|
async function fetchCards() {
|
||||||
const queryParams = new URLSearchParams({
|
const result = await fetch("/api/card/all");
|
||||||
preload_currencies: preloadCurrencies.toString(),
|
|
||||||
});
|
|
||||||
const result = await fetch(`/api/card/all?${queryParams}`);
|
|
||||||
if (!result.ok) {
|
if (!result.ok) {
|
||||||
const obj = await result.json();
|
const obj = await result.json();
|
||||||
error = obj.message;
|
error = obj.message;
|
||||||
|
@ -79,8 +72,6 @@
|
||||||
from_card_id: 0,
|
from_card_id: 0,
|
||||||
to_card_id: 0,
|
to_card_id: 0,
|
||||||
value: 0,
|
value: 0,
|
||||||
to_value: 0,
|
|
||||||
from_value: 0,
|
|
||||||
date: "",
|
date: "",
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
@ -92,9 +83,6 @@
|
||||||
const parts = transfer.date.split("T");
|
const parts = transfer.date.split("T");
|
||||||
mutateDate = parts[0];
|
mutateDate = parts[0];
|
||||||
selectedTime = parts[1].split("Z")[0];
|
selectedTime = parts[1].split("Z")[0];
|
||||||
if (valueRef) {
|
|
||||||
valueRef.value = NumberToFPA(transfer.value);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async function deleteTransfer(id: number) {
|
async function deleteTransfer(id: number) {
|
||||||
|
@ -112,28 +100,19 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
// Helper function to get the name of the parent category
|
// Helper function to get the name of the parent category
|
||||||
function doesCurrentTransferHasSameCurrencies(): boolean {
|
function getCardName(cardId: number) {
|
||||||
if (currentTransfer.from_card_id == 0 || currentTransfer.to_card_id == 0) {
|
if (cardId === 0) return "None";
|
||||||
return true;
|
const card = cards.find((card) => card.id === cardId);
|
||||||
}
|
return card ? card.name : "Unknown";
|
||||||
return (
|
|
||||||
cards.find((card) => card.id == currentTransfer.from_card_id)
|
|
||||||
?.currency_id ==
|
|
||||||
cards.find((card) => card.id == currentTransfer.to_card_id)?.currency_id
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
let valueRef: HTMLInputElement | null = $state(null);
|
function handleValueInput(
|
||||||
function createHandleValueInput(field: "value" | "from_value" | "to_value") {
|
event: Event & { currentTarget: EventTarget & HTMLInputElement },
|
||||||
return function (
|
): void {
|
||||||
event: Event & { currentTarget: EventTarget & HTMLInputElement },
|
const target = event.target as HTMLInputElement;
|
||||||
): void {
|
const rawValue = target.value.replace(/[^0-9]/g, "");
|
||||||
const target = event.target as HTMLInputElement;
|
currentTransfer.value = parseInt(rawValue || "0");
|
||||||
const rawValue = target.value.replace(/[^0-9]/g, "");
|
target.value = NumberToFPA(currentTransfer.value);
|
||||||
const parsedValue = parseInt(rawValue || "0");
|
|
||||||
currentTransfer[field] = parsedValue;
|
|
||||||
target.value = NumberToFPA(parsedValue);
|
|
||||||
};
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const constructedTime = $derived(`${mutateDate}T${selectedTime}Z`);
|
const constructedTime = $derived(`${mutateDate}T${selectedTime}Z`);
|
||||||
|
@ -182,39 +161,15 @@
|
||||||
</select>
|
</select>
|
||||||
</label>
|
</label>
|
||||||
|
|
||||||
{#if doesCurrentTransferHasSameCurrencies()}
|
<label class="block">
|
||||||
<label class="block">
|
<span class="text-gray-700">Value:</span>
|
||||||
<span class="text-gray-700">Value:</span>
|
<input
|
||||||
<input
|
type="text"
|
||||||
type="text"
|
oninput={handleValueInput}
|
||||||
oninput={createHandleValueInput("value")}
|
required
|
||||||
bind:this={valueRef}
|
class="mt-1 block w-full px-4 py-2 border border-gray-300 rounded-md focus:ring focus:ring-indigo-200 focus:border-indigo-500"
|
||||||
required
|
/>
|
||||||
class="mt-1 block w-full px-4 py-2 border border-gray-300 rounded-md focus:ring focus:ring-indigo-200 focus:border-indigo-500"
|
</label>
|
||||||
/>
|
|
||||||
</label>
|
|
||||||
{:else}
|
|
||||||
<label class="block">
|
|
||||||
<span class="text-gray-700">From Value:</span>
|
|
||||||
<input
|
|
||||||
type="text"
|
|
||||||
oninput={createHandleValueInput("from_value")}
|
|
||||||
bind:this={valueRef}
|
|
||||||
required
|
|
||||||
class="mt-1 block w-full px-4 py-2 border border-gray-300 rounded-md focus:ring focus:ring-indigo-200 focus:border-indigo-500"
|
|
||||||
/>
|
|
||||||
</label>
|
|
||||||
<label class="block">
|
|
||||||
<span class="text-gray-700">To Value:</span>
|
|
||||||
<input
|
|
||||||
type="text"
|
|
||||||
oninput={createHandleValueInput("to_value")}
|
|
||||||
bind:this={valueRef}
|
|
||||||
required
|
|
||||||
class="mt-1 block w-full px-4 py-2 border border-gray-300 rounded-md focus:ring focus:ring-indigo-200 focus:border-indigo-500"
|
|
||||||
/>
|
|
||||||
</label>
|
|
||||||
{/if}
|
|
||||||
|
|
||||||
<div class="flex items-center space-x-4">
|
<div class="flex items-center space-x-4">
|
||||||
<label>
|
<label>
|
||||||
|
@ -263,12 +218,18 @@
|
||||||
class="bg-white p-4 rounded-lg shadow-md flex justify-between items-center"
|
class="bg-white p-4 rounded-lg shadow-md flex justify-between items-center"
|
||||||
>
|
>
|
||||||
<div>
|
<div>
|
||||||
<strong class="block text-lg">{transfer.show_value}</strong>
|
<strong class="block text-lg">{NumberToFPA(transfer.value)}</strong>
|
||||||
<div class="text-sm text-gray-600">
|
<div class="text-sm text-gray-600">
|
||||||
<span class="font-bold">From:</span>
|
<span class="font-bold">From:</span>
|
||||||
{transfer.from_card.display_name}
|
{getCardName(transfer.from_card_id)}
|
||||||
|
<span class="text-sm"
|
||||||
|
>{`•${cards.find((card) => card.id == transfer.from_card_id)?.last_digits}`}</span
|
||||||
|
>
|
||||||
<span class="font-bold">To:</span>
|
<span class="font-bold">To:</span>
|
||||||
{transfer.to_card.display_name}
|
{getCardName(transfer.to_card_id)}
|
||||||
|
<span class="text-sm"
|
||||||
|
>{`•${cards.find((card) => card.id == transfer.to_card_id)?.last_digits}`}</span
|
||||||
|
>
|
||||||
<span class="font-bold">Date:</span>
|
<span class="font-bold">Date:</span>
|
||||||
{transfer.date}
|
{transfer.date}
|
||||||
</div>
|
</div>
|
||||||
|
|
Loading…
Reference in New Issue
Block a user