- Integrated toast notifications to display error messages when form submissions fail across various components, enhancing user feedback and experience. - Updated components including DeleteUser, FormDialog, ManageTwoFactor, TwoFactorRecoveryCodes, TwoFactorSetupModal, PayrollPeriodShow, EmployeeCreate, EmployeeEdit, CuttingCreate, CuttingEdit, PurchaseCreate, PurchaseEdit, RestockCreate, RestockEdit, TransactionCreate, TransactionEdit, Category management, Product management, Raw Material management, Role management, Settings, and Authentication pages.
136 lines
5.2 KiB
TypeScript
136 lines
5.2 KiB
TypeScript
import { Form } from '@inertiajs/react';
|
|
import { ShieldCheck } from 'lucide-react';
|
|
import { useEffect, useRef, useState } from 'react';
|
|
import { toast } from 'sonner';
|
|
import Heading from '@/components/heading';
|
|
import TwoFactorRecoveryCodes from '@/components/two-factor-recovery-codes';
|
|
import TwoFactorSetupModal from '@/components/two-factor-setup-modal';
|
|
import { Button } from '@/components/ui/button';
|
|
import { useTwoFactorAuth } from '@/hooks/use-two-factor-auth';
|
|
import { disable, enable } from '@/routes/two-factor';
|
|
|
|
export type Props = {
|
|
canManageTwoFactor?: boolean;
|
|
requiresConfirmation?: boolean;
|
|
twoFactorEnabled?: boolean;
|
|
};
|
|
|
|
export default function ManageTwoFactor(props: Props) {
|
|
const requiresConfirmation = props.requiresConfirmation ?? false;
|
|
const twoFactorEnabled = props.twoFactorEnabled ?? false;
|
|
|
|
const {
|
|
qrCodeSvg,
|
|
hasSetupData,
|
|
manualSetupKey,
|
|
clearSetupData,
|
|
clearTwoFactorAuthData,
|
|
fetchSetupData,
|
|
recoveryCodesList,
|
|
fetchRecoveryCodes,
|
|
errors,
|
|
} = useTwoFactorAuth();
|
|
const [showSetupModal, setShowSetupModal] = useState<boolean>(false);
|
|
const prevTwoFactorEnabled = useRef(twoFactorEnabled);
|
|
|
|
useEffect(() => {
|
|
if (prevTwoFactorEnabled.current && !twoFactorEnabled) {
|
|
clearTwoFactorAuthData();
|
|
}
|
|
|
|
prevTwoFactorEnabled.current = twoFactorEnabled;
|
|
}, [twoFactorEnabled, clearTwoFactorAuthData]);
|
|
|
|
if (!(props.canManageTwoFactor ?? false)) {
|
|
return null;
|
|
}
|
|
|
|
return (
|
|
<div className="space-y-6">
|
|
<Heading
|
|
variant="small"
|
|
title="Two-factor authentication"
|
|
description="Manage your two-factor authentication settings"
|
|
/>
|
|
{twoFactorEnabled ? (
|
|
<div className="flex flex-col items-start justify-start space-y-4">
|
|
<p className="text-sm text-muted-foreground">
|
|
You will be prompted for a secure, random pin during
|
|
login, which you can retrieve from the TOTP-supported
|
|
application on your phone.
|
|
</p>
|
|
|
|
<div className="relative inline">
|
|
<Form
|
|
{...disable.form()}
|
|
onError={() => {
|
|
toast.error('Terjadi kesalahan saat menyimpan data. Silakan periksa kembali input Anda.');
|
|
}}
|
|
>
|
|
{({ processing }) => (
|
|
<Button
|
|
variant="destructive"
|
|
type="submit"
|
|
disabled={processing}
|
|
>
|
|
Disable 2FA
|
|
</Button>
|
|
)}
|
|
</Form>
|
|
</div>
|
|
|
|
<TwoFactorRecoveryCodes
|
|
recoveryCodesList={recoveryCodesList}
|
|
fetchRecoveryCodes={fetchRecoveryCodes}
|
|
errors={errors}
|
|
/>
|
|
</div>
|
|
) : (
|
|
<div className="flex flex-col items-start justify-start space-y-4">
|
|
<p className="text-sm text-muted-foreground">
|
|
When you enable two-factor authentication, you will be
|
|
prompted for a secure pin during login. This pin can be
|
|
retrieved from a TOTP-supported application on your
|
|
phone.
|
|
</p>
|
|
|
|
<div>
|
|
{hasSetupData ? (
|
|
<Button onClick={() => setShowSetupModal(true)}>
|
|
<ShieldCheck />
|
|
Continue setup
|
|
</Button>
|
|
) : (
|
|
<Form
|
|
{...enable.form()}
|
|
onSuccess={() => setShowSetupModal(true)}
|
|
onError={() => {
|
|
toast.error('Terjadi kesalahan saat menyimpan data. Silakan periksa kembali input Anda.');
|
|
}}
|
|
>
|
|
{({ processing }) => (
|
|
<Button type="submit" disabled={processing}>
|
|
Enable 2FA
|
|
</Button>
|
|
)}
|
|
</Form>
|
|
)}
|
|
</div>
|
|
</div>
|
|
)}
|
|
|
|
<TwoFactorSetupModal
|
|
isOpen={showSetupModal}
|
|
onClose={() => setShowSetupModal(false)}
|
|
requiresConfirmation={requiresConfirmation}
|
|
twoFactorEnabled={twoFactorEnabled}
|
|
qrCodeSvg={qrCodeSvg}
|
|
manualSetupKey={manualSetupKey}
|
|
clearSetupData={clearSetupData}
|
|
fetchSetupData={fetchSetupData}
|
|
errors={errors}
|
|
/>
|
|
</div>
|
|
);
|
|
}
|