mirror of
https://gitlab.com/mbugroup/lti-web-client.git
synced 2026-05-20 13:32:00 +00:00
feat(FE-361,363): Add product category filter and API params
This commit is contained in:
@@ -10,6 +10,7 @@ import DateInput from '@/components/input/DateInput';
|
||||
import { AreaApi } from '@/services/api/master-data';
|
||||
import { SupplierApi } from '@/services/api/master-data';
|
||||
import { ProductApi } from '@/services/api/master-data';
|
||||
import { ProductCategoryApi } from '@/services/api/master-data';
|
||||
import { LogisticApi } from '@/services/api/logistic';
|
||||
import Table from '@/components/Table';
|
||||
import { ColumnDef } from '@tanstack/react-table';
|
||||
@@ -33,10 +34,6 @@ interface Totals {
|
||||
}
|
||||
|
||||
const PurchasesPerSupplierTab = () => {
|
||||
const [dataType, setDataType] = useState<'received_date' | 'po_date'>(
|
||||
'received_date'
|
||||
);
|
||||
|
||||
// ===== PAGINATION STATE =====
|
||||
const [currentPage, setCurrentPage] = useState(1);
|
||||
const [pageSize, setPageSize] = useState(10);
|
||||
@@ -50,10 +47,13 @@ const PurchasesPerSupplierTab = () => {
|
||||
area_id: '',
|
||||
supplier_id: '',
|
||||
product_id: '',
|
||||
product_category_id: '',
|
||||
received_date: '',
|
||||
po_date: '',
|
||||
start_date: '',
|
||||
end_date: '',
|
||||
sort_by: '',
|
||||
filter_by: 'received_date',
|
||||
},
|
||||
paramMap: {
|
||||
page: 'page',
|
||||
@@ -61,16 +61,6 @@ const PurchasesPerSupplierTab = () => {
|
||||
},
|
||||
});
|
||||
|
||||
const updateDataType = useCallback(
|
||||
(newDataType: 'received_date' | 'po_date') => {
|
||||
setDataType(newDataType);
|
||||
updateFilter('received_date', '');
|
||||
updateFilter('po_date', '');
|
||||
setIsSubmitted(false);
|
||||
},
|
||||
[updateFilter]
|
||||
);
|
||||
|
||||
const { options: areaOptions, isLoadingOptions: isLoadingAreas } = useSelect(
|
||||
AreaApi.basePath,
|
||||
'id',
|
||||
@@ -84,6 +74,11 @@ const PurchasesPerSupplierTab = () => {
|
||||
const { options: productOptions, isLoadingOptions: isLoadingProducts } =
|
||||
useSelect(ProductApi.basePath, 'id', 'name', 'search');
|
||||
|
||||
const {
|
||||
options: productCategoryOptions,
|
||||
isLoadingOptions: isLoadingProductCategories,
|
||||
} = useSelect(ProductCategoryApi.basePath, 'id', 'name', 'search');
|
||||
|
||||
const dataTypeOptions = useMemo(
|
||||
() => [
|
||||
{ value: 'received_date', label: 'Tanggal Terima' },
|
||||
@@ -119,15 +114,29 @@ const PurchasesPerSupplierTab = () => {
|
||||
[updateFilter]
|
||||
);
|
||||
|
||||
const dataTypeChangeHandler = useCallback(
|
||||
const productCategoryChangeHandler = useCallback(
|
||||
(val: OptionType | OptionType[] | null) => {
|
||||
const newVal = val as OptionType;
|
||||
updateDataType(
|
||||
(newVal?.value as 'received_date' | 'po_date') || 'received_date'
|
||||
updateFilter(
|
||||
'product_category_id',
|
||||
newVal?.value ? String(newVal.value) : ''
|
||||
);
|
||||
setIsSubmitted(false);
|
||||
},
|
||||
[updateDataType]
|
||||
[updateFilter]
|
||||
);
|
||||
|
||||
const dataTypeChangeHandler = useCallback(
|
||||
(val: OptionType | OptionType[] | null) => {
|
||||
const newVal = val as OptionType;
|
||||
const filterValue =
|
||||
(newVal?.value as 'received_date' | 'po_date') || 'received_date';
|
||||
updateFilter('filter_by', filterValue);
|
||||
updateFilter('received_date', '');
|
||||
updateFilter('po_date', '');
|
||||
setIsSubmitted(false);
|
||||
},
|
||||
[updateFilter]
|
||||
);
|
||||
|
||||
const startDateChangeHandler = useCallback<
|
||||
@@ -156,11 +165,13 @@ const PurchasesPerSupplierTab = () => {
|
||||
updateFilter('area_id', '');
|
||||
updateFilter('supplier_id', '');
|
||||
updateFilter('product_id', '');
|
||||
updateFilter('product_category_id', '');
|
||||
updateFilter('received_date', '');
|
||||
updateFilter('po_date', '');
|
||||
updateFilter('start_date', '');
|
||||
updateFilter('end_date', '');
|
||||
setDataType('received_date');
|
||||
updateFilter('sort_by', '');
|
||||
updateFilter('filter_by', 'received_date');
|
||||
setIsSubmitted(false);
|
||||
}, [updateFilter]);
|
||||
|
||||
@@ -183,10 +194,21 @@ const PurchasesPerSupplierTab = () => {
|
||||
product_id: tableFilterState.product_id
|
||||
? Number(tableFilterState.product_id)
|
||||
: undefined,
|
||||
received_date: tableFilterState.received_date || undefined,
|
||||
po_date: tableFilterState.po_date || undefined,
|
||||
product_category_id: tableFilterState.product_category_id
|
||||
? Number(tableFilterState.product_category_id)
|
||||
: undefined,
|
||||
received_date:
|
||||
tableFilterState.filter_by === 'received_date'
|
||||
? tableFilterState.start_date || undefined
|
||||
: undefined,
|
||||
po_date:
|
||||
tableFilterState.filter_by === 'po_date'
|
||||
? tableFilterState.start_date || undefined
|
||||
: undefined,
|
||||
start_date: tableFilterState.start_date || undefined,
|
||||
end_date: tableFilterState.end_date || undefined,
|
||||
sort_by: tableFilterState.sort_by || undefined,
|
||||
filter_by: tableFilterState.filter_by || undefined,
|
||||
page: currentPage,
|
||||
limit: pageSize,
|
||||
};
|
||||
@@ -199,10 +221,13 @@ const PurchasesPerSupplierTab = () => {
|
||||
params.area_id,
|
||||
params.supplier_id,
|
||||
params.product_id,
|
||||
params.product_category_id,
|
||||
params.received_date,
|
||||
params.po_date,
|
||||
params.start_date,
|
||||
params.end_date,
|
||||
params.sort_by,
|
||||
params.filter_by,
|
||||
params.page,
|
||||
params.limit
|
||||
)
|
||||
@@ -254,7 +279,6 @@ const PurchasesPerSupplierTab = () => {
|
||||
items: LogisticPurchasePerSupplierReport['rows'];
|
||||
}
|
||||
|
||||
// Group data by supplier for display
|
||||
const groupedData = useMemo(() => {
|
||||
const groups: { [key: number]: GroupedSupplierData } = {};
|
||||
|
||||
@@ -468,7 +492,7 @@ const PurchasesPerSupplierTab = () => {
|
||||
</Menu>
|
||||
</Dropdown>
|
||||
</div>
|
||||
<div className='grid grid-cols-12 gap-4'>
|
||||
<div className='grid grid-cols-3 gap-4'>
|
||||
<SelectInput
|
||||
label='Area'
|
||||
placeholder='Pilih Area'
|
||||
@@ -484,9 +508,6 @@ const PurchasesPerSupplierTab = () => {
|
||||
onChange={areaChangeHandler}
|
||||
isLoading={isLoadingAreas}
|
||||
isClearable
|
||||
className={{
|
||||
wrapper: 'col-span-12 sm:col-span-4',
|
||||
}}
|
||||
/>
|
||||
<SelectInput
|
||||
label='Supplier'
|
||||
@@ -503,9 +524,6 @@ const PurchasesPerSupplierTab = () => {
|
||||
onChange={supplierChangeHandler}
|
||||
isLoading={isLoadingSuppliers}
|
||||
isClearable
|
||||
className={{
|
||||
wrapper: 'col-span-12 sm:col-span-4',
|
||||
}}
|
||||
/>
|
||||
<SelectInput
|
||||
label='Produk'
|
||||
@@ -522,45 +540,55 @@ const PurchasesPerSupplierTab = () => {
|
||||
onChange={productChangeHandler}
|
||||
isLoading={isLoadingProducts}
|
||||
isClearable
|
||||
className={{
|
||||
wrapper: 'col-span-12 sm:col-span-4',
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
<div className='grid grid-cols-3 gap-4'>
|
||||
<SelectInput
|
||||
label='Kategori Produk'
|
||||
placeholder='Pilih Kategori Produk'
|
||||
options={productCategoryOptions}
|
||||
value={
|
||||
tableFilterState.product_category_id
|
||||
? productCategoryOptions.find(
|
||||
(option) =>
|
||||
option.value ===
|
||||
Number(tableFilterState.product_category_id)
|
||||
) || null
|
||||
: null
|
||||
}
|
||||
onChange={productCategoryChangeHandler}
|
||||
isLoading={isLoadingProductCategories}
|
||||
isClearable
|
||||
/>
|
||||
<SelectInput
|
||||
label='Tipe Data'
|
||||
placeholder='Pilih Tipe Data'
|
||||
label='Filter Berdasarkan'
|
||||
placeholder='Pilih Filter Berdasarkan'
|
||||
options={dataTypeOptions}
|
||||
value={
|
||||
dataTypeOptions?.find((option) => option.value === dataType) ||
|
||||
null
|
||||
dataTypeOptions?.find(
|
||||
(option) => option.value === tableFilterState.filter_by
|
||||
) || null
|
||||
}
|
||||
onChange={dataTypeChangeHandler}
|
||||
isLoading={false}
|
||||
isClearable={false}
|
||||
className={{
|
||||
wrapper: 'col-span-12 sm:col-span-4',
|
||||
}}
|
||||
/>
|
||||
<DateInput
|
||||
label='Tanggal Awal'
|
||||
name='start_date'
|
||||
placeholder='Pilih Tanggal Awal'
|
||||
value={tableFilterState.start_date}
|
||||
onChange={startDateChangeHandler}
|
||||
className={{
|
||||
wrapper: 'col-span-12 sm:col-span-4',
|
||||
}}
|
||||
/>
|
||||
<DateInput
|
||||
label='Tanggal Akhir'
|
||||
name='end_date'
|
||||
placeholder='Pilih Tanggal Akhir'
|
||||
value={tableFilterState.end_date}
|
||||
onChange={endDateChangeHandler}
|
||||
className={{
|
||||
wrapper: 'col-span-12 sm:col-span-4',
|
||||
}}
|
||||
/>
|
||||
<div className='flex flex-row gap-4'>
|
||||
<DateInput
|
||||
label='Tanggal Awal'
|
||||
name='start_date'
|
||||
placeholder='Pilih Tanggal Awal'
|
||||
value={tableFilterState.start_date}
|
||||
onChange={startDateChangeHandler}
|
||||
/>
|
||||
<DateInput
|
||||
label='Tanggal Akhir'
|
||||
name='end_date'
|
||||
placeholder='Pilih Tanggal Akhir'
|
||||
value={tableFilterState.end_date}
|
||||
onChange={endDateChangeHandler}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{!isSubmitted ? (
|
||||
|
||||
@@ -15,10 +15,13 @@ export class LogisticApiService extends BaseApiService<
|
||||
area_id?: number,
|
||||
supplier_id?: number,
|
||||
product_id?: number,
|
||||
product_category_id?: number,
|
||||
received_date?: string,
|
||||
po_date?: string,
|
||||
start_date?: string,
|
||||
end_date?: string,
|
||||
sort_by?: string,
|
||||
filter_by?: string,
|
||||
page?: number,
|
||||
limit?: number
|
||||
): Promise<BaseApiResponse<LogisticPurchasePerSupplierReport> | undefined> {
|
||||
@@ -30,10 +33,13 @@ export class LogisticApiService extends BaseApiService<
|
||||
area_id: area_id,
|
||||
supplier_id: supplier_id,
|
||||
product_id: product_id,
|
||||
product_category_id: product_category_id,
|
||||
received_date: received_date,
|
||||
po_date: po_date,
|
||||
start_date: start_date,
|
||||
end_date: end_date,
|
||||
sort_by: sort_by,
|
||||
filter_by: filter_by,
|
||||
page: page,
|
||||
limit: limit,
|
||||
},
|
||||
|
||||
Reference in New Issue
Block a user