feat(FE-170,175): extend GradingForm to support additional grading data and improve form initialization

This commit is contained in:
rstubryan
2025-11-07 14:56:03 +07:00
parent 2e35462300
commit 80fcabde7e
5 changed files with 99 additions and 52 deletions
@@ -35,7 +35,7 @@ const AddGrading = () => {
{(!recordingId || {(!recordingId ||
recordingId === 'new' || recordingId === 'new' ||
(!isLoadingRecording && recording && isResponseSuccess(recording))) && ( (!isLoadingRecording && recording && isResponseSuccess(recording))) && (
<GradingForm type='add' initialValues={isResponseSuccess(recording) ? recording.data?.recording_eggs?.[0] : undefined} /> <GradingForm type='add' initialValues={isResponseSuccess(recording) ? recording.data?.eggs?.[0] : undefined} />
)} )}
</div> </div>
); );
@@ -41,7 +41,7 @@ const EditGrading = () => {
{!isLoadingRecording && recording && isResponseSuccess(recording) && ( {!isLoadingRecording && recording && isResponseSuccess(recording) && (
<GradingForm <GradingForm
type='edit' type='edit'
initialValues={recording.data.recording_eggs?.find( initialValues={recording.data.eggs?.find(
(egg) => egg.id === parseInt(gradingId || '0') (egg) => egg.id === parseInt(gradingId || '0')
)} )}
/> />
@@ -4,7 +4,7 @@ import { useRouter, useSearchParams } from 'next/navigation';
import useSWR from 'swr'; import useSWR from 'swr';
import GradingForm from '@/components/pages/production/recording/grading/form/GradingForm'; import GradingForm from '@/components/pages/production/recording/grading/form/GradingForm';
import { RecordingApi } from '@/services/api/production'; import { RecordingApi } from '@/services/api/production';
import { isResponseError, isResponseSuccess } from '@/lib/api-helper'; import { isResponseSuccess } from '@/lib/api-helper';
const DetailGrading = () => { const DetailGrading = () => {
const router = useRouter(); const router = useRouter();
@@ -40,7 +40,7 @@ const DetailGrading = () => {
{!isLoadingGrading && grading && isResponseSuccess(grading) && ( {!isLoadingGrading && grading && isResponseSuccess(grading) && (
<GradingForm <GradingForm
type='detail' type='detail'
initialValues={grading.data.recording_eggs?.find( initialValues={grading.data.eggs?.find(
(egg) => egg.id === parseInt(gradingId) (egg) => egg.id === parseInt(gradingId)
)} )}
/> />
@@ -640,6 +640,7 @@ const RecordingForm = ({ type = 'add', initialValues }: RecordingFormProps) => {
RecordingGrowingFormValues | RecordingLayingFormValues RecordingGrowingFormValues | RecordingLayingFormValues
>({ >({
initialValues: formikInitialValues, initialValues: formikInitialValues,
enableReinitialize: true,
validationSchema: (() => { validationSchema: (() => {
if (isLayingCategory) { if (isLayingCategory) {
return type === 'edit' return type === 'edit'
@@ -915,6 +916,7 @@ const RecordingForm = ({ type = 'add', initialValues }: RecordingFormProps) => {
return; return;
} }
if (formik.values.project_flock_kandang_id !== projectFlockKandangId) {
formik.setFieldValue('project_flock_kandang_id', projectFlockKandangId); formik.setFieldValue('project_flock_kandang_id', projectFlockKandangId);
formik.setFieldValue('project_flock_kandang', { formik.setFieldValue('project_flock_kandang', {
@@ -924,12 +926,14 @@ const RecordingForm = ({ type = 'add', initialValues }: RecordingFormProps) => {
: `${selectedProjectFlock?.label || ''} - ${selectedKandang?.label || ''}`, : `${selectedProjectFlock?.label || ''} - ${selectedKandang?.label || ''}`,
}); });
} }
}
}, [ }, [
projectFlockKandangLookup, projectFlockKandangLookup,
selectedProjectFlock, selectedProjectFlock,
selectedKandang, selectedKandang,
type, type,
recordedProjectFlockKandangIds, recordedProjectFlockKandangIds,
formik.values.project_flock_kandang_id,
]); ]);
useEffect(() => { useEffect(() => {
@@ -959,6 +963,10 @@ const RecordingForm = ({ type = 'add', initialValues }: RecordingFormProps) => {
}; };
setSelectedKandang(kandangOption); setSelectedKandang(kandangOption);
if (
formik.values.project_flock_kandang_id !==
projectFlockKandangDetail.id
) {
formik.setFieldValue( formik.setFieldValue(
'project_flock_kandang_id', 'project_flock_kandang_id',
projectFlockKandangDetail.id projectFlockKandangDetail.id
@@ -971,7 +979,13 @@ const RecordingForm = ({ type = 'add', initialValues }: RecordingFormProps) => {
} }
} }
} }
}, [projectFlockKandangDetail, type, projectFlockOptions]); }
}, [
projectFlockKandangDetail,
type,
projectFlockOptions,
formik.values.project_flock_kandang_id,
]);
const approveHandler = async () => { const approveHandler = async () => {
setIsApproveLoading(true); setIsApproveLoading(true);
@@ -1345,7 +1359,9 @@ const RecordingForm = ({ type = 'add', initialValues }: RecordingFormProps) => {
Kembali Kembali
</Button> </Button>
{type === 'detail' && !isRecordingApproved(initialValues) && (!isLayingCategory || hasGradingData(initialValues)) && ( {type === 'detail' &&
!isRecordingApproved(initialValues) &&
(!isLayingCategory || hasGradingData(initialValues)) && (
<div className='flex flex-row gap-2'> <div className='flex flex-row gap-2'>
<Button <Button
variant='outline' variant='outline'
@@ -1354,7 +1370,11 @@ const RecordingForm = ({ type = 'add', initialValues }: RecordingFormProps) => {
isLoading={isApproveLoading} isLoading={isApproveLoading}
className='w-full sm:w-fit' className='w-full sm:w-fit'
> >
<Icon icon='material-symbols:check' width={24} height={24} /> <Icon
icon='material-symbols:check'
width={24}
height={24}
/>
Approve Approve
</Button> </Button>
@@ -1365,7 +1385,11 @@ const RecordingForm = ({ type = 'add', initialValues }: RecordingFormProps) => {
isLoading={isRejectLoading} isLoading={isRejectLoading}
className='w-full sm:w-fit' className='w-full sm:w-fit'
> >
<Icon icon='material-symbols:close' width={24} height={24} /> <Icon
icon='material-symbols:close'
width={24}
height={24}
/>
Reject Reject
</Button> </Button>
</div> </div>
@@ -2681,7 +2705,8 @@ const RecordingForm = ({ type = 'add', initialValues }: RecordingFormProps) => {
{/* Approve Confirmation Modal */} {/* Approve Confirmation Modal */}
{(type as 'add' | 'edit' | 'detail') === 'detail' && {(type as 'add' | 'edit' | 'detail') === 'detail' &&
!isRecordingApproved(initialValues) && (!isLayingCategory || hasGradingData(initialValues)) && ( !isRecordingApproved(initialValues) &&
(!isLayingCategory || hasGradingData(initialValues)) && (
<ConfirmationModal <ConfirmationModal
ref={approveModal.ref} ref={approveModal.ref}
type='success' type='success'
@@ -2700,7 +2725,8 @@ const RecordingForm = ({ type = 'add', initialValues }: RecordingFormProps) => {
{/* Reject Confirmation Modal */} {/* Reject Confirmation Modal */}
{(type as 'add' | 'edit' | 'detail') === 'detail' && {(type as 'add' | 'edit' | 'detail') === 'detail' &&
!isRecordingApproved(initialValues) && (!isLayingCategory || hasGradingData(initialValues)) && ( !isRecordingApproved(initialValues) &&
(!isLayingCategory || hasGradingData(initialValues)) && (
<ConfirmationModal <ConfirmationModal
ref={rejectModal.ref} ref={rejectModal.ref}
type='error' type='error'
@@ -49,7 +49,10 @@ import useSWR from 'swr';
// INTERFACES & PROPS // INTERFACES & PROPS
interface GradingFormProps { interface GradingFormProps {
type?: 'add' | 'edit' | 'detail'; type?: 'add' | 'edit' | 'detail';
initialValues?: RecordingEgg & { grading_eggs?: GradingEgg[] }; initialValues?: RecordingEgg & {
grading_eggs?: GradingEgg[];
gradings?: { grade: string; qty: number }[];
};
} }
const GradingForm = ({ type = 'add', initialValues }: GradingFormProps) => { const GradingForm = ({ type = 'add', initialValues }: GradingFormProps) => {
@@ -190,19 +193,37 @@ const GradingForm = ({ type = 'add', initialValues }: GradingFormProps) => {
recordingEggId = parseInt(recordingId || '0') || 0; recordingEggId = parseInt(recordingId || '0') || 0;
} }
return getRecordingGradingFormInitialValues({ let gradingData: {
recording_egg_id: recordingEggId, recording_egg_id: number;
eggs_grading: grade: string;
initialValues?.grading_eggs?.map((grading: GradingEgg) => ({ qty: number;
}[] = [];
if (initialValues?.grading_eggs && initialValues.grading_eggs.length > 0) {
gradingData = initialValues.grading_eggs.map((grading: GradingEgg) => ({
recording_egg_id: recordingEggId, recording_egg_id: recordingEggId,
grade: grading.grade, grade: grading.grade,
qty: grading.qty, qty: grading.qty,
})) || [], }));
} else if (initialValues?.gradings && initialValues.gradings.length > 0) {
gradingData = initialValues.gradings.map(
(grading: { grade: string; qty: number }) => ({
recording_egg_id: recordingEggId,
grade: grading.grade,
qty: grading.qty,
})
);
}
return getRecordingGradingFormInitialValues({
recording_egg_id: recordingEggId,
eggs_grading: gradingData,
}); });
}, [initialValues, recordingId, konsumsiBaikEggId]); }, [initialValues, recordingId, konsumsiBaikEggId]);
const formik = useFormik<RecordingGradingFormValues>({ const formik = useFormik<RecordingGradingFormValues>({
initialValues: formikInitialValues, initialValues: formikInitialValues,
enableReinitialize: true,
validationSchema: (() => { validationSchema: (() => {
return type === 'edit' return type === 'edit'
? UpdateRecordingGradingFormSchema ? UpdateRecordingGradingFormSchema
@@ -370,7 +391,7 @@ const GradingForm = ({ type = 'add', initialValues }: GradingFormProps) => {
{ recording_egg_id: konsumsiBaikEggId, grade: '', qty: '' }, { recording_egg_id: konsumsiBaikEggId, grade: '', qty: '' },
]); ]);
} }
}, [konsumsiBaikEggId, formik.values.eggs_grading]); }, [konsumsiBaikEggId, formik.values.eggs_grading.length]);
return ( return (
<> <>