mirror of
https://gitlab.com/mbugroup/lti-web-client.git
synced 2026-05-24 15:25:46 +00:00
refactor(FE-208,212): enhance PurchaseRequestForm with product and product warehouse fields
This commit is contained in:
@@ -2,6 +2,8 @@ import * as Yup from 'yup';
|
|||||||
import { Supplier } from '@/types/api/master-data/supplier';
|
import { Supplier } from '@/types/api/master-data/supplier';
|
||||||
import { Warehouse } from '@/types/api/master-data/warehouse';
|
import { Warehouse } from '@/types/api/master-data/warehouse';
|
||||||
import { CreatePurchaseRequestPayload } from '@/types/api/purchase/purchase';
|
import { CreatePurchaseRequestPayload } from '@/types/api/purchase/purchase';
|
||||||
|
import { Product } from '@/types/api/master-data/product';
|
||||||
|
import { ProductWarehouse } from '@/types/api/inventory/product-warehouse';
|
||||||
|
|
||||||
export const PurchaseRequestFormSchema = Yup.object({
|
export const PurchaseRequestFormSchema = Yup.object({
|
||||||
supplier: Yup.object({
|
supplier: Yup.object({
|
||||||
@@ -28,10 +30,18 @@ export const PurchaseRequestFormSchema = Yup.object({
|
|||||||
.required('Warehouse wajib diisi!')
|
.required('Warehouse wajib diisi!')
|
||||||
.min(1, 'Produk wajib diisi!')
|
.min(1, 'Produk wajib diisi!')
|
||||||
.typeError('Warehouse harus berupa angka!'),
|
.typeError('Warehouse harus berupa angka!'),
|
||||||
|
product: Yup.object({
|
||||||
|
value: Yup.number().min(1).required(),
|
||||||
|
label: Yup.string().required(),
|
||||||
|
}).nullable(),
|
||||||
product_id: Yup.number()
|
product_id: Yup.number()
|
||||||
.required('Produk wajib diisi!')
|
.required('Produk wajib diisi!')
|
||||||
.min(1, 'Produk wajib diisi!')
|
.min(1, 'Produk wajib diisi!')
|
||||||
.typeError('Produk harus berupa angka!'),
|
.typeError('Produk harus berupa angka!'),
|
||||||
|
product_warehouse: Yup.object({
|
||||||
|
value: Yup.number().min(1).required(),
|
||||||
|
label: Yup.string().required(),
|
||||||
|
}).nullable(),
|
||||||
product_warehouse_id: Yup.number()
|
product_warehouse_id: Yup.number()
|
||||||
.required('Product warehouse wajib diisi!')
|
.required('Product warehouse wajib diisi!')
|
||||||
.min(1, 'Product warehouse wajib diisi!')
|
.min(1, 'Product warehouse wajib diisi!')
|
||||||
@@ -57,10 +67,16 @@ export type PurchaseRequestFormValues = Yup.InferType<
|
|||||||
typeof PurchaseRequestFormSchema
|
typeof PurchaseRequestFormSchema
|
||||||
>;
|
>;
|
||||||
|
|
||||||
type PurchaseRequestFormData = Partial<CreatePurchaseRequestPayload> & {
|
type PurchaseRequestFormData = {
|
||||||
supplier?: Supplier;
|
supplier?: Supplier;
|
||||||
warehouse?: Warehouse[];
|
supplier_id?: number;
|
||||||
purchase_items?: CreatePurchaseRequestPayload['purchase_items'];
|
credit_term?: number;
|
||||||
|
notes?: string | null;
|
||||||
|
purchase_items?: (CreatePurchaseRequestPayload['purchase_items'][0] & {
|
||||||
|
warehouse?: Warehouse;
|
||||||
|
product?: Product;
|
||||||
|
product_warehouse?: ProductWarehouse;
|
||||||
|
})[];
|
||||||
};
|
};
|
||||||
|
|
||||||
export const getPurchaseRequestFormInitialValues = (
|
export const getPurchaseRequestFormInitialValues = (
|
||||||
@@ -73,22 +89,30 @@ export const getPurchaseRequestFormInitialValues = (
|
|||||||
}
|
}
|
||||||
: null,
|
: null,
|
||||||
supplier_id: initialValues?.supplier_id ?? 0,
|
supplier_id: initialValues?.supplier_id ?? 0,
|
||||||
credit_term: initialValues?.credit_term ?? 0,
|
credit_term: initialValues?.credit_term ?? 1,
|
||||||
notes: initialValues?.notes ?? '',
|
notes: initialValues?.notes ?? '',
|
||||||
purchase_items: initialValues?.purchase_items?.map(
|
purchase_items: initialValues?.purchase_items?.map(
|
||||||
(item: NonNullable<CreatePurchaseRequestPayload['purchase_items']>[0]) => ({
|
(item: NonNullable<PurchaseRequestFormData['purchase_items']>[0]) => ({
|
||||||
warehouse: initialValues?.warehouse?.find(
|
warehouse: item.warehouse
|
||||||
(w) => w.id === item.warehouse_ids
|
|
||||||
)
|
|
||||||
? {
|
? {
|
||||||
value: item.warehouse_ids,
|
value: item.warehouse.id,
|
||||||
label:
|
label: item.warehouse.name,
|
||||||
initialValues.warehouse.find((w) => w.id === item.warehouse_ids)
|
|
||||||
?.name || '',
|
|
||||||
}
|
}
|
||||||
: null,
|
: null,
|
||||||
warehouse_ids: item.warehouse_ids,
|
warehouse_ids: item.warehouse_ids,
|
||||||
|
product: item.product
|
||||||
|
? {
|
||||||
|
value: item.product.id,
|
||||||
|
label: item.product.name,
|
||||||
|
}
|
||||||
|
: null,
|
||||||
product_id: item.product_id,
|
product_id: item.product_id,
|
||||||
|
product_warehouse: item.product_warehouse
|
||||||
|
? {
|
||||||
|
value: item.product_warehouse.id,
|
||||||
|
label: item.product_warehouse.product.name,
|
||||||
|
}
|
||||||
|
: null,
|
||||||
product_warehouse_id: item.product_warehouse_id,
|
product_warehouse_id: item.product_warehouse_id,
|
||||||
total_qty: item.total_qty,
|
total_qty: item.total_qty,
|
||||||
price: item.price,
|
price: item.price,
|
||||||
@@ -97,7 +121,9 @@ export const getPurchaseRequestFormInitialValues = (
|
|||||||
{
|
{
|
||||||
warehouse: null,
|
warehouse: null,
|
||||||
warehouse_ids: 0,
|
warehouse_ids: 0,
|
||||||
|
product: null,
|
||||||
product_id: 0,
|
product_id: 0,
|
||||||
|
product_warehouse: null,
|
||||||
product_warehouse_id: 0,
|
product_warehouse_id: 0,
|
||||||
total_qty: 0,
|
total_qty: 0,
|
||||||
price: 0,
|
price: 0,
|
||||||
|
|||||||
@@ -97,21 +97,18 @@ const PurchaseRequestForm = ({
|
|||||||
validateOnBlur: true,
|
validateOnBlur: true,
|
||||||
onSubmit: async (values) => {
|
onSubmit: async (values) => {
|
||||||
const payload: CreatePurchaseRequestPayload = {
|
const payload: CreatePurchaseRequestPayload = {
|
||||||
supplier_id: values.supplier_id,
|
supplier_id: values.supplier_id || 0,
|
||||||
credit_term: values.credit_term || 0,
|
credit_term: values.credit_term || 0,
|
||||||
notes: values.notes || '',
|
notes: values.notes || '',
|
||||||
purchase_items: (values.purchase_items || []).map((item) => ({
|
purchase_items: (values.purchase_items || []).map((item) => ({
|
||||||
warehouse_ids: item.warehouse_ids,
|
warehouse_ids: item.warehouse_ids || 0,
|
||||||
product_id: item.product_id,
|
product_id: item.product_id || 0,
|
||||||
product_warehouse_id: item.product_warehouse_id,
|
product_warehouse_id: item.product_warehouse_id || 0,
|
||||||
total_qty:
|
total_qty: item.total_qty || 0,
|
||||||
typeof item.total_qty === 'number'
|
|
||||||
? item.total_qty
|
|
||||||
: parseFloat(String(item.total_qty)) || 0,
|
|
||||||
price:
|
price:
|
||||||
typeof item.price === 'number'
|
typeof item.price === 'number'
|
||||||
? item.price
|
? item.price
|
||||||
: parseFloat(String(item.price)) || 0,
|
: parseFloat(item.price) || 0,
|
||||||
})),
|
})),
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -149,8 +146,11 @@ const PurchaseRequestForm = ({
|
|||||||
const newPurchaseItems = [
|
const newPurchaseItems = [
|
||||||
...(formik.values.purchase_items || []),
|
...(formik.values.purchase_items || []),
|
||||||
{
|
{
|
||||||
|
warehouse: null,
|
||||||
warehouse_ids: 0,
|
warehouse_ids: 0,
|
||||||
|
product: null,
|
||||||
product_id: 0,
|
product_id: 0,
|
||||||
|
product_warehouse: null,
|
||||||
product_warehouse_id: 0,
|
product_warehouse_id: 0,
|
||||||
total_qty: 0,
|
total_qty: 0,
|
||||||
price: 0,
|
price: 0,
|
||||||
@@ -179,12 +179,23 @@ const PurchaseRequestForm = ({
|
|||||||
field: string,
|
field: string,
|
||||||
value: string | number
|
value: string | number
|
||||||
) => {
|
) => {
|
||||||
if (field === 'warehouse_ids') {
|
const integerFields = [
|
||||||
formik.setFieldValue(`purchase_items.${idx}.${field}`, value);
|
'warehouse_ids',
|
||||||
} else {
|
'product_id',
|
||||||
|
'product_warehouse_id',
|
||||||
|
'total_qty',
|
||||||
|
];
|
||||||
|
const floatFields = ['price'];
|
||||||
|
|
||||||
|
if (integerFields.includes(field)) {
|
||||||
|
const numValue = typeof value === 'string' ? parseInt(value) || 0 : value;
|
||||||
|
formik.setFieldValue(`purchase_items.${idx}.${field}`, numValue);
|
||||||
|
} else if (floatFields.includes(field)) {
|
||||||
const numValue =
|
const numValue =
|
||||||
typeof value === 'string' ? parseFloat(value) || 0 : value;
|
typeof value === 'string' ? parseFloat(value) || 0 : value;
|
||||||
formik.setFieldValue(`purchase_items.${idx}.${field}`, numValue);
|
formik.setFieldValue(`purchase_items.${idx}.${field}`, numValue);
|
||||||
|
} else {
|
||||||
|
formik.setFieldValue(`purchase_items.${idx}.${field}`, value);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -388,6 +399,7 @@ const PurchaseRequestForm = ({
|
|||||||
</td>
|
</td>
|
||||||
<td>
|
<td>
|
||||||
<TextInput
|
<TextInput
|
||||||
|
required
|
||||||
name={`purchase_items.${idx}.product_warehouse_id`}
|
name={`purchase_items.${idx}.product_warehouse_id`}
|
||||||
value={item.product_warehouse_id || ''}
|
value={item.product_warehouse_id || ''}
|
||||||
onChange={(e) =>
|
onChange={(e) =>
|
||||||
|
|||||||
@@ -6,7 +6,7 @@ import { PurchaseApi } from '@/services/api/purchasing';
|
|||||||
import {
|
import {
|
||||||
CreatePurchaseRequestPayload,
|
CreatePurchaseRequestPayload,
|
||||||
UpdatePurchaseRequestPayload,
|
UpdatePurchaseRequestPayload,
|
||||||
} from '@/types/api/purchase/purchasing';
|
} from '@/types/api/purchase/purchase';
|
||||||
import { isResponseError } from '@/lib/api-helper';
|
import { isResponseError } from '@/lib/api-helper';
|
||||||
|
|
||||||
export const usePurchaseRequestFormHandlers = (initialValuesId?: number) => {
|
export const usePurchaseRequestFormHandlers = (initialValuesId?: number) => {
|
||||||
@@ -30,7 +30,10 @@ export const usePurchaseRequestFormHandlers = (initialValuesId?: number) => {
|
|||||||
);
|
);
|
||||||
|
|
||||||
const updatePurchaseRequestHandler = useCallback(
|
const updatePurchaseRequestHandler = useCallback(
|
||||||
async (purchaseRequestId: number, payload: UpdatePurchaseRequestPayload) => {
|
async (
|
||||||
|
purchaseRequestId: number,
|
||||||
|
payload: UpdatePurchaseRequestPayload
|
||||||
|
) => {
|
||||||
const res = await PurchaseApi.update(purchaseRequestId, payload);
|
const res = await PurchaseApi.update(purchaseRequestId, payload);
|
||||||
if (res?.status === 'error') {
|
if (res?.status === 'error') {
|
||||||
setPurchaseRequestFormErrorMessage(res.message);
|
setPurchaseRequestFormErrorMessage(res.message);
|
||||||
@@ -67,4 +70,4 @@ export const usePurchaseRequestFormHandlers = (initialValuesId?: number) => {
|
|||||||
deletePurchaseRequestClickHandler,
|
deletePurchaseRequestClickHandler,
|
||||||
confirmationModalDeleteClickHandler,
|
confirmationModalDeleteClickHandler,
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,12 +1,12 @@
|
|||||||
import { BaseApiService } from './base';
|
import { BaseApiService } from './base';
|
||||||
import {
|
import {
|
||||||
CreatePurchasePayload,
|
CreatePurchaseRequestPayload,
|
||||||
Purchase,
|
Purchase,
|
||||||
UpdatePurchasePayload,
|
UpdatePurchaseRequestPayload,
|
||||||
} from '@/types/api/purchase/purchasing';
|
} from '@/types/api/purchase/purchase';
|
||||||
|
|
||||||
export const PurchaseApi = new BaseApiService<
|
export const PurchaseApi = new BaseApiService<
|
||||||
Purchase,
|
Purchase,
|
||||||
CreatePurchasePayload,
|
CreatePurchaseRequestPayload,
|
||||||
UpdatePurchasePayload
|
UpdatePurchaseRequestPayload
|
||||||
>('/purchase-requests');
|
>('/purchase-requests');
|
||||||
|
|||||||
Reference in New Issue
Block a user