refactor(FE): Refactor PDF table components to simplify imports

This commit is contained in:
rstubryan
2026-02-11 10:39:37 +07:00
parent 70b63f7773
commit 0f1d2ce477
6 changed files with 973 additions and 885 deletions
@@ -10,12 +10,7 @@ import {
} from '@react-pdf/renderer';
import { LogisticPurchasePerSupplierReport } from '@/types/api/report/logistic-stock';
import { formatCurrency, formatDate, formatNumber } from '@/lib/helper';
import {
PdfTable,
PdfColumn,
PdfTbodyCell,
PdfTfootCell,
} from '@/components/helper/pdf/table';
import { PdfTable, PdfColumn } from '@/components/helper/pdf/table';
import { PdfParamBadge } from '@/components/helper/pdf/badge/PdfParamBadge';
import { PdfStatusBadge } from '@/components/helper/pdf/badge/PdfStatusBadge';
import { PdfTypography } from '@/components/helper/pdf/typography/PdfTypography';
@@ -58,90 +53,118 @@ interface PurchasesPerSupplierExportParams {
};
}
const getTableColumns = (): PdfColumn[] => [
{ key: 'no', header: 'No', flex: 0.5, align: 'center' },
const getTableColumns = (
summary?: LogisticPurchasePerSupplierReport['summary']
): PdfColumn<LogisticPurchasePerSupplierReport['rows'][number]>[] => [
{
key: 'no',
header: 'No',
flex: 0.5,
align: 'center',
cell: ({ row, index }) => index + 1,
footer: 'Total',
},
{
key: 'receive_date',
header: 'Tanggal Terima',
flex: 1.2,
align: 'center',
cell: ({ row }) =>
row.receive_date ? formatDate(row.receive_date, 'DD MMM YY') : '-',
footer: '',
},
{
key: 'po_date',
header: 'Tanggal PO',
flex: 1.2,
align: 'center',
cell: ({ row }) =>
row.po_date ? formatDate(row.po_date, 'DD MMM YY') : '-',
footer: '',
},
{
key: 'po_number',
header: 'No. Referensi',
flex: 1.5,
align: 'left',
cell: ({ row }) => row.po_number || '-',
footer: '',
},
{
key: 'product',
header: 'Nama Produk',
flex: 2,
align: 'left',
cell: ({ row }) => row.product?.name || '-',
footer: '',
},
{
key: 'warehouse',
header: 'Tujuan',
flex: 1.5,
align: 'left',
cell: ({ row }) => row.warehouse?.name || '-',
footer: '',
},
{
key: 'qty',
header: 'QTY',
flex: 0.8,
align: 'right',
cell: ({ row }) => formatNumber(row.qty || 0),
footer: summary ? formatNumber(summary.total_qty || 0) : '',
footerAlign: 'right',
},
{
key: 'unit_price',
header: 'Harga Beli (Rp)',
flex: 1.5,
align: 'right',
cell: ({ row }) => formatCurrency(row.unit_price || 0),
footer: '',
},
{ key: 'po_date', header: 'Tanggal PO', flex: 1.2, align: 'center' },
{ key: 'po_number', header: 'No. Referensi', flex: 1.5, align: 'left' },
{ key: 'product', header: 'Nama Produk', flex: 2, align: 'left' },
{ key: 'warehouse', header: 'Tujuan', flex: 1.5, align: 'left' },
{ key: 'qty', header: 'QTY', flex: 0.8, align: 'right' },
{ key: 'unit_price', header: 'Harga Beli (Rp)', flex: 1.5, align: 'right' },
{
key: 'purchase_value',
header: 'Value Harga Beli (Rp)',
flex: 1.8,
align: 'right',
cell: ({ row }) => formatCurrency(row.purchase_value || 0),
footer: summary ? formatCurrency(summary.total_purchase_value || 0) : '',
footerAlign: 'right',
},
{
key: 'transport_unit_price',
header: 'Transport (Rp)',
flex: 1.3,
align: 'right',
cell: ({ row }) => formatCurrency(row.transport_unit_price || 0),
footer: '',
},
{
key: 'transport_value',
header: 'Value Transport (Rp)',
flex: 1.8,
align: 'right',
cell: ({ row }) => formatCurrency(row.transport_value || 0),
footer: summary ? formatCurrency(summary.total_transport_value || 0) : '',
footerAlign: 'right',
},
{ key: 'total_amount', header: 'Jumlah (Rp)', flex: 1.5, align: 'right' },
{ key: 'expedition', header: 'Ekspedisi', flex: 1.2, align: 'center' },
{ key: 'delivery_number', header: 'Surat Jalan', flex: 1.2, align: 'left' },
];
const getTableData = (
rows: LogisticPurchasePerSupplierReport['rows']
): PdfTbodyCell[][] => {
return rows.map((item, index) => [
{ key: 'no', value: index + 1 },
{
key: 'receive_date',
value: item.receive_date
? formatDate(item.receive_date, 'DD MMM YY')
: '-',
},
{
key: 'po_date',
value: item.po_date ? formatDate(item.po_date, 'DD MMM YY') : '-',
},
{ key: 'po_number', value: item.po_number || '-' },
{ key: 'product', value: item.product?.name || '-' },
{ key: 'warehouse', value: item.warehouse?.name || '-' },
{ key: 'qty', value: formatNumber(item.qty || 0), align: 'right' },
{
key: 'unit_price',
value: formatCurrency(item.unit_price || 0),
align: 'right',
},
{
key: 'purchase_value',
value: formatCurrency(item.purchase_value || 0),
align: 'right',
},
{
key: 'transport_unit_price',
value: formatCurrency(item.transport_unit_price || 0),
align: 'right',
},
{
key: 'transport_value',
value: formatCurrency(item.transport_value || 0),
align: 'right',
},
{
key: 'total_amount',
value: formatCurrency(item.total_amount || 0),
align: 'right',
},
{
key: 'expedition',
value: item.expedition ? (
{
key: 'total_amount',
header: 'Jumlah (Rp)',
flex: 1.5,
align: 'right',
cell: ({ row }) => formatCurrency(row.total_amount || 0),
footer: summary ? formatCurrency(summary.total_amount || 0) : '',
footerAlign: 'right',
},
{
key: 'expedition',
header: 'Ekspedisi',
flex: 1.2,
align: 'center',
cell: ({ row }) =>
row.expedition ? (
<View style={{ alignItems: 'center' }}>
<PdfStatusBadge
style={{
@@ -150,50 +173,22 @@ const getTableData = (
borderColor: '#60A5FA',
}}
>
{item.expedition}
{row.expedition}
</PdfStatusBadge>
</View>
) : (
'-'
),
},
{ key: 'delivery_number', value: item.delivery_number || '-' },
]);
};
const getTableFooter = (
summary: LogisticPurchasePerSupplierReport['summary']
): PdfTfootCell[] => [
{ key: 'no', value: 'Total' },
{ key: 'receive_date', value: '' },
{ key: 'po_date', value: '' },
{ key: 'po_number', value: '' },
{ key: 'product', value: '' },
{ key: 'warehouse', value: '' },
{
key: 'qty',
value: formatNumber(summary?.total_qty || 0),
align: 'right',
},
{ key: 'unit_price', value: '' },
{
key: 'purchase_value',
value: formatCurrency(summary?.total_purchase_value || 0),
align: 'right',
},
{ key: 'transport_unit_price', value: '' },
{
key: 'transport_value',
value: formatCurrency(summary?.total_transport_value || 0),
align: 'right',
footer: '',
},
{
key: 'total_amount',
value: formatCurrency(summary?.total_amount || 0),
align: 'right',
key: 'delivery_number',
header: 'Surat Jalan',
flex: 1.2,
align: 'left',
cell: ({ row }) => row.delivery_number || '-',
footer: '',
},
{ key: 'expedition', value: '' },
{ key: 'delivery_number', value: '' },
];
const createPDFDocument = (params: PurchasesPerSupplierExportParams) => {
@@ -253,13 +248,9 @@ const createPDFDocument = (params: PurchasesPerSupplierExportParams) => {
{/* Table */}
<PdfTable
columns={getTableColumns()}
data={getTableData(supplierReport.rows)}
footer={
supplierReport.summary
? getTableFooter(supplierReport.summary)
: undefined
}
columns={getTableColumns(supplierReport.summary)}
data={supplierReport.rows}
showFooter={!!supplierReport.summary}
/>
</Page>
))}