summaryrefslogtreecommitdiff
path: root/src/lib/auth
diff options
context:
space:
mode:
authorIT Fixcomart <it@fixcomart.co.id>2025-01-15 10:02:39 +0000
committerIT Fixcomart <it@fixcomart.co.id>2025-01-15 10:02:39 +0000
commit8035f129863f0a401f529cc0cd69a2131ccaba80 (patch)
tree21e0300680a724c8a24ed815ea4e9a32ab13a895 /src/lib/auth
parent7a14ed5ccdde86d0400d6aa02ac866317d4add63 (diff)
parent98236a47c3558c4b701009a275c7ae917ee8bf67 (diff)
Merged in Feature/switch-account (pull request #402)
Feature/switch account
Diffstat (limited to 'src/lib/auth')
-rw-r--r--src/lib/auth/api/switchAccountApi.js14
-rw-r--r--src/lib/auth/api/switchAccountProgresApi.js13
-rw-r--r--src/lib/auth/components/CompanyProfile.jsx125
-rw-r--r--src/lib/auth/components/Menu.jsx282
-rw-r--r--src/lib/auth/components/PersonalProfile.jsx154
-rw-r--r--src/lib/auth/components/StatusSwitchAccount.jsx5
-rw-r--r--src/lib/auth/components/SwitchAccount.jsx301
7 files changed, 695 insertions, 199 deletions
diff --git a/src/lib/auth/api/switchAccountApi.js b/src/lib/auth/api/switchAccountApi.js
new file mode 100644
index 00000000..79ca2553
--- /dev/null
+++ b/src/lib/auth/api/switchAccountApi.js
@@ -0,0 +1,14 @@
+import odooApi from '@/core/api/odooApi';
+import { getAuth } from '@/core/utils/auth';
+
+const switchAccountApi = async ({ data }) => {
+ const auth = getAuth();
+ const switchAccount = await odooApi(
+ 'PUT',
+ `/api/v1/user/${auth.partnerId}/switch`,
+ data
+ );
+ return switchAccount;
+};
+
+export default switchAccountApi;
diff --git a/src/lib/auth/api/switchAccountProgresApi.js b/src/lib/auth/api/switchAccountProgresApi.js
new file mode 100644
index 00000000..6289a5dd
--- /dev/null
+++ b/src/lib/auth/api/switchAccountProgresApi.js
@@ -0,0 +1,13 @@
+import odooApi from '@/core/api/odooApi';
+import { getAuth } from '@/core/utils/auth';
+
+const switchAccountProgresApi = async () => {
+ const auth = getAuth();
+ const switchAccount = await odooApi(
+ 'GET',
+ `/api/v1/user/${auth.partnerId}/switch_progres`
+ );
+ return switchAccount;
+};
+
+export default switchAccountProgresApi;
diff --git a/src/lib/auth/components/CompanyProfile.jsx b/src/lib/auth/components/CompanyProfile.jsx
index 220d5be1..410d6a23 100644
--- a/src/lib/auth/components/CompanyProfile.jsx
+++ b/src/lib/auth/components/CompanyProfile.jsx
@@ -9,9 +9,14 @@ import { toast } from 'react-hot-toast';
import BottomPopup from '@/core/components/elements/Popup/BottomPopup';
import { yupResolver } from '@hookform/resolvers/yup';
import * as Yup from 'yup';
+import SwitchAccount from '@/lib/auth/components/SwitchAccount';
+import { Checkbox } from '@chakra-ui/react';
const CompanyProfile = () => {
const [changeConfirmation, setChangeConfirmation] = useState(false);
+ const [changeType, setChangeType] = useState(false);
+ const [isChecked, setIsChecked] = useState(false);
+ const [company_type, setCompany_type] = useState('nonpkp');
const auth = useAuth();
const [isOpen, setIsOpen] = useState(false);
const toggle = () => setIsOpen(!isOpen);
@@ -53,14 +58,18 @@ const CompanyProfile = () => {
useEffect(() => {
const loadProfile = async () => {
- const dataProfile = await addressApi({ id: auth.parentId });
- setValue('name', dataProfile.name);
- setValue('industry', dataProfile.industryId);
- setValue('companyType', dataProfile.companyTypeId);
- setValue('taxName', dataProfile.taxName);
- setValue('npwp', dataProfile.npwp);
- setValue('alamat_wajib_pajak', dataProfile.alamatWajibPajak);
- setValue('alamat_bisnis', dataProfile.alamatBisnis);
+ const dataProfile = await addressApi({
+ id: auth.parentId ? auth.parentId : auth.parent_id,
+ });
+ setCompany_type(dataProfile?.companyType);
+ setValue('name', dataProfile?.name);
+ setValue('industry', dataProfile?.industryId);
+ setValue('companyType', dataProfile?.companyTypeId);
+ setValue('taxName', dataProfile?.taxName);
+ setValue('npwp', dataProfile?.npwp);
+ setValue('alamat_wajib_pajak', dataProfile?.alamatWajibPajak);
+ setValue('alamat_bisnis', dataProfile?.alamatBisnis);
+ setValue('company_type', dataProfile?.companyType);
setValue('email_bisnis', dataProfile.email);
setValue('mobile_bisnis', dataProfile.mobile);
};
@@ -97,10 +106,49 @@ const CompanyProfile = () => {
setChangeConfirmation(false);
handleSubmit(onSubmitHandler)();
};
+ const handleConfirmSubmitType = () => {
+ setChangeType(false);
+ setIsChecked(true);
+ setIsOpen(!isOpen);
+ };
+ const handleChange = async () => {
+ if (isChecked) {
+ setIsChecked(!isChecked);
+ setIsOpen(!isOpen);
+ } else {
+ setIsChecked(!isChecked);
+ setChangeType(true);
+ }
+ };
return (
<>
<BottomPopup
+ active={changeType}
+ close={() => setChangeType(false)} // Menutup popup
+ title='Ubah type akun'
+ >
+ <div className='leading-7 text-gray_r-12/80'>
+ Anda akan mengubah type akun anda?
+ </div>
+ <div className='flex mt-6 gap-x-4 md:justify-end'>
+ <button
+ className='btn-solid-red flex-1 md:flex-none'
+ type='button'
+ onClick={handleConfirmSubmitType}
+ >
+ Yakin
+ </button>
+ <button
+ className='btn-light flex-1 md:flex-none'
+ type='button'
+ onClick={() => setChangeType(false)}
+ >
+ Batal
+ </button>
+ </div>
+ </BottomPopup>
+ <BottomPopup
active={changeConfirmation}
close={() => setChangeConfirmation(true)}
title='Ubah profil Bisnis'
@@ -125,25 +173,37 @@ const CompanyProfile = () => {
</button>
</div>
</BottomPopup>
- <button
- type='button'
- onClick={toggle}
- className='p-4 flex items-center text-left w-full'
- >
+ <div className='p-4 flex-row items-center text-left w-full'>
+ {company_type === 'nonpkp' && (
+ <div className='text-sm mb-2 flex items-center'>
+ <Checkbox
+ borderColor='gray.600'
+ colorScheme='red'
+ size='lg'
+ isChecked={isChecked}
+ onChange={handleChange}
+ />
+ <p className='ml-2'>Ubah ke akun PKP</p>
+ </div>
+ )}
<div>
- <div className='font-semibold mb-2'>Informasi Usaha</div>
+ <div className='font-semibold mb-2 flex flex-row gap-x-2'>
+ <h2>Informasi Usaha</h2>
+ <div className='badge-red'>{company_type.toUpperCase()}</div>
+ </div>
<div className='text-gray_r-11'>
Dibawah ini adalah data usaha yang anda masukkan, periksa kembali
data usaha anda.
</div>
</div>
- <div className='ml-auto p-2 bg-gray_r-3 rounded'>
- {!isOpen && <ChevronDownIcon className='w-6' />}
- {isOpen && <ChevronUpIcon className='w-6' />}
- </div>
- </button>
-
- {isOpen && (
+ {/* <button
+ onClick={toggle}
+ className='btn-yellow w-full sm:w-fit sm:ml-auto min-w-[92px]'
+ >
+ Ubah
+ </button> */}
+ </div>
+ {!isOpen && (
<form
className='p-4 border-t border-gray_r-6'
onSubmit={(e) => {
@@ -264,6 +324,7 @@ const CompanyProfile = () => {
</button>
</form>
)}
+ {isOpen && <SwitchAccount company_type={company_type} />}
</>
);
};
@@ -272,14 +333,30 @@ export default CompanyProfile;
const validationSchema = Yup.object().shape({
alamat_bisnis: Yup.string().required('Harus di-isi'),
- alamat_wajib_pajak: Yup.string().required('Harus di-isi'),
- taxName: Yup.string().required('Harus di-isi'),
- npwp: Yup.string().required('Harus di-isi'),
name: Yup.string().required('Harus di-isi'),
email_bisnis: Yup.string().required('Harus di-isi'),
mobile_bisnis: Yup.string().required('Harus di-isi'),
industry: Yup.string().required('Harus di-pilih'),
companyType: Yup.string().required('Harus di-pilih'),
+ taxName: Yup.string(),
+ npwp: Yup.string(),
+ alamat_wajib_pajak: Yup.string(),
+ company_type: Yup.string(),
+ taxName: Yup.string().when('company_type', {
+ is: (company_type) => company_type !== 'Non PKP',
+ then: Yup.string().required('Harus di-isi'),
+ otherwise: Yup.string().notRequired(),
+ }),
+ npwp: Yup.string().when('company_type', {
+ is: (company_type) => company_type !== 'Non PKP',
+ then: Yup.string().required('Harus di-isi'),
+ otherwise: Yup.string().notRequired(),
+ }),
+ alamat_wajib_pajak: Yup.string().when('company_type', {
+ is: (company_type) => company_type !== 'Non PKP',
+ then: Yup.string().required('Harus di-isi'),
+ otherwise: Yup.string().notRequired(),
+ }),
});
const defaultValues = {
diff --git a/src/lib/auth/components/Menu.jsx b/src/lib/auth/components/Menu.jsx
index d99917d0..4682dbab 100644
--- a/src/lib/auth/components/Menu.jsx
+++ b/src/lib/auth/components/Menu.jsx
@@ -2,11 +2,24 @@ import Link from '@/core/components/elements/Link/Link';
import { useRouter } from 'next/router';
import ImageNext from 'next/image';
import whatsappUrl from '@/core/utils/whatsappUrl';
-import { deleteAuth } from '@/core/utils/auth';
import useAuth from '@/core/hooks/useAuth';
+import switchAccountProgresApi from '@/lib/auth/api/switchAccountProgresApi.js';
+import { useState, useEffect } from 'react';
+import { InfoIcon } from 'lucide-react';
+import { deleteAuth } from '@/core/utils/auth';
const Menu = () => {
const router = useRouter();
const auth = useAuth();
+ const [ubahAkun, setUbahAkun] = useState();
+ useEffect(() => {
+ const loadProgres = async () => {
+ const progresSwitchAccount = await switchAccountProgresApi();
+ if (progresSwitchAccount) {
+ setUbahAkun(progresSwitchAccount.status);
+ }
+ };
+ loadProgres();
+ }, []);
const routeStartWith = (route) => router.pathname.startsWith(route);
@@ -15,78 +28,134 @@ const Menu = () => {
router.push('/login');
});
};
-
return (
<div className='grid grid-cols-1 bg-white border border-gray_r-6 rounded py-2 px-4 sticky top-48'>
- <div className='mt-4 mb-1 font-medium'>Menu</div>
- <LinkItem href='/my/quotations' active={routeStartWith('/my/quotations')}>
- <div className='flex gap-x-3 items-center'>
- <ImageNext
- src='/images/icon/icon_daftar_quotation.svg'
- width={18}
- height={20}
- />
- <p>Daftar Quotation</p>
- </div>
- </LinkItem>
- <LinkItem
- href='/my/transactions'
- active={routeStartWith('/my/transactions')}
- >
- <div className='flex gap-x-3 items-center'>
- <ImageNext
- src='/images/icon/icon_daftar_transaksi.svg'
- width={18}
- height={20}
- />
- <p>Daftar Transaksi</p>
- </div>
- </LinkItem>
- <LinkItem href='/my/shipments' active={routeStartWith('/my/shipments')}>
- <div className='flex gap-x-3 items-center'>
- <ImageNext
- src='/images/icon/icon_pengiriman.svg'
- width={18}
- height={20}
- />
- <p>Daftar Pengiriman</p>
- </div>
- </LinkItem>
- <LinkItem href='/my/invoices' active={routeStartWith('/my/invoices')}>
- <div className='flex gap-x-3 items-center'>
- <ImageNext
- src='/images/icon/icon_invoice.svg'
- width={18}
- height={20}
- />
- <p>Invoice & Faktur Pajak</p>
- </div>
- </LinkItem>
- {auth &&
- auth.partnerTempo &&
- (auth.partnerTempo ||
- auth.tempoProgres === 'review') && (
- <LinkItem href='/my/tempo' active={routeStartWith('/my/tempo')}>
- <div className='flex gap-x-3 items-center'>
- <ImageNext
- src='/images/icon/icon_tempo.svg'
- width={18}
- height={20}
- />
- <p>Pembayaran Tempo</p>
- </div>
- </LinkItem>
- )}
- <LinkItem href='/my/wishlist' active={routeStartWith('/my/wishlist')}>
- <div className='flex gap-x-3 items-center'>
- <ImageNext
- src='/images/icon/icon_wishlist.svg'
- width={18}
- height={20}
- />
- <p>Wishlist</p>
+ <div className='flex justify-between py-4'>
+ <div className='font-semibold text-gray_r-12'>Akun Saya</div>
+ <div className='relative group'>
+ {auth?.company && !(ubahAkun === 'pending') && (
+ <>
+ <Link
+ href='/my/profile'
+ className='badge-solid-red mt-1 p-2 flex flex-row items-center gap-x-2'
+ >
+ <p className='text-white'>Akun Bisnis</p>{' '}
+ <InfoIcon size={14} color='white' />
+ </Link>
+ <div className='absolute bottom-full transform -translate-x-1/2 mb-2 hidden group-hover:block bg-gray-700 text-white text-xs rounded py-1 px-2 w-72 text-justify left-36'>
+ Anda terdaftar sebagai akun bisnis, segala bentuk transaksi anda
+ untuk perusahaan yang sudah anda daftarkan di Indoteknik.com
+ </div>
+ </>
+ )}
+ {ubahAkun === 'pending' && (
+ <>
+ <Link
+ href='/my/profile'
+ className='badge-yellow mt-1 p-2 flex flex-row items-center gap-x-2'
+ >
+ <p className='text-warning-900'>Review</p>
+ <InfoIcon size={14} className='text-warning-900' />
+ </Link>
+ <div className='absolute bottom-full transform -translate-x-1/2 mb-2 hidden group-hover:block bg-gray-700 text-white text-xs rounded py-1 px-2 w-72 text-justify left-36'>
+ Proses perubahan akun anda sedang kami review, mohon menunggu
+ hingga 2x24 jam.
+ </div>
+ </>
+ )}
+ {!auth?.company && !(ubahAkun === 'pending') && (
+ <>
+ <Link
+ href='/my/profile'
+ className='badge-gray mt-1 p-2 flex flex-row items-center gap-x-2'
+ >
+ <p className='text-gray_r-10'>Akun Individu</p>
+ <InfoIcon size={14} className='text-gray_r-10' />
+ </Link>
+ <div className='absolute bottom-full left-36 transform -translate-x-1/2 mb-3 w-72 text-justify hidden group-hover:block bg-gray-700 text-white text-xs rounded py-1 px-2'>
+ <p className='whitespace-pre-wrap break-words'>
+ Anda terdaftar sebagai akun individu, Segala bentuk transaksi
+ anda untuk Pribadi/Individu.
+ </p>
+ </div>
+ </>
+ )}
</div>
- </LinkItem>
+ </div>
+ <div className='mt-2 mb-1 font-medium'>Menu</div>
+ <div className='flex flex-col gap-y-2'>
+ <LinkItem
+ href='/my/quotations'
+ active={routeStartWith('/my/quotations')}
+ className=''
+ >
+ <div className='flex gap-x-3 items-center'>
+ <ImageNext
+ src='/images/icon/icon_daftar_quotation.svg'
+ width={18}
+ height={20}
+ />
+ <p>Daftar Quotation</p>
+ </div>
+ </LinkItem>
+ <LinkItem
+ href='/my/transactions'
+ active={routeStartWith('/my/transactions')}
+ >
+ <div className='flex gap-x-3 items-center'>
+ <ImageNext
+ src='/images/icon/icon_daftar_transaksi.svg'
+ width={18}
+ height={20}
+ />
+ <p>Daftar Transaksi</p>
+ </div>
+ </LinkItem>
+ <LinkItem href='/my/shipments' active={routeStartWith('/my/shipments')}>
+ <div className='flex gap-x-3 items-center'>
+ <ImageNext
+ src='/images/icon/icon_pengiriman.svg'
+ width={18}
+ height={20}
+ />
+ <p>Daftar Pengiriman</p>
+ </div>
+ </LinkItem>
+ <LinkItem href='/my/invoices' active={routeStartWith('/my/invoices')}>
+ <div className='flex gap-x-3 items-center'>
+ <ImageNext
+ src='/images/icon/icon_invoice.svg'
+ width={18}
+ height={20}
+ />
+ <p>Invoice & Faktur Pajak</p>
+ </div>
+ </LinkItem>
+ {auth &&
+ auth.partnerTempo &&
+ (auth.partnerTempo || auth.tempoProgres === 'review') && (
+ <LinkItem href='/my/tempo' active={routeStartWith('/my/tempo')}>
+ <div className='flex gap-x-3 items-center'>
+ <ImageNext
+ src='/images/icon/icon_tempo.svg'
+ width={18}
+ height={20}
+ />
+ <p>Pembayaran Tempo</p>
+ </div>
+ </LinkItem>
+ )}
+ <LinkItem href='/my/wishlist' active={routeStartWith('/my/wishlist')}>
+ <div className='flex gap-x-3 items-center'>
+ <ImageNext
+ src='/images/icon/icon_wishlist.svg'
+ width={18}
+ height={20}
+ />
+ <p>Wishlist</p>
+ </div>
+ </LinkItem>
+ </div>
<div className='mt-4 mb-1 font-medium'>Pusat Bantuan</div>
<LinkItem
@@ -104,40 +173,41 @@ const Menu = () => {
</div>
</LinkItem>
<div className='mt-4 mb-1 font-medium'>Pengaturan Akun</div>
- <LinkItem href='/my/address' active={routeStartWith('/my/address')}>
- <div className='flex gap-x-3 items-center'>
- <ImageNext
- src='/images/icon/icon_daftar_alamat.svg'
- width={18}
- height={20}
- />
- <p>Daftar Alamat</p>
- </div>
- </LinkItem>
- <LinkItem href='/my/profile' active={routeStartWith('/my/profile')}>
- <div className='flex gap-x-3 items-center'>
- <ImageNext
- src='/images/icon/icon_profile.svg'
- width={18}
- height={20}
- />
- <p>Profil Saya</p>
- </div>
- </LinkItem>
- <button
- type='button'
- onClick={logout}
- className='text-gray_r-12/80 p-2 text-left'
- >
- <div className='flex gap-x-3 items-center'>
- <ImageNext
- src='/images/icon/icon_logout.svg'
- width={18}
- height={20}
- />
- <p>Keluar Akun</p>
- </div>
- </button>
+ <div className='flex flex-col gap-y-2'>
+ <LinkItem href='/my/address' active={routeStartWith('/my/address')}>
+ <div className='flex gap-x-3 items-center'>
+ <ImageNext
+ src='/images/icon/icon_daftar_alamat.svg'
+ width={18}
+ height={20}
+ />
+ <p>Daftar Alamat</p>
+ </div>
+ </LinkItem>
+ <LinkItem href='/my/profile' active={routeStartWith('/my/profile')}>
+ <div className='flex gap-x-3 items-center'>
+ <ImageNext
+ src='/images/icon/icon_profile.svg'
+ width={18}
+ height={20}
+ />
+ <p>Profil Saya</p>
+ </div>
+ </LinkItem>
+ <button
+ type='button'
+ className='text-gray_r-12/80 p-2 text-left hover:bg-gray_r-5 '
+ >
+ <div className='flex gap-x-3 items-center'>
+ <ImageNext
+ src='/images/icon/icon_logout.svg'
+ width={18}
+ height={20}
+ />
+ <p>Keluar Akun</p>
+ </div>
+ </button>
+ </div>
</div>
);
};
@@ -145,8 +215,8 @@ const Menu = () => {
const LinkItem = ({ children, ...props }) => (
<Link
{...props}
- className={`!text-gray_r-12/80 !font-normal p-2 rounded ${
- props.active == true ? 'bg-gray_r-3' : ''
+ className={`!text-gray_r-12/80 !font-normal p-2 rounded transition-colors duration-200 ${
+ props.active ? 'bg-gray_r-3' : 'hover:bg-gray_r-5 '
}`}
>
{children}
diff --git a/src/lib/auth/components/PersonalProfile.jsx b/src/lib/auth/components/PersonalProfile.jsx
index b9fb3f5f..3053255d 100644
--- a/src/lib/auth/components/PersonalProfile.jsx
+++ b/src/lib/auth/components/PersonalProfile.jsx
@@ -1,96 +1,112 @@
-import useAuth from '@/core/hooks/useAuth'
-import { setAuth } from '@/core/utils/auth'
-import addressApi from '@/lib/address/api/addressApi'
-import { ChevronDownIcon, ChevronUpIcon } from '@heroicons/react/24/outline'
-import { useEffect, useState } from 'react'
-import { useForm } from 'react-hook-form'
-import { toast } from 'react-hot-toast'
-import editPersonalProfileApi from '../api/editPersonalProfileApi'
+import useAuth from '@/core/hooks/useAuth';
+import { setAuth } from '@/core/utils/auth';
+import addressApi from '@/lib/address/api/addressApi';
+import { ChevronDownIcon, ChevronUpIcon } from '@heroicons/react/24/outline';
+import { useEffect, useState } from 'react';
+import { useForm } from 'react-hook-form';
+import { toast } from 'react-hot-toast';
+import editPersonalProfileApi from '../api/editPersonalProfileApi';
const PersonalProfile = () => {
- const auth = useAuth()
- const [isOpen, setIsOpen] = useState(true)
- const toggle = () => setIsOpen(!isOpen)
+ const auth = useAuth();
+ const [isOpen, setIsOpen] = useState(true);
+ const toggle = () => setIsOpen(!isOpen);
const { register, setValue, handleSubmit } = useForm({
defaultValues: {
email: '',
name: '',
mobile: '',
- password: ''
- }
- })
+ password: '',
+ },
+ });
useEffect(() => {
const loadProfile = async () => {
- const dataProfile = await addressApi({ id: auth.partnerId })
- setValue('email', dataProfile?.email)
- setValue('name', dataProfile?.name)
- setValue('mobile', dataProfile?.mobile)
- }
- if (auth) loadProfile()
- }, [auth, setValue])
+ const dataProfile = await addressApi({
+ id: auth.partnerId ? auth.partnerId : auth.partner_id,
+ });
+ setValue('email', dataProfile?.email);
+ setValue('name', dataProfile?.name);
+ setValue('mobile', dataProfile?.mobile);
+ };
+ if (auth) loadProfile();
+ }, [auth, setValue]);
const onSubmitHandler = async (values) => {
- let data = values
- if (!values.password) delete data.password
- const isUpdated = await editPersonalProfileApi({ data })
+ let data = values;
+ if (!values.password) delete data.password;
+ const isUpdated = await editPersonalProfileApi({ data });
if (isUpdated?.user) {
- setAuth(isUpdated.user)
- setValue('password', '')
- toast.success('Berhasil mengubah profil', { duration: 1500 })
- return
+ setAuth(isUpdated.user);
+ setValue('password', '');
+ toast.success('Berhasil mengubah profil', { duration: 1500 });
+ return;
}
- toast.error('Terjadi kesalahan internal')
- }
+ toast.error('Terjadi kesalahan internal');
+ };
return (
<>
- <button type='button' onClick={toggle} className='p-4 flex items-center text-left w-full'>
+ <div type='button' className='p-4 flex items-center text-left w-full'>
<div>
<div className='font-semibold mb-2'>Informasi Akun</div>
<div className='text-gray_r-11'>
- Dibawah ini adalah data diri yang anda masukan, periksa kembali data diri anda
+ Dibawah ini adalah data diri yang anda masukan, periksa kembali data
+ diri anda
</div>
</div>
- <div className='ml-auto p-2 bg-gray_r-3 rounded'>
- {!isOpen && <ChevronDownIcon className='w-6' />}
- {isOpen && <ChevronUpIcon className='w-6' />}
- </div>
- </button>
+ </div>
- {isOpen && (
- <form className='p-4 border-t border-gray_r-6' onSubmit={handleSubmit(onSubmitHandler)}>
- <div className='grid grid-cols-1 sm:grid-cols-2 gap-4'>
- <div>
- <label>Email</label>
- <input {...register('email')} type='text' disabled className='form-input mt-3' />
- </div>
- <div>
- <label>Nama Lengkap</label>
- <input {...register('name')} type='text' className='form-input mt-3' />
- </div>
- <div>
- <label>No. Handphone</label>
- <input {...register('mobile')} type='tel' className='form-input mt-3' />
- </div>
- <div>
- <label>Kata Sandi</label>
- <input
- {...register('password')}
- type='password'
- className='form-input mt-3'
- placeholder='Isi jika ingin mengubah kata sandi'
- />
- </div>
+ <form
+ className='p-4 border-t border-gray_r-6'
+ onSubmit={handleSubmit(onSubmitHandler)}
+ >
+ <div className='grid grid-cols-1 sm:grid-cols-2 gap-4'>
+ <div>
+ <label>Email</label>
+ <input
+ {...register('email')}
+ type='text'
+ disabled
+ className='form-input mt-3'
+ />
+ </div>
+ <div>
+ <label>Nama Lengkap</label>
+ <input
+ {...register('name')}
+ type='text'
+ className='form-input mt-3'
+ />
</div>
- <button type='submit' className='btn-yellow w-full sm:w-fit sm:ml-auto mt-6'>
- Simpan
- </button>
- </form>
- )}
+ <div>
+ <label>No. Handphone</label>
+ <input
+ {...register('mobile')}
+ type='tel'
+ className='form-input mt-3'
+ />
+ </div>
+ <div>
+ <label>Kata Sandi</label>
+ <input
+ {...register('password')}
+ type='password'
+ className='form-input mt-3'
+ placeholder='Isi jika ingin mengubah kata sandi'
+ />
+ </div>
+ </div>
+ <button
+ type='submit'
+ className='btn-yellow w-full sm:w-fit sm:ml-auto mt-6 max-w-28'
+ >
+ Simpan
+ </button>
+ </form>
</>
- )
-}
+ );
+};
-export default PersonalProfile
+export default PersonalProfile;
diff --git a/src/lib/auth/components/StatusSwitchAccount.jsx b/src/lib/auth/components/StatusSwitchAccount.jsx
new file mode 100644
index 00000000..73316616
--- /dev/null
+++ b/src/lib/auth/components/StatusSwitchAccount.jsx
@@ -0,0 +1,5 @@
+const StatusSwitchAccount = ({ status }) => {
+ return <>Perpindahan akun anda masih {status}</>;
+};
+
+export default StatusSwitchAccount;
diff --git a/src/lib/auth/components/SwitchAccount.jsx b/src/lib/auth/components/SwitchAccount.jsx
new file mode 100644
index 00000000..46e57348
--- /dev/null
+++ b/src/lib/auth/components/SwitchAccount.jsx
@@ -0,0 +1,301 @@
+import useAuth from '@/core/hooks/useAuth';
+import { setAuth } from '@/core/utils/auth';
+import addressApi from '@/lib/address/api/addressApi';
+import { ChevronDownIcon, ChevronUpIcon } from '@heroicons/react/24/outline';
+import { useEffect, useState, useMemo } from 'react';
+import { useForm } from 'react-hook-form';
+import { toast } from 'react-hot-toast';
+import switchAccountApi from '../api/switchAccountApi';
+import FormBisnis from '~/modules/register/components/FormBisnis.tsx';
+import RegistrasiBisnis from '~/modules/register/components/RegistrasiBisnis.tsx';
+import { Radio, RadioGroup, Stack, Divider, Button } from '@chakra-ui/react';
+import { useRegisterStore } from '~/modules/register/stores/useRegisterStore.ts';
+import { registerUser } from '~/services/auth';
+import { useMutation } from 'react-query';
+import { isValid } from 'zod';
+import useDevice from '@/core/hooks/useDevice';
+import BottomPopup from '@/core/components/elements/Popup/BottomPopup';
+const SwitchAccount = ({ company_type }) => {
+ const { isDesktop, isMobile } = useDevice();
+ const auth = useAuth();
+ const [isOpen, setIsOpen] = useState(true);
+ const toggle = () => setIsOpen(!isOpen);
+ const [isPKP, setIsPKP] = useState(true);
+ const [isTerdaftar, setIsTerdaftar] = useState(false);
+ const [isChecked, setIsChecked] = useState(false);
+ const [selectedValueBisnis, setSelectedValueBisnis] = useState('false');
+ const [selectedValue, setSelectedValue] = useState('PKP');
+ const [buttonSubmitClick, setButtonSubmitClick] = useState(false);
+ const [changeConfirmation, setChangeConfirmation] = useState(false);
+ const { register, setValue, handleSubmit } = useForm({
+ defaultValues: {
+ email: '',
+ name: '',
+ phone: '',
+ password: '',
+ },
+ });
+ const mutation = useMutation({
+ mutationFn: (data) => registerUser(data),
+ });
+ const [notValid, setNotValid] = useState(false);
+ const {
+ form,
+ isCheckedTNC,
+ isValidCaptcha,
+ errors,
+ validate,
+ updateForm,
+ resetForm,
+ } = useRegisterStore();
+ const isFormValid = useMemo(() => Object.keys(errors).length === 0, [errors]);
+ useEffect(() => {
+ const loadProfile = async () => {
+ const dataProfile = await addressApi({ id: auth.partnerId });
+ setValue('email', dataProfile?.email);
+ setValue('name', dataProfile?.name);
+ setValue('phone', dataProfile?.phone);
+ };
+ if (auth) loadProfile();
+ }, [auth, setValue]);
+
+ useEffect(() => {
+ if (selectedValue === 'PKP') {
+ updateForm('is_pkp', 'true');
+ validate();
+ } else {
+ updateForm('is_pkp', 'false');
+ validate();
+ }
+ }, [selectedValue]);
+
+ useEffect(() => {
+ if (isTerdaftar) {
+ updateForm('is_terdaftar', 'true');
+ validate();
+ } else {
+ updateForm('is_terdaftar', 'false');
+ validate();
+ }
+ }, [isTerdaftar]);
+ useEffect(() => {
+ const loadProfile = async () => {
+ const dataProfile = await addressApi({
+ id: auth.parentId ? auth.parentId : auth.parent_id,
+ });
+ if (dataProfile?.companyType === 'nonpkp') {
+ setSelectedValue('PKP');
+ }
+ if (auth?.company) {
+ updateForm('email_partner', dataProfile?.email);
+ updateForm('business_name', dataProfile?.name);
+ updateForm('industry_id', `${dataProfile?.industryId}`);
+ updateForm('company_type_id', `${dataProfile?.companyTypeId}`);
+ updateForm('nama_wajib_pajak', dataProfile?.taxName);
+ updateForm('npwp', dataProfile?.npwp);
+ updateForm('sppkp', dataProfile?.sppkp);
+ updateForm('alamat_wajib_pajak', dataProfile?.alamatWajibPajak);
+ updateForm('alamat_bisnis', dataProfile?.alamatBisnis);
+ validate();
+ }
+ };
+ if (auth) loadProfile();
+ }, [auth, setValue]);
+ useEffect(() => {
+ updateForm('name', '-');
+ updateForm('email', 'example@mail.com');
+ updateForm('password', 'example@mail.com');
+ updateForm('phone', '081234567890');
+ validate();
+ }, [buttonSubmitClick, changeConfirmation]);
+
+ const handleChangeBisnis = (value) => {
+ resetForm();
+ setSelectedValueBisnis(value);
+ if (value === 'true') {
+ validate();
+ setIsTerdaftar(true);
+ } else {
+ validate();
+ setIsTerdaftar(false);
+ }
+ };
+ const handleChange = (value) => {
+ setSelectedValue(value);
+ if (value === 'PKP') {
+ validate();
+ setIsPKP(true);
+ } else {
+ validate();
+ setIsPKP(false);
+ setIsPKP(false);
+ }
+ };
+ const onSubmitHandler = async (values) => {
+ toast.loading('Mengubah status akun...');
+ updateForm('parent_id', `${auth.parentId}`);
+ setChangeConfirmation(false);
+ // let data = { ...form, id: `${auth.partnerId}` };
+ const data = form;
+ if (!isFormValid) {
+ setNotValid(true);
+ setButtonSubmitClick(!buttonSubmitClick);
+ return;
+ } else {
+ setButtonSubmitClick(!buttonSubmitClick);
+ setNotValid(false);
+ }
+ // if (!values.password) delete data.password;
+ const isUpdated = await switchAccountApi({ data });
+
+ if (isUpdated?.switch === 'Pending') {
+ // setAuth(isUpdated.user);
+ // setValue('password', '');
+ toast.success('Berhasil mengubah akun', { duration: 1500 });
+ setTimeout(() => {
+ window.location.reload();
+ }, 1500);
+ return;
+ }
+ toast.error('Terjadi kesalahan internal');
+ };
+
+ const onSubmitHandlerCancel = async (values) => {
+ window.location.reload();
+ };
+
+ return (
+ <>
+ <BottomPopup
+ active={changeConfirmation}
+ close={() => setChangeConfirmation(false)}
+ title='Ubah profil Bisnis'
+ >
+ <div className='leading-7 text-gray_r-12/80'>
+ Anda yakin akan merubah profil bisnis anda dari INDIVIDU menjadi{' '}
+ {selectedValue}?
+ </div>
+ <div className='flex mt-6 gap-x-4 md:justify-end'>
+ <button
+ className='btn-solid-red flex-1 md:flex-none'
+ type='button'
+ onClick={onSubmitHandler}
+ >
+ Ya, Ubah
+ </button>
+ <button
+ className='btn-light flex-1 md:flex-none'
+ type='button'
+ onClick={() => setChangeConfirmation(false)}
+ >
+ Batal
+ </button>
+ </div>
+ </BottomPopup>
+ {/* <div type='button' className='ml-4 flex items-center text-left w-full'>
+ <div
+ className={`flex ${
+ isDesktop ? 'flex-row' : 'flex-col gap-y-2'
+ } items-start justify-start bg-slate-50`}
+ >
+ <div className='flex font-semibold mr-2'>Informasi Bisnis</div>
+ <div className='text-red-500 text-xs'>
+ *Perubahan akun tidak dapat diubah kembali
+ </div>
+ </div>
+ </div> */}
+ <div className='px-4 '>
+ <div
+ class='flex items-center p-4 mb-4 text-sm border border-red-500 text-red-800 rounded-lg bg-red-50'
+ role='alert'
+ >
+ <svg
+ class='flex-shrink-0 inline w-4 h-4 mr-3'
+ aria-hidden='true'
+ fill='currentColor'
+ viewBox='0 0 20 20'
+ >
+ <path d='M10 .5a9.5 9.5 0 1 0 9.5 9.5A9.51 9.51 0 0 0 10 .5ZM9.5 4a1.5 1.5 0 1 1 0 3 1.5 1.5 0 0 1 0-3ZM12 15H8a1 1 0 0 1 0-2h1v-3H8a1 1 0 0 1 0-2h2a1 1 0 0 1 1 1v4h1a1 1 0 0 1 0 2Z' />
+ </svg>
+ <span class='sr-only'>Info</span>
+ <div className='text-justify'>
+ Mohon diperhatikan bahwa perubahan data akun bisnis akan
+ mengakibatkan perubahan pada informasi yang tertera di faktur pajak
+ dan invoice.
+ </div>
+ </div>
+ </div>
+
+ <div className='px-4 mb-4'>
+ {!auth?.company && company_type === 'nonpkp' && (
+ <>
+ <div className='mb-4'>
+ <p className='text-black font-bold mb-2'>
+ Bisnis Terdaftar di Indoteknik?
+ </p>
+ <RadioGroup
+ onChange={handleChangeBisnis}
+ value={selectedValueBisnis}
+ >
+ <Stack direction='row'>
+ <Radio colorScheme='red' value='true'>
+ Sudah Terdaftar
+ </Radio>
+ <Radio colorScheme='red' value='false' className='ml-2'>
+ Belum Terdaftar
+ </Radio>
+ </Stack>
+ </RadioGroup>
+ </div>
+ {!isTerdaftar && (
+ <div className=''>
+ <p className='text-black font-bold mb-2'>Tipe Bisnis</p>
+ <RadioGroup onChange={handleChange} value={selectedValue}>
+ <Stack direction='row' className='font-bold'>
+ <Radio colorScheme='red' value='PKP'>
+ PKP
+ </Radio>
+ {!auth?.company && company_type === 'nonpkp' && (
+ <Radio colorScheme='red' value='Non-PKP' className='ml-4'>
+ Non-PKP
+ </Radio>
+ )}
+ </Stack>
+ </RadioGroup>
+ </div>
+ )}
+ </>
+ )}
+ <FormBisnis
+ type={isDesktop ? 'profil' : 'bisnis'}
+ required={isTerdaftar}
+ isPKP={isPKP}
+ chekValid={notValid}
+ buttonSubmitClick={buttonSubmitClick}
+ />
+ <div className='flex flex-row justify-end mt-4 '>
+ <div className='mr-4'>
+ <button
+ type='submit'
+ onClick={() => setChangeConfirmation(true)}
+ className='btn-yellow w-full sm:w-fit sm:ml-auto mt-6 mr-8 md:mr-4'
+ >
+ {mutation.isLoading ? 'Loading...' : 'Simpan Perubahan'}
+ </button>
+ </div>
+ <div>
+ <button
+ type='submit'
+ onClick={onSubmitHandlerCancel}
+ className='btn-solid-red w-full sm:w-fit sm:ml-auto mt-6'
+ >
+ {mutation.isLoading ? 'Loading...' : 'Batal'}
+ </button>
+ </div>
+ </div>
+ </div>
+ </>
+ );
+};
+
+export default SwitchAccount;