diff --git a/web/src/app/home/pipelines/components/pipeline-form/PipelineFormComponent.tsx b/web/src/app/home/pipelines/components/pipeline-form/PipelineFormComponent.tsx index ee3ab7eb..c64c3149 100644 --- a/web/src/app/home/pipelines/components/pipeline-form/PipelineFormComponent.tsx +++ b/web/src/app/home/pipelines/components/pipeline-form/PipelineFormComponent.tsx @@ -22,6 +22,32 @@ import { import { IDynamicFormItemSchema } from '@/app/infra/entities/form/dynamic'; import DynamicFormComponent from '@/app/home/components/dynamic-form/DynamicFormComponent'; import { Button } from '@/components/ui/button'; +import { useForm } from "react-hook-form" +import { zodResolver } from "@hookform/resolvers/zod" +import { z } from "zod" +import { Input } from "@/components/ui/input" +import { + Form, + FormControl, + FormDescription, + FormField, + FormItem, + FormLabel, + FormMessage, +} from "@/components/ui/form" + +const formSchema = z.object({ + basic: z.object({ + name: z.string().min(1, { message: '名称不能为空' }), + description: z.string().min(1, { message: '描述不能为空' }), + }), + ai: z.record(z.string(), z.any()), + trigger: z.record(z.string(), z.any()), + safety: z.record(z.string(), z.any()), + output: z.record(z.string(), z.any()), +}); + +type FormValues = z.infer; export default function PipelineFormComponent({ initValues, @@ -58,6 +84,17 @@ export default function PipelineFormComponent({ const [safetyConfigTabSchema, setSafetyConfigTabSchema] = useState(); const [outputConfigTabSchema, setOutputConfigTabSchema] = useState(); + const form = useForm({ + resolver: zodResolver(formSchema), + defaultValues: { + basic: {}, + ai: {}, + trigger: {}, + safety: {}, + output: {}, + }, + }); + useEffect(() => { getLLMModelList(); @@ -77,16 +114,11 @@ export default function PipelineFormComponent({ }); }, []); - // useEffect(() => { - // console.log('initValues change: ', initValues); - // if (initValues) { - // // basicForm.setFieldsValue(initValues.basic); - // // aiForm.setFieldsValue(initValues.ai); - // // triggerForm.setFieldsValue(initValues.trigger); - // // safetyForm.setFieldsValue(initValues.safety); - // // outputForm.setFieldsValue(initValues.output); - // } - // }, [aiForm, basicForm, initValues, outputForm, safetyForm, triggerForm]); + useEffect(() => { + if (initValues) { + form.reset(initValues); + } + }, [initValues, form]); function getLLMModelList() { httpClient @@ -138,120 +170,154 @@ export default function PipelineFormComponent({ } } - function handleCommit() { + function handleFormSubmit(values: FormValues) { if (isEditMode) { - handleModify(); + handleModify(values); } else { - handleCreate(); + handleCreate(values); } } - function handleCreate() { - // Promise.all([ - // // basicForm.validateFields(), - // // aiForm.validateFields(), - // // triggerForm.validateFields(), - // // safetyForm.validateFields(), - // // outputForm.validateFields(), - // ]) - // .then(() => { - // const pipeline = assembleForm(); - // httpClient.createPipeline(pipeline).then(() => onFinish()); - // }) - // .catch((e) => { - // console.error(e); - // }); + function handleCreate(values: FormValues) { + const pipeline: Pipeline = { + config: values, + created_at: '', + description: '', + for_version: '', + name: '', + stages: [], + updated_at: '', + uuid: UUID.generate(), + is_default: false, + }; + httpClient.createPipeline(pipeline).then(() => onFinish()); } - function handleModify() { - // Promise.all([ - // // basicForm.validateFields(), - // // aiForm.validateFields(), - // // triggerForm.validateFields(), - // // safetyForm.validateFields(), - // // outputForm.validateFields(), - // ]) - // .then(() => { - // const pipeline = assembleForm(); - // httpClient - // .updatePipeline(pipelineId || '', pipeline) - // .then(() => onFinish()); - // }) - // .catch((e) => { - // console.error(e); - // }); + function handleModify(values: FormValues) { + const pipeline: Pipeline = { + config: values, + created_at: '', + description: '', + for_version: '', + name: '', + stages: [], + updated_at: '', + uuid: pipelineId || '', + is_default: false, + }; + httpClient.updatePipeline(pipelineId || '', pipeline).then(() => onFinish()); } - // TODO 类型混乱,需要优化 - // function assembleForm(): Pipeline { - // console.log('basicForm:', basicForm.getFieldsValue()); - // console.log('aiForm:', aiForm.getFieldsValue()); - // console.log('triggerForm:', triggerForm.getFieldsValue()); - // console.log('safetyForm:', safetyForm.getFieldsValue()); - // console.log('outputForm:', outputForm.getFieldsValue()); - // const config: object = { - // ai: aiForm.getFieldsValue(), - // trigger: triggerForm.getFieldsValue(), - // safety: safetyForm.getFieldsValue(), - // output: outputForm.getFieldsValue(), - // }; - - // return { - // config, - // created_at: '', - // description: basicForm.getFieldsValue().description, - // for_version: '', - // name: basicForm.getFieldsValue().name, - // stages: [], - // updated_at: '', - // uuid: UUID.generate(), - // }; - // } + function renderDynamicForms(stage: PipelineConfigStage, formName: keyof FormValues) { + return ( +
+
{stage.label.zh_CN}
+ {stage.description && ( +
{stage.description.zh_CN}
+ )} + )?.[stage.name] || {}} + onSubmit={(values) => { + const currentValues = form.getValues(formName) as Record || {}; + form.setValue(formName, { + ...currentValues, + [stage.name]: values, + }); + }} + /> +
+ ); + } return (
- - - - {formLabelList.map((formLabel) => ( - - {formLabel.label} - - ))} - - {formLabelList.map((formLabel) => ( - -

{formLabel.label}

-
name: {formLabel.name}
+
+ + + + {formLabelList.map((formLabel) => ( + + {formLabel.label} + + ))} + - - ))} - + {formLabelList.map((formLabel) => ( + +

{formLabel.label}

+ + {formLabel.name === 'basic' && ( +
+ ( + + 名称* + + + + + + )} + /> + ( + + 描述* + + + + + + )} + /> +
+ )} - {/*
- - + {formLabel.name === 'ai' && aiConfigTabSchema && ( +
+ {aiConfigTabSchema.stages.map((stage) => renderDynamicForms(stage, 'ai'))} +
+ )} - -
*/} + {formLabel.name === 'trigger' && triggerConfigTabSchema && ( +
+ {triggerConfigTabSchema.stages.map((stage) => renderDynamicForms(stage, 'trigger'))} +
+ )} + + {formLabel.name === 'safety' && safetyConfigTabSchema && ( +
+ {safetyConfigTabSchema.stages.map((stage) => renderDynamicForms(stage, 'safety'))} +
+ )} + + {formLabel.name === 'output' && outputConfigTabSchema && ( +
+ {outputConfigTabSchema.stages.map((stage) => renderDynamicForms(stage, 'output'))} +
+ )} +
+ ))} + + +
+
+ + +
+
+
+
); } diff --git a/web/src/app/infra/entities/pipeline/index.ts b/web/src/app/infra/entities/pipeline/index.ts index 6bd79ccb..2c364b08 100644 --- a/web/src/app/infra/entities/pipeline/index.ts +++ b/web/src/app/infra/entities/pipeline/index.ts @@ -18,5 +18,6 @@ export interface PipelineConfigTab { export interface PipelineConfigStage { name: string; label: I18nLabel; + description?: I18nLabel; config: IDynamicFormItemSchema[]; } \ No newline at end of file