dev-tmp1
tangjie 2026-08-24 14:18:37 +08:00
parent 4ed3c0e6fe
commit d78705dc15
2 changed files with 51 additions and 15 deletions

View File

@ -34,25 +34,25 @@ const STAT_ITEMS = [
key: "monitoringCount",
title: "在监项目",
color: "#1677ff",
},
{
key: "normalCount",
title: "正常执行",
color: "#52c41a",
},
{
key: "warningCount",
title: "进度/人员预警",
color: "#faad14",
},
{
key: "monthPlanCompleteCount",
title: "本月计划完成",
color: "#722ed1",
},
];
@ -90,9 +90,9 @@ const EvalProjectMonitor = (props) => {
planEndDateRange:
router.query.planEndDateStart && router.query.planEndDateEnd
? [
dayjs(router.query.planEndDateStart),
dayjs(router.query.planEndDateEnd),
]
dayjs(router.query.planEndDateStart),
dayjs(router.query.planEndDateEnd),
]
: undefined,
});
getStat();
@ -166,16 +166,19 @@ const EvalProjectMonitor = (props) => {
{
title: "行业",
dataIndex: "industryCode",
width: 140,
width: 180,
ellipsis: true,
render: (code) => QUALIFICATION_INDUSTRY_OPTIONS_MAP[code] || code,
render: (code) => {
const arr = code ? code.split(",") : [];
return arr.map((code) => QUALIFICATION_INDUSTRY_OPTIONS_MAP[code] || code).join("、") || "-";
},
},
{ title: "负责人", dataIndex: "leaderName", width: 90 },
{ title: "计划完成", dataIndex: "planEndDate", width: 120 },
{
title: "监管状态",
width: 100,
render: (_,{waringStatus}) => {
render: (_, { waringStatus }) => {
const { color, text } = MONITOR_WARING_STATUS_MAP[waringStatus] || {};
return <Tag color={color}>{text}</Tag>;
},

View File

@ -1,6 +1,6 @@
import React, { useState, useEffect } from "react";
import { Form, Button, Flex, Typography, Steps, Tag, Card, Table, message, Popover, Image, Checkbox } from "antd";
import { CheckCircleFilled, DownloadOutlined, QuestionOutlined, PictureOutlined } from "@ant-design/icons";
import { DownloadOutlined, QuestionOutlined, PictureOutlined } from "@ant-design/icons";
import { Connect } from "@cqsjjb/jjb-dva-runtime";
import { NS_SAFETY_EVAL_BUSINESS } from "~/enumerate/namespace";
import { tools } from "@cqsjjb/jjb-common-lib";
@ -20,6 +20,22 @@ const STAGES = [
{ key: "RECTIFICATION_REVIEW", index: "05", label: "整改复查" },
];
/** 各步骤附件必传校验:至少一个文件上传完成;有文件上传中时提示稍后 */
const attachRequiredRules = (label) => [
{
required: true,
validator: (_, value) => {
const fileList = value || [];
if (fileList.some((f) => f.status === "uploading")) {
return Promise.reject(new Error("文件上传中,请稍后再操作"));
}
return fileList.some((f) => f.status === "done" && f.url)
? Promise.resolve()
: Promise.reject(new Error(`请上传${label}`));
},
},
];
const downloadTemplate = async () => {
try {
const res = await fetch("https://test-dragon-yf-pub.oss-cn-hangzhou.aliyuncs.com/jjb/6a6bff3ee4b021a75404adfb.docx");
@ -68,6 +84,7 @@ const NoticePanel = ({ readOnly }) => (
maxCount={1}
accept=".docx,.pdf"
disabled={readOnly}
rules={attachRequiredRules("从业告知书")}
extra="仅支持上传 Word、PDF 格式文件"
/>
</div>
@ -160,6 +177,7 @@ const InspectionPanel = ({ dataSource = [], evalProjectDetailData = {}, readOnly
maxCount={10}
accept=".pdf,.doc,.docx,.xls,.xlsx,.png,.jpg,.jpeg"
disabled={readOnly}
rules={attachRequiredRules("现场检查表")}
extra="检查表应包含项目名称检查日期检查人员检查依据逐项检查结果和不符合项记录上传后与人员打卡记录共同作为现场踏勘凭证
支持 PDFWordExcelPNGJPG 格式最多上传 10 个文件"
/>
@ -185,6 +203,7 @@ const RectificationNoticePanel = ({ readOnly }) => (
maxCount={10}
accept=".pdf,.doc,.docx,.xls,.xlsx,.png,.jpg,.jpeg"
disabled={readOnly}
rules={attachRequiredRules("整改通知单")}
extra="支持 PDF、Word、Excel、PNG、JPG 格式,最多上传 10 个文件"
/>
</div>
@ -205,6 +224,7 @@ const EnterpriseRectificationPanel = ({ readOnly }) => (
maxCount={10}
accept=".pdf,.doc,.docx,.xls,.xlsx,.png,.jpg,.jpeg"
disabled={readOnly}
rules={attachRequiredRules("企业整改报告")}
extra="支持 PDF、Word、Excel、PNG、JPG 格式,最多上传 10 个文件"
/>
</div>
@ -225,6 +245,7 @@ const RectificationReviewPanel = ({ readOnly }) => (
maxCount={10}
accept=".pdf,.doc,.docx,.xls,.xlsx,.png,.jpg,.jpeg"
disabled={readOnly}
rules={attachRequiredRules("整改情况复查单")}
extra="支持 PDF、Word、Excel、PNG、JPG 格式,最多上传 10 个文件"
/>
</div>
@ -240,6 +261,12 @@ const SurveyContent = ({ readOnly, ...props }) => {
const currentIdx = STAGES.findIndex((s) => s.key === activeStage);
const isFirst = currentIdx === 0;
const isLast = currentIdx === STAGES.length - 1;
/** STAGES Steps
* 注意useWatch 传数组会被解析为嵌套字段路径多字段需用函数选择器入参为表单 values */
const stepFiles = Form.useWatch(
(values) => STAGES.map((s) => values?.[s.key]),
form,
);
const loadAttachments = async () => {
if (!projectId) return;
@ -355,10 +382,16 @@ const SurveyContent = ({ readOnly, ...props }) => {
current={currentIdx}
onChange={(idx) => setActiveStage(STAGES[idx].key)}
style={{ marginBottom: 16 }}
items={STAGES.map((s) => ({
title: s.label,
...(readOnly ? { status: "finish" } : {}),
}))}
items={STAGES.map((s, idx) => {
const uploaded = (stepFiles?.[idx] || []).some(
(f) => f.status === "done" && f.url,
);
console.log(stepFiles)
return {
title: s.label,
...(uploaded ? { status: "finish" } : {}),
};
})}
/>
<Form form={form} layout="vertical" disabled={readOnly} scrollToFirstError>