"use client"; import { Dispatch, SetStateAction, useState, useTransition } from "react"; import { zodResolver } from "@hookform/resolvers/zod"; import { User } from "@prisma/client"; import { useForm } from "react-hook-form"; import { toast } from "sonner"; import { CreateDNSRecord, RecordType } from "@/lib/cloudflare"; import { UserRecordFormData } from "@/lib/dto/cloudflare-dns-record"; import { RECORD_TYPE_ENUMS, TTL_ENUMS } from "@/lib/enums"; import { createRecordSchema } from "@/lib/validations/record"; import { Button } from "@/components/ui/button"; import { Input } from "@/components/ui/input"; import { Label } from "@/components/ui/label"; import { Icons } from "@/components/shared/icons"; import { FormSectionColumns } from "../dashboard/form-section-columns"; import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue, } from "../ui/select"; export type FormData = CreateDNSRecord; export type FormType = "add" | "edit"; export interface RecordFormProps { user: Pick; isShowForm: boolean; setShowForm: Dispatch>; type: FormType; initData?: UserRecordFormData | null; action: string; onRefresh: () => void; } export function RecordForm({ user, isShowForm, setShowForm, type, initData, action, onRefresh, }: RecordFormProps) { const [isPending, startTransition] = useTransition(); const [isDeleting, startDeleteTransition] = useTransition(); const [currentRecordType, setCurrentRecordType] = useState( initData?.type || "CNAME", ); const { handleSubmit, register, formState: { errors }, getValues, setValue, } = useForm({ resolver: zodResolver(createRecordSchema), defaultValues: { type: initData?.type || "CNAME", ttl: initData?.ttl || 1, proxied: initData?.proxied || false, comment: initData?.comment || "", name: (initData?.name.endsWith(".wr.do") ? initData?.name.slice(0, -6) : initData?.name) || "", content: initData?.content || "", }, }); const onSubmit = handleSubmit((data) => { if (type === "add") { handleCreateRecord(data); } else if (type === "edit") { handleUpdateRecord(data); } }); const handleCreateRecord = async (data: CreateDNSRecord) => { startTransition(async () => { const response = await fetch(`${action}/add`, { method: "POST", body: JSON.stringify({ records: [data], }), }); if (!response.ok || response.status !== 200) { toast.error("Created Failed!", { description: response.statusText, }); } else { const res = await response.json(); toast.success(`Created successfully!`); setShowForm(false); onRefresh(); } }); }; const handleUpdateRecord = async (data: CreateDNSRecord) => { startTransition(async () => { if (type === "edit") { const response = await fetch(`${action}/update`, { method: "POST", body: JSON.stringify({ recordId: initData?.record_id, record: data, userId: initData?.userId, }), }); if (!response.ok || response.status !== 200) { toast.error("Update Failed", { description: response.statusText, }); } else { const res = await response.json(); toast.success(`Update successfully!`); setShowForm(false); onRefresh(); } } }); }; const handleDeleteRecord = async () => { if (type === "edit") { startDeleteTransition(async () => { const response = await fetch(`${action}/delete`, { method: "POST", body: JSON.stringify({ record_id: initData?.record_id, zone_id: initData?.zone_id, active: initData?.active, userId: initData?.userId, }), }); if (!response.ok || response.status !== 200) { toast.error("Delete Failed", { description: response.statusText, }); } else { await response.json(); toast.success(`Success`); setShowForm(false); onRefresh(); } }); } }; return (

Required.

.wr.do
{errors?.name ? (

{errors.name.message}

) : (

Required. Use @ for root.

)}
{errors?.content ? (

{errors.content.message}

) : (

{currentRecordType === "CNAME" ? "Required. E.g. www.example.com" : currentRecordType === "A" ? "Required. E.g. 8.8.8.8" : "Required."}

)}

Optional. Time To Live.

Enter your comment here (up to 100 characters)

{/*

Proxy status

*/}
{/* Action buttons */}
{type === "edit" && ( )}
); }