feat(FE): API integration debt supplier report

This commit is contained in:
randy-ar
2026-01-11 21:02:58 +07:00
parent 0da9f9d651
commit 677025b4a2
6 changed files with 91 additions and 282 deletions
@@ -2,7 +2,7 @@
import Tabs from '@/components/Tabs';
import CustomerPaymentTab from '@/components/pages/report/finance/tab/CustomerPaymentTab';
import DebtSupplier from '@/components/pages/report/finance/tab/DebtSupplier';
import DebtSupplierTab from '@/components/pages/report/finance/tab/DebtSupplierTab';
const FinanceTabs = () => {
const tabs = [
@@ -16,7 +16,7 @@ const FinanceTabs = () => {
id: '2',
label: 'Rekapitulasi Hutang Ke Supplier',
content: <DebtSupplier />,
content: <DebtSupplierTab />,
},
];
@@ -22,6 +22,7 @@ import { ColumnDef } from '@tanstack/react-table';
import { useCallback, useMemo, useState } from 'react';
import toast from 'react-hot-toast';
import useSWR from 'swr';
import Pagination from '@/components/Pagination';
const DebtSupplierTab = () => {
// ===== STATE MANAGEMENT =====
@@ -87,37 +88,37 @@ const DebtSupplierTab = () => {
}, [filterModal, filterStartDate, filterEndDate]);
// ===== DATA FETCHING =====
// const { data: debtSupplier, isLoading } = useSWR(
// isSubmitted
// ? () => {
// const params = {
// supplier_id:
// filterSupplier.length > 0
// ? filterSupplier.map((v) => String(v.value)).join(',')
// : undefined,
// filter_by: 'do_date' as const,
// start_date: filterStartDate || undefined,
// end_date: filterEndDate || undefined,
// page: currentPage,
// limit: pageSize,
// };
const { data: debtSupplier, isLoading } = useSWR(
isSubmitted
? () => {
const params = {
supplier_id:
filterSupplier.length > 0
? filterSupplier.map((v) => String(v.value)).join(',')
: undefined,
filter_by: 'do_date' as const,
start_date: filterStartDate || undefined,
end_date: filterEndDate || undefined,
page: currentPage,
limit: pageSize,
};
// return ['debt-supplier-report', params];
// }
// : null,
// ([, params]) =>
// FinanceApi.getDebtSupplierReport(
// params.supplier_id,
// params.filter_by,
// params.start_date,
// params.end_date,
// params.page,
// params.limit
// )
// );
const { data: debtSupplier, isLoading } = useSWR(FinanceApi.basePath, () =>
FinanceApi.getDebtSupplierReport()
return ['debt-supplier-report', params];
}
: null,
([, params]) =>
FinanceApi.getDebtSupplierReport(
params.supplier_id,
params.filter_by,
params.start_date,
params.end_date,
params.page,
params.limit
)
);
// const { data: debtSupplier, isLoading } = useSWR(FinanceApi.basePath, () =>
// FinanceApi.getDebtSupplierReport()
// );
const data: DebtSupplier[] = useMemo(
() =>
@@ -391,7 +392,7 @@ const DebtSupplierTab = () => {
<>
<div className='w-full p-0 sm:p-4 flex flex-col gap-4'>
<Card
subtitle='Laporan > Kontrol Pembayaran Customer'
subtitle='Laporan > Kontrol Hutang Supplier'
className={{ wrapper: 'w-full', body: 'p-1!' }}
>
<div className='mb-4 flex justify-end gap-2 [&_button]:px-4'>
@@ -421,7 +422,7 @@ const DebtSupplierTab = () => {
</div>
</Card>
{/* {!isSubmitted ? (
{!isSubmitted ? (
<div className='mt-6 text-center text-gray-500'>
Silakan klik tombol Filter untuk mengatur filter dan menampilkan
data.
@@ -434,44 +435,59 @@ const DebtSupplierTab = () => {
<div className='mt-6 text-center text-gray-500'>
Tidak ada data yang dapat ditampilkan...
</div>
) : ( */}
{data.map((supplierReport) => {
return (
<Card
key={supplierReport.supplier.id}
title={supplierReport.supplier.name}
className={{ wrapper: 'w-full' }}
variant='bordered'
collapsible={true}
>
<Table
data={supplierReport.rows}
columns={getTableColumns(supplierReport)}
pageSize={10}
renderFooter={supplierReport.rows.length > 0}
className={{
containerClassName: 'w-full',
tableWrapperClassName: 'overflow-x-auto mt-4',
tableClassName: 'w-full table-auto text-sm',
headerRowClassName: 'border-b border-b-gray-200 bg-gray-50',
headerColumnClassName:
'px-4 py-3 text-xs font-semibold text-gray-700 text-left border border-gray-200',
bodyRowClassName:
'hover:bg-gray-50 transition-colors border-b border-l border-r border-b-gray-200 border-l-gray-200 border-r-gray-200',
bodyColumnClassName:
'px-4 py-3 text-xs text-gray-900 whitespace-nowrap',
tableFooterClassName:
'bg-gray-100 font-semibold border border-gray-200',
footerRowClassName: 'border-t-2 border-gray-300',
footerColumnClassName:
'px-4 py-3 text-xs text-gray-900 whitespace-nowrap',
paginationClassName: 'hidden',
}}
/>
</Card>
);
})}
) : (
data.map((supplierReport) => {
return (
<Card
key={supplierReport.supplier.id}
title={supplierReport.supplier.name}
className={{ wrapper: 'w-full' }}
variant='bordered'
collapsible={true}
>
<Table
data={supplierReport.rows}
columns={getTableColumns(supplierReport)}
pageSize={10}
renderFooter={supplierReport.rows.length > 0}
className={{
containerClassName: 'w-full',
tableWrapperClassName: 'overflow-x-auto mt-4',
tableClassName: 'w-full table-auto text-sm',
headerRowClassName: 'border-b border-b-gray-200 bg-gray-50',
headerColumnClassName:
'px-4 py-3 text-xs font-semibold text-gray-700 text-left border border-gray-200',
bodyRowClassName:
'hover:bg-gray-50 transition-colors border-b border-l border-r border-b-gray-200 border-l-gray-200 border-r-gray-200',
bodyColumnClassName:
'px-4 py-3 text-xs text-gray-900 whitespace-nowrap',
tableFooterClassName:
'bg-gray-100 font-semibold border border-gray-200',
footerRowClassName: 'border-t-2 border-gray-300',
footerColumnClassName:
'px-4 py-3 text-xs text-gray-900 whitespace-nowrap',
paginationClassName: 'hidden',
}}
/>
</Card>
);
})
)}
</div>
{meta && data.length > 0 && (
<div className='mt-6'>
<Pagination
currentPage={meta.page}
totalItems={meta.total_results}
onPageChange={handlePageChange}
onRowChange={handleRowChange}
onNextPage={handleNextPage}
onPrevPage={handlePrevPage}
rowOptions={[10, 25, 50, 100]}
itemsPerPage={meta.limit}
/>
</div>
)}
{/* Filter Modal */}
<Modal
@@ -557,11 +573,10 @@ const DebtSupplierTab = () => {
label='Filter Berdasarkan'
placeholder='Pilih Filter Berdasarkan'
options={dataTypeOptions}
value={dataTypeOptions[0]}
value={filterDataType}
onChange={(val) => {
setFilterDataType(val ? (val as OptionType) : undefined);
}}
isDisabled={true}
className={{ wrapper: 'w-full' }}
/>
</div>