Add support for fetching only desired transactions related to specified profile
This commit is contained in:
@@ -10,7 +10,7 @@ in
|
||||
pname = "actual-importer";
|
||||
version = "0.0.1";
|
||||
src = ./.;
|
||||
npmDepsHash = "sha256-yU3LzlExba2hq4EfuEb05TWaIS3gza1r8lu9Q/myXqE=";
|
||||
npmDepsHash = "sha256-GHNfMeFg5UB/A031NYYjne9M8rXr1zeYCmBH2/FARt8=";
|
||||
|
||||
postInstall = ''
|
||||
mkdir -p $out/lib/node_modules/actual-importer/public
|
||||
|
||||
@@ -14,9 +14,9 @@ export type SubmitOptions =
|
||||
|
||||
type ActualTransaction = {
|
||||
id?: string;
|
||||
account?: string;
|
||||
account: string;
|
||||
date: string;
|
||||
amount?: number;
|
||||
amount: number;
|
||||
payee?: string;
|
||||
payee_name?: string;
|
||||
imported_payee?: string;
|
||||
@@ -51,7 +51,7 @@ export class Actual {
|
||||
}
|
||||
|
||||
#map(transaction: Transaction, accounts: ActualAccount[], payees: ActualPayee[]): ActualTransaction {
|
||||
const actualTransaction: ActualTransaction = {
|
||||
const actualTransaction: Omit<ActualTransaction, 'account'> & { account?: string } = {
|
||||
imported_id: transaction.id,
|
||||
date: transaction.date,
|
||||
amount: utils.amountToInteger(transaction.amount),
|
||||
@@ -94,7 +94,7 @@ export class Actual {
|
||||
break;
|
||||
}
|
||||
|
||||
return actualTransaction;
|
||||
return actualTransaction as ActualTransaction;
|
||||
}
|
||||
|
||||
async #api<T>(fn: () => Promise<T>): Promise<T> {
|
||||
@@ -194,7 +194,8 @@ export class Actual {
|
||||
|
||||
const query = api.q('transactions')
|
||||
.limit(limit)
|
||||
.select(['*']);
|
||||
.select(['*'])
|
||||
.options({ splits: 'grouped' });
|
||||
|
||||
const { data } = await api.runQuery(query) as { data: ActualTransaction[] };
|
||||
|
||||
@@ -209,7 +210,8 @@ export class Actual {
|
||||
|
||||
const query = api.q('transactions')
|
||||
.filter({ date: [{ $gte: start }, { $lte: end }] })
|
||||
.select(['*']);
|
||||
.select(['*'])
|
||||
.options({ splits: 'grouped' });
|
||||
|
||||
const { data } = await api.runQuery(query) as { data: ActualTransaction[] };
|
||||
|
||||
|
||||
@@ -4,6 +4,7 @@ import express from "express";
|
||||
import multer from "multer";
|
||||
import { Readable } from "stream";
|
||||
import path from 'path';
|
||||
import { Transaction } from "@/types/transaction";
|
||||
|
||||
|
||||
export function serve(config: Config, port: number) {
|
||||
@@ -22,18 +23,23 @@ export function serve(config: Config, port: number) {
|
||||
|
||||
app.get("/servers/:server/transactions", async (req, res) => {
|
||||
const { start, end } = req.query;
|
||||
let data: Transaction[]|undefined;
|
||||
|
||||
if (start && end) {
|
||||
const data = await getTransactionsFromRange(req.params.server, config, start.toString(), end.toString());
|
||||
res.json(data);
|
||||
data = await getTransactionsFromRange(req.params.server, config, start.toString(), end.toString());
|
||||
}
|
||||
|
||||
else {
|
||||
const limitParam = req.query.limit?.toString();
|
||||
const limit = (limitParam && Number.parseInt(limitParam)) || undefined;
|
||||
const data = await getTransactions(req.params.server, config, limit);
|
||||
res.json(data);
|
||||
data = await getTransactions(req.params.server, config, limit);
|
||||
}
|
||||
|
||||
const profile = req.query.profile?.toString() || undefined;
|
||||
const supportedAccounts = profile !== undefined ? config.profiles[profile].supportedAccounts : undefined;
|
||||
const filterAccounts = supportedAccounts !== undefined ? (t: Transaction) => supportedAccounts.includes(t.from) || supportedAccounts.includes(t.to) : () => true;
|
||||
|
||||
res.json(data.filter(filterAccounts))
|
||||
});
|
||||
|
||||
app.post("/prepare", upload.single("file"), async (req, res) => {
|
||||
|
||||
@@ -11,6 +11,7 @@ export type ProfileConfig = {
|
||||
encoding?: string;
|
||||
config?: ParserConfig;
|
||||
csv?: Record<string, unknown>;
|
||||
supportedAccounts?: string[];
|
||||
};
|
||||
|
||||
export type ParserConfig = {
|
||||
|
||||
@@ -7,5 +7,5 @@ buildNpmPackage {
|
||||
pname = "actual-importer-frontend";
|
||||
version = "0.0.1";
|
||||
src = ./.;
|
||||
npmDepsHash = "sha256-/G8OZBAkCuc0LTmpB1v8HTgaWdYd9AJfZTC0/eUQIx0=";
|
||||
npmDepsHash = "sha256-Xh+zpYX8u+wKuvBjGc4hxUI2Ed4tiXKC3zk8kFExBbc=";
|
||||
}
|
||||
|
||||
@@ -79,7 +79,7 @@ export default function PrepareTransactionsPage() {
|
||||
|
||||
// If no "from" filter active, pull the latest 10 transactions
|
||||
if (!debouncedUserFilter.from) {
|
||||
const transactions = await getLatestTransactions(state.server, 10);
|
||||
const transactions = await getLatestTransactions(state.server, 10, state.profile);
|
||||
setExistingTransactions(transactions);
|
||||
return;
|
||||
}
|
||||
@@ -87,7 +87,7 @@ export default function PrepareTransactionsPage() {
|
||||
const start = debouncedUserFilter.from.format("YYYY-MM-DD");
|
||||
const end = (debouncedUserFilter.to ?? dayjs()).format("YYYY-MM-DD");
|
||||
|
||||
const transactions = await getDateRangedTransactions(state.server, start, end);
|
||||
const transactions = await getDateRangedTransactions(state.server, start, end, state.profile);
|
||||
setExistingTransactions(transactions);
|
||||
}, [enabledExistingTransactions, state.server, debouncedUserFilter]);
|
||||
|
||||
|
||||
@@ -40,21 +40,29 @@ export async function submitTransactions(transactions: Transaction[], server: st
|
||||
return data as SubmitResponse;
|
||||
}
|
||||
|
||||
export async function getLatestTransactions(server: string, limit: number = 5): Promise<Transaction[]> {
|
||||
export async function getLatestTransactions(server: string, limit: number = 5, profile?: string): Promise<Transaction[]> {
|
||||
const params = new URLSearchParams();
|
||||
params.append('limit', limit.toString());
|
||||
|
||||
if (profile !== undefined) {
|
||||
params.append('profile', profile);
|
||||
}
|
||||
|
||||
const response = await fetch(`/servers/${server}/transactions?${params.toString()}`);
|
||||
const data = await response.json();
|
||||
return data as Transaction[];
|
||||
}
|
||||
|
||||
export async function getDateRangedTransactions(server: string, start: string, end: string): Promise<Transaction[]> {
|
||||
export async function getDateRangedTransactions(server: string, start: string, end: string, profile?: string): Promise<Transaction[]> {
|
||||
const params = new URLSearchParams();
|
||||
|
||||
params.append('start', start);
|
||||
params.append('end', end);
|
||||
|
||||
if (profile !== undefined) {
|
||||
params.append('profile', profile);
|
||||
}
|
||||
|
||||
const response = await fetch(`/servers/${server}/transactions?${params.toString()}`);
|
||||
const data = await response.json();
|
||||
return data as Transaction[];
|
||||
|
||||
Reference in New Issue
Block a user