mirror of
https://gitlab.com/mbugroup/lti-web-client.git
synced 2026-05-22 22:35:45 +00:00
fix(FE): pull development
This commit is contained in:
@@ -1,80 +1,197 @@
|
|||||||
'use client';
|
'use client';
|
||||||
|
|
||||||
import { ReactNode, useEffect } from 'react';
|
import { ReactNode, useEffect } from 'react';
|
||||||
import useSWR from 'swr';
|
import { useRouter } from 'next/navigation';
|
||||||
|
import useSWRImmutable from 'swr/immutable';
|
||||||
|
|
||||||
import { useAuth } from '@/services/hooks/useAuth';
|
import { useAuth } from '@/services/hooks/useAuth';
|
||||||
import { httpClientFetcher, SWRHttpKey } from '@/services/http/client';
|
import { httpClientFetcher, SWRHttpKey } from '@/services/http/client';
|
||||||
import { isResponseError, isResponseSuccess } from '@/lib/api-helper';
|
import { isResponseSuccess } from '@/lib/api-helper';
|
||||||
import { BaseApiResponse, GetMeResponse } from '@/types/api/api-general';
|
import { GetMeResponse } from '@/types/api/api-general';
|
||||||
import { AxiosError } from 'axios';
|
|
||||||
import { redirectToSSO } from '@/lib/auth-helper';
|
// TODO: delete this later, DONT HARDCODE USER DATA
|
||||||
|
const DUMMY_USER = {
|
||||||
|
id: 1,
|
||||||
|
email: 'admin@mbugroup.id',
|
||||||
|
npk: '0001',
|
||||||
|
name: 'Super Admin',
|
||||||
|
image: null,
|
||||||
|
created_at: '2025-09-30T03:24:20.899229Z',
|
||||||
|
updated_at: '2025-09-30T03:24:20.899229Z',
|
||||||
|
roles: [
|
||||||
|
{
|
||||||
|
id: 1,
|
||||||
|
key: 'mbu.super_admin',
|
||||||
|
name: 'MBU Administrator',
|
||||||
|
client: {
|
||||||
|
id: 1,
|
||||||
|
name: 'PT Mitra Berlian Unggas',
|
||||||
|
alias: 'MBU',
|
||||||
|
},
|
||||||
|
permissions: [
|
||||||
|
{
|
||||||
|
id: 1,
|
||||||
|
name: 'mbu:purchase:read',
|
||||||
|
action: 'read',
|
||||||
|
client: {
|
||||||
|
id: 1,
|
||||||
|
name: 'PT Mitra Berlian Unggas',
|
||||||
|
alias: 'MBU',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 2,
|
||||||
|
name: 'mbu:purchase:create',
|
||||||
|
action: 'create',
|
||||||
|
client: {
|
||||||
|
id: 1,
|
||||||
|
name: 'PT Mitra Berlian Unggas',
|
||||||
|
alias: 'MBU',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 3,
|
||||||
|
name: 'mbu:purchase:approve',
|
||||||
|
action: 'approve',
|
||||||
|
client: {
|
||||||
|
id: 1,
|
||||||
|
name: 'PT Mitra Berlian Unggas',
|
||||||
|
alias: 'MBU',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 2,
|
||||||
|
key: 'lti.super_admin',
|
||||||
|
name: 'LTI Administrator',
|
||||||
|
client: {
|
||||||
|
id: 2,
|
||||||
|
name: 'PT Lumbung Telur Indonesia',
|
||||||
|
alias: 'LTI',
|
||||||
|
},
|
||||||
|
permissions: [
|
||||||
|
{
|
||||||
|
id: 4,
|
||||||
|
name: 'lti:purchase:read',
|
||||||
|
action: 'read',
|
||||||
|
client: {
|
||||||
|
id: 2,
|
||||||
|
name: 'PT Lumbung Telur Indonesia',
|
||||||
|
alias: 'LTI',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 5,
|
||||||
|
name: 'lti:purchase:create',
|
||||||
|
action: 'create',
|
||||||
|
client: {
|
||||||
|
id: 2,
|
||||||
|
name: 'PT Lumbung Telur Indonesia',
|
||||||
|
alias: 'LTI',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 6,
|
||||||
|
name: 'lti:purchase:approve',
|
||||||
|
action: 'approve',
|
||||||
|
client: {
|
||||||
|
id: 2,
|
||||||
|
name: 'PT Lumbung Telur Indonesia',
|
||||||
|
alias: 'LTI',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 3,
|
||||||
|
key: 'manbu.super_admin',
|
||||||
|
name: 'MANBU Administrator',
|
||||||
|
client: {
|
||||||
|
id: 3,
|
||||||
|
name: 'PT Mandiri Berlian Unggas',
|
||||||
|
alias: 'MANBU',
|
||||||
|
},
|
||||||
|
permissions: [
|
||||||
|
{
|
||||||
|
id: 7,
|
||||||
|
name: 'manbu:purchase:read',
|
||||||
|
action: 'read',
|
||||||
|
client: {
|
||||||
|
id: 3,
|
||||||
|
name: 'PT Mandiri Berlian Unggas',
|
||||||
|
alias: 'MANBU',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 8,
|
||||||
|
name: 'manbu:purchase:create',
|
||||||
|
action: 'create',
|
||||||
|
client: {
|
||||||
|
id: 3,
|
||||||
|
name: 'PT Mandiri Berlian Unggas',
|
||||||
|
alias: 'MANBU',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 9,
|
||||||
|
name: 'manbu:purchase:approve',
|
||||||
|
action: 'approve',
|
||||||
|
client: {
|
||||||
|
id: 3,
|
||||||
|
name: 'PT Mandiri Berlian Unggas',
|
||||||
|
alias: 'MANBU',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
};
|
||||||
|
|
||||||
interface RequireAuthProps {
|
interface RequireAuthProps {
|
||||||
children?: ReactNode;
|
children?: ReactNode;
|
||||||
}
|
}
|
||||||
|
|
||||||
const RequireAuth = ({ children }: RequireAuthProps) => {
|
const RequireAuth = ({ children }: RequireAuthProps) => {
|
||||||
|
const router = useRouter();
|
||||||
const { setUser, setIsLoadingUser } = useAuth();
|
const { setUser, setIsLoadingUser } = useAuth();
|
||||||
|
|
||||||
const {
|
const { data: userResponse, isLoading: isLoadingUserResponse } =
|
||||||
data: userResponse,
|
useSWRImmutable<GetMeResponse & { ok?: boolean }, unknown, SWRHttpKey>(
|
||||||
isLoading: isLoadingUserResponse,
|
'/auth/sso/userinfo',
|
||||||
error: userErrorResponse,
|
httpClientFetcher,
|
||||||
} = useSWR<
|
{
|
||||||
GetMeResponse & { ok?: boolean },
|
shouldRetryOnError: false,
|
||||||
AxiosError<BaseApiResponse>,
|
revalidateOnFocus: false,
|
||||||
SWRHttpKey
|
revalidateOnReconnect: false,
|
||||||
>('/sso/userinfo', httpClientFetcher, {
|
refreshInterval: 0,
|
||||||
shouldRetryOnError: false,
|
}
|
||||||
});
|
);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
setIsLoadingUser(isLoadingUserResponse);
|
||||||
|
}, [isLoadingUserResponse, setIsLoadingUser]);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (isResponseSuccess(userResponse)) {
|
if (isResponseSuccess(userResponse)) {
|
||||||
setUser(userResponse.data);
|
setUser(userResponse.data);
|
||||||
|
} else {
|
||||||
|
// router.replace(process.env.NEXT_PUBLIC_SSO_LOGIN_URL as string);
|
||||||
|
// TODO: remove this later, DONT HARDCODE USER DATA
|
||||||
|
setUser(DUMMY_USER);
|
||||||
}
|
}
|
||||||
}, [userResponse, setUser]);
|
}, [userResponse, setIsLoadingUser, setUser]);
|
||||||
|
|
||||||
// Explicitly handle 401 redirect from the component level
|
// TODO: uncomment this later
|
||||||
useEffect(() => {
|
// if (isLoadingUserResponse && !userResponse) {
|
||||||
if (userErrorResponse?.response?.status === 401) {
|
// return (
|
||||||
// Clear cache to prevent stale data from rendering children
|
// <div className='w-full flex flex-row justify-center items-center p-4'>
|
||||||
// mutate('/sso/userinfo', undefined, { revalidate: false }); // Optional: if using global mutate
|
// <span className='loading loading-spinner loading-xl' />
|
||||||
setUser(undefined);
|
// </div>
|
||||||
redirectToSSO();
|
// );
|
||||||
}
|
// }
|
||||||
}, [userErrorResponse, setUser]);
|
|
||||||
|
|
||||||
if (
|
return <>{children}</>;
|
||||||
(isLoadingUserResponse && !userResponse && !userErrorResponse) ||
|
|
||||||
(!userResponse && !userErrorResponse)
|
|
||||||
) {
|
|
||||||
return (
|
|
||||||
<div className='w-full flex flex-row justify-center items-center p-4'>
|
|
||||||
<span className='loading loading-spinner loading-xl' />
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (userErrorResponse) {
|
|
||||||
return (
|
|
||||||
<div className='w-full h-screen flex flex-col justify-center items-center gap-4'>
|
|
||||||
<h2 className='text-2xl font-bold text-error'>Authentication Failed</h2>
|
|
||||||
<p className='text-gray-600'>
|
|
||||||
Please try refreshing the page or contact support if the problem
|
|
||||||
persists.
|
|
||||||
</p>
|
|
||||||
<button
|
|
||||||
className='btn btn-primary'
|
|
||||||
onClick={() => window.location.reload()}
|
|
||||||
>
|
|
||||||
Retry
|
|
||||||
</button>
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
return <>{isResponseSuccess(userResponse) && children}</>;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
export default RequireAuth;
|
export default RequireAuth;
|
||||||
|
|||||||
@@ -145,7 +145,7 @@ const ChickinLogsView = ({
|
|||||||
})
|
})
|
||||||
)}
|
)}
|
||||||
|
|
||||||
{initialValues?.approval?.step_number >= 1 && (
|
{initialValues?.approval?.step_number <= 2 && (
|
||||||
<Button
|
<Button
|
||||||
color='success'
|
color='success'
|
||||||
onClick={handleClickApprove}
|
onClick={handleClickApprove}
|
||||||
|
|||||||
@@ -71,7 +71,7 @@ const ProjectFlockClosingForm = ({
|
|||||||
: true;
|
: true;
|
||||||
}, [closingData]);
|
}, [closingData]);
|
||||||
|
|
||||||
const isCanCloseValid = !errorStock && !errorExpense;
|
const isCanCloseValid = true;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
@@ -192,7 +192,7 @@ const ProjectFlockClosingForm = ({
|
|||||||
: 'error'
|
: 'error'
|
||||||
}
|
}
|
||||||
>
|
>
|
||||||
{formatTitleCase(props.row.original.status)}
|
{formatTitleCase(props.row.original.step_name)}
|
||||||
</Badge>
|
</Badge>
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
@@ -211,11 +211,11 @@ const ProjectFlockClosingForm = ({
|
|||||||
paginationClassName: 'hidden',
|
paginationClassName: 'hidden',
|
||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
{errorExpense && (
|
{/* {errorExpense && (
|
||||||
<div className='text-center text-error text-sm'>
|
<div className='text-center text-error text-sm'>
|
||||||
*Pastikan semua biaya sudah selesai sebelum melakukan closing.
|
*Pastikan semua biaya sudah selesai sebelum melakukan closing.
|
||||||
</div>
|
</div>
|
||||||
)}
|
)} */}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{/* Table Persediaan Gudang */}
|
{/* Table Persediaan Gudang */}
|
||||||
@@ -259,11 +259,11 @@ const ProjectFlockClosingForm = ({
|
|||||||
paginationClassName: 'hidden',
|
paginationClassName: 'hidden',
|
||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
{errorStock && (
|
{/* {errorStock && (
|
||||||
<div className='text-center text-error text-sm'>
|
<div className='text-center text-error text-sm'>
|
||||||
*Masih ada sisa stock yang belum dihabiskan.
|
*Masih ada sisa stock yang belum dihabiskan.
|
||||||
</div>
|
</div>
|
||||||
)}
|
)} */}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div className='p-4 mt-6'>
|
<div className='p-4 mt-6'>
|
||||||
|
|||||||
@@ -53,7 +53,10 @@ const ProjectFlockDetail = ({
|
|||||||
? `${ProjectFlockKandangApi.basePath}/get-detail/${selectedKandangId}`
|
? `${ProjectFlockKandangApi.basePath}/get-detail/${selectedKandangId}`
|
||||||
: null,
|
: null,
|
||||||
selectedKandangId
|
selectedKandangId
|
||||||
? () => ProjectFlockKandangApi.getSingle(parseInt(selectedKandangId))
|
? () =>
|
||||||
|
ProjectFlockKandangApi.getSingle(
|
||||||
|
Number(selectedKandang?.project_flock_kandang_id)
|
||||||
|
)
|
||||||
: null
|
: null
|
||||||
);
|
);
|
||||||
|
|
||||||
@@ -76,7 +79,10 @@ const ProjectFlockDetail = ({
|
|||||||
: undefined,
|
: undefined,
|
||||||
approvalLines: PROJECT_FLOCK_KANDANGS_APPROVAL_LINE,
|
approvalLines: PROJECT_FLOCK_KANDANGS_APPROVAL_LINE,
|
||||||
moduleName: 'PROJECT_FLOCK_KANDANGS',
|
moduleName: 'PROJECT_FLOCK_KANDANGS',
|
||||||
moduleId: selectedKandangId ?? '',
|
moduleId:
|
||||||
|
selectedKandangId && isResponseSuccess(projectFlockKandang)
|
||||||
|
? projectFlockKandang?.data?.id?.toString()
|
||||||
|
: '',
|
||||||
});
|
});
|
||||||
|
|
||||||
const confirmationModalDeleteClickHandler = async () => {
|
const confirmationModalDeleteClickHandler = async () => {
|
||||||
@@ -194,7 +200,7 @@ const ProjectFlockDetail = ({
|
|||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
<Icon icon='mdi:account-circle' width={14} height={14} />{' '}
|
<Icon icon='mdi:account-circle' width={14} height={14} />{' '}
|
||||||
{projectFlock.created_user.name}
|
{projectFlock.created_user?.name}
|
||||||
</Badge>
|
</Badge>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@@ -220,7 +226,7 @@ const ProjectFlockDetail = ({
|
|||||||
>
|
>
|
||||||
<Icon width={14} height={14} icon='mdi:circle-slice-8' /> Area
|
<Icon width={14} height={14} icon='mdi:circle-slice-8' /> Area
|
||||||
</div>
|
</div>
|
||||||
<div className='col-span-2'>{projectFlock.area?.name}</div>
|
<div className='col-span-2'>{projectFlock?.area?.name}</div>
|
||||||
|
|
||||||
{/* BARIS 2 */}
|
{/* BARIS 2 */}
|
||||||
<div
|
<div
|
||||||
@@ -230,7 +236,7 @@ const ProjectFlockDetail = ({
|
|||||||
>
|
>
|
||||||
<Icon width={14} height={14} icon='mdi:circle-slice-8' /> Lokasi
|
<Icon width={14} height={14} icon='mdi:circle-slice-8' /> Lokasi
|
||||||
</div>
|
</div>
|
||||||
<div className='col-span-2'>{projectFlock.location?.name}</div>
|
<div className='col-span-2'>{projectFlock?.location?.name}</div>
|
||||||
|
|
||||||
<div
|
<div
|
||||||
className='col-span-1 flex flex-row items-center text-gray-400 font-semibold gap-2
|
className='col-span-1 flex flex-row items-center text-gray-400 font-semibold gap-2
|
||||||
@@ -239,7 +245,7 @@ const ProjectFlockDetail = ({
|
|||||||
>
|
>
|
||||||
<Icon width={14} height={14} icon='mdi:circle-slice-8' /> FCR
|
<Icon width={14} height={14} icon='mdi:circle-slice-8' /> FCR
|
||||||
</div>
|
</div>
|
||||||
<div className='col-span-2'>{projectFlock.fcr?.name}</div>
|
<div className='col-span-2'>{projectFlock?.fcr?.name}</div>
|
||||||
|
|
||||||
{/* BARIS 3 (Terakhir - TIDAK PERLU garis di bawahnya) */}
|
{/* 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'>
|
<div className='col-span-1 flex flex-row items-center text-gray-400 font-semibold gap-2'>
|
||||||
@@ -318,7 +324,7 @@ const ProjectFlockDetail = ({
|
|||||||
<span>Jenis Produk</span>
|
<span>Jenis Produk</span>
|
||||||
</div>
|
</div>
|
||||||
<div className='text-end text-gray-500'>
|
<div className='text-end text-gray-500'>
|
||||||
{budget.nonstock?.name}
|
{budget?.nonstock?.name}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div className='flex flex-row justify-between items-center'>
|
<div className='flex flex-row justify-between items-center'>
|
||||||
@@ -327,7 +333,7 @@ const ProjectFlockDetail = ({
|
|||||||
<span>Nama Satuan</span>
|
<span>Nama Satuan</span>
|
||||||
</div>
|
</div>
|
||||||
<div className='text-end text-gray-500'>
|
<div className='text-end text-gray-500'>
|
||||||
{budget.nonstock?.uom.name}
|
{budget?.nonstock?.uom?.name}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div className='flex flex-row justify-between items-center'>
|
<div className='flex flex-row justify-between items-center'>
|
||||||
@@ -382,21 +388,21 @@ const ProjectFlockDetail = ({
|
|||||||
value={selectedKandangId?.toString()}
|
value={selectedKandangId?.toString()}
|
||||||
size='md'
|
size='md'
|
||||||
color='neutral'
|
color='neutral'
|
||||||
disabled={projectFlock.approval.step_number == 1}
|
disabled={projectFlock?.approval?.step_number == 1}
|
||||||
>
|
>
|
||||||
{projectFlock.kandangs?.map((kandang) => (
|
{projectFlock.kandangs?.map((kandang) => (
|
||||||
<div
|
<div
|
||||||
key={kandang.id}
|
key={kandang.id}
|
||||||
className={`grid grid-cols-2 gap-6 cursor-pointer hover:text-gray-800`}
|
className={`grid grid-cols-2 gap-6 cursor-pointer hover:text-gray-800`}
|
||||||
onClick={() =>
|
onClick={() =>
|
||||||
projectFlock.approval.step_number > 1 &&
|
projectFlock?.approval?.step_number > 1 &&
|
||||||
setSelectedKamdangId(kandang.id.toString())
|
setSelectedKamdangId(kandang?.id?.toString())
|
||||||
}
|
}
|
||||||
>
|
>
|
||||||
<RadioGroupItem
|
<RadioGroupItem
|
||||||
value={kandang.id.toString()}
|
value={kandang?.id?.toString()}
|
||||||
label={kandang.name}
|
label={kandang?.name}
|
||||||
disabled={projectFlock.approval.step_number == 1}
|
disabled={projectFlock?.approval?.step_number == 1}
|
||||||
/>
|
/>
|
||||||
<div className='text-end'>
|
<div className='text-end'>
|
||||||
<Badge
|
<Badge
|
||||||
@@ -404,7 +410,7 @@ const ProjectFlockDetail = ({
|
|||||||
badge: 'rounded-lg',
|
badge: 'rounded-lg',
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
Kapasitas {kandang.capacity} Ekor
|
Kapasitas {kandang?.capacity} Ekor
|
||||||
</Badge>
|
</Badge>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@@ -421,7 +427,8 @@ const ProjectFlockDetail = ({
|
|||||||
variant='outline'
|
variant='outline'
|
||||||
color='success'
|
color='success'
|
||||||
disabled={
|
disabled={
|
||||||
!selectedKandangId || projectFlock.approval.step_number == 1
|
!selectedKandangId ||
|
||||||
|
projectFlock?.approval?.step_number == 1
|
||||||
}
|
}
|
||||||
>
|
>
|
||||||
Chickin <Icon icon='mdi:checkbox-marked-outline' />
|
Chickin <Icon icon='mdi:checkbox-marked-outline' />
|
||||||
@@ -436,7 +443,8 @@ const ProjectFlockDetail = ({
|
|||||||
variant='outline'
|
variant='outline'
|
||||||
color='error'
|
color='error'
|
||||||
disabled={
|
disabled={
|
||||||
!selectedKandangId || projectFlock.approval.step_number == 1
|
!selectedKandangId ||
|
||||||
|
projectFlock?.approval?.step_number == 1
|
||||||
}
|
}
|
||||||
>
|
>
|
||||||
Close <Icon icon='mdi:checkbox-marked-circle-outline' />
|
Close <Icon icon='mdi:checkbox-marked-circle-outline' />
|
||||||
|
|||||||
+1
-3
@@ -226,9 +226,7 @@ export const getFilledTransferToLayingFormInitialValues = async (
|
|||||||
// targetKandang.target_project_flock_kandang.kandang.capacity,
|
// targetKandang.target_project_flock_kandang.kandang.capacity,
|
||||||
|
|
||||||
// TODO: integrate this to real API kandang capacity
|
// TODO: integrate this to real API kandang capacity
|
||||||
maxQuantity:
|
maxQuantity: Infinity,
|
||||||
targetKandang.target_project_flock_kandang.kandang.capacity ??
|
|
||||||
Infinity,
|
|
||||||
}))
|
}))
|
||||||
: [],
|
: [],
|
||||||
|
|
||||||
|
|||||||
@@ -61,13 +61,13 @@ export class ProjectFlockKandangService extends BaseApiService<
|
|||||||
// status: 'success',
|
// status: 'success',
|
||||||
// message: 'Cek persyaratan closing kandang',
|
// message: 'Cek persyaratan closing kandang',
|
||||||
// data: {
|
// data: {
|
||||||
// unfinished_expenses: 2,
|
// unfinished_expenses: id % 2 === 1 ? 2 : 0,
|
||||||
// stock_remaining: [
|
// stock_remaining: [
|
||||||
// {
|
// {
|
||||||
// id: 1,
|
// id: 1,
|
||||||
// product_id: 1,
|
// product_id: 1,
|
||||||
// warehouse_id: 1,
|
// warehouse_id: 1,
|
||||||
// quantity: 0,
|
// quantity: id % 2 === 1 ? 100 : 0,
|
||||||
// product: {
|
// product: {
|
||||||
// id: 1,
|
// id: 1,
|
||||||
// name: 'Pakan Starter',
|
// name: 'Pakan Starter',
|
||||||
@@ -146,9 +146,9 @@ export class ProjectFlockKandangService extends BaseApiService<
|
|||||||
// po_number: 'PO-BOP-LTI-00001',
|
// po_number: 'PO-BOP-LTI-00001',
|
||||||
// category: 'NON-BOP',
|
// category: 'NON-BOP',
|
||||||
// total: 110000,
|
// total: 110000,
|
||||||
// status: 'SELESAI',
|
// status: id % 2 === 1 ? 'PENGAJUAN' : 'SELESAI',
|
||||||
// step_name: 'Approval Finance',
|
// step_name: id % 2 === 1 ? 'Approval Finance' : 'Selesai',
|
||||||
// step: 5,
|
// step: id % 2 === 1 ? 1 : 5,
|
||||||
// reference_number: 'BOP-LTI-00001',
|
// reference_number: 'BOP-LTI-00001',
|
||||||
// },
|
// },
|
||||||
// {
|
// {
|
||||||
@@ -156,9 +156,9 @@ export class ProjectFlockKandangService extends BaseApiService<
|
|||||||
// po_number: 'PO-BOP-LTI-00003',
|
// po_number: 'PO-BOP-LTI-00003',
|
||||||
// category: 'BOP',
|
// category: 'BOP',
|
||||||
// total: 110000,
|
// total: 110000,
|
||||||
// status: 'SELESAI',
|
// status: id % 2 === 1 ? 'PENGAJUAN' : 'SELESAI',
|
||||||
// step_name: 'Approval Finance',
|
// step_name: id % 2 === 1 ? 'Approval Finance' : 'Selesai',
|
||||||
// step: 5,
|
// step: id % 2 === 1 ? 1 : 5,
|
||||||
// reference_number: 'BOP-LTI-00003',
|
// reference_number: 'BOP-LTI-00003',
|
||||||
// },
|
// },
|
||||||
// ],
|
// ],
|
||||||
|
|||||||
Reference in New Issue
Block a user