feat: add view detail cash flow transaction.

This commit is contained in:
elforjani13
2021-10-25 17:31:07 +02:00
parent f99b01de3b
commit 0a21c5fa41
19 changed files with 600 additions and 45 deletions

View File

@@ -0,0 +1,40 @@
import React from 'react';
import Icon from 'components/Icon';
import { Button, Classes, NavbarGroup, Intent } from '@blueprintjs/core';
import { FormattedMessage as T } from 'components';
import DashboardActionsBar from 'components/Dashboard/DashboardActionsBar';
import { useCashflowTransactionDrawerContext } from './CashflowTransactionDrawerProvider';
import withAlertsActions from 'containers/Alert/withAlertActions';
import { compose } from 'utils';
/**
* Cashflow transaction drawer action bar.
*/
function CashflowTransactionDrawerActionBar({
// #withAlertsDialog
openAlert,
}) {
const { referenceId } = useCashflowTransactionDrawerContext();
// Handle cashflow transaction delete action.
const handleDeleteCashflowTransaction = () => {
openAlert('account-transaction-delete', { referenceId });
};
return (
<DashboardActionsBar>
<NavbarGroup>
<Button
className={Classes.MINIMAL}
icon={<Icon icon="trash-16" iconSize={16} />}
text={<T id={'delete'} />}
intent={Intent.DANGER}
onClick={handleDeleteCashflowTransaction}
/>
</NavbarGroup>
</DashboardActionsBar>
);
}
export default compose(withAlertsActions)(CashflowTransactionDrawerActionBar);

View File

@@ -0,0 +1,23 @@
import React from 'react';
import 'style/components/Drawers/CashflowTransactionDrawer.scss';
import { DrawerBody } from 'components';
import { CashflowTransactionDrawerProvider } from './CashflowTransactionDrawerProvider';
import CashflowTransactionDrawerDetails from './CashflowTransactionDrawerDetails';
/**
* Cash flow transction drawer content.
*/
export default function CashflowTransactionDrawerContent({
// #ownProp
referenceId,
}) {
return (
<CashflowTransactionDrawerProvider referenceId={referenceId}>
<DrawerBody>
<CashflowTransactionDrawerDetails />
</DrawerBody>
</CashflowTransactionDrawerProvider>
);
}

View File

@@ -0,0 +1,25 @@
import React from 'react';
import { Card } from 'components';
import CashflowTransactionDrawerActionBar from './CashflowTransactionDrawerActionBar';
import CashflowTransactionDrawerHeader from './CashflowTransactionDrawerHeader';
import CashflowTransactionDrawerTable from './CashflowTransactionDrawerTable';
import CashflowTransactionDrawerFooter from './CashflowTransactionDrawerFooter';
/**
* Cashflow transaction view details.
*/
export default function CashflowTransactionDrawerDetails() {
return (
<div className={'cashflow-drawer'}>
<CashflowTransactionDrawerActionBar />
<div className="cashflow-drawer__content">
<Card>
<CashflowTransactionDrawerHeader />
<CashflowTransactionDrawerTable />
<CashflowTransactionDrawerFooter />
</Card>
</div>
</div>
);
}

View File

@@ -0,0 +1,34 @@
import React from 'react';
import { useCashflowTransactionDrawerContext } from './CashflowTransactionDrawerProvider';
import { T, FormatNumber } from '../../../components';
export default function CashflowTransactionDrawerFooter() {
const {
cashflowTransaction: { amount },
} = useCashflowTransactionDrawerContext();
return (
<div className="cashflow-drawer__content-footer">
<div class="total-lines">
<div class="total-lines__line total-lines__line--subtotal">
<div class="title">
<T id={'manual_journal.details.subtotal'} />
</div>
<div class="debit">
<FormatNumber value={amount} />
</div>
<div class="credit">
<FormatNumber value={amount} />
</div>
</div>
<div class="total-lines__line total-lines__line--total">
<div class="title">
<T id={'manual_journal.details.total'} />
</div>
<div class="debit">{amount}</div>
<div class="credit">{amount}</div>
</div>
</div>
</div>
);
}

View File

@@ -0,0 +1,63 @@
import React from 'react';
import { defaultTo } from 'lodash';
import {
DetailsMenu,
DetailItem,
FormatDate,
FormattedMessage as T,
} from 'components';
import { useCashflowTransactionDrawerContext } from './CashflowTransactionDrawerProvider';
/**
* Cashlflow transaction drawer detail Header.
*/
export default function CashflowTransactionDrawerHeader() {
const {
cashflowTransaction: {
amount,
transaction_type,
transaction_number,
reference_no,
date,
description,
},
} = useCashflowTransactionDrawerContext();
return (
<div className={'cashflow-drawer__content-header'}>
<DetailsMenu>
<DetailItem name={'total'} label={<T id={'total'} />}>
<h3 class="amount">{amount}</h3>
</DetailItem>
<DetailItem
name={'transaction_type'}
label={<T id={'cash_flow_drawer.label_transaction_type'} />}
>
{transaction_type}
</DetailItem>
<DetailItem
name={'transaction_number'}
label={<T id={'cash_flow.drawer.label_transaction_no'} />}
>
{transaction_number}
</DetailItem>
<DetailItem
label={<T id={'date'} />}
children={<FormatDate value={date} />}
/>
<DetailItem name={'reference-no'} label={<T id={'reference_no'} />}>
{defaultTo(reference_no, '-')}
</DetailItem>
</DetailsMenu>
<div class="cashflow-drawer__content-description">
<b class="title">
<T id={'description'} />
</b>
: {defaultTo(description, '—')}
</div>
</div>
);
}

View File

@@ -0,0 +1,50 @@
import React from 'react';
import intl from 'react-intl-universal';
import { useCashflowTransaction } from 'hooks/query';
import { DrawerLoading, DrawerHeaderContent } from 'components';
const CashflowTransactionDrawerContext = React.createContext();
/**
* Cashflow transaction drawer provider.
*/
function CashflowTransactionDrawerProvider({ referenceId, ...props }) {
// Fetch the specific cashflow transaction details.
const {
data: cashflowTransaction,
isLoading: isCashflowTransactionLoading,
isFetching: isCashflowTransactionFetching,
} = useCashflowTransaction(referenceId, {
enabled: !!referenceId,
});
// Provider.
const provider = {
referenceId,
cashflowTransaction,
isCashflowTransactionFetching,
isCashflowTransactionLoading,
};
return (
<DrawerLoading loading={isCashflowTransactionLoading}>
<DrawerHeaderContent
name={'cashflow-transaction-drawer'}
title={intl.get('cash_flow.drawer.label_transaction', {
number: cashflowTransaction?.transaction_number,
})}
/>
<CashflowTransactionDrawerContext.Provider value={provider} {...props} />
</DrawerLoading>
);
}
const useCashflowTransactionDrawerContext = () =>
React.useContext(CashflowTransactionDrawerContext);
export {
CashflowTransactionDrawerProvider,
useCashflowTransactionDrawerContext,
};

View File

@@ -0,0 +1,22 @@
import React from 'react';
import { DataTable, If, FormattedMessage as T } from 'components';
import { useCashflowTransactionColumns } from './utils';
import { useCashflowTransactionDrawerContext } from './CashflowTransactionDrawerProvider';
/**
* Cashflow transaction drawer table.
*/
export default function CashflowTransactionDrawerTable() {
const columns = useCashflowTransactionColumns();
const {
cashflowTransaction: { transactions },
} = useCashflowTransactionDrawerContext();
return (
<div className="cashflow-drawer__content-table">
<DataTable columns={columns} data={transactions} />
</div>
);
}

View File

@@ -0,0 +1,35 @@
import React from 'react';
import { Drawer, DrawerSuspense } from 'components';
import withDrawers from 'containers/Drawer/withDrawers';
import { compose } from 'utils';
const CashFlowTransactionDrawerContent = React.lazy(() =>
import('./CashflowTransactionDrawerContent'),
);
/**
* Cash flow transaction drawer
*/
function CashflowTransactionDetailDrawer({
name,
// #withDrawer
isOpen,
payload: { referenceId },
}) {
return (
<Drawer
isOpen={isOpen}
name={name}
size={'65%'}
style={{ minWidth: '700px', maxWidth: '900px' }}
>
<DrawerSuspense>
<CashFlowTransactionDrawerContent referenceId={referenceId} />
</DrawerSuspense>
</Drawer>
);
}
export default compose(withDrawers())(CashflowTransactionDetailDrawer);

View File

@@ -0,0 +1,76 @@
import intl from 'react-intl-universal';
import React from 'react';
import { Classes, Tooltip, Position } from '@blueprintjs/core';
import { FormatNumberCell, If, Icon } from '../../../components';
/**
* Note column accessor.
*/
export function NoteAccessor(row) {
return (
<If condition={row.note}>
<Tooltip
className={Classes.TOOLTIP_INDICATOR}
content={row.note}
position={Position.LEFT_TOP}
hoverOpenDelay={50}
>
<Icon icon={'file-alt'} iconSize={16} />
</Tooltip>
</If>
);
}
/**
* Retrieve cashflow transaction entries columns.
*/
export const useCashflowTransactionColumns = () =>
React.useMemo(
() => [
{
Header: intl.get('account_name'),
accessor: 'account.name',
width: 130,
disableSortBy: true,
className: 'account',
},
{
Header: intl.get('contact'),
accessor: 'contact.display_name',
width: 130,
disableSortBy: true,
className: 'contact',
},
{
Header: intl.get('note'),
accessor: NoteAccessor,
width: 80,
disableSortBy: true,
className: 'note',
},
{
Header: intl.get('credit'),
accessor: 'credit',
Cell: FormatNumberCell,
width: 100,
disableResizable: true,
disableSortBy: true,
formatNumber: { noZero: true },
className: 'credit',
align: 'right',
},
{
Header: intl.get('debit'),
accessor: 'debit',
Cell: FormatNumberCell,
width: 100,
disableResizable: true,
disableSortBy: true,
formatNumber: { noZero: true },
className: 'debit',
align: 'right',
},
],
[],
);