mirror of
https://github.com/actualbudget/actual.git
synced 2026-04-30 18:49:32 -05:00
* Migrate setupTests.js to TypeScript with proper types (#6871) * Initial plan * Rename setupTests.js to setupTests.ts and add proper types Co-authored-by: joel-jeremy <20313680+joel-jeremy@users.noreply.github.com> * Extract Size type to avoid duplication Co-authored-by: joel-jeremy <20313680+joel-jeremy@users.noreply.github.com> * Add release note for setupTests TypeScript migration Co-authored-by: joel-jeremy <20313680+joel-jeremy@users.noreply.github.com> * Rename release note file to match PR number 6871 Co-authored-by: joel-jeremy <20313680+joel-jeremy@users.noreply.github.com> --------- Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: joel-jeremy <20313680+joel-jeremy@users.noreply.github.com> * Delete setupTests PR release note * Add refetchOnSync to useTransactions to refetch when a server sync event is emitted * Add release note for useTransactions refetchOnSync feature (#6937) * Initial plan * Add release note for PR 6936 Co-authored-by: joel-jeremy <20313680+joel-jeremy@users.noreply.github.com> --------- Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: joel-jeremy <20313680+joel-jeremy@users.noreply.github.com> * Coderabbit feedback --------- Co-authored-by: Copilot <198982749+Copilot@users.noreply.github.com> Co-authored-by: joel-jeremy <20313680+joel-jeremy@users.noreply.github.com>
140 lines
4.8 KiB
TypeScript
140 lines
4.8 KiB
TypeScript
import React, { useCallback, useMemo, useState } from 'react';
|
|
import { useTranslation } from 'react-i18next';
|
|
|
|
import { send } from 'loot-core/platform/client/fetch';
|
|
import type { Query } from 'loot-core/shared/query';
|
|
import { isPreviewId } from 'loot-core/shared/transactions';
|
|
import type { TransactionEntity } from 'loot-core/types/models';
|
|
|
|
import { TransactionListWithBalances } from '@desktop-client/components/mobile/transactions/TransactionListWithBalances';
|
|
import { SchedulesProvider } from '@desktop-client/hooks/useCachedSchedules';
|
|
import { useDateFormat } from '@desktop-client/hooks/useDateFormat';
|
|
import { useNavigate } from '@desktop-client/hooks/useNavigate';
|
|
import { usePreviewTransactions } from '@desktop-client/hooks/usePreviewTransactions';
|
|
import { getSchedulesQuery } from '@desktop-client/hooks/useSchedules';
|
|
import { useTransactions } from '@desktop-client/hooks/useTransactions';
|
|
import { useTransactionsSearch } from '@desktop-client/hooks/useTransactionsSearch';
|
|
import { collapseModals, pushModal } from '@desktop-client/modals/modalsSlice';
|
|
import * as queries from '@desktop-client/queries';
|
|
import { useDispatch } from '@desktop-client/redux';
|
|
import * as bindings from '@desktop-client/spreadsheet/bindings';
|
|
|
|
export function AllAccountTransactions() {
|
|
const schedulesQuery = useMemo(() => getSchedulesQuery(), []);
|
|
|
|
return (
|
|
<SchedulesProvider query={schedulesQuery}>
|
|
<TransactionListWithPreviews />
|
|
</SchedulesProvider>
|
|
);
|
|
}
|
|
|
|
function TransactionListWithPreviews() {
|
|
const { t } = useTranslation();
|
|
const baseTransactionsQuery = useCallback(
|
|
() => queries.transactions().options({ splits: 'all' }).select('*'),
|
|
[],
|
|
);
|
|
|
|
const [transactionsQuery, setTransactionsQuery] = useState<Query>(
|
|
baseTransactionsQuery(),
|
|
);
|
|
const {
|
|
transactions,
|
|
isPending: isTransactionsLoading,
|
|
isFetchingNextPage: isLoadingMoreTransactions,
|
|
fetchNextPage: fetchMoreTransactions,
|
|
} = useTransactions({
|
|
query: transactionsQuery,
|
|
});
|
|
const { previewTransactions, isLoading: isPreviewTransactionsLoading } =
|
|
usePreviewTransactions();
|
|
|
|
const dateFormat = useDateFormat() || 'MM/dd/yyyy';
|
|
const dispatch = useDispatch();
|
|
const navigate = useNavigate();
|
|
|
|
const { isSearching, search: onSearch } = useTransactionsSearch({
|
|
updateQuery: setTransactionsQuery,
|
|
resetQuery: () => setTransactionsQuery(baseTransactionsQuery()),
|
|
dateFormat,
|
|
});
|
|
|
|
const onOpenTransaction = useCallback(
|
|
(transaction: TransactionEntity) => {
|
|
if (!isPreviewId(transaction.id)) {
|
|
navigate(`/transactions/${transaction.id}`);
|
|
} else {
|
|
dispatch(
|
|
pushModal({
|
|
modal: {
|
|
name: 'scheduled-transaction-menu',
|
|
options: {
|
|
transactionId: transaction.id,
|
|
onPost: async transactionId => {
|
|
const parts = transactionId.split('/');
|
|
await send('schedule/post-transaction', { id: parts[1] });
|
|
dispatch(
|
|
collapseModals({
|
|
rootModalName: 'scheduled-transaction-menu',
|
|
}),
|
|
);
|
|
},
|
|
onSkip: async transactionId => {
|
|
const parts = transactionId.split('/');
|
|
await send('schedule/skip-next-date', { id: parts[1] });
|
|
dispatch(
|
|
collapseModals({
|
|
rootModalName: 'scheduled-transaction-menu',
|
|
}),
|
|
);
|
|
},
|
|
onComplete: async transactionId => {
|
|
const parts = transactionId.split('/');
|
|
await send('schedule/update', {
|
|
schedule: { id: parts[1], completed: true },
|
|
});
|
|
dispatch(
|
|
collapseModals({
|
|
rootModalName: 'scheduled-transaction-menu',
|
|
}),
|
|
);
|
|
},
|
|
},
|
|
},
|
|
}),
|
|
);
|
|
}
|
|
},
|
|
[dispatch, navigate],
|
|
);
|
|
|
|
const balanceBindings = useMemo(
|
|
() => ({
|
|
balance: bindings.allAccountBalance(),
|
|
}),
|
|
[],
|
|
);
|
|
|
|
const transactionsToDisplay = !isSearching
|
|
? // Do not render child transactions in the list, unless searching
|
|
previewTransactions.concat(transactions.filter(t => !t.is_child))
|
|
: transactions;
|
|
|
|
return (
|
|
<TransactionListWithBalances
|
|
isLoading={
|
|
isSearching ? isTransactionsLoading : isPreviewTransactionsLoading
|
|
}
|
|
transactions={transactionsToDisplay}
|
|
balance={balanceBindings.balance}
|
|
isLoadingMore={isLoadingMoreTransactions}
|
|
onLoadMore={fetchMoreTransactions}
|
|
searchPlaceholder={t('Search All Accounts')}
|
|
onSearch={onSearch}
|
|
onOpenTransaction={onOpenTransaction}
|
|
showMakeTransfer
|
|
/>
|
|
);
|
|
}
|