diff --git a/jjb.config.js b/jjb.config.js
index 7f51fa3..f261548 100644
--- a/jjb.config.js
+++ b/jjb.config.js
@@ -13,8 +13,8 @@ module.exports = {
//API_HOST: "https://gbs-gateway.qhdsafety.com",
//API_HOST: "http://192.168.0.152",
- //API_HOST: "http://192.168.0.150", //太浅
- API_HOST: "http://192.168.0.152",
+ API_HOST: "http://192.168.0.150", //太浅
+ //API_HOST: "http://192.168.0.152",
//API_HOST: "http://192.168.0.103", //huwei
},
production: {
diff --git a/src/api/safetyEvalBusiness/index.js b/src/api/safetyEvalBusiness/index.js
index 27a5826..3cf2c81 100644
--- a/src/api/safetyEvalBusiness/index.js
+++ b/src/api/safetyEvalBusiness/index.js
@@ -165,4 +165,74 @@ export const evalSurveyList = declareRequest(
export const evalSurveySaveAttach = declareRequest(
"evalSurveySaveAttachLoading",
"Post > @/safetyEval/institution/eval-survey/saveSurveyAttach",
+);
+
+// ===== 内部审核 =====
+
+export const evalInternalReviewDetail = declareRequest(
+ "internalReviewDetailLoading",
+ "Get > /safetyEval/institution/eval-internal-review/detail",
+ "internalReviewDetail: {} | res.data || {}",
+);
+
+export const evalInternalReviewConfirm = declareRequest(
+ "internalReviewConfirmLoading",
+ "Post > @/safetyEval/institution/eval-internal-review/confirm",
+);
+
+export const evalInternalReviewAssign = declareRequest(
+ "internalReviewAssignLoading",
+ "Post > @/safetyEval/institution/eval-internal-review/assign",
+);
+
+// ===== 技术审核 =====
+
+export const evalTechReviewDetail = declareRequest(
+ "techReviewDetailLoading",
+ "Get > /safetyEval/institution/eval-tech-review/detail",
+ "techReviewDetail: {} | res.data || {}",
+);
+
+export const evalTechReviewConfirm = declareRequest(
+ "techReviewConfirmLoading",
+ "Post > @/safetyEval/institution/eval-tech-review/confirm",
+);
+
+export const evalTechReviewAssign = declareRequest(
+ "techReviewAssignLoading",
+ "Post > @/safetyEval/institution/eval-tech-review/assign",
+);
+
+// ===== 过程控制 =====
+
+export const evalProcessControlDetail = declareRequest(
+ "processControlDetailLoading",
+ "Get > /safetyEval/institution/eval-process-control/detail",
+ "processControlDetail: {} | res.data || {}",
+);
+
+export const evalProcessControlConfirm = declareRequest(
+ "processControlConfirmLoading",
+ "Post > @/safetyEval/institution/eval-process-control/confirm",
+);
+
+export const evalProcessControlAssign = declareRequest(
+ "processControlAssignLoading",
+ "Post > @/safetyEval/institution/eval-process-control/assign",
+);
+
+export const evalProcessControlGenerateHandover = declareRequest(
+ "processControlHandoverLoading",
+ "Post > @/safetyEval/institution/eval-process-control/generate-handover-form",
+);
+
+export const evalProcessControlArchive = declareRequest(
+ "processControlArchiveLoading",
+ "Post > @/safetyEval/institution/eval-process-control/archive",
+);
+
+export const evalProcessControlFiles = declareRequest(
+ "processControlFilesLoading",
+ "Get > /safetyEval/institution/eval-process-control/process-files",
+ "processControlFiles: [] | res.data || []",
);
\ No newline at end of file
diff --git a/src/pages/Container/SafetyEvalBusiness/ProjectFlow/ControlContent.js b/src/pages/Container/SafetyEvalBusiness/ProjectFlow/ControlContent.js
index 62c03d7..2ae9e8d 100644
--- a/src/pages/Container/SafetyEvalBusiness/ProjectFlow/ControlContent.js
+++ b/src/pages/Container/SafetyEvalBusiness/ProjectFlow/ControlContent.js
@@ -1,26 +1,423 @@
-import React from "react";
-import { Card, Empty, Table } from "antd";
+import React, { useState, useEffect } from "react";
+import { Tag, Button, Card, Row, Col, Table, Select, Input, Flex, Typography, message } from "antd";
+import { Connect } from "@cqsjjb/jjb-dva-runtime";
+import { NS_SAFETY_EVAL_BUSINESS } from "~/enumerate/namespace";
+import { tools } from "@cqsjjb/jjb-common-lib";
-const ControlContent = () => (
-
-
-
-
-);
+const { TextArea } = Input;
+const { router } = tools;
-export default ControlContent;
\ No newline at end of file
+const CONCLUSION_OPTIONS = [
+ { value: "conform_to", label: "符合" },
+ { value: "not_conform_to", label: "需修改" },
+];
+
+const ControlContent = (props) => {
+ const projectId = router.query?.id;
+ const { processControlDetail, processControlFiles } = props.safetyEvalBusiness || {};
+ const { processControl, controllers, reviewItems } = processControlDetail || {};
+
+ // 当前步骤:1-过程控制审核 2-机构负责人签发 3-项目归档
+ const [step, setStep] = useState(1);
+
+ // 过程控制审核
+ const [rows, setRows] = useState([]);
+ const [opinionContent, setOpinionContent] = useState("");
+
+ // 项目归档
+ const [files, setFiles] = useState([]);
+
+ const fetchDetail = () => {
+ props.evalProcessControlDetail({ projectId });
+ };
+
+ const fetchFiles = () => {
+ props.evalProcessControlFiles({ projectId });
+ };
+
+ useEffect(() => {
+ if (projectId) {
+ fetchDetail();
+ fetchFiles();
+ }
+ }, [projectId]);
+
+ useEffect(() => {
+ if (reviewItems) {
+ setRows(
+ reviewItems.map((item) => ({
+ ...item,
+ _key: item.id || item.reviewDimensionCode,
+ })),
+ );
+ }
+ if (processControl?.opinionContent) {
+ setOpinionContent(processControl.opinionContent);
+ }
+ }, [processControlDetail]);
+
+ useEffect(() => {
+ if (processControlFiles) {
+ setFiles(processControlFiles);
+ }
+ }, [processControlFiles]);
+
+ const updateRow = (index, field, value) => {
+ const next = [...rows];
+ next[index] = { ...next[index], [field]: value };
+ setRows(next);
+ };
+
+ const controllerName = processControl?.controllerName || "";
+ const isDispatched = processControl?.reviewerSignatureTaskStatus !== "non_dispatched";
+ const isSignatureCompleted = processControl?.reviewerSignatureTaskStatus === "completed";
+ const hasHandoverForm = !!processControl?.handoverFormUrl;
+ const problemCount = rows.filter((r) => r.reviewConclusion === "not_conform_to").length;
+ const canArchive = isSignatureCompleted && hasHandoverForm;
+
+ // 过程控制签字提交(confirm)
+ const handleConfirm = async (resultCode) => {
+ if (!projectId) return;
+ const payload = {
+ id: processControl?.id,
+ projectId,
+ resultCode,
+ opinionContent,
+ reviewItems: rows.map((r) => ({
+ bizType: "eval_process_control",
+ bizId: processControl?.id,
+ reviewDimensionCode: r.reviewDimensionCode,
+ reviewDimensionName: r.reviewDimensionName,
+ reviewFocus: r.reviewFocus,
+ reviewConclusion: r.reviewConclusion,
+ reviewOpinion: r.reviewOpinion,
+ })),
+ };
+ const res = await props.evalProcessControlConfirm(payload);
+ if (res?.success !== false) {
+ message.success(resultCode === "passed" ? "已提交通过审核" : "已提交退回修改");
+ fetchDetail();
+ }
+ };
+
+ // 下发签字任务(assign)
+ const handleAssign = async () => {
+ if (!projectId) return;
+ const res = await props.evalProcessControlAssign({ projectId });
+ if (res?.success !== false) {
+ message.success("已下发签字任务");
+ fetchDetail();
+ }
+ };
+
+ // 生成归档交接单
+ const handleGenerateHandover = async () => {
+ if (!projectId) return;
+ const res = await props.evalProcessControlGenerateHandover({ projectId });
+ if (res?.success !== false) {
+ message.success("归档交接单已生成");
+ fetchDetail();
+ }
+ };
+
+ // 归档项目并入库
+ const handleArchive = async () => {
+ if (!projectId) return;
+ const res = await props.evalProcessControlArchive({ projectId });
+ if (res?.success !== false) {
+ message.success("项目已归档入库");
+ fetchDetail();
+ }
+ };
+
+ const reviewColumns = [
+ { title: "审核维度", dataIndex: "reviewDimensionName", width: 120 },
+ { title: "审核重点", dataIndex: "reviewFocus", width: 200 },
+ {
+ title: "结论",
+ dataIndex: "reviewConclusion",
+ width: 120,
+ render: (val, _, idx) => (
+
+ ),
+ },
+ {
+ title: "审核意见",
+ dataIndex: "reviewOpinion",
+ render: (val, _, idx) => (
+ updateRow(idx, "reviewOpinion", e.target.value)}
+ />
+ ),
+ },
+ ];
+
+ const fileColumns = [
+ { title: "流程名称", dataIndex: "processName", width: 100 },
+ { title: "条目名称", dataIndex: "itemName", width: 120 },
+ { title: "文件名称", dataIndex: "materialName", width: 200 },
+ {
+ title: "文件地址",
+ dataIndex: "projectDocUrl",
+ width: 200,
+ render: (url) =>
+ url ? (
+
+ 查看文件
+
+ ) : (
+ "-"
+ ),
+ },
+ { title: "资料类型", dataIndex: "materialType", width: 100 },
+ ];
+
+ const STEP_ITEMS = [
+ { key: 1, label: "过程控制审核" },
+ { key: 2, label: "机构负责人签发" },
+ { key: 3, label: "项目归档" },
+ ];
+
+ return (
+
+
+ {STEP_ITEMS.map((item) => (
+
+ ))}
+
+
+ {step === 1 && (
+
+
+
+ 过程控制负责人
+
+ 过程控制负责人核验前7节点完成及签字记录
+
+
+
+
+
+ 过程控制负责人
+
+ {controllerName || "-"}
+
+
+
+
+
+ 审核项
+
+ {rows.length}项
+
+
+
+
+
+ 问题
+
+ 0 ? "warning" : undefined}>
+ {problemCount}项
+
+
+
+
+
+
+
+
+
+ 总体过程控制意见
+
+
+
+
+ 过程控制负责人签字
+ {controllerName}
+
+
+
+
+
+
+
+
+ )}
+
+ {step === 2 && (
+
+
+
+ 评价机构负责人
+
+ 机构负责人终审并签发,确认项目成果
+
+
+
+ {controllers?.map((c) => (
+
+
+ 机构负责人
+
+ {c.personnelName}
+
+ {c.deptName && (
+
+
+ {c.deptName}
+
+
+ )}
+
+
+ ))}
+ {(!controllers || controllers.length === 0) && (
+
+ 暂无机构负责人信息
+
+ )}
+
+
+
+
+
+
+ )}
+
+ {step === 3 && (
+
+
+
+ 项目归档
+
+ 项目过程文件清单,确认签字完成后归档入库
+
+
+ `${record.processName}-${record.materialName}-${record.itemName}`}
+ pagination={false}
+ size="small"
+ />
+
+
+
+ {!hasHandoverForm && (
+
+ )}
+ {hasHandoverForm && (
+
+ 归档交接单已生成
+ {processControl?.handoverFormUrl && (
+
+ 查看
+
+ )}
+
+ )}
+
+
+
+
+ )}
+
+ );
+};
+
+export default Connect([NS_SAFETY_EVAL_BUSINESS], true)(ControlContent);
\ No newline at end of file
diff --git a/src/pages/Container/SafetyEvalBusiness/ProjectFlow/InternalReviewContent.js b/src/pages/Container/SafetyEvalBusiness/ProjectFlow/InternalReviewContent.js
index 5f356eb..7e84ebc 100644
--- a/src/pages/Container/SafetyEvalBusiness/ProjectFlow/InternalReviewContent.js
+++ b/src/pages/Container/SafetyEvalBusiness/ProjectFlow/InternalReviewContent.js
@@ -1,20 +1,63 @@
-import React, { useState } from "react";
-import { Tag, Button, Card, Table, Select, Input, Flex, Typography, Row, Col } from "antd";
+import React, { useState, useEffect } from "react";
+import {
+ Tag,
+ Button,
+ Card,
+ Table,
+ Select,
+ Input,
+ Flex,
+ Typography,
+ Row,
+ Col,
+ message,
+} from "antd";
+import { Connect } from "@cqsjjb/jjb-dva-runtime";
+import { NS_SAFETY_EVAL_BUSINESS } from "~/enumerate/namespace";
+import { tools } from "@cqsjjb/jjb-common-lib";
const { TextArea } = Input;
+const { router } = tools;
-const INITIAL_ROWS = [
- { dim: "评价依据", focus: "充分、有效", result: "符合", opinion: "补充地方标准有效版本", feedback: "已验证", feedbackType: "success" },
- { dim: "危险辨识", focus: "全面、无遗漏", result: "需修改", opinion: "补充液氨装卸泄漏场景", feedback: "待反馈", feedbackType: "warning" },
- { dim: "单元划分", focus: "科学合理", result: "符合", opinion: "划分合理", feedback: "—", feedbackType: "default" },
- { dim: "评价方法", focus: "适用、过程正确", result: "符合", opinion: "方法适用", feedback: "—", feedbackType: "default" },
- { dim: "对策措施", focus: "针对性、可操作性", result: "需修改", opinion: "细化报警联锁措施", feedback: "已验证", feedbackType: "success" },
- { dim: "评价结论", focus: "客观、正确", result: "符合", opinion: "结论客观", feedback: "—", feedbackType: "default" },
- { dim: "报告规范", focus: "格式、文字、数据逻辑", result: "符合", opinion: "统一图表编号", feedback: "—", feedbackType: "default" },
+const CONCLUSION_OPTIONS = [
+ { value: "conform_to", label: "符合" },
+ { value: "not_conform_to", label: "需修改" },
];
-const InternalReviewContent = () => {
- const [rows, setRows] = useState(INITIAL_ROWS);
+const InternalReviewContent = (props) => {
+ const projectId = router.query?.id;
+ const {
+ internalReviewDetail,
+ internalReviewAssignLoading,
+ internalReviewConfirmLoading,
+ internalReviewDetailLoading,
+ } = props.safetyEvalBusiness || {};
+ const { internalReview, reviewers, reviewItems } = internalReviewDetail || {};
+
+ const [rows, setRows] = useState([]);
+ const [overallOpinion, setOverallOpinion] = useState("");
+
+ const fetchDetail = () => {
+ props.evalInternalReviewDetail({ projectId });
+ };
+
+ useEffect(() => {
+ if (projectId) fetchDetail();
+ }, [projectId]);
+
+ useEffect(() => {
+ if (reviewItems) {
+ setRows(
+ reviewItems.map((item) => ({
+ ...item,
+ _key: item.id || item.reviewDimensionCode,
+ })),
+ );
+ }
+ if (internalReview?.opinionContent) {
+ setOverallOpinion(internalReview.opinionContent);
+ }
+ }, [internalReviewDetail]);
const updateRow = (index, field, value) => {
const next = [...rows];
@@ -22,74 +65,179 @@ const InternalReviewContent = () => {
setRows(next);
};
+ const reviewerName = internalReview?.reviewerName || "";
+ const isDispatched =
+ internalReview?.reviewerSignatureTaskStatus === "dispatched";
+ const problemCount = rows.filter(
+ (r) => r.reviewConclusion === "not_conform_to",
+ ).length;
+
+ const handleAssign = async () => {
+ if (!projectId) return;
+ const res = await props.evalInternalReviewAssign({ projectId });
+ if (res?.success !== false) {
+ message.success("已下发签字任务");
+ fetchDetail();
+ }
+ };
+
+ const handleConfirm = async (resultCode) => {
+ if (!projectId) return;
+ const payload = {
+ id: internalReview?.id,
+ projectId,
+ resultCode,
+ opinionContent: overallOpinion,
+ reviewItems: rows.map((r) => ({
+ bizType: "eval_internal_review",
+ bizId: internalReview?.id,
+ reviewDimensionCode: r.reviewDimensionCode,
+ reviewDimensionName: r.reviewDimensionName,
+ reviewFocus: r.reviewFocus,
+ reviewConclusion: r.reviewConclusion,
+ reviewOpinion: r.reviewOpinion,
+ })),
+ };
+ const res = await props.evalInternalReviewConfirm(payload);
+ if (res?.success !== false) {
+ message.success(
+ resultCode === "passed" ? "已提交" : "已保存",
+ );
+ fetchDetail();
+ }
+ };
+
+ const columns = [
+ { title: "审核维度", dataIndex: "reviewDimensionName", width: 100 },
+ { title: "审核重点", dataIndex: "reviewFocus", width: 160 },
+ {
+ title: "结论",
+ dataIndex: "reviewConclusion",
+ width: 120,
+ render: (val, _, idx) => (
+
+ ),
+ },
+ {
+ title: "审核意见",
+ dataIndex: "reviewOpinion",
+ width: 180,
+ render: (val, _, idx) => (
+ updateRow(idx, "reviewOpinion", e.target.value)}
+ />
+ ),
+ },
+ ];
+
return (
- 内部审核人
+
+ 内部审核人
+
审核、修改、反馈、验证闭环
-
- 审核版本V1.3
- 内审人王丽萍
- 审核项7项
- 问题2项
-
+
+
+
+ 内审人
+
+ {reviewerName || "-"}
+
+
+
+
+
+ 审核项
+
+ {rows.length}项
+
+
+
+
+
+ 问题
+
+ 0 ? "warning" : undefined}
+ >
+ {problemCount}项
+
+
+
+
+
-
(
-
- ),
- },
- {
- title: "审核意见", dataIndex: "opinion", width: 180,
- render: (val, _, idx) => (
- updateRow(idx, "opinion", e.target.value)} />
- ),
- },
- {
- title: "修改反馈", dataIndex: "feedback", width: 120,
- render: (val, record) => {
- if (record.feedbackType === "success") return 已验证;
- if (record.feedbackType === "warning") return 待反馈;
- return —;
- },
- },
- ]}
- rowKey="dim"
- pagination={false}
- size="small"
+
+
+
+ 总体审核意见
+
-
- 总体审核意见
-
-
-
-
-
- 内审人独立签字
- 王丽萍
-
-
+
+
+ 内审人独立签字
+ {reviewerName}
+
+
-
-
-
-
-
+
+
+
+
);
};
-export default InternalReviewContent;
\ No newline at end of file
+export default Connect([NS_SAFETY_EVAL_BUSINESS], true)(InternalReviewContent);
diff --git a/src/pages/Container/SafetyEvalBusiness/ProjectFlow/RiskAnalysisContent.js b/src/pages/Container/SafetyEvalBusiness/ProjectFlow/RiskAnalysisContent.js
index 91505f3..5517ce9 100644
--- a/src/pages/Container/SafetyEvalBusiness/ProjectFlow/RiskAnalysisContent.js
+++ b/src/pages/Container/SafetyEvalBusiness/ProjectFlow/RiskAnalysisContent.js
@@ -80,6 +80,10 @@ const RiskAnalysisContent = (props) => {
const values = await form.validateFields();
const { analysisDate, ...rest } = values;
+ if (!rest.participants?.length) {
+ message.warning("请选择风险分析人员");
+ return;
+ }
const res = await evalRiskAnalysisSave({
...rest,
projectId,
diff --git a/src/pages/Container/SafetyEvalBusiness/ProjectFlow/TeamContent.js b/src/pages/Container/SafetyEvalBusiness/ProjectFlow/TeamContent.js
index ce1462a..28562bd 100644
--- a/src/pages/Container/SafetyEvalBusiness/ProjectFlow/TeamContent.js
+++ b/src/pages/Container/SafetyEvalBusiness/ProjectFlow/TeamContent.js
@@ -74,6 +74,14 @@ const TeamContent = (props) => {
if (selectedPersons.length === 0) { message.warning("请至少选择1名人员"); return; }
const role = ROLE_DEFINITIONS.find((r) => r.value === selectedRole);
if (role?.unique && selectedPersons.length > 1) { message.warning("该角色为单人唯一角色,只能选择1名人员"); return; }
+ // 唯一角色校验:检查是否已有人担任该角色
+ if (role?.unique) {
+ const existing = teamMembers.some((m) => m.roles.some((r) => r.role === selectedRole));
+ if (existing) {
+ message.warning(`"${role.name}"已配置,不可重复添加`);
+ return;
+ }
+ }
const newEntries = selectedPersons.map((personId) => {
const p = participants.find((item) => item.id === personId);
@@ -110,6 +118,15 @@ const TeamContent = (props) => {
};
const handleSave = async () => {
+ const allRoles = teamMembers.flatMap((m) => m.roles.map((r) => r.role));
+ if (!allRoles.includes("PROJECT_LEAD")) {
+ message.warning("请先配置项目负责人(项目组组长)");
+ return;
+ }
+ if (!allRoles.includes("PROCESS_CONTROL_LEAD")) {
+ message.warning("请先配置过程控制负责人");
+ return;
+ }
const payload = teamMembers.map((m) => ({
id: m.id,
projectId,
@@ -124,6 +141,7 @@ const TeamContent = (props) => {
if (res?.success !== false) {
message.success("保存成功");
fetchData();
+ props.getDetail();
}
};
@@ -134,10 +152,16 @@ const TeamContent = (props) => {
{ title: "部门/岗位", dataIndex: "deptName", width: 200, ellipsis: true },
{
title: "项目角色", dataIndex: "roles", width: 350,
- render: (roles) => (
+ render: (roles, record) => (
{roles.map((r) => (
-
+ {
+ setTeamMembers((prev) => prev.map((m) => {
+ if (m.personnelId !== record.personnelId) return m;
+ const updated = m.roles.filter((role) => role.role !== r.role);
+ return updated.length > 0 ? { ...m, roles: updated } : null;
+ }).filter(Boolean));
+ }}>
{ROLE_DEFINITIONS.find((d) => d.value === r.role)?.name || r.role}
))}
@@ -216,7 +240,7 @@ const TeamContent = (props) => {
-
+
setModalOpen(false)} width={700}
diff --git a/src/pages/Container/SafetyEvalBusiness/ProjectFlow/TechnicalReviewContent.js b/src/pages/Container/SafetyEvalBusiness/ProjectFlow/TechnicalReviewContent.js
index 900da16..87ff460 100644
--- a/src/pages/Container/SafetyEvalBusiness/ProjectFlow/TechnicalReviewContent.js
+++ b/src/pages/Container/SafetyEvalBusiness/ProjectFlow/TechnicalReviewContent.js
@@ -1,18 +1,46 @@
-import React, { useState } from "react";
-import { Tag, Button, Card, Row, Col, Table, Select, Input, Flex, Typography } from "antd";
+import React, { useState, useEffect } from "react";
+import { Tag, Button, Card, Row, Col, Table, Select, Input, Flex, Typography, message } from "antd";
+import { Connect } from "@cqsjjb/jjb-dva-runtime";
+import { NS_SAFETY_EVAL_BUSINESS } from "~/enumerate/namespace";
+import { tools } from "@cqsjjb/jjb-common-lib";
const { TextArea } = Input;
+const { router } = tools;
-const INITIAL_ROWS = [
- { dim: "资料有效性", focus: "现场资料和检测报告齐全有效", result: "符合", opinion: "资料有效" },
- { dim: "危险辨识", focus: "辨识充分、规律准确", result: "符合", opinion: "辨识充分" },
- { dim: "评价方法", focus: "选型合理、计算正确", result: "需修改", opinion: "补充事故模拟参数来源" },
- { dim: "对策措施", focus: "针对性和可行性", result: "符合", opinion: "措施可行" },
- { dim: "评价结论", focus: "结论正确、反映风险", result: "符合", opinion: "结论正确" },
+const CONCLUSION_OPTIONS = [
+ { value: "conform_to", label: "符合" },
+ { value: "not_conform_to", label: "需修改" },
];
-const TechnicalReviewContent = () => {
- const [rows, setRows] = useState(INITIAL_ROWS);
+const TechnicalReviewContent = (props) => {
+ const projectId = router.query?.id;
+ const { techReviewDetail } = props.safetyEvalBusiness || {};
+ const { techReview, reviewers, reviewItems } = techReviewDetail || {};
+
+ const [rows, setRows] = useState([]);
+ const [overallOpinion, setOverallOpinion] = useState("");
+
+ const fetchDetail = () => {
+ props.evalTechReviewDetail({ projectId });
+ };
+
+ useEffect(() => {
+ if (projectId) fetchDetail();
+ }, [projectId]);
+
+ useEffect(() => {
+ if (reviewItems) {
+ setRows(
+ reviewItems.map((item) => ({
+ ...item,
+ _key: item.id || item.reviewDimensionCode,
+ })),
+ );
+ }
+ if (techReview?.opinionContent) {
+ setOverallOpinion(techReview.opinionContent);
+ }
+ }, [techReviewDetail]);
const updateRow = (index, field, value) => {
const next = [...rows];
@@ -20,68 +48,166 @@ const TechnicalReviewContent = () => {
setRows(next);
};
+ const reviewerName = techReview?.reviewerName || "";
+ const isDispatched = techReview?.reviewerSignatureTaskStatus !== "non_dispatched";
+ const staffMatch = techReview?.staffMatchCode === 1 ? "满足" : "不满足";
+ const inBizScope = techReview?.inBizScopeFlag === 1 ? "在范围内" : "不在范围内";
+
+ const handleAssign = async () => {
+ if (!projectId) return;
+ const res = await props.evalTechReviewAssign({ projectId });
+ if (res?.success !== false) {
+ message.success("已下发签字任务");
+ fetchDetail();
+ }
+ };
+
+ const handleConfirm = async (resultCode) => {
+ if (!projectId) return;
+ const payload = {
+ id: techReview?.id,
+ projectId,
+ resultCode,
+ opinionContent: overallOpinion,
+ reviewItems: rows.map((r) => ({
+ bizType: "eval_tech_review",
+ bizId: techReview?.id,
+ reviewDimensionCode: r.reviewDimensionCode,
+ reviewDimensionName: r.reviewDimensionName,
+ reviewFocus: r.reviewFocus,
+ reviewConclusion: r.reviewConclusion,
+ reviewOpinion: r.reviewOpinion,
+ })),
+ };
+ const res = await props.evalTechReviewConfirm(payload);
+ if (res?.success !== false) {
+ message.success(resultCode === "1" ? "已确认技审并提交过程控制" : "已保存");
+ fetchDetail();
+ }
+ };
+
+ const columns = [
+ { title: "审核维度", dataIndex: "reviewDimensionName", width: 120 },
+ { title: "技术审核重点", dataIndex: "reviewFocus", width: 200 },
+ {
+ title: "结论",
+ dataIndex: "reviewConclusion",
+ width: 120,
+ render: (val, _, idx) => (
+
+ ),
+ },
+ {
+ title: "技术意见",
+ dataIndex: "reviewOpinion",
+ render: (val, _, idx) => (
+ updateRow(idx, "reviewOpinion", e.target.value)}
+ />
+ ),
+ },
+ ];
+
return (
- 技术负责人
+
+ 技术负责人
+
技术负责人独立审核技术路线和结论
-
-
- 审核版本V1.4
- 技术负责人陈志强
- 专业匹配化工安全
- 备案校验有效
-
+
+
+
+ 技术负责人
+
+ {reviewerName || "-"}
+
+
+
+
+
+ 专业匹配
+
+
+ {staffMatch}
+
+
+
+
+
+
+ 资质范围
+
+
+ {inBizScope}
+
+
+
+
+
-
(
-
- ),
- },
- {
- title: "技术意见", dataIndex: "opinion",
- render: (val, _, idx) => (
- updateRow(idx, "opinion", e.target.value)} />
- ),
- },
- ]}
- rowKey="dim"
- pagination={false}
- size="small"
+
+
+
+ 技术审核意见
+
-
- 技术审核意见
-
-
-
-
-
- 技术负责人签字
- 陈志强
-
-
+
+
+ 技术负责人签字
+ {reviewerName}
+
+
-
-
-
-
-
-
+
+
+
+
);
};
-export default TechnicalReviewContent;
\ No newline at end of file
+export default Connect([NS_SAFETY_EVAL_BUSINESS], true)(TechnicalReviewContent);
\ No newline at end of file