223 lines
6.4 KiB
JavaScript
223 lines
6.4 KiB
JavaScript
|
|
import React, { useState, useEffect } from "react";
|
|||
|
|
import {
|
|||
|
|
Tag,
|
|||
|
|
Button,
|
|||
|
|
Card,
|
|||
|
|
Table,
|
|||
|
|
Input,
|
|||
|
|
Flex,
|
|||
|
|
Popover,
|
|||
|
|
Image,
|
|||
|
|
Row,
|
|||
|
|
Col,
|
|||
|
|
DatePicker,
|
|||
|
|
Form,
|
|||
|
|
message,
|
|||
|
|
} from "antd";
|
|||
|
|
import dayjs from "dayjs";
|
|||
|
|
import { Connect } from "@cqsjjb/jjb-dva-runtime";
|
|||
|
|
import { NS_SAFETY_EVAL_BUSINESS } from "~/enumerate/namespace";
|
|||
|
|
import { tools } from "@cqsjjb/jjb-common-lib";
|
|||
|
|
|
|||
|
|
const { router } = tools;
|
|||
|
|
|
|||
|
|
const ArchiveContent = ({ readOnly, ...props }) => {
|
|||
|
|
const projectId = router.query?.id;
|
|||
|
|
const { processControlDetail, processControlFiles, evalProjectDetailData } =
|
|||
|
|
props.safetyEvalBusiness || {};
|
|||
|
|
const { processControl } = processControlDetail || {};
|
|||
|
|
|
|||
|
|
const [files, setFiles] = useState([]);
|
|||
|
|
const [archiveForm] = Form.useForm();
|
|||
|
|
|
|||
|
|
const fetchDetail = () => {
|
|||
|
|
props.evalProcessControlDetail({ projectId });
|
|||
|
|
};
|
|||
|
|
|
|||
|
|
const fetchFiles = () => {
|
|||
|
|
props.evalProcessControlFiles({ projectId });
|
|||
|
|
};
|
|||
|
|
|
|||
|
|
useEffect(() => {
|
|||
|
|
if (projectId) {
|
|||
|
|
fetchDetail();
|
|||
|
|
fetchFiles();
|
|||
|
|
}
|
|||
|
|
}, [projectId]);
|
|||
|
|
|
|||
|
|
useEffect(() => {
|
|||
|
|
if (processControlDetail) {
|
|||
|
|
archiveForm.setFieldsValue({
|
|||
|
|
projectNo: evalProjectDetailData.projectNo,
|
|||
|
|
archiveTransferorName: processControlDetail.archiveTransferorName || "",
|
|||
|
|
archiveArchivistName: processControlDetail.archiveArchivistName || "",
|
|||
|
|
archiveDate: processControlDetail.archiveDate
|
|||
|
|
? dayjs(processControlDetail.archiveDate)
|
|||
|
|
: null,
|
|||
|
|
});
|
|||
|
|
}
|
|||
|
|
}, [processControlDetail]);
|
|||
|
|
|
|||
|
|
useEffect(() => {
|
|||
|
|
if (processControlFiles) {
|
|||
|
|
setFiles(processControlFiles);
|
|||
|
|
}
|
|||
|
|
}, [processControlFiles]);
|
|||
|
|
|
|||
|
|
const isSignatureCompleted =
|
|||
|
|
processControl?.reviewerSignatureTaskStatus === "completed";
|
|||
|
|
const canArchive = isSignatureCompleted;
|
|||
|
|
|
|||
|
|
const handleArchive = async () => {
|
|||
|
|
if (!projectId) return;
|
|||
|
|
const values = await archiveForm.validateFields();
|
|||
|
|
const res = await props.evalProcessControlArchive({ projectId, ...values });
|
|||
|
|
if (res?.success !== false) {
|
|||
|
|
message.success("项目已归档入库");
|
|||
|
|
fetchDetail();
|
|||
|
|
props.getDetail?.();
|
|||
|
|
}
|
|||
|
|
};
|
|||
|
|
|
|||
|
|
const isImage = (name) =>
|
|||
|
|
/\.(jpg|jpeg|png|gif|webp|bmp|svg)$/i.test(name || "");
|
|||
|
|
|
|||
|
|
const fileColumns = [
|
|||
|
|
{ title: "流程名称", dataIndex: "processName", ellipsis: true },
|
|||
|
|
{ title: "条目名称", dataIndex: "itemName", ellipsis: true },
|
|||
|
|
{
|
|||
|
|
title: "文件",
|
|||
|
|
dataIndex: "projectDocUrl",
|
|||
|
|
render: (val) => {
|
|||
|
|
let fileList = [];
|
|||
|
|
if (typeof val === "string") {
|
|||
|
|
try {
|
|||
|
|
fileList = JSON.parse(val);
|
|||
|
|
} catch {
|
|||
|
|
fileList = [];
|
|||
|
|
}
|
|||
|
|
} else if (Array.isArray(val)) {
|
|||
|
|
fileList = val;
|
|||
|
|
}
|
|||
|
|
if (!fileList.length) return "-";
|
|||
|
|
return (
|
|||
|
|
<Flex vertical gap={2}>
|
|||
|
|
<Popover
|
|||
|
|
title="附件列表"
|
|||
|
|
content={
|
|||
|
|
<Flex vertical gap={4}>
|
|||
|
|
{fileList.map((f, i) => {
|
|||
|
|
const url = f.url || f.response?.url;
|
|||
|
|
return isImage(f.name) ? (
|
|||
|
|
<Flex key={f.uid || i} align="center" gap={4}>
|
|||
|
|
{<Image src={url} width={80} />}
|
|||
|
|
</Flex>
|
|||
|
|
) : (
|
|||
|
|
<a
|
|||
|
|
key={f.uid || i}
|
|||
|
|
style={{ cursor: "pointer" }}
|
|||
|
|
onClick={() => window.open(url)}
|
|||
|
|
>
|
|||
|
|
{f.name || "查看文件"}
|
|||
|
|
</a>
|
|||
|
|
);
|
|||
|
|
})}
|
|||
|
|
</Flex>
|
|||
|
|
}
|
|||
|
|
trigger="hover"
|
|||
|
|
placement="topLeft"
|
|||
|
|
>
|
|||
|
|
<a
|
|||
|
|
onClick={(e) => e.preventDefault()}
|
|||
|
|
style={{ cursor: "pointer" }}
|
|||
|
|
>
|
|||
|
|
{fileList.length}个附件
|
|||
|
|
</a>
|
|||
|
|
</Popover>
|
|||
|
|
</Flex>
|
|||
|
|
);
|
|||
|
|
},
|
|||
|
|
},
|
|||
|
|
];
|
|||
|
|
|
|||
|
|
return (
|
|||
|
|
<Card
|
|||
|
|
title="项目归档"
|
|||
|
|
style={{ marginBottom: 16 }}
|
|||
|
|
styles={{ body: { paddingBottom: 0 } }}
|
|||
|
|
>
|
|||
|
|
<div className="pf-permission">
|
|||
|
|
<Tag color="blue" className="pf-tag">
|
|||
|
|
项目归档
|
|||
|
|
</Tag>
|
|||
|
|
<span className="pf-desc">
|
|||
|
|
项目过程文件清单,确认签字完成后归档入库
|
|||
|
|
</span>
|
|||
|
|
</div>
|
|||
|
|
|
|||
|
|
<Table
|
|||
|
|
dataSource={files}
|
|||
|
|
columns={fileColumns}
|
|||
|
|
rowKey={(record) =>
|
|||
|
|
`${record.processName}-${record.materialName}-${record.itemName}`
|
|||
|
|
}
|
|||
|
|
pagination={false}
|
|||
|
|
size="small"
|
|||
|
|
/>
|
|||
|
|
|
|||
|
|
<Form form={archiveForm} layout="vertical" disabled={readOnly}>
|
|||
|
|
<Row gutter={16} style={{ marginTop: 16, marginBottom: 16 }}>
|
|||
|
|
<Col span={6}>
|
|||
|
|
<Form.Item label="项目编号" name="projectNo">
|
|||
|
|
<Input placeholder="请输入项目编号" disabled />
|
|||
|
|
</Form.Item>
|
|||
|
|
</Col>
|
|||
|
|
<Col span={6}>
|
|||
|
|
<Form.Item label="移交人" name="archiveTransferorName" rules={[{ required: true, message: "请输入移交人" }]}>
|
|||
|
|
<Input placeholder="请输入移交人" allowClear maxLength={10} />
|
|||
|
|
</Form.Item>
|
|||
|
|
</Col>
|
|||
|
|
<Col span={6}>
|
|||
|
|
<Form.Item label="档案管理员" name="archiveArchivistName" rules={[{ required: true, message: "请输入档案管理员" }]}>
|
|||
|
|
<Input placeholder="请输入档案管理员" allowClear maxLength={10} />
|
|||
|
|
</Form.Item>
|
|||
|
|
</Col>
|
|||
|
|
{processControlDetail?.archiveDate && (
|
|||
|
|
<Col span={6}>
|
|||
|
|
<Form.Item label="入库日期" name="archiveDate">
|
|||
|
|
<DatePicker style={{ width: "100%" }} disabled />
|
|||
|
|
</Form.Item>
|
|||
|
|
</Col>
|
|||
|
|
)}
|
|||
|
|
</Row>
|
|||
|
|
</Form>
|
|||
|
|
|
|||
|
|
<Flex
|
|||
|
|
justify="space-between"
|
|||
|
|
align="center"
|
|||
|
|
style={{ marginTop: 12, paddingBottom: 16 }}
|
|||
|
|
>
|
|||
|
|
{!readOnly && (
|
|||
|
|
<Button
|
|||
|
|
type="primary"
|
|||
|
|
onClick={handleArchive}
|
|||
|
|
loading={props.safetyEvalBusiness?.processControlArchiveLoading}
|
|||
|
|
disabled={!canArchive}
|
|||
|
|
title={
|
|||
|
|
!canArchive
|
|||
|
|
? !isSignatureCompleted
|
|||
|
|
? "需签字完成后才可归档"
|
|||
|
|
: "需生成归档交接单后才可归档"
|
|||
|
|
: ""
|
|||
|
|
}
|
|||
|
|
>
|
|||
|
|
双方签字并确认入库
|
|||
|
|
</Button>
|
|||
|
|
)}
|
|||
|
|
</Flex>
|
|||
|
|
</Card>
|
|||
|
|
);
|
|||
|
|
};
|
|||
|
|
|
|||
|
|
export default Connect([NS_SAFETY_EVAL_BUSINESS], true)(ArchiveContent);
|