diff --git a/src/utils/routerHelper.ts b/src/utils/routerHelper.ts index af6a9c3c..a6825653 100644 --- a/src/utils/routerHelper.ts +++ b/src/utils/routerHelper.ts @@ -1,10 +1,22 @@ +import type { RouteLocationNormalized, Router, RouteRecordNormalized } from 'vue-router' import { createRouter, createWebHashHistory, RouteRecordRaw } from 'vue-router' -import type { Router, RouteLocationNormalized, RouteRecordNormalized } from 'vue-router' import { isUrl } from '@/utils/is' -import { omit, cloneDeep } from 'lodash-es' +import { cloneDeep, omit } from 'lodash-es' const modules = import.meta.glob('../views/**/*.{vue,tsx}') - +/** + * 注册一个异步组件 + * @param componentPath 例:/bpm/oa/leave/detail + */ +export const registerComponent = (componentPath: string) => { + for (const item in modules) { + if (item.includes(componentPath)) { + // 使用异步组件的方式来动态加载组件 + // @ts-ignore + return defineAsyncComponent(modules[item]) + } + } +} /* Layout */ export const Layout = () => import('@/layout/Layout.vue') diff --git a/src/views/bpm/form/editor/index.vue b/src/views/bpm/form/editor/index.vue index c56a7747..f11c1228 100644 --- a/src/views/bpm/form/editor/index.vue +++ b/src/views/bpm/form/editor/index.vue @@ -44,10 +44,13 @@ import { CommonStatusEnum } from '@/utils/constants' import * as FormApi from '@/api/bpm/form' import FcDesigner from '@form-create/designer' import { encodeConf, encodeFields, setConfAndFields } from '@/utils/formCreate' +import { useTagsViewStore } from '@/store/modules/tagsView' const { t } = useI18n() // 国际化 const message = useMessage() // 消息 -const { query } = useRoute() // 路由 +const { push, currentRoute } = useRouter() // 路由 +const { query } = useRoute() // 路由信息 +const { delView } = useTagsViewStore() // 视图操作 const designer = ref() // 表单设计器 const dialogVisible = ref(false) // 弹窗是否展示 @@ -88,10 +91,16 @@ const submitForm = async () => { message.success(t('common.updateSuccess')) } dialogVisible.value = false + close() } finally { formLoading.value = false } } +/** 关闭按钮 */ +const close = () => { + delView(unref(currentRoute)) + push('/bpm/manager/form') +} /** 初始化 **/ onMounted(async () => { diff --git a/src/views/bpm/form/index.vue b/src/views/bpm/form/index.vue index 915bd0bd..48bb3698 100644 --- a/src/views/bpm/form/index.vue +++ b/src/views/bpm/form/index.vue @@ -2,26 +2,33 @@ <ContentWrap> <!-- 搜索工作栏 --> <el-form - class="-mb-15px" - :model="queryParams" ref="queryFormRef" :inline="true" + :model="queryParams" + class="-mb-15px" label-width="68px" > <el-form-item label="表单名" prop="name"> <el-input v-model="queryParams.name" - placeholder="请输入表单名" - clearable - @keyup.enter="handleQuery" class="!w-240px" + clearable + placeholder="请输入表单名" + @keyup.enter="handleQuery" /> </el-form-item> <el-form-item> - <el-button @click="handleQuery"><Icon icon="ep:search" class="mr-5px" /> 搜索</el-button> - <el-button @click="resetQuery"><Icon icon="ep:refresh" class="mr-5px" /> 重置</el-button> - <el-button type="primary" plain @click="openForm" v-hasPermi="['bpm:form:create']"> - <Icon icon="ep:plus" class="mr-5px" /> 新增 + <el-button @click="handleQuery"> + <Icon class="mr-5px" icon="ep:search" /> + 搜索 + </el-button> + <el-button @click="resetQuery"> + <Icon class="mr-5px" icon="ep:refresh" /> + 重置 + </el-button> + <el-button v-hasPermi="['bpm:form:create']" plain type="primary" @click="openForm"> + <Icon class="mr-5px" icon="ep:plus" /> + 新增 </el-button> </el-form-item> </el-form> @@ -30,38 +37,38 @@ <!-- 列表 --> <ContentWrap> <el-table v-loading="loading" :data="list"> - <el-table-column label="编号" align="center" prop="id" /> - <el-table-column label="表单名" align="center" prop="name" /> - <el-table-column label="状态" align="center" prop="status"> + <el-table-column align="center" label="编号" prop="id" /> + <el-table-column align="center" label="表单名" prop="name" /> + <el-table-column align="center" label="状态" prop="status"> <template #default="scope"> <dict-tag :type="DICT_TYPE.COMMON_STATUS" :value="scope.row.status" /> </template> </el-table-column> - <el-table-column label="备注" align="center" prop="remark" /> + <el-table-column align="center" label="备注" prop="remark" /> <el-table-column - label="创建时间" - align="center" - prop="createTime" :formatter="dateFormatter" + align="center" + label="创建时间" + prop="createTime" /> - <el-table-column label="操作" align="center"> + <el-table-column align="center" label="操作"> <template #default="scope"> <el-button + v-hasPermi="['bpm:form:update']" link type="primary" @click="openForm(scope.row.id)" - v-hasPermi="['bpm:form:update']" > 编辑 </el-button> - <el-button link @click="openDetail(scope.row.id)" v-hasPermi="['bpm:form:query']"> + <el-button v-hasPermi="['bpm:form:query']" link @click="openDetail(scope.row.id)"> 详情 </el-button> <el-button + v-hasPermi="['bpm:form:delete']" link type="danger" @click="handleDelete(scope.row.id)" - v-hasPermi="['bpm:form:delete']" > 删除 </el-button> @@ -70,27 +77,28 @@ </el-table> <!-- 分页 --> <Pagination - :total="total" - v-model:page="queryParams.pageNo" v-model:limit="queryParams.pageSize" + v-model:page="queryParams.pageNo" + :total="total" @pagination="getList" /> </ContentWrap> <!-- 表单详情的弹窗 --> - <Dialog title="表单详情" v-model="detailVisible" width="800"> - <form-create :rule="detailData.rule" :option="detailData.option" /> + <Dialog v-model="detailVisible" title="表单详情" width="800"> + <form-create :option="detailData.option" :rule="detailData.rule" /> </Dialog> </template> -<script setup lang="ts" name="BpmForm"> +<script lang="ts" name="BpmForm" setup> import { DICT_TYPE } from '@/utils/dict' import { dateFormatter } from '@/utils/formatTime' import * as FormApi from '@/api/bpm/form' import { setConfAndFields2 } from '@/utils/formCreate' + const message = useMessage() // 消息弹窗 const { t } = useI18n() // 国际化 -const { push } = useRouter() // 路由 +const { currentRoute, push } = useRouter() // 路由 const loading = ref(true) // 列表的加载中 const total = ref(0) // 列表的总页数 @@ -128,12 +136,16 @@ const resetQuery = () => { /** 添加/修改操作 */ const openForm = (id?: number) => { - push({ - name: 'BpmFormEditor', - query: { + const toRouter: { name: string; query?: { id: number } } = { + name: 'BpmFormEditor' + } + // 表单新建的时候id传的是event需要排除 + if (typeof id === 'number') { + toRouter.query = { id } - }) + } + push(toRouter) } /** 删除按钮操作 */ @@ -162,7 +174,16 @@ const openDetail = async (rowId: number) => { // 弹窗打开 detailVisible.value = true } - +/**表单保存返回后重新加载列表 */ +watch( + () => currentRoute.value, + () => { + getList() + }, + { + immediate: true + } +) /** 初始化 **/ onMounted(() => { getList() diff --git a/src/views/bpm/group/UserGroupForm.vue b/src/views/bpm/group/UserGroupForm.vue index 1adbea15..5a3ca804 100644 --- a/src/views/bpm/group/UserGroupForm.vue +++ b/src/views/bpm/group/UserGroupForm.vue @@ -11,7 +11,7 @@ <el-input v-model="formData.name" placeholder="请输入组名" /> </el-form-item> <el-form-item label="描述"> - <el-input v-model="formData.name" placeholder="请输入描述" type="textarea" /> + <el-input v-model="formData.description" placeholder="请输入描述" type="textarea" /> </el-form-item> <el-form-item label="成员" prop="memberUserIds"> <el-select v-model="formData.memberUserIds" multiple placeholder="请选择成员"> diff --git a/src/views/bpm/oa/leave/detail.vue b/src/views/bpm/oa/leave/detail.vue index 2ce8a39d..a1b646a1 100644 --- a/src/views/bpm/oa/leave/detail.vue +++ b/src/views/bpm/oa/leave/detail.vue @@ -1,6 +1,6 @@ <template> <ContentWrap> - <el-descriptions border :column="1"> + <el-descriptions :column="1" border> <el-descriptions-item label="请假类型"> <dict-tag :type="DICT_TYPE.BPM_OA_LEAVE_TYPE" :value="detailData.type" /> </el-descriptions-item> @@ -21,6 +21,7 @@ import { DICT_TYPE } from '@/utils/dict' import { formatDate } from '@/utils/formatTime' import { propTypes } from '@/utils/propTypes' import * as LeaveApi from '@/api/bpm/leave' + const { query } = useRoute() // 查询参数 const props = defineProps({ @@ -34,7 +35,7 @@ const queryId = query.id as unknown as number // 从 URL 传递过来的 id 编 const getInfo = async () => { detailLoading.value = true try { - detailData.value = await LeaveApi.getLeave(queryId || props.id) + detailData.value = await LeaveApi.getLeave(props.id || queryId) } finally { detailLoading.value = false } diff --git a/src/views/bpm/processInstance/detail/index.vue b/src/views/bpm/processInstance/detail/index.vue index 62fe3ab2..eb01e6e0 100644 --- a/src/views/bpm/processInstance/detail/index.vue +++ b/src/views/bpm/processInstance/detail/index.vue @@ -2,81 +2,78 @@ <ContentWrap> <!-- 审批信息 --> <el-card - class="box-card" - v-loading="processInstanceLoading" v-for="(item, index) in runningTasks" :key="index" + v-loading="processInstanceLoading" + class="box-card" > <template #header> <span class="el-icon-picture-outline">审批任务【{{ item.name }}】</span> </template> - <el-col :span="16" :offset="6"> + <el-col :offset="6" :span="16"> <el-form :ref="'form' + index" :model="auditForms[index]" :rules="auditRule" label-width="100px" > - <el-form-item label="流程名" v-if="processInstance && processInstance.name"> + <el-form-item v-if="processInstance && processInstance.name" label="流程名"> {{ processInstance.name }} </el-form-item> - <el-form-item label="流程发起人" v-if="processInstance && processInstance.startUser"> + <el-form-item v-if="processInstance && processInstance.startUser" label="流程发起人"> {{ processInstance.startUser.nickname }} - <el-tag type="info" size="small">{{ processInstance.startUser.deptName }}</el-tag> + <el-tag size="small" type="info">{{ processInstance.startUser.deptName }}</el-tag> </el-form-item> <el-form-item label="审批建议" prop="reason"> <el-input - type="textarea" v-model="auditForms[index].reason" placeholder="请输入审批建议" + type="textarea" /> </el-form-item> </el-form> <div style="margin-left: 10%; margin-bottom: 20px; font-size: 14px"> <el-button type="success" @click="handleAudit(item, true)"> - <Icon icon="ep:select" /> 通过 + <Icon icon="ep:select" /> + 通过 </el-button> <el-button type="danger" @click="handleAudit(item, false)"> - <Icon icon="ep:close" /> 不通过 + <Icon icon="ep:close" /> + 不通过 </el-button> <el-button type="primary" @click="openTaskUpdateAssigneeForm(item.id)"> - <Icon icon="ep:edit" /> 转办 + <Icon icon="ep:edit" /> + 转办 </el-button> <el-button type="primary" @click="handleDelegate(item)"> - <Icon icon="ep:position" /> 委派 + <Icon icon="ep:position" /> + 委派 </el-button> <el-button type="warning" @click="handleBack(item)"> - <Icon icon="ep:back" /> 回退 + <Icon icon="ep:back" /> + 回退 </el-button> </div> </el-col> </el-card> <!-- 申请信息 --> - <el-card class="box-card" v-loading="processInstanceLoading"> + <el-card v-loading="processInstanceLoading" class="box-card"> <template #header> <span class="el-icon-document">申请信息【{{ processInstance.name }}】</span> </template> <!-- 情况一:流程表单 --> - <el-col v-if="processInstance?.processDefinition?.formType === 10" :span="16" :offset="6"> + <el-col v-if="processInstance?.processDefinition?.formType === 10" :offset="6" :span="16"> <form-create ref="fApi" - :rule="detailForm.rule" - :option="detailForm.option" v-model="detailForm.value" + :option="detailForm.option" + :rule="detailForm.rule" /> </el-col> - <!-- 情况二:流程表单 --> + <!-- 情况二:业务表单 --> <div v-if="processInstance?.processDefinition?.formType === 20"> - <router-link - :to=" - processInstance.processDefinition.formCustomViewPath + - '?id=' + - processInstance.businessKey - " - > - <el-button type="primary"><Icon icon="ep:view" /> 点击查看</el-button> - </router-link> + <autoComponent :id="processInstance.businessKey" /> </div> </el-card> @@ -85,18 +82,18 @@ <!-- 高亮流程图 --> <ProcessInstanceBpmnViewer - :id="id" - :process-instance="processInstance" - :loading="processInstanceLoading" - :tasks="tasks" + :id="`${id}`" :bpmn-xml="bpmnXML" + :loading="processInstanceLoading" + :process-instance="processInstance" + :tasks="tasks" /> <!-- 弹窗:转派审批人 --> <TaskUpdateAssigneeForm ref="taskUpdateAssigneeFormRef" @success="getDetail" /> </ContentWrap> </template> -<script setup lang="ts" name="BpmProcessInstanceDetail"> +<script lang="ts" name="BpmProcessInstanceDetail" setup> import { useUserStore } from '@/store/modules/user' import { setConfAndFields2 } from '@/utils/formCreate' import type { ApiAttrs } from '@form-create/element-ui/types/config' @@ -106,6 +103,8 @@ import * as TaskApi from '@/api/bpm/task' import TaskUpdateAssigneeForm from './TaskUpdateAssigneeForm.vue' import ProcessInstanceBpmnViewer from './ProcessInstanceBpmnViewer.vue' import ProcessInstanceTaskList from './ProcessInstanceTaskList.vue' +import { registerComponent } from '@/utils/routerHelper' + const { query } = useRoute() // 查询参数 const message = useMessage() // 消息弹窗 const { proxy } = getCurrentInstance() as any @@ -184,7 +183,7 @@ const getDetail = () => { // 2. 获得流程任务列表(审批记录) getTaskList() } - +const autoComponent = ref(null) // 异步组件 /** 加载流程实例 */ const getProcessInstance = async () => { try { @@ -195,7 +194,7 @@ const getProcessInstance = async () => { return } processInstance.value = data - + autoComponent.value = registerComponent(data.processDefinition.formCustomViewPath) // 设置表单信息 const processDefinition = data.processDefinition if (processDefinition.formType === 10) { @@ -213,7 +212,7 @@ const getProcessInstance = async () => { } // 加载流程图 - bpmnXML.value = await DefinitionApi.getProcessDefinitionBpmnXML(processDefinition.id) + bpmnXML.value = await DefinitionApi.getProcessDefinitionBpmnXML(processDefinition.id as number) } finally { processInstanceLoading.value = false } diff --git a/src/views/infra/codegen/index.vue b/src/views/infra/codegen/index.vue index b23c6fd9..6a554d5d 100644 --- a/src/views/infra/codegen/index.vue +++ b/src/views/infra/codegen/index.vue @@ -5,46 +5,53 @@ <!-- 搜索 --> <ContentWrap> <el-form - class="-mb-15px" - :model="queryParams" ref="queryFormRef" :inline="true" + :model="queryParams" + class="-mb-15px" label-width="68px" > <el-form-item label="表名称" prop="tableName"> <el-input v-model="queryParams.tableName" - placeholder="请输入表名称" - clearable - @keyup.enter="handleQuery" class="!w-240px" + clearable + placeholder="请输入表名称" + @keyup.enter="handleQuery" /> </el-form-item> <el-form-item label="表描述" prop="tableComment"> <el-input v-model="queryParams.tableComment" - placeholder="请输入表描述" - clearable - @keyup.enter="handleQuery" class="!w-240px" + clearable + placeholder="请输入表描述" + @keyup.enter="handleQuery" /> </el-form-item> <el-form-item label="创建时间" prop="createTime"> <el-date-picker v-model="queryParams.createTime" - value-format="YYYY-MM-dd HH:mm:ss" - type="daterange" - start-placeholder="开始日期" - end-placeholder="结束日期" :default-time="[new Date('1 00:00:00'), new Date('1 23:59:59')]" class="!w-240px" + end-placeholder="结束日期" + start-placeholder="开始日期" + type="daterange" + value-format="YYYY-MM-dd HH:mm:ss" /> </el-form-item> <el-form-item> - <el-button @click="handleQuery"><Icon icon="ep:search" class="mr-5px" />搜索</el-button> - <el-button @click="resetQuery"><Icon icon="ep:refresh" class="mr-5px" />重置</el-button> - <el-button type="primary" v-hasPermi="['infra:codegen:create']" @click="openImportTable()"> - <Icon icon="ep:zoom-in" class="mr-5px" /> 导入 + <el-button @click="handleQuery"> + <Icon class="mr-5px" icon="ep:search" /> + 搜索 + </el-button> + <el-button @click="resetQuery"> + <Icon class="mr-5px" icon="ep:refresh" /> + 重置 + </el-button> + <el-button v-hasPermi="['infra:codegen:create']" type="primary" @click="openImportTable()"> + <Icon class="mr-5px" icon="ep:zoom-in" /> + 导入 </el-button> </el-form-item> </el-form> @@ -53,75 +60,75 @@ <!-- 列表 --> <ContentWrap> <el-table v-loading="loading" :data="list"> - <el-table-column label="数据源" align="center"> + <el-table-column align="center" label="数据源"> <template #default="scope"> {{ dataSourceConfigList.find((config) => config.id === scope.row.dataSourceConfigId)?.name }} </template> </el-table-column> - <el-table-column label="表名称" align="center" prop="tableName" width="200" /> + <el-table-column align="center" label="表名称" prop="tableName" width="200" /> <el-table-column - label="表描述" - align="center" - prop="tableComment" :show-overflow-tooltip="true" + align="center" + label="表描述" + prop="tableComment" width="200" /> - <el-table-column label="实体" align="center" prop="className" width="200" /> + <el-table-column align="center" label="实体" prop="className" width="200" /> <el-table-column + :formatter="dateFormatter" + align="center" label="创建时间" - align="center" prop="createTime" width="180" - :formatter="dateFormatter" /> <el-table-column - label="更新时间" + :formatter="dateFormatter" align="center" + label="更新时间" prop="createTime" width="180" - :formatter="dateFormatter" /> - <el-table-column label="操作" align="center" width="300px" fixed="right"> + <el-table-column align="center" fixed="right" label="操作" width="300px"> <template #default="scope"> <el-button + v-hasPermi="['infra:codegen:preview']" link type="primary" @click="handlePreview(scope.row)" - v-hasPermi="['infra:codegen:preview']" > 预览 </el-button> <el-button + v-hasPermi="['infra:codegen:update']" link type="primary" @click="handleUpdate(scope.row.id)" - v-hasPermi="['infra:codegen:update']" > 编辑 </el-button> <el-button + v-hasPermi="['infra:codegen:delete']" link type="danger" @click="handleDelete(scope.row.id)" - v-hasPermi="['infra:codegen:delete']" > 删除 </el-button> <el-button + v-hasPermi="['infra:codegen:update']" link type="primary" @click="handleSyncDB(scope.row)" - v-hasPermi="['infra:codegen:update']" > 同步 </el-button> <el-button + v-hasPermi="['infra:codegen:download']" link type="primary" @click="handleGenTable(scope.row)" - v-hasPermi="['infra:codegen:download']" > 生成代码 </el-button> @@ -130,25 +137,26 @@ </el-table> <!-- 分页 --> <Pagination - :total="total" - v-model:page="queryParams.pageNo" v-model:limit="queryParams.pageSize" + v-model:page="queryParams.pageNo" + :total="total" @pagination="getList" /> </ContentWrap> <!-- 弹窗:导入表 --> - <ImportTable ref="importRef" success="getList" /> + <ImportTable ref="importRef" @success="getList" /> <!-- 弹窗:预览代码 --> <PreviewCode ref="previewRef" /> </template> -<script setup lang="ts" name="InfraCodegen"> +<script lang="ts" name="InfraCodegen" setup> import { dateFormatter } from '@/utils/formatTime' import download from '@/utils/download' import * as CodegenApi from '@/api/infra/codegen' import * as DataSourceConfigApi from '@/api/infra/dataSourceConfig' import ImportTable from './ImportTable.vue' import PreviewCode from './PreviewCode.vue' + const message = useMessage() // 消息弹窗 const { t } = useI18n() // 国际化 const { push } = useRouter() // 路由跳转