|
|
import { apiFileDelete, apiFileUpload } from '@/services/business/file';
|
|
|
import {
|
|
|
ProForm,
|
|
|
ProFormInstance,
|
|
|
ProFormList,
|
|
|
ProFormText,
|
|
|
ProFormTextArea,
|
|
|
ProFormUploadDragger,
|
|
|
StepsForm,
|
|
|
} from '@ant-design/pro-components';
|
|
|
import { FormListActionType } from '@ant-design/pro-form/lib';
|
|
|
import { FormattedMessage, useIntl } from '@umijs/max';
|
|
|
import { Modal, UploadFile, message } from 'antd';
|
|
|
import yaml from 'js-yaml';
|
|
|
import React, { useEffect, useRef, useState } from 'react';
|
|
|
import {
|
|
|
proFormItemStyleProps,
|
|
|
proFormSmallItemStyleProps,
|
|
|
proFormSmallModelWidth,
|
|
|
proFormStepsFormProps,
|
|
|
} from '../../../../../config/defaultForm';
|
|
|
// import {beforeUploadFile} from "@/utils/common";
|
|
|
// @ts-ignore
|
|
|
import { fileApiActionUrl } from '../../../../../config/defaultApi';
|
|
|
|
|
|
export type CreateFormProps = {
|
|
|
createModalOpen: boolean;
|
|
|
handleModal: () => void;
|
|
|
modelInfo: Record<string, any>;
|
|
|
reload: any;
|
|
|
};
|
|
|
const waitTime = (time: number = 100) => {
|
|
|
return new Promise((resolve) => {
|
|
|
setTimeout(() => {
|
|
|
resolve(true);
|
|
|
}, time);
|
|
|
});
|
|
|
};
|
|
|
// interface ProjectConfig {
|
|
|
// params: Array<object>;
|
|
|
// }
|
|
|
const CreateForm: React.FC<CreateFormProps> = (props) => {
|
|
|
const actionFormListRef = useRef<
|
|
|
FormListActionType<{
|
|
|
name: string;
|
|
|
}>
|
|
|
>();
|
|
|
|
|
|
const intl = useIntl();
|
|
|
|
|
|
const [dataFormList] = useState<any>([]);
|
|
|
const dataFormListRef = useRef(dataFormList);
|
|
|
// const [projectFileList, setProjectFileList] = useState<UploadFile<any>[]>([]);
|
|
|
const [configFileList, setConfigFileList] = useState<UploadFile<any>[]>([]);
|
|
|
|
|
|
// const [form] = Form.useForm<Record<string, any>>();
|
|
|
|
|
|
const [current, setCurrent] = useState(0);
|
|
|
const formBaseRef = useRef<ProFormInstance>();
|
|
|
const formProjectFileRef = useRef<ProFormInstance>();
|
|
|
// const [filePath, setFilePath] = useState('');
|
|
|
|
|
|
const handleFileChange = ({ file }: { file: UploadFile }) => {
|
|
|
console.log(configFileList, 'handleFileChange_configFileList');
|
|
|
let curFile: any;
|
|
|
|
|
|
switch (file.status) {
|
|
|
case 'uploading':
|
|
|
case 'done':
|
|
|
curFile = [file];
|
|
|
break;
|
|
|
case 'removed':
|
|
|
default:
|
|
|
curFile = [];
|
|
|
break;
|
|
|
}
|
|
|
|
|
|
setConfigFileList([...curFile]);
|
|
|
};
|
|
|
|
|
|
// test 测试数据
|
|
|
useEffect(() => {
|
|
|
// if (formBaseRef) {
|
|
|
formBaseRef.current?.setFieldsValue({
|
|
|
version: '0.0.91', // 设备分类的suid
|
|
|
comment:
|
|
|
'测试一下备注测试一下备注测试一下备注测试一下备注测试一下备注测试一下备注测试一下备注测试一下备注测试一下备注测试一下备注测试一下备注测试一下备注',
|
|
|
});
|
|
|
|
|
|
// }
|
|
|
}, [props.createModalOpen]);
|
|
|
return (
|
|
|
<StepsForm<{
|
|
|
name: string;
|
|
|
}>
|
|
|
onFinish={async (values) => {
|
|
|
console.log('All form values:', values, { model_id: props.modelInfo?.model_id });
|
|
|
// 在这里处理提交数据,例如调用API
|
|
|
message.success('提交成功');
|
|
|
}}
|
|
|
stepsProps={proFormStepsFormProps.stepsProps}
|
|
|
current={current}
|
|
|
onCurrentChange={setCurrent}
|
|
|
formProps={{
|
|
|
validateMessages: {
|
|
|
required: '此项为必填项',
|
|
|
},
|
|
|
}}
|
|
|
stepsFormRender={(dom, submitter) => {
|
|
|
return (
|
|
|
<Modal
|
|
|
className="gn_model_steps_form"
|
|
|
title={
|
|
|
<FormattedMessage id="model_detail.version.table.list.add" defaultMessage="新增" />
|
|
|
}
|
|
|
width={proFormSmallModelWidth}
|
|
|
onCancel={() => {
|
|
|
setCurrent(0);
|
|
|
formBaseRef.current?.resetFields();
|
|
|
// setProjectFileList([]);
|
|
|
props.handleModal();
|
|
|
}}
|
|
|
open={props.createModalOpen}
|
|
|
footer={submitter}
|
|
|
destroyOnClose
|
|
|
>
|
|
|
{dom}
|
|
|
</Modal>
|
|
|
);
|
|
|
}}
|
|
|
>
|
|
|
{/* 版本信息 */}
|
|
|
<StepsForm.StepForm<{
|
|
|
name: string;
|
|
|
}>
|
|
|
className="gn_form"
|
|
|
name="base"
|
|
|
formRef={formBaseRef}
|
|
|
title={
|
|
|
<FormattedMessage id="model_detail.version.stepForm.base" defaultMessage="版本信息" />
|
|
|
}
|
|
|
stepProps={{
|
|
|
description: (
|
|
|
<FormattedMessage
|
|
|
id="model_detail.version.stepForm.base.description"
|
|
|
defaultMessage="填写版本基础信息"
|
|
|
/>
|
|
|
),
|
|
|
}}
|
|
|
onFinish={async () => {
|
|
|
// setFormData(formBaseRef.current?.getFieldsValue());
|
|
|
await waitTime(500);
|
|
|
return true;
|
|
|
}}
|
|
|
>
|
|
|
<ProForm.Group>
|
|
|
{/* 默认填充模型 无需选择 */}
|
|
|
<ProFormText
|
|
|
width={proFormSmallItemStyleProps.width}
|
|
|
name="model_name"
|
|
|
label={
|
|
|
<FormattedMessage id="model_detail.version.form.modelFkId" defaultMessage="$$$" />
|
|
|
}
|
|
|
required={true}
|
|
|
initialValue={props.modelInfo?.name}
|
|
|
debounceTime={1000}
|
|
|
disabled={true}
|
|
|
// request={async (keyWord) => {
|
|
|
// const resp = await postAlgorithmModelGetAlgorithmModelFkSelect({
|
|
|
// keyword: keyWord?.keyWords || '',
|
|
|
// });
|
|
|
// return resp.data.list.map((v: any) => {
|
|
|
// return {
|
|
|
// label: v.name,
|
|
|
// value: v.id,
|
|
|
// };
|
|
|
// });
|
|
|
// }}
|
|
|
/>
|
|
|
<ProFormText
|
|
|
width={proFormSmallItemStyleProps.width}
|
|
|
fieldProps={{
|
|
|
prefix: <span>V</span>,
|
|
|
}}
|
|
|
name="version"
|
|
|
label={<FormattedMessage id="model_detail.version.form.name" defaultMessage="版本号" />}
|
|
|
placeholder={`${intl.formatMessage({
|
|
|
id: 'common.please_input',
|
|
|
defaultMessage: '$$$',
|
|
|
})}${intl.formatMessage({
|
|
|
id: 'model_detail.version.form.name',
|
|
|
defaultMessage: '$$$',
|
|
|
})}`}
|
|
|
required={true}
|
|
|
rules={[
|
|
|
{
|
|
|
required: true,
|
|
|
message: (
|
|
|
<FormattedMessage
|
|
|
id="model_detail.version.form.required.name"
|
|
|
defaultMessage="name is required"
|
|
|
/>
|
|
|
),
|
|
|
},
|
|
|
]}
|
|
|
/>
|
|
|
<ProFormTextArea
|
|
|
width={proFormSmallItemStyleProps.width}
|
|
|
name="comment"
|
|
|
label={<FormattedMessage id="model_detail.version.form.remark" defaultMessage="备注" />}
|
|
|
placeholder={`${intl.formatMessage({
|
|
|
id: 'common.please_input',
|
|
|
defaultMessage: '$$$',
|
|
|
})}${intl.formatMessage({
|
|
|
id: 'model_detail.version.form.remark',
|
|
|
defaultMessage: '$$$',
|
|
|
})}`}
|
|
|
required={false}
|
|
|
disabled={false}
|
|
|
/>
|
|
|
</ProForm.Group>
|
|
|
</StepsForm.StepForm>
|
|
|
{/* 版本上传 */}
|
|
|
<StepsForm.StepForm<{
|
|
|
project_file: string;
|
|
|
}>
|
|
|
formRef={formProjectFileRef}
|
|
|
className="gn_form"
|
|
|
name="project_file"
|
|
|
title={
|
|
|
<FormattedMessage
|
|
|
id="model_detail.version.stepForm.project_file"
|
|
|
defaultMessage="版本上传"
|
|
|
/>
|
|
|
}
|
|
|
style={{ width: proFormItemStyleProps.width }}
|
|
|
stepProps={{
|
|
|
description: (
|
|
|
<FormattedMessage
|
|
|
id="model_detail.version.stepForm.project_file.description"
|
|
|
defaultMessage="上传模型文件"
|
|
|
/>
|
|
|
),
|
|
|
}}
|
|
|
onFinish={async (values: any) => {
|
|
|
console.log(values, 'values');
|
|
|
// if ('projectFilePath' in values && values['projectFilePath'].length > 0) {
|
|
|
// let projectFilePath = values['projectFilePath'][0]?.response?.data?.path || '';
|
|
|
// setFilePath(projectFilePath);
|
|
|
// }
|
|
|
return true;
|
|
|
}}
|
|
|
>
|
|
|
<ProFormUploadDragger
|
|
|
label={<span className="font-bold">上传模型文件</span>}
|
|
|
title={
|
|
|
<div className="gn_uploadfile_title py-[16px] text1 text-center">
|
|
|
<span>拖拽文件到这里,或</span>
|
|
|
<a>点此添加</a>
|
|
|
</div>
|
|
|
}
|
|
|
description=""
|
|
|
icon={<i className="iconfont icon-shangchuanwenjian text_primary text-[32px]"></i>}
|
|
|
name="model_file_name"
|
|
|
// action={fileApiActionUrl}
|
|
|
onRemove={async (file) => {
|
|
|
// 这里可以添加删除文件的接口调用逻辑
|
|
|
// await deleteFileFromServer(file);
|
|
|
|
|
|
// setFileList((prevList) => {
|
|
|
// const newList = prevList.filter((item) => item.uid !== file.uid);
|
|
|
// return newList;
|
|
|
// });
|
|
|
const currFileId = formProjectFileRef?.current?.getFieldValue('model_file');
|
|
|
const resp = await apiFileDelete({ file_md5: currFileId });
|
|
|
console.log(resp, 'apiFileDelete_resp', file);
|
|
|
message.success('文件已删除');
|
|
|
return true; // 确保文件从文件列表中移除
|
|
|
}}
|
|
|
onChange={async ({ file, fileList }) => {
|
|
|
// 检查文件状态
|
|
|
|
|
|
console.log(
|
|
|
file,
|
|
|
fileList,
|
|
|
'onChange_ProjectFile',
|
|
|
formProjectFileRef?.current?.getFieldValue('model_file'),
|
|
|
);
|
|
|
if (file.status === 'removed') {
|
|
|
// 删除文件
|
|
|
// setProjectFileList(fileList.filter((item) => item.uid !== file.uid));
|
|
|
// const currFileId = formProjectFileRef?.current?.getFieldValue('model_file')
|
|
|
// const resp = await apiFileDelete({file_md5: currFileId})
|
|
|
// console.log(resp,'apiFileDelete_resp')
|
|
|
// message.success(`${file.name} 删除成功`);
|
|
|
} else {
|
|
|
// 处理上传
|
|
|
// formProjectFileRef?.current?.setFieldValue('model_file_name', [file]);
|
|
|
// handleUpload(file);
|
|
|
}
|
|
|
// setProjectFileList(fileList);
|
|
|
}}
|
|
|
max={1}
|
|
|
fieldProps={{
|
|
|
className: 'gn_proFormUploadDragger_formItem',
|
|
|
name: 'file',
|
|
|
// beforeUpload: beforeUploadFile,
|
|
|
data: { path: `models/${Date.now()}` },
|
|
|
|
|
|
headers: {
|
|
|
// 'X-CSRFToken': cookie.load('csrftoken'),
|
|
|
// Authorization: `Bearer ${localStorage.getItem('access') || ''}`,
|
|
|
},
|
|
|
beforeUpload: async (file) => {
|
|
|
const formData = new FormData();
|
|
|
formData.append('file', file);
|
|
|
const resp = await apiFileUpload(formData);
|
|
|
formProjectFileRef?.current?.setFieldValue('model_file', resp?.data?.result);
|
|
|
console.log(resp, 'apiFileUpload_resp');
|
|
|
// form.setFieldValue('logo', base64);
|
|
|
return false; // 阻止自动上传
|
|
|
},
|
|
|
}}
|
|
|
/>
|
|
|
<div style={{ color: '#666666', marginTop: '-8px' }}>请上传格式为zip.tar.gz的模型文件</div>
|
|
|
</StepsForm.StepForm>
|
|
|
{/* 参数配置 */}
|
|
|
<StepsForm.StepForm<{
|
|
|
config: string;
|
|
|
}>
|
|
|
className="gn_form"
|
|
|
name="config"
|
|
|
title={
|
|
|
<FormattedMessage id="model_detail.version.stepForm.config" defaultMessage="参数配置" />
|
|
|
}
|
|
|
stepProps={{
|
|
|
description: (
|
|
|
<FormattedMessage
|
|
|
id="model_detail.version.stepForm.config.description"
|
|
|
defaultMessage="参数配置"
|
|
|
/>
|
|
|
),
|
|
|
}}
|
|
|
onFinish={async (values: any) => {
|
|
|
// setConfigFileList([]);
|
|
|
console.log(values, 'config_values');
|
|
|
let formData1 = formBaseRef.current?.getFieldsValue();
|
|
|
if (formData1?.model_name) {
|
|
|
await waitTime(500);
|
|
|
// formData1.modelConfig = { params: values?.params || [] };
|
|
|
// if (filePath) {
|
|
|
// formData1.path = filePath;
|
|
|
// }
|
|
|
// postModelVersionCreateModelVersion(formData)
|
|
|
// .then(() => {
|
|
|
// message.success(
|
|
|
// intl.formatMessage({ id: 'common.action.success', defaultMessage: '$$$' }),
|
|
|
// );
|
|
|
// props.handleModal();
|
|
|
// props.reload();
|
|
|
// })
|
|
|
// .catch(() => {
|
|
|
// message.error(intl.formatMessage({ id: 'common.action.failure', defaultMessage: '$$$' }));
|
|
|
// return false;
|
|
|
// });
|
|
|
}
|
|
|
return true;
|
|
|
}}
|
|
|
>
|
|
|
<ProFormUploadDragger
|
|
|
width={proFormSmallItemStyleProps.width}
|
|
|
max={1}
|
|
|
label={<span className="font-bold">模型配置文件上传</span>}
|
|
|
title={
|
|
|
<div className="gn_uploadfile_title py-[16px] text1 text-center">
|
|
|
<span>拖拽文件到这里,或</span>
|
|
|
<a>点此添加</a>
|
|
|
</div>
|
|
|
}
|
|
|
description=""
|
|
|
icon={<i className="iconfont icon-shangchuanwenjian text_primary text-[32px]"></i>}
|
|
|
name="config_file"
|
|
|
action={fileApiActionUrl}
|
|
|
fieldProps={{
|
|
|
className: 'gn_proFormUploadDragger_formItem',
|
|
|
onChange: handleFileChange,
|
|
|
onRemove: () => {
|
|
|
let index_ids = actionFormListRef.current?.getList()?.map((v, i) => {
|
|
|
return i;
|
|
|
});
|
|
|
actionFormListRef.current?.remove(index_ids || []);
|
|
|
},
|
|
|
beforeUpload: (file) => {
|
|
|
if (
|
|
|
!file.name.endsWith('.yaml') &&
|
|
|
!file.name.endsWith('.yml') &&
|
|
|
!file.name.endsWith('.json')
|
|
|
) {
|
|
|
message.error('请上传yaml或json文件').then(() => {});
|
|
|
return false;
|
|
|
} else {
|
|
|
let parsedData = {};
|
|
|
file
|
|
|
.text()
|
|
|
.then((text) => {
|
|
|
if (file.name.endsWith('.yaml') || file.name.endsWith('.yml')) {
|
|
|
parsedData = yaml.load(text) as Record<string, unknown>;
|
|
|
}
|
|
|
if (file.name.endsWith('.json')) {
|
|
|
parsedData = JSON.parse(text) as Record<string, unknown>;
|
|
|
}
|
|
|
if (Object.keys(parsedData).length > 0) {
|
|
|
dataFormListRef.current = Object.entries(parsedData).map(([key, value]) => ({
|
|
|
name: key,
|
|
|
default: value,
|
|
|
}));
|
|
|
|
|
|
dataFormListRef.current.forEach((v: any, i: number) => {
|
|
|
actionFormListRef.current?.add(v, i);
|
|
|
});
|
|
|
}
|
|
|
return true;
|
|
|
})
|
|
|
.catch(() => {
|
|
|
return false;
|
|
|
});
|
|
|
}
|
|
|
},
|
|
|
}}
|
|
|
/>
|
|
|
<div style={{ color: '#666666', marginTop: '-8px', marginBottom: '16px' }}>
|
|
|
请上传格式为zip.tar.gz的模型文件
|
|
|
</div>
|
|
|
|
|
|
{/* // TODO label字重与上面统一, 操作按钮需要与输入框对齐 */}
|
|
|
<ProFormList
|
|
|
name="config_str_arr"
|
|
|
label={
|
|
|
<div>
|
|
|
<span className="font-bold">模型参数</span>
|
|
|
<div style={{ color: '#333333', padding: '8px 0 4px' }}>
|
|
|
暂未上传模型配置文件,可根据业务需求手动添加参数字段~
|
|
|
</div>
|
|
|
</div>
|
|
|
}
|
|
|
actionRef={actionFormListRef}
|
|
|
itemContainerRender={(doms) => {
|
|
|
return <ProForm.Group>{doms}</ProForm.Group>;
|
|
|
}}
|
|
|
alwaysShowItemLabel
|
|
|
>
|
|
|
{() => {
|
|
|
return (
|
|
|
<>
|
|
|
<ProFormText width={268} key="name" name="name" label="键名" />
|
|
|
<ProFormText width={268} key="default" name="default" label="默认值" />
|
|
|
</>
|
|
|
);
|
|
|
}}
|
|
|
</ProFormList>
|
|
|
</StepsForm.StepForm>
|
|
|
</StepsForm>
|
|
|
);
|
|
|
};
|
|
|
export default CreateForm;
|