mirror of
https://gitlab.com/mbugroup/lti-web-client.git
synced 2026-05-20 13:32:00 +00:00
641 lines
23 KiB
TypeScript
641 lines
23 KiB
TypeScript
'use client';
|
|
|
|
import Badge from '@/components/Badge';
|
|
import Button from '@/components/Button';
|
|
import Card from '@/components/Card';
|
|
import SelectInput, {
|
|
OptionType,
|
|
useSelect,
|
|
} from '@/components/input/SelectInput';
|
|
import PillBadge from '@/components/PillBadge';
|
|
import Table from '@/components/Table';
|
|
import { isResponseSuccess } from '@/lib/api-helper';
|
|
import { cn, formatDate, formatTitleCase } from '@/lib/helper';
|
|
import { ProjectFlockApi } from '@/services/api/production/project-flock';
|
|
import { ProjectFlockKandangApi } from '@/services/api/production';
|
|
import { useTableFilter } from '@/services/hooks/useTableFilter';
|
|
import { ProjectFlock } from '@/types/api/production/project-flock';
|
|
import { ProjectFlockKandang } from '@/types/api/production/project-flock-kandang';
|
|
import { Icon } from '@iconify/react';
|
|
import { useRouter } from 'next/navigation';
|
|
import { useEffect, useState } from 'react';
|
|
import useSWR from 'swr';
|
|
import { FormHeader } from '@/components/helper/form/FormHeader';
|
|
import Link from 'next/link';
|
|
|
|
const ProjectFlockChickinDetail = ({
|
|
projectFlockId,
|
|
}: {
|
|
projectFlockId: number | undefined;
|
|
}) => {
|
|
const router = useRouter();
|
|
|
|
// Tables Props
|
|
const { state: tableFilterState } = useTableFilter({
|
|
initial: { search: '' },
|
|
paramMap: { page: 'page', pageSize: 'limit' },
|
|
});
|
|
|
|
// States
|
|
const [searchProjectFlock, setSearchProjectFlock] = useState('');
|
|
const [selectedProjectFlock, setSelectedProjectFlock] =
|
|
useState<OptionType | null>(null);
|
|
const [projectFlock, setProjectFlock] = useState<ProjectFlock>();
|
|
|
|
// Fetch Data
|
|
const { data: listProjectFlockKandang } = useSWR(
|
|
`${ProjectFlockKandangApi.basePath}?${new URLSearchParams({
|
|
search: searchProjectFlock,
|
|
project_flock_id:
|
|
projectFlock?.id?.toString() ?? projectFlockId?.toString() ?? '',
|
|
}).toString()}`,
|
|
ProjectFlockKandangApi.getAllFetcher
|
|
);
|
|
|
|
const {
|
|
options: options,
|
|
isLoadingOptions: isLoadingListProjectFlock,
|
|
rawData: listProjectFlock,
|
|
} = useSelect<ProjectFlock>(
|
|
ProjectFlockApi.basePath,
|
|
'id',
|
|
'flock_name',
|
|
'',
|
|
{
|
|
search: searchProjectFlock,
|
|
}
|
|
);
|
|
|
|
// Handle Function
|
|
const handleChickinClick = async (
|
|
projectFlockKandang: ProjectFlockKandang
|
|
) => {
|
|
router.push(
|
|
`/production/project-flock/chickin/add/kandang?projectFlockKandangId=${projectFlockKandang.id}&projectFlockId=${projectFlockId ?? selectedProjectFlock?.value}`
|
|
);
|
|
};
|
|
|
|
const handleChangeProjectFlock = (val: OptionType | null) => {
|
|
setSelectedProjectFlock(val);
|
|
if (isResponseSuccess(listProjectFlock) && val) {
|
|
const selected = listProjectFlock.data.find(
|
|
(pf) => pf.id === Number(val.value)
|
|
);
|
|
setProjectFlock(selected);
|
|
} else {
|
|
setProjectFlock(undefined);
|
|
}
|
|
if (projectFlockId) {
|
|
router.push('/production/project-flock/chickin/add');
|
|
}
|
|
if (!val && projectFlockId) {
|
|
router.push('/production/project-flock/chickin/add');
|
|
}
|
|
};
|
|
|
|
useEffect(() => {
|
|
if (projectFlockId && isResponseSuccess(listProjectFlock)) {
|
|
setProjectFlock(
|
|
listProjectFlock.data.find((pf) => pf.id === Number(projectFlockId))
|
|
);
|
|
}
|
|
}, [projectFlockId, listProjectFlock]);
|
|
return (
|
|
<>
|
|
{/* Header */}
|
|
<div className='flex flex-row justify-between items-center px-4 py-4'>
|
|
<div className='flex flex-row items-center h-full gap-2'>
|
|
<Link
|
|
href={`/production/project-flock/detail?projectFlockId=${projectFlock?.id}`}
|
|
className='hover:text-gray-400'
|
|
>
|
|
<Icon icon='mdi:arrow-left' width={24} height={24} />
|
|
</Link>
|
|
<div className='divider divider-horizontal p-0 m-0'></div>
|
|
<div className='text-sm text-neutral'>
|
|
Chick In {projectFlock?.flock_name}
|
|
</div>
|
|
</div>
|
|
</div>
|
|
{/* <FormHeader
|
|
title={`Chick In ${projectFlock?.flock_name ?? 'Project Flock'}`}
|
|
backUrl={`/production/project-flock/detail?projectFlockId=${projectFlock?.id}`}
|
|
/> */}
|
|
{/* <div className='flex flex-col gap-4 w-full my-4'>
|
|
<div className='max-w-full sm:max-w-1/2 md:max-w-3/5 lg:max-w-2/5'>
|
|
<SelectInput
|
|
required
|
|
label='Ganti Project Flock'
|
|
placeholder='Pilih Project Flock'
|
|
options={options}
|
|
onInputChange={(val) => {
|
|
setSearchProjectFlock(val);
|
|
}}
|
|
isLoading={isLoadingListProjectFlock}
|
|
value={
|
|
projectFlock
|
|
? {
|
|
label: `${projectFlock?.flock_name}`,
|
|
value: projectFlock?.id,
|
|
}
|
|
: null
|
|
}
|
|
onChange={(val) => {
|
|
handleChangeProjectFlock(val as OptionType | null);
|
|
}}
|
|
isSearchable
|
|
isClearable
|
|
startAdornment={
|
|
projectFlock && (
|
|
<Badge
|
|
variant='soft'
|
|
color='success'
|
|
size='sm'
|
|
className={{
|
|
badge: 'whitespace-nowrap font-semibold',
|
|
}}
|
|
>
|
|
Periode {projectFlock?.period}
|
|
</Badge>
|
|
)
|
|
}
|
|
/>
|
|
</div>
|
|
</div> */}
|
|
{/* Informasi Umum */}
|
|
{projectFlock && (
|
|
<div className='border-t-1 border-gray-300'>
|
|
<div className='p-4 flex flex-col gap-4'>
|
|
<h2 className='text-2xl font-semibold'>Informasi Umum</h2>
|
|
{/* Badge Row */}
|
|
<div className='flex flex-row gap-2'>
|
|
<Badge
|
|
variant='soft'
|
|
color={
|
|
projectFlock.approval.step_number == 1
|
|
? 'neutral'
|
|
: projectFlock.approval.step_number == 2
|
|
? 'success'
|
|
: projectFlock.approval.step_number >= 3
|
|
? 'error'
|
|
: undefined
|
|
}
|
|
className={{
|
|
badge: 'rounded-lg px-2',
|
|
}}
|
|
>
|
|
<Icon
|
|
icon='mdi:circle'
|
|
width={12}
|
|
height={12}
|
|
color={
|
|
projectFlock.approval.step_number == 1
|
|
? 'neutral'
|
|
: projectFlock.approval.step_number == 2
|
|
? 'success'
|
|
: projectFlock.approval.step_number >= 3
|
|
? 'error'
|
|
: undefined
|
|
}
|
|
/>{' '}
|
|
{projectFlock.approval.step_name}
|
|
</Badge>
|
|
<div className='divider divider-horizontal p-0 m-0'></div>
|
|
<Badge
|
|
color='neutral'
|
|
variant='soft'
|
|
className={{ badge: 'rounded-lg px-2' }}
|
|
>
|
|
<Icon icon='mdi:bookmark' width={12} height={12} />
|
|
{` ${formatTitleCase(projectFlock.category)}`}
|
|
</Badge>
|
|
</div>
|
|
{/* Information Grid */}
|
|
<div className='grid grid-cols-3 gap-4'>
|
|
<div className='col-span-1 flex flex-row items-center text-gray-400 font-semibold gap-2'>
|
|
<Icon width={14} height={14} icon='mdi:account' /> Submitted
|
|
</div>
|
|
<div className='col-span-2'>
|
|
<Badge
|
|
variant='soft'
|
|
color='neutral'
|
|
className={{
|
|
badge: 'rounded-lg px-2',
|
|
}}
|
|
>
|
|
<Icon icon='mdi:account-circle' width={14} height={14} />{' '}
|
|
{projectFlock.created_user.name}
|
|
</Badge>
|
|
</div>
|
|
|
|
<div className='col-span-1 flex flex-row items-center text-gray-400 font-semibold gap-2'>
|
|
<Icon width={14} height={14} icon={'mdi:clock'} /> History
|
|
</div>
|
|
<div className='col-span-2'>
|
|
<Button variant='outline' className='py-1 text-sm'>
|
|
See History{' '}
|
|
<Icon
|
|
icon='mdi:arrow-top-right-thin'
|
|
width={11}
|
|
height={11}
|
|
/>
|
|
</Button>
|
|
</div>
|
|
|
|
{/* BARIS 1 */}
|
|
<div
|
|
className='col-span-1 flex flex-row items-center text-gray-400 font-semibold gap-2
|
|
relative
|
|
before:content-[""] before:absolute before:left-[5px] before:top-[90%] before:bottom-[-100%] before:w-[1px] before:border-1 before:border-dashed before:border-gray-400'
|
|
>
|
|
<Icon width={14} height={14} icon='mdi:circle-slice-8' /> Area
|
|
</div>
|
|
<div className='col-span-2'>{projectFlock.area.name}</div>
|
|
|
|
{/* BARIS 2 */}
|
|
<div
|
|
className='col-span-1 flex flex-row items-center text-gray-400 font-semibold gap-2
|
|
relative
|
|
before:content-[""] before:absolute before:left-[5px] before:top-[90%] before:bottom-[-100%] before:w-[1px] before:border-1 before:border-dashed before:border-gray-400'
|
|
>
|
|
<Icon width={14} height={14} icon='mdi:circle-slice-8' /> Lokasi
|
|
</div>
|
|
<div className='col-span-2'>{projectFlock.location.name}</div>
|
|
|
|
<div
|
|
className='col-span-1 flex flex-row items-center text-gray-400 font-semibold gap-2
|
|
relative
|
|
before:content-[""] before:absolute before:left-[5px] before:top-[90%] before:bottom-[-100%] before:w-[1px] before:border-1 before:border-dashed before:border-gray-400'
|
|
>
|
|
<Icon width={14} height={14} icon='mdi:circle-slice-8' /> FCR
|
|
</div>
|
|
<div className='col-span-2'>{projectFlock.fcr.name}</div>
|
|
|
|
{/* BARIS 3 (Terakhir - TIDAK PERLU garis di bawahnya) */}
|
|
<div className='col-span-1 flex flex-row items-center text-gray-400 font-semibold gap-2'>
|
|
<Icon width={14} height={14} icon='mdi:circle-slice-8' />{' '}
|
|
Kategori
|
|
</div>
|
|
<div className='col-span-2'>
|
|
{formatTitleCase(projectFlock.category)}
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
)}
|
|
{/* <Card
|
|
title='Informasi Flock'
|
|
className={{
|
|
wrapper: 'w-full bg-white mb-3',
|
|
}}
|
|
>
|
|
<Table<ProjectFlock>
|
|
emptyContent={
|
|
<div className='w-full p-5 text-center'>
|
|
<span className='text-lg opacity-50'>
|
|
Pilih project flock terlebih dahulu...
|
|
</span>
|
|
</div>
|
|
}
|
|
data={projectFlock ? [projectFlock] : []}
|
|
columns={[
|
|
{
|
|
header: 'ID',
|
|
accessorKey: 'id',
|
|
},
|
|
{
|
|
header: 'Area',
|
|
accessorKey: 'area.name',
|
|
},
|
|
{
|
|
header: 'Lokasi',
|
|
accessorKey: 'location.name',
|
|
},
|
|
{
|
|
header: 'Nama Flock',
|
|
accessorKey: 'flock_name',
|
|
},
|
|
{
|
|
header: 'Kategori',
|
|
accessorKey: 'category',
|
|
},
|
|
{
|
|
header: 'Status',
|
|
accessorKey: 'status',
|
|
cell: (props) => {
|
|
return props.row.original.approval?.step_name ? (
|
|
<PillBadge
|
|
color={(() => {
|
|
switch (
|
|
props.row.original.approval?.step_name.toUpperCase()
|
|
) {
|
|
case 'AKTIF':
|
|
return 'red';
|
|
case 'PENGAJUAN':
|
|
return 'green';
|
|
default:
|
|
return 'gray';
|
|
}
|
|
})()}
|
|
content={props.row.original.approval?.step_name
|
|
.toLowerCase()
|
|
.replace(/_/g, ' ')
|
|
.replace(/\b\w/g, (char) => char.toUpperCase())}
|
|
/>
|
|
) : (
|
|
'-'
|
|
);
|
|
},
|
|
},
|
|
{
|
|
header: 'FCR Layer',
|
|
accessorKey: 'fcr.name',
|
|
},
|
|
]}
|
|
page={undefined}
|
|
className={{
|
|
containerClassName: cn({
|
|
'mb-20': projectFlock && projectFlock.kandangs?.length === 0,
|
|
}),
|
|
tableWrapperClassName: 'overflow-x-auto min-h-full!',
|
|
tableClassName: 'font-inter w-full table-auto min-h-full!',
|
|
headerRowClassName: 'border-b border-b-gray-200',
|
|
headerColumnClassName:
|
|
'px-6 py-3 text-xs font-semibold text-gray-500 last:flex last:flex-row last:justify-end',
|
|
bodyRowClassName: 'border-b border-b-gray-200',
|
|
bodyColumnClassName:
|
|
'px-6 py-3 last:flex last:flex-row last:justify-end',
|
|
paginationClassName: 'hidden',
|
|
}}
|
|
/>
|
|
</Card> */}
|
|
{/* Card Kandangs */}
|
|
<div className='border-t-1 border-gray-300'>
|
|
<div className='p-4 flex flex-col gap-4'>
|
|
<h2 className='text-2xl font-semibold'>Daftar Kandang</h2>
|
|
{isResponseSuccess(listProjectFlock) ? (
|
|
<>
|
|
{/* Badge Row */}
|
|
<div className='flex flex-row gap-2'>
|
|
<Badge
|
|
variant='soft'
|
|
color={'success'}
|
|
className={{
|
|
badge: 'rounded-lg px-2',
|
|
}}
|
|
>
|
|
<Icon
|
|
icon='mdi:circle'
|
|
width={12}
|
|
height={12}
|
|
color={'success'}
|
|
/>{' '}
|
|
Disetujui (
|
|
{isResponseSuccess(listProjectFlockKandang) &&
|
|
listProjectFlockKandang.data.filter(
|
|
(k) => k.approval?.step_number == 1
|
|
).length}
|
|
)
|
|
</Badge>
|
|
<div className='divider divider-horizontal p-0 m-0'></div>
|
|
<Badge
|
|
variant='soft'
|
|
color={'neutral'}
|
|
className={{
|
|
badge: 'rounded-lg px-2',
|
|
}}
|
|
>
|
|
<Icon
|
|
icon='mdi:circle'
|
|
width={12}
|
|
height={12}
|
|
color={'neutral'}
|
|
/>{' '}
|
|
Pengajuan (
|
|
{isResponseSuccess(listProjectFlockKandang) &&
|
|
listProjectFlockKandang.data.filter(
|
|
(k) => k.approval?.step_number == 2
|
|
).length}
|
|
)
|
|
</Badge>
|
|
<div className='divider divider-horizontal p-0 m-0'></div>
|
|
<Badge
|
|
color='error'
|
|
variant='soft'
|
|
className={{ badge: 'rounded-lg px-2' }}
|
|
>
|
|
<Icon
|
|
icon={`mdi:circle`}
|
|
width={12}
|
|
height={12}
|
|
color='error'
|
|
/>
|
|
Belum Chickin (
|
|
{isResponseSuccess(listProjectFlockKandang) &&
|
|
listProjectFlockKandang.data.filter(
|
|
(k) => k.approval == null
|
|
).length}
|
|
)
|
|
</Badge>
|
|
</div>
|
|
{/* Card Kandang */}
|
|
<Card
|
|
variant='bordered'
|
|
className={{
|
|
wrapper: 'w-full',
|
|
body: 'p-3',
|
|
}}
|
|
>
|
|
<div className='flex flex-col gap-6'>
|
|
{isResponseSuccess(listProjectFlockKandang) &&
|
|
listProjectFlockKandang.data.map((kandang) => (
|
|
<div
|
|
key={kandang.id}
|
|
className='flex flex-row justify-between items-center'
|
|
>
|
|
<div className='flex flex-row gap-2 items-center cursor-pointer text-gray-400'>
|
|
<Badge
|
|
variant='soft'
|
|
color={
|
|
kandang.approval
|
|
? kandang.approval.step_number == 1
|
|
? 'success'
|
|
: 'neutral'
|
|
: 'error'
|
|
}
|
|
className={{
|
|
badge: 'rounded-lg px-2',
|
|
}}
|
|
>
|
|
<Icon
|
|
icon='mdi:circle'
|
|
width={12}
|
|
height={12}
|
|
color={
|
|
kandang.approval
|
|
? kandang.approval.step_number == 1
|
|
? 'success'
|
|
: 'neutral'
|
|
: 'gray'
|
|
}
|
|
/>
|
|
</Badge>
|
|
<span className='font-semibold'>
|
|
{kandang.kandang.name}
|
|
</span>
|
|
</div>
|
|
<Button
|
|
variant='outline'
|
|
className='py-1 text-sm'
|
|
onClick={() => {
|
|
handleChickinClick(kandang);
|
|
}}
|
|
disabled={projectFlock?.approval?.step_number === 1}
|
|
>
|
|
Chick In{' '}
|
|
<Icon
|
|
icon='mdi:arrow-top-right-thin'
|
|
width={11}
|
|
height={11}
|
|
/>
|
|
</Button>
|
|
</div>
|
|
))}
|
|
</div>
|
|
</Card>
|
|
</>
|
|
) : (
|
|
<div className='w-full p-5 text-center'>
|
|
<span className='text-lg opacity-50'>
|
|
Pilih project flock terlebih dahulu...
|
|
</span>
|
|
</div>
|
|
)}
|
|
</div>
|
|
</div>
|
|
{/* <Card
|
|
title='Daftar Kandang'
|
|
className={{
|
|
wrapper: 'w-full bg-white',
|
|
}}
|
|
>
|
|
<Table<ProjectFlockKandang>
|
|
emptyContent={
|
|
<div className='w-full p-5 text-center'>
|
|
<span className='text-lg opacity-50'>
|
|
Pilih project flock terlebih dahulu...
|
|
</span>
|
|
</div>
|
|
}
|
|
data={
|
|
projectFlock && isResponseSuccess(listProjectFlockKandang)
|
|
? listProjectFlockKandang.data
|
|
: []
|
|
}
|
|
columns={[
|
|
{
|
|
header: '#',
|
|
cell: (props) =>
|
|
tableFilterState.pageSize * (tableFilterState.page - 1) +
|
|
props.row.index +
|
|
1,
|
|
},
|
|
{
|
|
accessorFn: (row) => row?.project_flock?.area?.name,
|
|
header: 'Area',
|
|
},
|
|
{
|
|
accessorFn: (row) => row?.project_flock?.location?.name,
|
|
header: 'Lokasi',
|
|
},
|
|
{
|
|
accessorKey: 'kandang.name',
|
|
header: 'Kandang',
|
|
},
|
|
{
|
|
accessorKey: 'kandang.capacity',
|
|
header: 'Kapasitas',
|
|
},
|
|
{
|
|
accessorFn: () => projectFlock?.period,
|
|
header: 'Periode',
|
|
},
|
|
{
|
|
accessorKey: 'approval.step_name',
|
|
header: 'Status',
|
|
cell: (props) => {
|
|
return props.row.original.approval?.step_name ? (
|
|
<PillBadge
|
|
color={(() => {
|
|
switch (
|
|
props.row.original.approval?.step_name.toUpperCase()
|
|
) {
|
|
case 'DISETUJUI':
|
|
return 'green';
|
|
case 'PENGAJUAN':
|
|
return 'yellow';
|
|
default:
|
|
return 'gray';
|
|
}
|
|
})()}
|
|
content={props.row.original.approval?.step_name
|
|
.toLowerCase()
|
|
.replace(/_/g, ' ')
|
|
.replace(/\b\w/g, (char) => char.toUpperCase())}
|
|
/>
|
|
) : projectFlock?.approval?.step_number === 1 ? (
|
|
<PillBadge color='red' content={'Tidak Dapat Chick In'} />
|
|
) : (
|
|
<PillBadge color='gray' content={'Belum Chick In'} />
|
|
);
|
|
},
|
|
},
|
|
{
|
|
header: 'Aksi',
|
|
cell: (props) => {
|
|
return (
|
|
<>
|
|
<Button
|
|
color='success'
|
|
variant='outline'
|
|
onClick={() => {
|
|
handleChickinClick(props.row.original);
|
|
}}
|
|
className='p-1'
|
|
disabled={projectFlock?.approval?.step_number === 1}
|
|
>
|
|
<Icon
|
|
icon='mdi:home-import-outline'
|
|
width={18}
|
|
height={18}
|
|
/>
|
|
Chickin
|
|
</Button>
|
|
</>
|
|
);
|
|
},
|
|
},
|
|
]}
|
|
page={undefined}
|
|
className={{
|
|
containerClassName: cn({
|
|
'mb-20': projectFlock && projectFlock.kandangs?.length === 0,
|
|
}),
|
|
tableWrapperClassName: 'overflow-x-auto min-h-full!',
|
|
tableClassName: 'font-inter w-full table-auto min-h-full!',
|
|
headerRowClassName: 'border-b border-b-gray-200',
|
|
headerColumnClassName:
|
|
'px-6 py-3 text-xs font-semibold text-gray-500 last:flex last:flex-row last:justify-end',
|
|
bodyRowClassName: 'border-b border-b-gray-200',
|
|
bodyColumnClassName:
|
|
'px-6 py-3 last:flex last:flex-row last:justify-end',
|
|
paginationClassName: 'hidden',
|
|
}}
|
|
/>
|
|
</Card> */}
|
|
</>
|
|
);
|
|
};
|
|
|
|
export default ProjectFlockChickinDetail;
|