feat: 添加入住证签发和工作票审核功能

refactor(EnterpriseManagement): 优化企业管理和账号管理逻辑

fix(EntryExitPermitIssue): 修正出入证签发状态显示和查询功能

style: 调整部分页面样式和布局

perf(TicketIssueAudit): 提升工作票审核性能和用户体验
This commit is contained in:
liangbin 2026-02-02 17:49:22 +08:00
parent c3698c515a
commit 4db148f33a
10 changed files with 403 additions and 233 deletions

37
src/api/Pass.js Normal file
View File

@ -0,0 +1,37 @@
import request from "@/utils/request";
// 获取出入证列表
export const FetchPassagewayList = (query) => {
return request({
url: "/manage/owner/accessPermitIssuance/list",
method: "get",
params: query,
});
};
// 查询出入证详情
export const FetchPassagewayDetail = (id) => {
return request({
url: `/manage/owner/accessPermitIssuance/${id}`,
method: "get",
});
};
// 签发出入证
export const SignPassageway = (data) => {
return request({
url: `/manage/owner/accessPermitIssuance/issue`,
method: "post",
data,
});
};
// 查看关联票证
export const FetchAssociatedTicket = (id) => {
return request({
url: `/manage/owner/accessPermitIssuance/${id}/relatedTicket`,
method: "get",
});
};

View File

@ -16,3 +16,21 @@ export function FetchWorkTicketDetail(id) {
method: 'get', method: 'get',
}) })
} }
// 工作票审核通过
export function AuditWorkTicketPass(params) {
return request({
url: '/manage/contractor/workTicket/approve/' + params.ticketId,
method: 'put',
params
})
}
// 工作票审核驳回
export function AuditWorkTicketRefuse(params) {
return request({
url: '/manage/contractor/workTicket/reject/' + params.ticketId,
method: 'put',
params
})
}

View File

@ -97,7 +97,8 @@
</el-table-column> </el-table-column>
<el-table-column label="操作"> <el-table-column label="操作">
<template #default="{ row }"> <template #default="{ row }">
<el-button type="text" icon="Edit" @click="handleEditUser(row)">编辑</el-button> <el-button v-if="row.status === '2'" type="text" icon="Edit"
@click="handleEditUser(row)">编辑</el-button>
<el-button type="text" icon="Delete" @click="handleDeleteUser(row)">删除</el-button> <el-button type="text" icon="Delete" @click="handleDeleteUser(row)">删除</el-button>
</template> </template>
</el-table-column> </el-table-column>

View File

@ -8,37 +8,37 @@
<el-col :span="12"> <el-col :span="12">
<div class="info-item"> <div class="info-item">
<label>项目名称</label> <label>项目名称</label>
<span>XX新能源电池建设项目</span> <span>{{ detailData.projectName }}</span>
</div> </div>
</el-col> </el-col>
<el-col :span="12"> <el-col :span="12">
<div class="info-item"> <div class="info-item">
<label>票证编号</label> <label>票证编号</label>
<span>ZY-20250405-001</span> <span>{{ detailData.permitNumber }}</span>
</div> </div>
</el-col> </el-col>
<el-col :span="12"> <el-col :span="12">
<div class="info-item"> <div class="info-item">
<label>作业地点</label> <label>作业地点</label>
<span>1号厂房东侧区域</span> <span>{{ detailData.workLocation }}</span>
</div> </div>
</el-col> </el-col>
<el-col :span="12"> <el-col :span="12">
<div class="info-item"> <div class="info-item">
<label>作业单位</label> <label>作业单位</label>
<span>江苏建工集团有限公司</span> <span>{{ detailData.enterpriseName }}</span>
</div> </div>
</el-col> </el-col>
<el-col :span="12"> <el-col :span="12">
<div class="info-item"> <div class="info-item">
<label>工作负责人</label> <label>工作负责人</label>
<span>刘建国</span> <span>{{ detailData.proprietorName }}</span>
</div> </div>
</el-col> </el-col>
<el-col :span="12"> <el-col :span="12">
<div class="info-item"> <div class="info-item">
<label>联系方式</label> <label>联系方式</label>
<span>138****8821</span> <span>{{ detailData.contactPhone }}</span>
</div> </div>
</el-col> </el-col>
</el-row> </el-row>
@ -46,19 +46,19 @@
<!-- 出入证有效期 --> <!-- 出入证有效期 -->
<el-form label-width="120px" label-position="top" :model="formData"> <el-form label-width="120px" label-position="top" :model="formData">
<el-form-item label="出入证有效期"> <el-form-item label="出入证有效期">
<el-date-picker v-model="formData.dateRange" type="daterange" value-format="yyyy-MM-dd" <div style="width: 200px;">
range-separator="至" start-placeholder="开始日期" end-placeholder="结束日期" style="width: 300px;" /> <el-date-picker v-model="formData.dateRange" type="daterange" value-format="yyyy-MM-dd"
range-separator="至" start-placeholder="开始日期" end-placeholder="结束日期" />
</div>
</el-form-item> </el-form-item>
<div class="tip-text">默认与作业时间一致最长不超过票证有效期</div> <div class="tip-text">默认与作业时间一致最长不超过票证有效期</div>
<!-- 作业组成员清单 --> <!-- 作业组成员清单 -->
<el-form-item label="作业组成员清单"> <el-form-item label="作业组成员清单">
<el-checkbox-group v-model="formData.selectedMembers"> <el-checkbox-group v-model="formData.selectedMembers">
<el-checkbox label="张伟(320**********1234)" /> <el-checkbox v-for="member in detailData.sysUserList" :label="member.userId"
<el-checkbox label="李娜(320**********5678)" /> :key="member.userId">{{ member.nickName }}({{ member.phonenumber }})</el-checkbox>
<el-checkbox label="王强(320**********9012)" />
<el-checkbox label="赵敏(320**********3456)" />
<el-checkbox label="孙浩(320**********7890)" />
</el-checkbox-group> </el-checkbox-group>
</el-form-item> </el-form-item>
@ -67,10 +67,11 @@
<div style="margin-bottom: 15px;"> <div style="margin-bottom: 15px;">
<el-button type="primary" size="small" @click="addVehicle">+ 添加车辆</el-button> <el-button type="primary" size="small" @click="addVehicle">+ 添加车辆</el-button>
</div> </div>
<div v-for="(vehicle, index) in vehicles" :key="index" class="vehicle-item"> <div v-for="(vehicle, index) in vehicleList" :key="index" class="vehicle-item">
<el-input v-model="vehicle.plateNumber" placeholder="请输入车牌号" <el-input v-model="vehicle.licensePlate" placeholder="请输入车牌号"
style="width: 200px; margin-right: 20px;" />
<el-input v-model="vehicle.vehicleType" placeholder="请输入车型"
style="width: 200px; margin-right: 20px;" /> style="width: 200px; margin-right: 20px;" />
<el-input v-model="vehicle.type" placeholder="请输入车型" style="width: 200px; margin-right: 20px;" />
<el-button type="danger" size="small" @click="removeVehicle(index)"> <el-button type="danger" size="small" @click="removeVehicle(index)">
<el-icon> <el-icon>
<Delete /> <Delete />
@ -95,31 +96,16 @@
</template> </template>
<script setup> <script setup>
import { ref } from 'vue' import { ref, onMounted } from 'vue'
import { Delete } from '@element-plus/icons-vue' import { Delete } from '@element-plus/icons-vue'
import { ElMessage } from 'element-plus'
const formData = ref({ import { FetchPassagewayDetail, SignPassageway } from '@/api/Pass'
dateRange: [],
selectedMembers: [],
remark: ''
})
const vehicles = ref([{ plateNumber: '', type: '' }])
//
const addVehicle = () => {
vehicles.value.push({ plateNumber: '', type: '' })
}
//
const removeVehicle = (index) => {
vehicles.value.splice(index, 1)
}
const props = defineProps({ const props = defineProps({
Rid: {
type: Object,
default: () => { }
},
show: { show: {
type: Boolean, type: Boolean,
default: false default: false
@ -130,16 +116,66 @@ const props = defineProps({
} }
}) })
//
const detailData = ref({})
//
const formData = ref({
dateRange: [],
selectedMembers: [],
remark: ''
})
//
const vehicleList = ref([{ licensePlate: '', vehicleType: '' }])
onMounted(() => {
if (props.Rid) {
getDetail()
}
})
//
const getDetail = async () => {
const res = await FetchPassagewayDetail(props.Rid)
if (res.code === 200) {
detailData.value = res.data,
vehicleList.value = res.data.vehicleList || []
}
}
//
const addVehicle = () => {
vehicleList.value.push({ plateNumber: '', type: '' })
}
//
const removeVehicle = (index) => {
vehicleList.value.splice(index, 1)
}
// //
const handleClose = () => { const handleClose = () => {
props.CloseDialog() props.CloseDialog()
} }
const handleSubmit = () => { const handleSubmit = async () => {
// //
console.log('提交分配信息', formData.value) let pamams = {
props.CloseDialog() ...detailData.value,
vehicleList: vehicleList.value
}
let res = await SignPassageway(pamams)
if (res.code === 200) {
ElMessage.success('签发成功')
props.CloseDialog()
} else {
ElMessage.error(res.msg)
}
} }
</script> </script>

View File

@ -2,45 +2,50 @@
<template> <template>
<el-dialog title="关联票证详情" v-model="props.show" @close="handleClose" width="900px"> <el-dialog title="关联票证详情" v-model="props.show" @close="handleClose" width="900px">
<div class="Cneter-box"> <div class="Cneter-box">
<el-form :model="formData" label-width="120px" class="demo-form" label-position="top"> <el-form label-width="120px" class="demo-form" label-position="top">
<el-row :gutter="20"> <el-row :gutter="20">
<el-col :span="12"> <el-col :span="12">
<el-form-item label="项目名称"> <el-form-item label="项目名称">
<el-input v-model="formData.projectName" disabled /> <div>{{ associatedTicket.projectName }}</div>
</el-form-item> </el-form-item>
</el-col> </el-col>
<el-col :span="12"> <el-col :span="12">
<el-form-item label="票证编号"> <el-form-item label="票证编号">
<el-input v-model="formData.permitNumber" disabled /> <div>{{ associatedTicket.ticketNumber }}</div>
</el-form-item> </el-form-item>
</el-col> </el-col>
</el-row> </el-row>
<el-row :gutter="20"> <el-row :gutter="20">
<el-col :span="12"> <el-col :span="12">
<el-form-item label="施工单位"> <el-form-item label="施工单位">
<el-input v-model="formData.constructionUnit" disabled /> <div>{{ associatedTicket.workContent }}</div>
</el-form-item> </el-form-item>
</el-col> </el-col>
<el-col :span="12"> <el-col :span="12">
<el-form-item label="作业类型"> <el-form-item label="作业类型">
<el-input v-model="formData.workType" disabled /> <div>{{ associatedTicket.riskType }}</div>
</el-form-item> </el-form-item>
</el-col> </el-col>
</el-row> </el-row>
<el-row :gutter="20"> <el-row :gutter="20">
<el-col :span="12"> <el-col :span="12">
<el-form-item label="作业时间"> <el-form-item label="作业时间">
<el-input v-model="formData.workTime" disabled /> <div>{{ associatedTicket.workStartTime }} - {{ associatedTicket.workEndTime }}</div>
</el-form-item> </el-form-item>
</el-col> </el-col>
<el-col :span="12"> <el-col :span="12">
<el-form-item label="工作负责人"> <el-form-item label="工作负责人">
<el-input v-model="formData.responsiblePerson" disabled /> <div>{{ associatedTicket.supervisorName }}</div>
</el-form-item> </el-form-item>
</el-col> </el-col>
</el-row> </el-row>
<el-form-item label="安全措施"> <el-form-item label="安全措施">
<el-input type="textarea" v-model="formData.safetyMeasures" disabled :rows="4" /> <div style="display: flex; flex-wrap: wrap;flex-direction: column;">
<div v-for="(item, index) in associatedTicket.generalSafetyMeasures" :key="index">
{{ index + 1 }}. {{ item }}
</div>
</div>
</el-form-item> </el-form-item>
</el-form> </el-form>
</div> </div>
@ -53,10 +58,15 @@
</template> </template>
<script setup> <script setup>
import { ref } from 'vue' import { ref, onMounted } from 'vue'
import { FetchAssociatedTicket } from '@/api/Pass'
const props = defineProps({ const props = defineProps({
Rid: {
type: Number,
default: 0
},
show: { show: {
type: Boolean, type: Boolean,
default: false default: false
@ -68,18 +78,23 @@ const props = defineProps({
}) })
//
const associatedTicket = ref({})
// //
const formData = ref({ onMounted(() => {
projectName: '滨海新区LNG 接收站项目', if (props.Rid) {
permitNumber: 'WZ202312001', FetchAssociatedTicket(props.Rid).then(res => {
constructionUnit: '中国化学工程第三建设有限公司', if (res.code === 200) {
workType: '高空作业', associatedTicket.value = res.data || {}
workTime: '2023-12-01 至 2023-12-05', associatedTicket.value.generalSafetyMeasures = JSON.parse(associatedTicket.value.generalSafetyMeasures || '[]')
responsiblePerson: '李建国', } else {
safetyMeasures: '1. 佩戴安全帽和安全带\n2. 设置安全警戒线\n3. 安排专职安全员监护' ElMessage.error(res.msg)
}
})
}
}) })
@ -88,12 +103,6 @@ const handleClose = () => {
props.CloseDialog() props.CloseDialog()
} }
const handleSubmit = () => {
//
console.log('提交分配信息', formData.value)
props.CloseDialog()
}
</script> </script>
<style scoped lang="scss"> <style scoped lang="scss">

View File

@ -1,35 +1,36 @@
<!-- 业主模块-出入证签发-列表页 --> <!-- 业主模块-出入证签发-列表页 -->
<template> <template>
<div class="MainBox"> <div class="MainBox">
<el-tabs v-model="activeTab" class="mb-4"> <!-- <el-tabs v-model="activeTab" class="mb-4">
<el-tab-pane label="签发列表" name="1"></el-tab-pane> <el-tab-pane label="签发列表" name="1"></el-tab-pane>
<el-tab-pane label="历史记录" name="2"></el-tab-pane> <el-tab-pane label="历史记录" name="2"></el-tab-pane>
<el-tab-pane label="统计报表" name="3"></el-tab-pane> <el-tab-pane label="统计报表" name="3"></el-tab-pane>
</el-tabs> </el-tabs> -->
<el-form :model="queryForm" inline class="card-box mb-4" label-position="top"> <el-form :model="queryForm" inline class="card-box mb-4" label-position="top">
<el-form-item label="项目名称/编号"> <el-form-item label="项目名称/编号">
<el-input v-model="queryForm.name" placeholder="请输入项目名称/编号"></el-input> <el-input v-model="queryForm.projectName" placeholder="请输入项目名称/编号"></el-input>
</el-form-item> </el-form-item>
<el-form-item label="时间范围"> <el-form-item label="时间范围">
<el-date-picker v-model="queryForm.dateRange" type="daterange" value-format="yyyy-MM-dd" <el-date-picker v-model="queryForm.dateRange" type="daterange" value-format="YYYY-MM-DD"
range-separator="至" start-placeholder="开始日期" end-placeholder="结束日期"></el-date-picker> range-separator="至" start-placeholder="开始日期" end-placeholder="结束日期"></el-date-picker>
</el-form-item> </el-form-item>
<el-form-item label="票证编号"> <el-form-item label="票证编号">
<el-input v-model="queryForm.ticketNumber" placeholder="请输入票证编号"></el-input> <el-input v-model="queryForm.permitNumber" placeholder="请输入票证编号"></el-input>
</el-form-item> </el-form-item>
<el-form-item label="施工单位"> <el-form-item label="施工单位">
<el-input v-model="queryForm.enterpriseName" placeholder="请输入施工单位"></el-input> <el-input v-model="queryForm.enterpriseName" placeholder="请输入施工单位"></el-input>
</el-form-item> </el-form-item>
<el-form-item label="出入证状态"> <el-form-item label="出入证状态">
<el-select v-model="queryForm.status" placeholder="请选择出入证状态"> <el-select v-model="queryForm.status" placeholder="请选择出入证状态">
<el-option label="待签发" value="1"></el-option> <el-option label="待审核" value="0"></el-option>
<el-option label="已签发" value="2"></el-option> <el-option label="已签发" value="1"></el-option>
<el-option label="已驳回" value="2"></el-option>
<el-option label="已作废" value="3"></el-option> <el-option label="已作废" value="3"></el-option>
</el-select> </el-select>
</el-form-item> </el-form-item>
<el-form-item style="margin-top: 28px;"> <el-form-item style="margin-top: 28px;">
<el-button size="default">重置</el-button> <el-button size="default" @click="handleReset">重置</el-button>
<el-button type="primary" size="default">查询</el-button> <el-button type="primary" size="default" @click="handleSearch">查询</el-button>
</el-form-item> </el-form-item>
</el-form> </el-form>
@ -37,31 +38,33 @@
<div class="button-group" style="margin-bottom: 20px;"> <div class="button-group" style="margin-bottom: 20px;">
<h2 style="font-size: 16px;">签发列表</h2> <h2 style="font-size: 16px;">签发列表</h2>
<div class="button-group"> <div class="button-group">
<el-button type="primary" size="default">导出Excel</el-button> <el-button type="primary" size="default" @click="handleExportExcel">导出Excel</el-button>
<el-button type="info" size="default">打印</el-button> <el-button type="info" size="default">打印</el-button>
</div> </div>
</div> </div>
<el-table :data="tableData"> <el-table :data="tableData" :loading="loading">
<el-table-column prop="projectName" label="项目名称"></el-table-column> <el-table-column prop="projectName" label="项目名称"></el-table-column>
<el-table-column prop="ticketNumber" label="票证编号"></el-table-column> <el-table-column prop="permitNumber" label="票证编号"></el-table-column>
<el-table-column prop="projectName" label="施工单位"></el-table-column> <el-table-column prop="projectName" label="施工单位"></el-table-column>
<el-table-column prop="workTime" label="作业时间"></el-table-column> <el-table-column prop="validityStartTime;" label="作业时间"></el-table-column>
<el-table-column prop="proprietorName" label="工作负责人"></el-table-column> <el-table-column prop="sysUserListLength" label="成员数量">
<el-table-column prop="memberCount" label="成员数量"></el-table-column> <template #default="scope">
{{ scope.row.sysUserList?.length }}
</template>
</el-table-column>
<el-table-column prop="status" label="状态"> <el-table-column prop="status" label="状态">
<template #default="scope"> <template #default="scope">
<el-tag <el-tag :type="getStatusType(scope.row.status)">
:type="scope.row.status === '待签发' ? 'primary' : (scope.row.status === '已签发' ? 'success' : 'danger')"> {{ statusMap[scope.row.status] || '-' }}
{{ scope.row.status }}
</el-tag> </el-tag>
</template> </template>
</el-table-column> </el-table-column>
<el-table-column label="操作" width="210"> <el-table-column label="操作" width="210">
<template #default="scope"> <template #default="scope">
<el-button size="small" type="primary" link <el-button size="small" type="primary" link v-if="scope.row.status === '0'"
@click="handleIssueClick(scope.row)">签发出入证</el-button> @click="handleIssueClick(scope.row)">签发出入证</el-button>
<el-button size="small" type="info" link <el-button size="small" type="info" link
@click="handleDetailClick(scope.row)">查看管理票证</el-button> @click="handleDetailClick(scope.row)">查看关联票证</el-button>
</template> </template>
</el-table-column> </el-table-column>
</el-table> </el-table>
@ -71,79 +74,149 @@
total }} total }}
</span> </span>
<el-pagination v-model:current-page="pageNum" v-model:page-size="pageSize" :page-sizes="[5, 10, 20]" <el-pagination v-model:current-page="pageNum" v-model:page-size="pageSize" :page-sizes="[5, 10, 20]"
:total="total" layout="prev, pager, next"></el-pagination> :total="total" layout="prev, pager, next" @current-change="handleCurrentChange"></el-pagination>
</div> </div>
</div> </div>
<!-- 出入证签发-弹窗详情 --> <!-- 出入证签发-弹窗详情 -->
<DialogBox v-if="dialogShow" ref="dialogRef" :show="dialogShow" :CloseDialog="handleCancel" /> <DialogBox v-if="dialogShow" :Rid="rowInfo.permitId" ref="dialogRef" :show="dialogShow"
:CloseDialog="handleCancel" />
<!-- 关联票证-弹窗详情 --> <!-- 关联票证-弹窗详情 -->
<DialogBox2 v-if="dialogShow2" ref="dialogRef2" :show="dialogShow2" :CloseDialog="handleCancel" /> <DialogBox2 v-if="dialogShow2" :Rid="rowInfo.permitId" ref="dialogRef2" :show="dialogShow2"
:CloseDialog="handleCancel" />
</div> </div>
</template> </template>
<script setup name="Index"> <script setup name="Index">
import dayjs from 'dayjs';
import { ElMessage } from 'element-plus';
import { FetchPassagewayList } from "@/api/Pass";
import DialogBox from "./DialogBox.vue"; import DialogBox from "./DialogBox.vue";
import DialogBox2 from "./DialogBox2.vue"; import DialogBox2 from "./DialogBox2.vue";
import { ref } from "vue"; import { ref, onMounted } from "vue";
//
const statusMap = {
'0': "待审核",
'1': "已签发",
'2': "已驳回",
'3': "已作废"
}
const activeTab = ref("1"); // tab const activeTab = ref("1"); // tab
// //
const queryForm = ref({ const queryForm = ref({
name: "", projectName: "", //
status: "" dateRange: "", //
permitNumber: "", //
enterpriseName: "", //
status: "" //
}); });
//
const rowInfo = ref({});
const dialogShow = ref(false); // const dialogShow = ref(false); //
const dialogShow2 = ref(false); // const dialogShow2 = ref(false); //
const loading = ref(false); //
// //
const tableData = ref([ const tableData = ref();
{
id: 1,
ticketNumber: "123456",
projectName: "项目A",
enterpriseName: "中建一局",
proprietorName: "张三",
memberCount: 3,
workTime: "2023-05-12 14:30",
status: "待签发"
},
{
id: 2,
ticketNumber: "123457",
projectName: "项目B",
enterpriseName: "中铁建工",
proprietorName: "李四",
memberCount: 2,
workTime: "2023-05-13 09:45",
status: "已签发"
},
{
id: 3,
ticketNumber: "123457",
projectName: "项目B",
enterpriseName: "中铁建工",
proprietorName: "李四",
memberCount: 2,
workTime: "2023-05-13 09:45",
status: "已作废"
}
]);
const pageNum = ref(1); // const pageNum = ref(1); //
const pageSize = ref(5); // const pageSize = ref(10); //
const total = ref(20); // const total = ref(0); //
onMounted(() => {
getList();
});
//
const getStatusType = (status) => {
if (status === null || status === undefined) {
return 'info';
}
switch (status) {
case '0':
return 'primary';
case '1':
return 'success';
case '2':
return 'danger';
case '3':
return 'info';
default:
return 'info';
}
}
//
const handleSearch = () => {
pageNum.value = 1;
getList();
}
//
const handleReset = () => {
queryForm.value = {
projectName: "",
dateRange: "",
permitNumber: "",
enterpriseName: "",
status: ""
}
getList();
}
//
const handleCurrentChange = (val) => {
pageNum.value = val;
getList();
}
//
const getList = async () => {
let params = {
pageNum: pageNum.value,
pageSize: pageSize.value,
projectName: queryForm.value.projectName,
permitNumber: queryForm.value.permitNumber,
enterpriseName: queryForm.value.enterpriseName,
status: queryForm.value.status
}
if (queryForm.value.dateRange) {
params.validityStartTime = dayjs(queryForm.value.dateRange[0]).format('YYYY-MM-DD');
params.validityEndTime = dayjs(queryForm.value.dateRange[1]).format('YYYY-MM-DD');
}
loading.value = true;
const res = await FetchPassagewayList(params);
loading.value = false;
if (res.code === 200) {
tableData.value = res.rows;
total.value = res.total;
}
}
// Excel
const handleExportExcel = async () => {
ElMessage({
message: '导出Excel成功',
type: 'success'
})
}
// //
const handleIssueClick = (row) => { const handleIssueClick = (row) => {
console.log("签发", row); console.log("签发", row);
rowInfo.value = row;
dialogShow.value = true; dialogShow.value = true;
} }
// //
const handleDetailClick = (row) => { const handleDetailClick = (row) => {
console.log("关联票证", row); console.log("关联票证", row);
rowInfo.value = row;
dialogShow2.value = true; dialogShow2.value = true;
} }
@ -152,6 +225,8 @@ const handleCancel = () => {
console.log('关闭弹窗') console.log('关闭弹窗')
dialogShow.value = false dialogShow.value = false
dialogShow2.value = false dialogShow2.value = false
rowInfo.value = {}
getList();
} }

View File

@ -8,19 +8,23 @@
<div class="ticket-detail"> <div class="ticket-detail">
<h3>票证详情</h3> <h3>票证详情</h3>
<el-descriptions :column="1" border :size="small"> <el-descriptions :column="1" border :size="small">
<el-descriptions-item label="票证编号">PT20250405-001</el-descriptions-item> <el-descriptions-item label="票证编号">{{ detailData.ticketNumber }}</el-descriptions-item>
<el-descriptions-item label="票证类型"> <el-descriptions-item label="票证类型">
<span class="high-risk">危险作业票高风险</span> <span class="high-risk">{{ detailData.riskType }}</span>
</el-descriptions-item>
<el-descriptions-item label="项目名称">{{ detailData.projectName }}</el-descriptions-item>
<el-descriptions-item label="施工单位">{{ detailData.supervisorDeptName
}}</el-descriptions-item>
<el-descriptions-item label="提交人">{{ detailData.supervisorName }}</el-descriptions-item>
<el-descriptions-item label="提交时间">{{ detailData.submitTime }}</el-descriptions-item>
<el-descriptions-item label="施工地点">{{ detailData.workLocation }}</el-descriptions-item>
<el-descriptions-item label="施工内容">{{ detailData.workContent }}</el-descriptions-item>
<el-descriptions-item label="安全措施">
<div v-for="(item, index) in detailData.safetyMeasuresList" :key="index">{{ index + 1
}}. {{ item }}</div>
</el-descriptions-item> </el-descriptions-item>
<el-descriptions-item label="项目名称">新建厂房项目一期</el-descriptions-item>
<el-descriptions-item label="施工单位">中建一局</el-descriptions-item>
<el-descriptions-item label="提交人">李建国</el-descriptions-item>
<el-descriptions-item label="提交时间">2025-04-05 09:30</el-descriptions-item>
<el-descriptions-item label="施工地点">A栋西侧脚手架区域</el-descriptions-item>
<el-descriptions-item label="施工内容">高空拆除旧管道作业</el-descriptions-item>
<el-descriptions-item label="安全措施">系好安全绳设置警戒线配备灭火器材</el-descriptions-item>
<el-descriptions-item label="注意事项"> <el-descriptions-item label="注意事项">
<span class="warning">风力超过五级严禁作业</span> <span class="warning">{{ detailData.attention }}</span>
</el-descriptions-item> </el-descriptions-item>
</el-descriptions> </el-descriptions>
</div> </div>
@ -29,25 +33,18 @@
<el-col :span="11"> <el-col :span="11">
<div class="audit-operation"> <div class="audit-operation">
<h3>审核操作</h3> <h3>审核操作</h3>
<el-form label-width="100px" :model="formData" label-position="top"> <el-form label-width="100px" v-model="formData" label-position="top">
<el-form-item label="审核结果"> <el-form-item label="审核结果">
<el-radio-group v-model="auditResult"> <el-radio-group v-model="formData.auditResult">
<el-radio label="通过">通过</el-radio> <el-radio label="1">通过</el-radio>
<el-radio label="驳回">驳回</el-radio> <el-radio label="2">驳回</el-radio>
</el-radio-group> </el-radio-group>
</el-form-item> </el-form-item>
<el-form-item label="审核意见"> <el-form-item label="审核意见">
<el-input type="textarea" placeholder="请输入审核意见..." :rows="4"></el-input> <el-input v-model="formData.reviewComment" type="textarea" placeholder="请输入审核意见..."
</el-form-item> :rows="4"></el-input>
<el-form-item label="附件上传">
<el-upload style="width: 100%;" class="upload-demo" drag
action="https://jsonplaceholder.typicode.com/posts/" multiple>
<el-icon class="el-icon--upload"><upload-filled /></el-icon>
<div class="el-upload__text">
点击上传文件或拖拽至此处
</div>
</el-upload>
</el-form-item> </el-form-item>
</el-form> </el-form>
</div> </div>
</el-col> </el-col>
@ -63,11 +60,10 @@
</template> </template>
<script setup> <script setup>
import { ref,onBeforeMount } from 'vue' import { ref, onBeforeMount } from 'vue'
import { UploadFilled } from '@element-plus/icons-vue' import { ElMessage } from 'element-plus'
import { FetchWorkTicketDetail } from '@/api/workTicket' import { FetchWorkTicketDetail, AuditWorkTicketPass, AuditWorkTicketRefuse } from '@/api/workTicket'
const auditResult = ref('')
const props = defineProps({ const props = defineProps({
Tid: { Tid: {
type: Number || String, type: Number || String,
@ -83,9 +79,21 @@ const props = defineProps({
} }
}) })
//
const detailData = ref({})
//
const formData = ref({
ticketId: props.Tid,
auditResult: '1',
reviewComment: ''
})
onBeforeMount(() => { onBeforeMount(() => {
console.log('props.Tid', props.Tid)
if (props.Tid) { if (props.Tid) {
getDetail(); getDetail();
} }
}) })
@ -94,64 +102,33 @@ onBeforeMount(() => {
const getDetail = async () => { const getDetail = async () => {
let res = await FetchWorkTicketDetail(props.Tid); let res = await FetchWorkTicketDetail(props.Tid);
if (res.code == 200) { if (res.code == 200) {
formData.value = res.data; detailData.value = res.data;
} }
} }
//
const projectTreeData = ref([
{
id: 1,
label: '北京市',
children: [
{
id: 2,
label: '朝阳区',
children: [
{ id: 3, label: 'CBD大厦项目' },
{ id: 4, label: '国贸三期项目' }
]
},
{ id: 5, label: '海淀区' }
]
}
])
//
const treeProps = ref({
children: 'children',
label: 'label'
})
//
const formData = ref({
name: '',
account: '',
department: '',
roles: [],
selectedProjects: [],
phone: '',
expireDate: null,
forever: false,
remark: ''
})
//
const handleCheckChange = (checkedNodes) => {
console.log('选中的项目节点:', checkedNodes)
}
// //
const handleClose = () => { const handleClose = () => {
props.CloseDialog() props.CloseDialog()
} }
const handleSubmit = () => { const handleSubmit = async () => {
// let FUN = formData.value.auditResult == '1' ? AuditWorkTicketPass : AuditWorkTicketRefuse;
console.log('提交分配信息', formData.value) let params = {
props.CloseDialog() ticketId: props.Tid,
reviewComment: formData.value.reviewComment
}
let res = await FUN(params);
if (res.code == 200) {
ElMessage.success('操作成功');
props.CloseDialog();
} else {
ElMessage.error(res.msg || '操作失败');
}
} }
</script> </script>
@ -161,14 +138,15 @@ const handleSubmit = () => {
padding: 20px; padding: 20px;
} }
.ticket-detail, .audit-operation { .ticket-detail,
background: #fff; .audit-operation {
border-radius: 8px; background: #fff;
padding: 20px; border-radius: 8px;
box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1); padding: 20px;
height: 100%; box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
display: flex; height: 100%;
flex-direction: column; display: flex;
flex-direction: column;
} }
.ticket-detail h3, .ticket-detail h3,
@ -194,18 +172,18 @@ const handleSubmit = () => {
} }
.el-form-item { .el-form-item {
margin-bottom: 20px; margin-bottom: 20px;
} }
.el-form { .el-form {
flex: 1; flex: 1;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
} }
.el-form-item:last-child { .el-form-item:last-child {
margin-bottom: 0; margin-bottom: 0;
flex: 1; flex: 1;
} }
.el-upload { .el-upload {

View File

@ -9,8 +9,6 @@
<el-tab-pane label="已作废" name="4"></el-tab-pane> <el-tab-pane label="已作废" name="4"></el-tab-pane>
</el-tabs> </el-tabs>
<el-form :model="queryForm" inline class="card-box mb-4" label-position="top"> <el-form :model="queryForm" inline class="card-box mb-4" label-position="top">
<el-form-item label="项目名称/编号"> <el-form-item label="项目名称/编号">
<el-input v-model="queryForm.keyword" placeholder="请输入项目名称/编号"></el-input> <el-input v-model="queryForm.keyword" placeholder="请输入项目名称/编号"></el-input>
@ -42,7 +40,7 @@
<el-table-column prop="updateTime" label="提交时间"></el-table-column> <el-table-column prop="updateTime" label="提交时间"></el-table-column>
<el-table-column prop="status" label="当前状态"> <el-table-column prop="status" label="当前状态">
<template #default="scope"> <template #default="scope">
<el-tag :type="scope.row.status === '1' ? 'primary' : 'danger'"> <el-tag :type="getStatusType(scope.row.status)">
{{ statusCodeMap[scope.row.status] }} {{ statusCodeMap[scope.row.status] }}
</el-tag> </el-tag>
</template> </template>
@ -52,7 +50,6 @@
<el-button size="small" type="primary" link <el-button size="small" type="primary" link
@click="handleAuditClick(scope.row)">审核签发</el-button> @click="handleAuditClick(scope.row)">审核签发</el-button>
<el-button size="small" type="info" link @click="handleDetailClick(scope.row)">查看详情</el-button> <el-button size="small" type="info" link @click="handleDetailClick(scope.row)">查看详情</el-button>
<el-button size="small" type="danger" link>退回重提</el-button>
</template> </template>
</el-table-column> </el-table-column>
</el-table> </el-table>
@ -113,10 +110,28 @@ onBeforeMount(() => {
getInit(); getInit();
}) })
//
const getStatusType = (status) => {
switch (status) {
case '0':
return 'info';
case '1':
return 'primary';
case '2':
return 'success';
case '3':
return 'danger';
case '4':
return 'info';
default:
return 'info';
}
}
// //
const handleAuditClick = (row) => { const handleAuditClick = (row) => {
console.log("审核签发", row); console.log("审核签发", row);
Tid.value = row.id; Tid.value = row.ticketId;
dialogShow.value = true; dialogShow.value = true;
} }
@ -161,8 +176,9 @@ const getInit = async () => {
params.startTime = dayjs(queryForm.value.dateRange[0]).format('YYYY-MM-DD'); params.startTime = dayjs(queryForm.value.dateRange[0]).format('YYYY-MM-DD');
params.endTime = dayjs(queryForm.value.dateRange[1]).format('YYYY-MM-DD'); params.endTime = dayjs(queryForm.value.dateRange[1]).format('YYYY-MM-DD');
} }
loading.value = true;
let res = await FetchWorkTicketList(params); let res = await FetchWorkTicketList(params);
loading.value = false;
console.log("数据列表", res); console.log("数据列表", res);
if (res.code === 200) { if (res.code === 200) {
tableData.value = res.rows; tableData.value = res.rows;
@ -192,6 +208,7 @@ const handleCancel = () => {
console.log('关闭弹窗') console.log('关闭弹窗')
dialogShow.value = false; dialogShow.value = false;
Tid.value = ''; Tid.value = '';
getInit();
} }

View File

@ -176,7 +176,7 @@
</div> </div>
</template> </template>
<script setup name="Index"> <script setup name="Index">
import { ref, computed, onMounted, getCurrentInstance } from "vue"; import { ref, onBeforeMount, computed, onMounted, getCurrentInstance } from "vue";
import { useRouter } from "vue-router"; import { useRouter } from "vue-router";
import { listUser, addUser, getUser, updateUser, delUser, changeUserStatus, resetUserPwd, deptTreeSelect } from "@/api/system/user"; import { listUser, addUser, getUser, updateUser, delUser, changeUserStatus, resetUserPwd, deptTreeSelect } from "@/api/system/user";
import { ElMessage, ElMessageBox } from "element-plus"; import { ElMessage, ElMessageBox } from "element-plus";
@ -221,6 +221,10 @@ const pageNum = ref(1); // 当前页码
const pageSize = ref(10); // const pageSize = ref(10); //
const total = ref(0); // const total = ref(0); //
onBeforeMount(() => {
getDeptTree();
});
// //
const getList = async () => { const getList = async () => {
if (!unitId.value) { if (!unitId.value) {
@ -596,7 +600,7 @@ const handleBack = () => {
onMounted(() => { onMounted(() => {
const route = router.currentRoute.value; const route = router.currentRoute.value;
// IDID // IDID
const id = route.query.unitId; const id = route.query.deptId;
const deptIdParam = route.query.deptId; const deptIdParam = route.query.deptId;
const enterpriseName = route.query.enterpriseName; const enterpriseName = route.query.enterpriseName;
@ -608,8 +612,6 @@ onMounted(() => {
if (enterpriseName) { if (enterpriseName) {
enterpriseData.value.enterpriseName = enterpriseName; enterpriseData.value.enterpriseName = enterpriseName;
} }
//
getDeptTree();
// //
getList(); getList();
} else { } else {

View File

@ -10,12 +10,10 @@
<div class="button-group mg-2"> <div class="button-group mg-2">
<div class="button-group"> <div class="button-group">
<el-button type="primary" size="default" @click="handleAddEnterprise">新增单位建档</el-button> <el-button type="primary" size="default" @click="handleAddEnterprise">新增单位建档</el-button>
<el-button type="warning" size="default">批量创建账号</el-button> <!-- <el-button type="warning" size="default">批量创建账号</el-button> -->
<el-button size="default">导入账号</el-button> <el-button size="default">导入账号</el-button>
<el-button size="default">导出账号</el-button> <el-button size="default">导出账号</el-button>
</div> </div>
<el-button size="default" class="float-right" icon="Refresh" @click="handleRefresh">刷新</el-button>
</div> </div>
<el-form :model="queryForm" inline class="card-box mb-4"> <el-form :model="queryForm" inline class="card-box mb-4">
@ -92,7 +90,6 @@ const queryForm = ref({
areaName: "", areaName: "",
status: "" status: ""
}); });
// //
const tableData = ref([]); const tableData = ref([]);
const pageNum = ref(1); // const pageNum = ref(1); //
@ -190,7 +187,7 @@ const handleAccountManagement = (row) => {
// //
const handleEdit = (row) => { const handleEdit = (row) => {
router.push(`/Tenement/newEnterprise?unitId=${row.unitId || row.id}`); router.push(`/Tenement/newEnterprise?unitId=${row.deptId}`);
}; };
// //