re-structure to monorepo.

This commit is contained in:
a.bouhuolia
2023-02-03 01:02:31 +02:00
parent 8242ec64ba
commit 7a0a13f9d5
10400 changed files with 46966 additions and 17223 deletions

View File

@@ -0,0 +1,17 @@
// @ts-nocheck
import React from 'react';
import ItemDetailTab from './ItemDetailTab';
import ItemDetailActionsBar from './ItemDetailActionsBar';
/**
* Item detail.
*/
export default function ItemDetail() {
return (
<div className="item-drawer">
<ItemDetailActionsBar />
<ItemDetailTab />
</div>
);
}

View File

@@ -0,0 +1,82 @@
// @ts-nocheck
import React from 'react';
import { useHistory } from 'react-router-dom';
import {
Button,
NavbarGroup,
Classes,
NavbarDivider,
Intent,
} from '@blueprintjs/core';
import { useItemDetailDrawerContext } from './ItemDetailDrawerProvider';
import { ItemAction, AbilitySubject } from '@/constants/abilityOption';
import withAlertsActions from '@/containers/Alert/withAlertActions';
import withDrawerActions from '@/containers/Drawer/withDrawerActions';
import {
DashboardActionsBar,
Icon,
FormattedMessage as T,
Can,
} from '@/components';
import { compose } from '@/utils';
/**
* Item action-bar of readonly details drawer.
*/
function ItemDetailActionsBar({
// #withAlertsActions
openAlert,
// #withDrawerActions
closeDrawer,
}) {
// Item readonly drawer context.
const { itemId } = useItemDetailDrawerContext();
const history = useHistory();
// Handle edit item.
const handleEditItem = () => {
history.push(`/items/${itemId}/edit`);
closeDrawer('item-detail-drawer');
};
// Handle delete item.
const handleDeleteItem = () => {
openAlert('item-delete', { itemId });
};
return (
<DashboardActionsBar>
<NavbarGroup>
<Can I={ItemAction.Edit} a={AbilitySubject.Item}>
<Button
className={Classes.MINIMAL}
icon={<Icon icon="pen-18" />}
text={<T id={'edit_item'} />}
onClick={handleEditItem}
/>
</Can>
<Can I={ItemAction.Delete} a={AbilitySubject.Item}>
<NavbarDivider />
<Button
className={Classes.MINIMAL}
icon={<Icon icon={'trash-16'} iconSize={16} />}
text={<T id={'delete'} />}
intent={Intent.DANGER}
onClick={handleDeleteItem}
/>
</Can>
</NavbarGroup>
</DashboardActionsBar>
);
}
export default compose(
withDrawerActions,
withAlertsActions,
)(ItemDetailActionsBar);

View File

@@ -0,0 +1,24 @@
// @ts-nocheck
import React from 'react';
import '@/style/components/Drawers/ItemDrawer.scss';
import { DrawerBody } from '@/components';
import ItemContentDetails from './ItemContentDetails';
import { ItemDetailDrawerProvider } from './ItemDetailDrawerProvider';
/**
* Item detail drawer content.
*/
export default function ItemDetailDrawerContent({
// #ownProp
itemId,
}) {
return (
<ItemDetailDrawerProvider itemId={itemId}>
<DrawerBody>
<ItemContentDetails />
</DrawerBody>
</ItemDetailDrawerProvider>
);
}

View File

@@ -0,0 +1,43 @@
// @ts-nocheck
import React from 'react';
import { DrawerHeaderContent, DrawerLoading } from '@/components';
import { useItem } from '@/hooks/query';
import { inactiveStatus } from './utlis';
const ItemDetailDrawerContext = React.createContext();
/**
* Item detail provider
*/
function ItemDetailDrawerProvider({ itemId, ...props }) {
// transaction type payload.
const [value, setValue] = React.useState('invoices');
// Fetches the given item detail.
const { isLoading: isItemLoading, data: item } = useItem(itemId, {
enabled: !!itemId,
});
//provider.
const provider = {
item,
itemId,
isItemLoading,
value,
setValue,
};
return (
<DrawerLoading loading={isItemLoading}>
<DrawerHeaderContent
name="item-detail-drawer"
title={inactiveStatus(item)}
/>
<ItemDetailDrawerContext.Provider value={provider} {...props} />
</DrawerLoading>
);
}
const useItemDetailDrawerContext = () =>
React.useContext(ItemDetailDrawerContext);
export { ItemDetailDrawerProvider, useItemDetailDrawerContext };

View File

@@ -0,0 +1,88 @@
// @ts-nocheck
import React from 'react';
import intl from 'react-intl-universal';
import classNames from 'classnames';
import { defaultTo } from 'lodash';
import { If, DetailsMenu, DetailItem, Card } from '@/components';
import { useItemDetailDrawerContext } from './ItemDetailDrawerProvider';
/**
* Item header drawer of readonly details.
*/
export default function ItemDetailHeader() {
const { item } = useItemDetailDrawerContext();
return (
<Card>
<div class="item-drawer__content">
<DetailsMenu direction={'vertical'}>
<DetailItem
name={'name'}
label={intl.get('item_name')}
children={item.name}
/>
<DetailItem
label={intl.get('sell_price')}
children={item.sell_price_formatted}
align={'right'}
/>
<DetailItem
label={intl.get('cost_price')}
children={item.cost_price_formatted}
align={'right'}
/>
</DetailsMenu>
<DetailsMenu direction={'horizantal'}>
<DetailItem
label={intl.get('item_type')}
children={item.type_formatted}
/>
<DetailItem
label={intl.get('item_code')}
children={defaultTo(item.code, '-')}
/>
<If condition={item.type === 'inventory'}>
<DetailItem name={'quantity'} label={intl.get('quantity_on_hand')}>
<span
className={classNames({
mines: item.quantity_on_hand <= 0,
plus: item.quantity_on_hand > 0,
})}
>
{defaultTo(item.quantity_on_hand, '-')}
</span>
</DetailItem>
</If>
<DetailItem
label={intl.get('category_name')}
children={defaultTo(item.category?.name, '-')}
/>
<DetailItem
label={intl.get('sell_account_id')}
children={defaultTo(item?.sell_account?.name, '-')}
/>
<DetailItem
label={intl.get('cost_account_id')}
children={defaultTo(item.cost_account?.name, '-')}
/>
<If condition={item.type === 'inventory'}>
<DetailItem
label={intl.get('inventory_account')}
children={defaultTo(item?.inventory_account?.name, '-')}
/>
</If>
<DetailItem
label={intl.get('item.sell_description')}
children={defaultTo(item.sell_description, '-')}
/>
<DetailItem
label={intl.get('item.purchase_description')}
children={defaultTo(item.purchase_description, '-')}
/>
</DetailsMenu>
</div>
</Card>
);
}

View File

@@ -0,0 +1,37 @@
// @ts-nocheck
import React from 'react';
import { Tab } from '@blueprintjs/core';
import { DrawerMainTabs, FormattedMessage as T } from '@/components';
import { ItemPaymentTransactions } from './ItemPaymentTransactions';
import ItemDetailHeader from './ItemDetailHeader';
import WarehousesLocationsTable from './WarehousesLocations';
import { Features } from '@/constants';
import { useFeatureCan } from '@/hooks/state';
export default function ItemDetailTab() {
const { featureCan } = useFeatureCan();
return (
<DrawerMainTabs renderActiveTabPanelOnly={true}>
<Tab
id={'overview'}
title={<T id={'overview'} />}
panel={<ItemDetailHeader />}
/>
<Tab
id={'transactions'}
title={<T id={'transactions'} />}
panel={<ItemPaymentTransactions />}
/>
{featureCan(Features.Warehouses) && (
<Tab
id={'warehouses'}
title={<T id={'warehouse_locations.label'} />}
panel={<WarehousesLocationsTable />}
/>
)}
</DrawerMainTabs>
);
}

View File

@@ -0,0 +1,98 @@
// @ts-nocheck
import React from 'react';
import intl from 'react-intl-universal';
import clsx from 'classnames';
import { Intent, Menu, MenuItem, MenuDivider } from '@blueprintjs/core';
import { CLASSES } from '@/constants/classes';
import { Can, FormatDateCell, Icon } from '@/components';
import { safeCallback } from '@/utils';
import { BillAction, AbilitySubject } from '@/constants/abilityOption';
/**
* Table actions menu.
*/
export function ActionsMenu({
row: { original },
payload: { onEdit, onDelete },
}) {
return (
<Menu>
<Can I={BillAction.Edit} a={AbilitySubject.Bill}>
<MenuItem
icon={<Icon icon="pen-18" />}
text={intl.get('invoice_transactions.action.edit_transaction')}
onClick={safeCallback(onEdit, original)}
/>
</Can>
<Can I={BillAction.Delete} a={AbilitySubject.Bill}>
<MenuDivider />
<MenuItem
text={intl.get('invoice_transactions.action.delete_transaction')}
intent={Intent.DANGER}
onClick={safeCallback(onDelete, original)}
icon={<Icon icon="trash-16" iconSize={16} />}
/>
</Can>
</Menu>
);
}
/**
* Retrieve bill transactions associated with item table columns.
*/
export const useBillTransactionsColumns = () => {
return React.useMemo(
() => [
{
id: 'bill_date',
Header: intl.get('date'),
accessor: 'formatted_bill_date',
Cell: FormatDateCell,
width: 120,
className: 'bill_date',
},
{
id: 'vendor',
Header: intl.get('vendor'),
accessor: 'vendor_display_name',
width: 140,
className: 'vendor',
textOverview: true,
},
{
id: 'bill_number',
Header: intl.get('bill_number'),
accessor: (row) => (row.bill_number ? `${row.bill_number}` : null),
width: 100,
className: 'bill_number',
},
{
id: 'qunatity',
Header: intl.get('item.drawer_quantity_sold'),
accessor: 'quantity',
align: 'right',
width: 100,
},
{
id: 'rate',
Header: 'Rate',
accessor: 'formatted_rate',
align: 'right',
width: 100,
className: clsx(CLASSES.FONT_BOLD),
textOverview: true,
},
{
id: 'amount',
Header: intl.get('total'),
accessor: 'formatted_amount',
align: 'right',
width: 100,
className: clsx(CLASSES.FONT_BOLD),
textOverview: true,
},
],
[],
);
};

View File

@@ -0,0 +1,74 @@
// @ts-nocheck
import React from 'react';
import { useHistory } from 'react-router-dom';
import { DataTable, TableSkeletonRows } from '@/components';
import { TableStyle } from '@/constants';
import { useItemDetailDrawerContext } from '../../ItemDetailDrawerProvider';
import { useItemAssociatedBillTransactions } from '@/hooks/query';
import { useBillTransactionsColumns, ActionsMenu } from './components';
import withAlertsActions from '@/containers/Alert/withAlertActions';
import withDrawerActions from '@/containers/Drawer/withDrawerActions';
import { compose } from '@/utils';
/**
* Bill payment transactions data table.
*/
function BillPaymentTransactions({
// #withAlertsActions
openAlert,
// #withDrawerActions
closeDrawer,
}) {
const history = useHistory();
const columns = useBillTransactionsColumns();
const { itemId } = useItemDetailDrawerContext();
// Handle fetch Estimate associated transactions.
const {
isLoading: isBillTransactionsLoading,
isFetching: isBillTransactionFetching,
data: paymentTransactions,
} = useItemAssociatedBillTransactions(itemId, {
enabled: !!itemId,
});
// Handles delete payment transactions.
const handleDeletePaymentTransactons = ({ bill_id }) => {
openAlert('bill-delete', {
billId: bill_id,
});
};
// Handles edit payment transactions.
const handleEditPaymentTransactions = ({ bill_id }) => {
history.push(`/bills/${bill_id}/edit`);
closeDrawer('item-detail-drawer');
};
return (
<DataTable
columns={columns}
data={paymentTransactions}
loading={isBillTransactionsLoading}
headerLoading={isBillTransactionsLoading}
progressBarLoading={isBillTransactionFetching}
ContextMenu={ActionsMenu}
payload={{
onEdit: handleEditPaymentTransactions,
onDelete: handleDeletePaymentTransactons,
}}
styleName={TableStyle.Constrant}
TableLoadingRenderer={TableSkeletonRows}
sticky={true}
/>
);
}
export default compose(
withAlertsActions,
withDrawerActions,
)(BillPaymentTransactions);

View File

@@ -0,0 +1,100 @@
// @ts-nocheck
import React from 'react';
import intl from 'react-intl-universal';
import { Intent, Menu, MenuItem, MenuDivider } from '@blueprintjs/core';
import clsx from 'classnames';
import { safeCallback } from '@/utils';
import { CLASSES } from '@/constants/classes';
import { Can, FormatDateCell, Icon } from '@/components';
import { SaleEstimateAction, AbilitySubject } from '@/constants/abilityOption';
/**
* Table actions menu.
*/
export function ActionsMenu({
row: { original },
payload: { onEdit, onDelete },
}) {
return (
<Menu>
<Can I={SaleEstimateAction.Edit} a={AbilitySubject.Estimate}>
<MenuItem
icon={<Icon icon="pen-18" />}
text={intl.get('invoice_transactions.action.edit_transaction')}
onClick={safeCallback(onEdit, original)}
/>
</Can>
<Can I={SaleEstimateAction.Delete} a={AbilitySubject.Estimate}>
<MenuDivider />
<MenuItem
text={intl.get('invoice_transactions.action.delete_transaction')}
intent={Intent.DANGER}
onClick={safeCallback(onDelete, original)}
icon={<Icon icon="trash-16" iconSize={16} />}
/>
</Can>
</Menu>
);
}
/**
* Retrieve estimate transactions associated with item table columns.
*/
export const useEstimateTransactionsColumns = () => {
return React.useMemo(
() => [
{
id: 'estimate_date',
Header: intl.get('date'),
accessor: 'formatted_estimate_date',
Cell: FormatDateCell,
width: 120,
className: 'estimate_date',
textOverview: true,
},
{
id: 'customer',
Header: intl.get('customer'),
accessor: 'customer_display_name',
width: 140,
className: 'customer',
textOverview: true,
},
{
id: 'estimate_number',
Header: intl.get('estimate_no'),
accessor: 'estimate_number',
width: 120,
className: 'estimate_number',
textOverview: true,
},
{
id: 'qunatity',
Header: intl.get('item.drawer_quantity_sold'),
accessor: 'quantity',
align: 'right',
width: 100,
},
{
id: 'rate',
Header: 'Rate',
accessor: 'formatted_rate',
align: 'right',
width: 100,
className: clsx(CLASSES.FONT_BOLD),
textOverview: true,
},
{
id: 'amount',
Header: intl.get('total'),
accessor: 'formatted_amount',
align: 'right',
width: 100,
className: clsx(CLASSES.FONT_BOLD),
textOverview: true,
},
],
[],
);
};

View File

@@ -0,0 +1,76 @@
// @ts-nocheck
import React from 'react';
import { useHistory } from 'react-router-dom';
import { DataTable, TableSkeletonRows } from '@/components';
import { TableStyle } from '@/constants';
import { useItemDetailDrawerContext } from '../../ItemDetailDrawerProvider';
import { useItemAssociatedEstimateTransactions } from '@/hooks/query';
import { useEstimateTransactionsColumns, ActionsMenu } from './components';
import withAlertsActions from '@/containers/Alert/withAlertActions';
import withDrawerActions from '@/containers/Drawer/withDrawerActions';
import { compose } from '@/utils';
/**
* Esimtate payment transactions.
*/
function EstimatePaymentTransactions({
// #withAlertsActions
openAlert,
// #withDrawerActions
closeDrawer,
}) {
const history = useHistory();
const columns = useEstimateTransactionsColumns();
const { itemId } = useItemDetailDrawerContext();
// Handle fetch Estimate associated transactions.
const {
isLoading: isEstimateTransactionsLoading,
isFetching: isEstimateTransactionFetching,
data: paymentTransactions,
} = useItemAssociatedEstimateTransactions(itemId, {
enabled: !!itemId,
});
// Handles delete payment transactions.
const handleDeletePaymentTransactons = ({ estimate_id }) => {
openAlert('estimate-delete', {
estimateId: estimate_id,
});
};
// Handles edit payment transactions.
const handleEditPaymentTransactions = ({ estimate_id }) => {
history.push(`/estimates/${estimate_id}/edit`);
closeDrawer('item-detail-drawer');
};
return (
<DataTable
columns={columns}
data={paymentTransactions}
loading={isEstimateTransactionsLoading}
headerLoading={isEstimateTransactionsLoading}
progressBarLoading={isEstimateTransactionFetching}
ContextMenu={ActionsMenu}
payload={{
onEdit: handleEditPaymentTransactions,
onDelete: handleDeletePaymentTransactons,
}}
styleName={TableStyle.Constrant}
TableLoadingRenderer={TableSkeletonRows}
sticky={true}
/>
);
}
export default compose(
withAlertsActions,
withDrawerActions,
)(EstimatePaymentTransactions);

View File

@@ -0,0 +1,100 @@
// @ts-nocheck
import React from 'react';
import intl from 'react-intl-universal';
import { Intent, Menu, MenuItem, MenuDivider } from '@blueprintjs/core';
import clsx from 'classnames';
import { CLASSES } from '@/constants/classes';
import { Can, FormatDateCell, Icon } from '@/components';
import { safeCallback } from '@/utils';
import { SaleInvoiceAction, AbilitySubject } from '@/constants/abilityOption';
/**
* Table actions menu.
*/
export function ActionsMenu({
row: { original },
payload: { onEdit, onDelete },
}) {
return (
<Menu>
<Can I={SaleInvoiceAction.Edit} a={AbilitySubject.Invoice}>
<MenuItem
icon={<Icon icon="pen-18" />}
text={intl.get('invoice_transactions.action.edit_transaction')}
onClick={safeCallback(onEdit, original)}
/>
</Can>
<Can I={SaleInvoiceAction.Delete} a={AbilitySubject.Invoice}>
<MenuDivider />
<MenuItem
text={intl.get('invoice_transactions.action.delete_transaction')}
intent={Intent.DANGER}
onClick={safeCallback(onDelete, original)}
icon={<Icon icon="trash-16" iconSize={16} />}
/>
</Can>
</Menu>
);
}
/**
* Retrieve invoice payment transactions associated with item table columns.
*/
export const useInvoicePaymentTransactionsColumns = () => {
return React.useMemo(
() => [
{
id: 'invoice_date',
Header: intl.get('date'),
accessor: 'formatted_invoice_date',
Cell: FormatDateCell,
width: 120,
className: 'invoice_date',
textOverview: true,
},
{
id: 'customer',
Header: intl.get('customer'),
accessor: 'customer_display_name',
width: 140,
className: 'customer',
textOverview: true,
},
{
id: 'invoice_no',
Header: intl.get('invoice_no__'),
accessor: 'invoice_number',
width: 120,
className: 'invoice_no',
textOverview: true,
},
{
id: 'qunatity',
Header: intl.get('item.drawer_quantity_sold'),
accessor: 'quantity',
align: 'right',
width: 100,
},
{
id: 'rate',
Header: intl.get('rate'),
accessor: 'formatted_rate',
align: 'right',
width: 100,
className: clsx(CLASSES.FONT_BOLD),
textOverview: true,
},
{
id: 'amount',
Header: intl.get('total'),
accessor: 'formatted_amount',
align: 'right',
width: 100,
className: clsx(CLASSES.FONT_BOLD),
textOverview: true,
},
],
[],
);
};

View File

@@ -0,0 +1,79 @@
// @ts-nocheck
import React from 'react';
import { useHistory } from 'react-router-dom';
import { DataTable, TableSkeletonRows } from '@/components';
import { useItemAssociatedInvoiceTransactions } from '@/hooks/query';
import { useItemDetailDrawerContext } from '../../ItemDetailDrawerProvider';
import {
useInvoicePaymentTransactionsColumns,
ActionsMenu,
} from './components';
import { TableStyle } from '@/constants';
import withAlertsActions from '@/containers/Alert/withAlertActions';
import withDrawerActions from '@/containers/Drawer/withDrawerActions';
import { compose } from '@/utils';
/**
* Invoice payment transactions.
*/
function InvoicePaymentTransactions({
// #withAlertsActions
openAlert,
// #withDrawerActions
closeDrawer,
}) {
const history = useHistory();
const columns = useInvoicePaymentTransactionsColumns();
const { itemId } = useItemDetailDrawerContext();
// Handle fetch invoice associated transactions.
const {
isLoading: isInvoiceTransactionsLoading,
isFetching: isInvoiceTransactionFetching,
data: paymentTransactions,
} = useItemAssociatedInvoiceTransactions(itemId, {
enabled: !!itemId,
});
// Handles delete payment transactions.
const handleDeletePaymentTransactons = ({ invoice_id }) => {
openAlert('invoice-delete', {
invoiceId: invoice_id,
});
};
// Handles edit payment transactions.
const handleEditPaymentTransactions = ({ invoice_id }) => {
history.push(`/invoices/${invoice_id}/edit`);
closeDrawer('item-detail-drawer');
};
return (
<DataTable
columns={columns}
data={paymentTransactions}
loading={isInvoiceTransactionsLoading}
headerLoading={isInvoiceTransactionsLoading}
progressBarLoading={isInvoiceTransactionFetching}
ContextMenu={ActionsMenu}
payload={{
onEdit: handleEditPaymentTransactions,
onDelete: handleDeletePaymentTransactons,
}}
styleName={TableStyle.Constrant}
TableLoadingRenderer={TableSkeletonRows}
sticky={true}
/>
);
}
export default compose(
withAlertsActions,
withDrawerActions,
)(InvoicePaymentTransactions);

View File

@@ -0,0 +1,23 @@
// @ts-nocheck
import React from 'react';
import InvoicePaymentTransactions from './InvoicePaymentTransactions';
import EstimatePaymentTransactions from './EstimatePaymentTransactions';
import ReceiptPaymentTransactions from './ReceiptPaymentTransactions';
import BillPaymentTransactions from './BillPaymentTransactions';
export default function ItemPaymentTransactionsContent({ tansactionType }) {
const handleType = () => {
switch (tansactionType) {
case 'invoices':
default:
return <InvoicePaymentTransactions />;
case 'estimates':
return <EstimatePaymentTransactions />;
case 'receipts':
return <ReceiptPaymentTransactions />;
case 'bills':
return <BillPaymentTransactions />;
}
};
return handleType();
}

View File

@@ -0,0 +1,101 @@
// @ts-nocheck
import React from 'react';
import intl from 'react-intl-universal';
import { Intent, Menu, MenuItem, MenuDivider } from '@blueprintjs/core';
import clsx from 'classnames';
import { safeCallback } from '@/utils';
import { CLASSES } from '@/constants/classes';
import { Can, FormatDateCell, Icon } from '@/components';
import { SaleReceiptAction, AbilitySubject } from '@/constants/abilityOption';
/**
* Table actions menu.
*/
export function ActionsMenu({
row: { original },
payload: { onEdit, onDelete },
}) {
return (
<Menu>
<Can I={SaleReceiptAction.Edit} a={AbilitySubject.Receipt}>
<MenuItem
icon={<Icon icon="pen-18" />}
text={intl.get('invoice_transactions.action.edit_transaction')}
onClick={safeCallback(onEdit, original)}
/>
</Can>
<Can I={SaleReceiptAction.Edit} a={AbilitySubject.Receipt}>
<MenuDivider />
<MenuItem
text={intl.get('invoice_transactions.action.delete_transaction')}
intent={Intent.DANGER}
onClick={safeCallback(onDelete, original)}
icon={<Icon icon="trash-16" iconSize={16} />}
/>
</Can>
</Menu>
);
}
/**
* Retrieve receipt transactions associated with item table columns.
*/
export const useReceiptTransactionsColumns = () => {
return React.useMemo(
() => [
{
id: 'receipt_date',
Header: intl.get('date'),
accessor: 'formatted_receipt_date',
Cell: FormatDateCell,
width: 120,
className: 'receipt_date',
textOverview: true,
},
{
id: 'customer',
Header: intl.get('customer'),
accessor: 'customer_display_name',
width: 140,
className: 'customer',
textOverview: true,
},
{
id: 'receipt_number',
Header: intl.get('receipt_no'),
accessor: 'receip_number',
width: 120,
className: 'receipt_number',
clickable: true,
textOverview: true,
},
{
id: 'qunatity',
Header: intl.get('item.drawer_quantity_sold'),
accessor: 'quantity',
align: 'right',
width: 100,
},
{
id: 'rate',
Header: 'Rate',
accessor: 'formatted_rate',
align: 'right',
width: 100,
className: clsx(CLASSES.FONT_BOLD),
textOverview: true,
},
{
id: 'amount',
Header: intl.get('total'),
accessor: 'formatted_amount',
align: 'right',
width: 100,
className: clsx(CLASSES.FONT_BOLD),
textOverview: true,
},
],
[],
);
};

View File

@@ -0,0 +1,76 @@
// @ts-nocheck
import React from 'react';
import { useHistory } from 'react-router-dom';
import { TableStyle } from '@/constants';
import { DataTable, TableSkeletonRows } from '@/components';
import { useItemDetailDrawerContext } from '../../ItemDetailDrawerProvider';
import { useItemAssociatedReceiptTransactions } from '@/hooks/query';
import { useReceiptTransactionsColumns, ActionsMenu } from './components';
import withAlertsActions from '@/containers/Alert/withAlertActions';
import withDrawerActions from '@/containers/Drawer/withDrawerActions';
import { compose } from '@/utils';
/**
* Receipt payment transactions.
*/
function ReceiptPaymentTransactions({
// #withAlertsActions
openAlert,
// #withDrawerActions
closeDrawer,
}) {
const history = useHistory();
const columns = useReceiptTransactionsColumns();
const { itemId } = useItemDetailDrawerContext();
// Handle fetch receipts associated transactions.
const {
isLoading: isReceiptTransactionsLoading,
isFetching: isReceiptTransactionFetching,
data: paymentTransactions,
} = useItemAssociatedReceiptTransactions(itemId, {
enabled: !!itemId,
});
// Handles delete payment transactions.
const handleDeletePaymentTransactons = ({ receipt_id }) => {
openAlert('receipt-delete', {
receiptId: receipt_id,
});
};
// Handles edit payment transactions.
const handleEditPaymentTransactions = ({ receipt_id }) => {
history.push(`/receipts/${receipt_id}/edit`);
closeDrawer('item-detail-drawer');
};
return (
<DataTable
columns={columns}
data={paymentTransactions}
loading={isReceiptTransactionsLoading}
headerLoading={isReceiptTransactionsLoading}
progressBarLoading={isReceiptTransactionFetching}
ContextMenu={ActionsMenu}
payload={{
onEdit: handleEditPaymentTransactions,
onDelete: handleDeletePaymentTransactons,
}}
styleName={TableStyle.Constrant}
TableLoadingRenderer={TableSkeletonRows}
sticky={true}
/>
);
}
export default compose(
withAlertsActions,
withDrawerActions,
)(ReceiptPaymentTransactions);

View File

@@ -0,0 +1,43 @@
// @ts-nocheck
import React from 'react';
import styled from 'styled-components';
import { Card } from '@/components';
import { ItemManuTransaction } from './utils';
import ItemPaymentTransactionContent from './ItemPaymentTransactionContent';
import { useItemDetailDrawerContext } from '../ItemDetailDrawerProvider';
export function ItemPaymentTransactions() {
const { value } = useItemDetailDrawerContext();
return (
<Card>
<ItemTransactionsHeader />
<ItemPaymentTransactionContent tansactionType={value} />
</Card>
);
}
/**
* Item transactions header.
* @returns {React.JSX}
*/
export function ItemTransactionsHeader() {
const { setValue } = useItemDetailDrawerContext();
// handle item change.
const handleItemChange = (item) => {
setValue(item);
};
return (
<ItemTransactionsHeaderRoot>
<ItemManuTransaction onChange={handleItemChange} />
</ItemTransactionsHeaderRoot>
);
}
export const ItemTransactionsHeaderRoot = styled.div`
margin-bottom: 10px;
`;

View File

@@ -0,0 +1,66 @@
// @ts-nocheck
import React from 'react';
import styled from 'styled-components';
import {
Button,
MenuItem,
Menu,
Popover,
PopoverInteractionKind,
Position,
} from '@blueprintjs/core';
import { FormattedMessage as T } from '@/components';
import { useItemDetailDrawerContext } from '../ItemDetailDrawerProvider';
import { useGetItemPaymentTransactionsMenu } from '@/constants/itemPaymentTranactionsOption';
export const ItemManuTransaction = ({ onChange }) => {
const { value, setValue } = useItemDetailDrawerContext();
const itemTransactionMenu = useGetItemPaymentTransactionsMenu();
if (itemTransactionMenu.length === 0) {
return null;
}
const handleClickItem = (item) => {
onChange && onChange(item);
};
const content = itemTransactionMenu.map(({ name, label }) => (
<MenuItem onClick={() => handleClickItem(name)} text={label} />
));
return (
<Popover
minimal={true}
interactionKind={PopoverInteractionKind.CLICK}
position={Position.BOTTOM_LEFT}
modifiers={{
offset: { offset: '0, 4' },
}}
content={<Menu>{content}</Menu>}
>
<ItemSwitchButton
minimal={true}
text={<T id={'item.drawer_transactions_by'} />}
rightIcon={'caret-down'}
>
<ItemSwitchText>
<T id={value} />
</ItemSwitchText>
</ItemSwitchButton>
</Popover>
);
};
const ItemSwitchButton = styled(Button)`
.bp3-button-text {
display: flex;
color: #727983;
}
`;
const ItemSwitchText = styled.span`
font-weight: 600;
color: #33304a;
padding-left: 3px;
`;

View File

@@ -0,0 +1,41 @@
// @ts-nocheck
import React from 'react';
import intl from 'react-intl-universal';
import { FormatNumberCell, FormattedMessage as T } from '@/components';
/**
* Warehouse locations columns
*/
export const useWarehouseLocationsColumns = () => {
return React.useMemo(
() => [
{
id: 'warehouse_name',
accessor: 'warehouse_name',
Header: intl.get('warehouse_locations.column.warehouse_name'),
width: 120,
},
{
id: 'warehouse_code',
accessor: 'warehouse_code',
Header: intl.get('warehouse_locations.column.warehouse_code'),
width: 100,
},
{
id: 'quantity',
accessor: 'quantity_on_hand_formatted',
Header: intl.get('warehouse_locations.column.quantity'),
Cell: FormatNumberCell,
align: 'right',
width: 100,
},
{
id: 'available_for_sale',
Header: intl.get('warehouse_locations.column.available_for_sale'),
align: 'right',
width: 100,
},
],
[],
);
};

View File

@@ -0,0 +1,41 @@
// @ts-nocheck
import React from 'react';
import styled from 'styled-components';
import { TableStyle } from '@/constants';
import { DataTable, TableSkeletonRows, Card } from '@/components';
import { useItemDetailDrawerContext } from '../ItemDetailDrawerProvider';
import { useWarehouseLocationsColumns } from './components';
import { useItemWarehouseLocation } from '@/hooks/query';
/**
* Warehouses locations table columns.
*/
export default function WarehouseLocationsTable() {
// Warehouses locations table columns.
const columns = useWarehouseLocationsColumns();
const { itemId } = useItemDetailDrawerContext();
// Handle fetch Estimate associated transactions.
const {
isLoading: isItemWarehousesLoading,
isFetching: isItemWarehousesFetching,
data: itemWarehouses,
} = useItemWarehouseLocation(itemId, { enabled: !!itemId });
return (
<WarehouseLocationsGLEntriesRoot>
<DataTable
columns={columns}
data={itemWarehouses}
headerLoading={isItemWarehousesLoading}
progressBarLoading={isItemWarehousesFetching}
TableLoadingRenderer={TableSkeletonRows}
styleName={TableStyle.Constrant}
/>
</WarehouseLocationsGLEntriesRoot>
);
}
const WarehouseLocationsGLEntriesRoot = styled(Card)``;

View File

@@ -0,0 +1,35 @@
// @ts-nocheck
import React from 'react';
import { Drawer, DrawerSuspense } from '@/components';
import withDrawers from '@/containers/Drawer/withDrawers';
import { compose } from '@/utils';
const ItemDetailDrawerContent = React.lazy(() =>
import('./ItemDetailDrawerContent'),
);
/**
* Item Detail drawer.
*/
function ItemDetailDrawer({
name,
// #withDrawer
isOpen,
payload: { itemId },
}) {
return (
<Drawer
isOpen={isOpen}
name={name}
style={{ minWidth: '700px', maxWidth: '900px' }}
size={'65%'}
>
<DrawerSuspense>
<ItemDetailDrawerContent itemId={itemId} />
</DrawerSuspense>
</Drawer>
);
}
export default compose(withDrawers())(ItemDetailDrawer);

View File

@@ -0,0 +1,28 @@
// @ts-nocheck
import React from 'react';
import styled from 'styled-components';
import { Intent, Tag } from '@blueprintjs/core';
import { Choose, FormattedMessage as T } from '@/components';
/**
* items inactive status.
* @returns {React.JSX}
*/
export function inactiveStatus(item) {
return (
<Choose>
<Choose.When condition={!item.active}>
{item.name}
<StatusTag intent={Intent.NONE} minimal={true} round={true}>
<T id={'item.details.inactive'} />
</StatusTag>
</Choose.When>
<Choose.Otherwise>{item.name}</Choose.Otherwise>
</Choose>
);
}
const StatusTag = styled(Tag)`
font-size: 11px;
margin-left: 10px;
`;