204 lines
7.2 KiB
TypeScript
204 lines
7.2 KiB
TypeScript
"use client";
|
|
import { SdmRegForm, type DemandCompType } from "./form";
|
|
import { Button } from "@common/components/ui";
|
|
import { zodResolver } from "@hookform/resolvers/zod";
|
|
import { useCallback, useEffect, useState } from "react";
|
|
import { FormProvider, useForm, type SubmitHandler } from "react-hook-form";
|
|
import { toast, Toaster } from "sonner";
|
|
import * as z from "zod";
|
|
import type { SelectDataType } from "../search_input_select";
|
|
import { getCookie } from "@common/components/lib";
|
|
|
|
type thisProps = {
|
|
selectSidoData: SelectDataType[];
|
|
selectSigunData: SelectDataType[];
|
|
dataList: DemandCompType[];
|
|
rtnValue: (searchText: string, pageCnt: number) => void;
|
|
rtnInputData: (data: DemandCompType) => void;
|
|
bodyClassNm?: string;
|
|
updateList?:DemandCompType;
|
|
readOnly?:boolean;
|
|
openNetwork:boolean;
|
|
}
|
|
|
|
const createFormSchema = (isBznmTotNoDisabled: boolean, isDuplicate: boolean ,updateList?:DemandCompType) => z.object({
|
|
ctpvCd: z.string().min(1, "시/도를 선택해주세요"),
|
|
sggCd: z.string().min(1, "시/군/구를 선택해주세요"),
|
|
dmdCoNm: z.string()
|
|
.min(1, "회사명을 입력해주세요")
|
|
.max(20, "회사명은 20자 이내로 입력해주세요"),
|
|
dmdInfoId: z.string()
|
|
.min(1, "사업자등록번호를 입력해주세요")
|
|
.regex(/^\d{10}$/, "사업자등록번호는 10자리 숫자만 입력 가능합니다")
|
|
.refine(() => isBznmTotNoDisabled ? !isDuplicate : true, "이미 등록된 사업자등록번호입니다"),
|
|
zip: z.string().optional(),
|
|
bznmTotNo: isBznmTotNoDisabled
|
|
? z.string().optional()
|
|
: z.string()
|
|
.length(4, "종사업자등록번호는 4자리 숫자만 입력 가능합니다")
|
|
.refine(() => !isDuplicate, "이미 등록된 사업자등록번호입니다"),
|
|
daddr: z.string()
|
|
.min(1, "주소를 입력해주세요")
|
|
// .min(6, "주소는 6자 이상 입력해주세요")
|
|
.max(40, "주소는 40자 이내로 입력해주세요"),
|
|
daddr2: z.string().optional(),
|
|
telno: z.string()
|
|
.min(8, "전화번호는 8자 이상 입력해주세요")
|
|
.max(11, "전화번호는 11자 이내로 입력해주세요")
|
|
.regex(/^[0-9]+$/, "전화번호는 숫자만 입력 가능합니다"),
|
|
rgtr: z.string().optional(),
|
|
mdfr: z.string().nullish(),
|
|
dmdAplyPswd : updateList?.dmdInfoId // 업데이트일경우
|
|
? z.string().optional() // 패스워드는 선택 사항이며 길이 제한 없음
|
|
: z.string().optional()
|
|
.refine((val) => !val || (val.length >= 8 && val.length <= 16), "패스워드는 8자 이상 16자 이내로 입력해주세요"),
|
|
dmdAplyPswdConfirm: updateList?.dmdInfoId // 업데이트일경우
|
|
? z.string().optional() // 패스워드는 선택 사항이며 길이 제한 없음
|
|
:z.string()
|
|
.min(1, "패스워드확인을 입력해주세요"),
|
|
}).refine((data) => {
|
|
// 패스워드 확인 검증
|
|
if (data.dmdAplyPswd && data.dmdAplyPswdConfirm) {
|
|
return data.dmdAplyPswd === data.dmdAplyPswdConfirm;
|
|
}
|
|
return true;
|
|
}, {
|
|
message: "패스워드가 일치하지 않습니다",
|
|
path: ["dmdAplyPswdConfirm"], // 에러를 패스워드 확인 필드에 표시
|
|
});
|
|
|
|
type FormSchema = z.infer<ReturnType<typeof createFormSchema>>;
|
|
|
|
const defaultValues: FormSchema = {
|
|
ctpvCd: '',
|
|
sggCd: '',
|
|
dmdCoNm: '',
|
|
dmdInfoId: '',
|
|
zip: '',
|
|
bznmTotNo: '',
|
|
daddr: '',
|
|
daddr2: '',
|
|
telno: '',
|
|
rgtr: '',
|
|
mdfr: '',
|
|
dmdAplyPswd: '',
|
|
dmdAplyPswdConfirm: '',
|
|
};
|
|
|
|
/**
|
|
* 수요처 등록 폼
|
|
* @param selectSidoData 시/도 데이터
|
|
* @param selectSigunData 시/군/구 데이터
|
|
* @param dataList 수요처 목록
|
|
* @param rtnValue 검색 결과(텍스트) 콜백
|
|
* @param rtnInputData 수요처관리 콜백 : 등록/수정 처리
|
|
* @returns
|
|
*/
|
|
export default function SdmInsertForm({selectSidoData, selectSigunData, dataList, rtnValue, rtnInputData
|
|
, bodyClassNm, updateList, readOnly, openNetwork}: thisProps) {
|
|
|
|
const [isBznmTotNoDisabled, setIsBznmTotNoDisabled] = useState(false); // 종사업자등록번호 해당없음
|
|
const [isDuplicate, setIsDuplicate] = useState(false);
|
|
const formSchema = createFormSchema(isBznmTotNoDisabled, isDuplicate, updateList );
|
|
|
|
const form = useForm<FormSchema>({
|
|
resolver: zodResolver(formSchema),
|
|
defaultValues,
|
|
mode: "onChange",
|
|
criteriaMode: "all",
|
|
shouldFocusError: false,
|
|
shouldUnregister: false
|
|
});
|
|
|
|
// 체크박스 상태가 변경될 때마다 bznmTotNo 필드의 에러를 초기화
|
|
useEffect(() => {
|
|
if (isBznmTotNoDisabled===true) {
|
|
form.clearErrors('bznmTotNo');
|
|
form.setValue('bznmTotNo', '');
|
|
}
|
|
}, [isBznmTotNoDisabled, form]);
|
|
|
|
const setRtnValue = useCallback((searchText: string, pageCnt: number) => {
|
|
rtnValue(searchText, pageCnt);
|
|
}, [rtnValue]);
|
|
|
|
const onSubmit: SubmitHandler<FormSchema> = async (data) => {
|
|
try {
|
|
// form 에러 체크
|
|
const formErrors = form.formState.errors;
|
|
|
|
const myUUID = getCookie('token-id') ||'c475824c-0e82-4a06-a282-2b55a20df265';
|
|
|
|
if (Object.keys(formErrors).length > 0 ) {
|
|
const errorMessage = Object.values(formErrors)[0]?.message || '입력값을 확인해주세요.';
|
|
toast.error(errorMessage);
|
|
return;
|
|
}
|
|
|
|
|
|
|
|
const dmdInfoId = data.dmdInfoId + (data.bznmTotNo || '0000');
|
|
const formData = {
|
|
...data,
|
|
dmdCoSn: updateList?.dmdCoSn ?? "",
|
|
dmdInfoId,
|
|
bzmnNo: data.dmdInfoId,
|
|
daddr: data.daddr?.trim() || "",
|
|
daddr2: data.daddr2?.trim() || "",
|
|
rgtr: myUUID ,
|
|
};
|
|
|
|
|
|
/* await insertSdmData(formData); */
|
|
rtnInputData(formData as unknown as DemandCompType); // 수요처 등록/수정 처리
|
|
|
|
|
|
//router.push(`/pages/sdmMng/sdmInfoInsert?${queryParams.toString()}`);
|
|
} catch (error) {
|
|
console.error('Error submitting form:', error);
|
|
}
|
|
};
|
|
|
|
return (
|
|
<>
|
|
<div className="mb-8">
|
|
<h2 className="px-[1.8rem] pt-[2rem] text-[2.4rem] font-semibold text-title">
|
|
{!updateList ? '수요처 등록' : readOnly == true ? '수요처 상세정보' : '수요처 수정'}
|
|
</h2>
|
|
</div>
|
|
|
|
<div className= {bodyClassNm?bodyClassNm:"!max-w-3xl mx-auto bg-white rounded-lg shadow-md p-6"}>
|
|
<FormProvider {...form}>
|
|
<form onSubmit={form.handleSubmit(onSubmit)} className="space-y-6">
|
|
<SdmRegForm
|
|
form={form}
|
|
onCheckboxChange={setIsBznmTotNoDisabled}
|
|
selectSidoData={selectSidoData}
|
|
selectSigunData={selectSigunData}
|
|
dataList={dataList}
|
|
rtnValue={setRtnValue}
|
|
setIsDuplicate={setIsDuplicate}
|
|
updateList={updateList}
|
|
readOnly={readOnly}
|
|
openNetwork={openNetwork}
|
|
/>
|
|
<div className="flex justify-center pt-4">
|
|
{readOnly==true?<>
|
|
</>:
|
|
<Button
|
|
type="submit"
|
|
className="w-32 bg-blue-600 hover:bg-blue-700 text-white font-semibold py-2 px-4 rounded-md transition-colors duration-200"
|
|
>
|
|
{updateList ?'수정' :'등록'}
|
|
</Button>
|
|
}
|
|
|
|
</div>
|
|
</form>
|
|
</FormProvider>
|
|
</div>
|
|
<Toaster position="top-center" />
|
|
</>
|
|
);
|
|
}
|