|
@@ -1,29 +1,12 @@
|
|
|
<template>
|
|
<template>
|
|
|
<AidopDemoShell :title="pageTitle" subtitle="S0 / Sales / 订单优先级">
|
|
<AidopDemoShell :title="pageTitle" subtitle="S0 / Sales / 订单优先级">
|
|
|
|
|
+ <!-- ── 查询栏 ── -->
|
|
|
<el-form :inline="true" :model="query" class="mb12" @submit.prevent>
|
|
<el-form :inline="true" :model="query" class="mb12" @submit.prevent>
|
|
|
<el-form-item label="关键字">
|
|
<el-form-item label="关键字">
|
|
|
- <el-input v-model="query.keyword" placeholder="名称/来源表/工单字段/业务维度" clearable style="width: 180px" />
|
|
|
|
|
- </el-form-item>
|
|
|
|
|
- <el-form-item label="域编码">
|
|
|
|
|
- <el-input v-model="query.domainCode" clearable style="width: 120px" />
|
|
|
|
|
- </el-form-item>
|
|
|
|
|
- <el-form-item label="名称">
|
|
|
|
|
- <el-input v-model="query.descr" clearable style="width: 140px" />
|
|
|
|
|
- </el-form-item>
|
|
|
|
|
- <el-form-item label="优先级">
|
|
|
|
|
- <el-input-number v-model="query.priority" :min="0" clearable controls-position="right" style="width: 110px" />
|
|
|
|
|
- </el-form-item>
|
|
|
|
|
- <el-form-item label="来源表">
|
|
|
|
|
- <el-input v-model="query.sourceTable" clearable style="width: 130px" />
|
|
|
|
|
- </el-form-item>
|
|
|
|
|
- <el-form-item label="来源字段">
|
|
|
|
|
- <el-input v-model="query.sourceColumn" clearable style="width: 120px" />
|
|
|
|
|
- </el-form-item>
|
|
|
|
|
- <el-form-item label="工单字段">
|
|
|
|
|
- <el-input v-model="query.value" clearable style="width: 120px" />
|
|
|
|
|
|
|
+ <el-input v-model="query.keyword" placeholder="规则名称/编码" clearable style="width: 180px" />
|
|
|
</el-form-item>
|
|
</el-form-item>
|
|
|
<el-form-item label="生效">
|
|
<el-form-item label="生效">
|
|
|
- <el-select v-model="query.isActive" clearable placeholder="全部" style="width: 100px">
|
|
|
|
|
|
|
+ <el-select v-model="query.isEnabled" clearable placeholder="全部" style="width: 100px">
|
|
|
<el-option label="是" :value="true" />
|
|
<el-option label="是" :value="true" />
|
|
|
<el-option label="否" :value="false" />
|
|
<el-option label="否" :value="false" />
|
|
|
</el-select>
|
|
</el-select>
|
|
@@ -32,30 +15,35 @@
|
|
|
<el-button type="primary" @click="loadList">查询</el-button>
|
|
<el-button type="primary" @click="loadList">查询</el-button>
|
|
|
<el-button @click="resetQuery">重置</el-button>
|
|
<el-button @click="resetQuery">重置</el-button>
|
|
|
<el-button type="success" @click="openCreate">新增规则</el-button>
|
|
<el-button type="success" @click="openCreate">新增规则</el-button>
|
|
|
|
|
+ <el-button @click="configDialogVisible = true">配置维护</el-button>
|
|
|
</el-form-item>
|
|
</el-form-item>
|
|
|
</el-form>
|
|
</el-form>
|
|
|
|
|
|
|
|
|
|
+ <!-- ── 主列表 ── -->
|
|
|
<el-table :data="rows" v-loading="loading" border stripe style="width: 100%" max-height="calc(100vh - 260px)">
|
|
<el-table :data="rows" v-loading="loading" border stripe style="width: 100%" max-height="calc(100vh - 260px)">
|
|
|
- <el-table-column prop="descr" label="名称" min-width="160" show-overflow-tooltip />
|
|
|
|
|
- <el-table-column prop="priority" label="优先级" width="88" align="center" />
|
|
|
|
|
- <el-table-column prop="orderByText" label="排序" width="88" align="center" />
|
|
|
|
|
- <el-table-column prop="sourceTable" label="来源表" width="130" show-overflow-tooltip />
|
|
|
|
|
- <el-table-column prop="sourceColumn" label="来源字段" width="120" show-overflow-tooltip />
|
|
|
|
|
- <el-table-column prop="sourceType" label="来源类型" width="100" show-overflow-tooltip />
|
|
|
|
|
- <el-table-column prop="sourceId" label="来源关联" width="110" show-overflow-tooltip />
|
|
|
|
|
- <el-table-column prop="value" label="工单字段" width="120" show-overflow-tooltip />
|
|
|
|
|
- <el-table-column prop="valueType" label="工单类型" width="100" show-overflow-tooltip />
|
|
|
|
|
- <el-table-column prop="valueId" label="工单关联" width="110" show-overflow-tooltip />
|
|
|
|
|
- <el-table-column label="生效" width="72" align="center">
|
|
|
|
|
|
|
+ <el-table-column prop="name" label="规则名称" min-width="160" show-overflow-tooltip />
|
|
|
|
|
+ <el-table-column label="客户类型" width="120" show-overflow-tooltip>
|
|
|
|
|
+ <template #default="{ row }">{{ row.customerTypeLabel || '—' }}</template>
|
|
|
|
|
+ </el-table-column>
|
|
|
|
|
+ <el-table-column label="订单类型" width="120" show-overflow-tooltip>
|
|
|
|
|
+ <template #default="{ row }">{{ row.orderTypeLabel || '—' }}</template>
|
|
|
|
|
+ </el-table-column>
|
|
|
|
|
+ <el-table-column label="交期条件" width="100" show-overflow-tooltip>
|
|
|
|
|
+ <template #default="{ row }">{{ row.dueStatusLabel || '—' }}</template>
|
|
|
|
|
+ </el-table-column>
|
|
|
|
|
+ <el-table-column prop="priorityLevel" label="优先级" width="80" align="center" />
|
|
|
|
|
+ <el-table-column prop="sortDirection" label="排序方向" width="88" align="center" />
|
|
|
|
|
+ <el-table-column label="是否生效" width="88" align="center">
|
|
|
<template #default="{ row }">
|
|
<template #default="{ row }">
|
|
|
- <el-tag :type="row.isActive ? 'success' : 'info'" size="small">{{ row.isActive ? '是' : '否' }}</el-tag>
|
|
|
|
|
|
|
+ <el-tag :type="row.isEnabled ? 'success' : 'info'" size="small">{{ row.isEnabled ? '是' : '否' }}</el-tag>
|
|
|
</template>
|
|
</template>
|
|
|
</el-table-column>
|
|
</el-table-column>
|
|
|
- <el-table-column label="操作" width="220" fixed="right" align="center">
|
|
|
|
|
|
|
+ <el-table-column prop="remark" label="备注" min-width="140" show-overflow-tooltip />
|
|
|
|
|
+ <el-table-column label="操作" width="200" fixed="right" align="center">
|
|
|
<template #default="{ row }">
|
|
<template #default="{ row }">
|
|
|
<el-button link type="primary" @click="openEdit(row)">编辑</el-button>
|
|
<el-button link type="primary" @click="openEdit(row)">编辑</el-button>
|
|
|
- <el-button link :type="row.isActive ? 'warning' : 'success'" @click="toggleActive(row)">
|
|
|
|
|
- {{ row.isActive ? '停用' : '生效' }}
|
|
|
|
|
|
|
+ <el-button link :type="row.isEnabled ? 'warning' : 'success'" @click="toggleEnabled(row)">
|
|
|
|
|
+ {{ row.isEnabled ? '停用' : '生效' }}
|
|
|
</el-button>
|
|
</el-button>
|
|
|
<el-button link type="danger" @click="onDelete(row)">删除</el-button>
|
|
<el-button link type="danger" @click="onDelete(row)">删除</el-button>
|
|
|
</template>
|
|
</template>
|
|
@@ -74,42 +62,165 @@
|
|
|
/>
|
|
/>
|
|
|
</div>
|
|
</div>
|
|
|
|
|
|
|
|
- <el-dialog v-model="dialogVisible" :title="dialogTitle" width="760px" destroy-on-close @closed="() => { if (!dialogVisible) resetForm(); }">
|
|
|
|
|
- <el-form ref="formRef" :model="form" :rules="rules" label-width="130px">
|
|
|
|
|
|
|
+ <!-- ── 新增/编辑规则弹窗 ── -->
|
|
|
|
|
+ <el-dialog
|
|
|
|
|
+ v-model="ruleDialogVisible"
|
|
|
|
|
+ :title="ruleDialogTitle"
|
|
|
|
|
+ width="680px"
|
|
|
|
|
+ destroy-on-close
|
|
|
|
|
+ @closed="resetRuleForm"
|
|
|
|
|
+ >
|
|
|
|
|
+ <el-form ref="ruleFormRef" :model="ruleForm" :rules="ruleFormRules" label-width="110px">
|
|
|
<el-row :gutter="16">
|
|
<el-row :gutter="16">
|
|
|
<el-col :span="12">
|
|
<el-col :span="12">
|
|
|
- <el-form-item label="名称 Descr" prop="descr">
|
|
|
|
|
- <el-input v-model="form.descr" />
|
|
|
|
|
|
|
+ <el-form-item label="规则编码" prop="code">
|
|
|
|
|
+ <el-input v-model="ruleForm.code" placeholder="可自动填充或手动输入" />
|
|
|
</el-form-item>
|
|
</el-form-item>
|
|
|
</el-col>
|
|
</el-col>
|
|
|
<el-col :span="12">
|
|
<el-col :span="12">
|
|
|
- <el-form-item label="优先级">
|
|
|
|
|
- <el-input-number v-model="form.priority" :min="0" style="width: 100%" controls-position="right" />
|
|
|
|
|
|
|
+ <el-form-item label="规则名称" prop="name">
|
|
|
|
|
+ <el-input v-model="ruleForm.name" />
|
|
|
</el-form-item>
|
|
</el-form-item>
|
|
|
</el-col>
|
|
</el-col>
|
|
|
<el-col :span="12">
|
|
<el-col :span="12">
|
|
|
- <el-form-item label="排序 OrderBy">
|
|
|
|
|
- <el-select v-model="form.orderBy" style="width: 100%">
|
|
|
|
|
- <el-option label="正序" :value="true" />
|
|
|
|
|
- <el-option label="倒序" :value="false" />
|
|
|
|
|
|
|
+ <el-form-item label="客户类型">
|
|
|
|
|
+ <el-select v-model="ruleForm.customerType" clearable placeholder="不限" style="width: 100%">
|
|
|
|
|
+ <el-option
|
|
|
|
|
+ v-for="opt in dictOptions.customerType"
|
|
|
|
|
+ :key="opt.value"
|
|
|
|
|
+ :label="opt.label"
|
|
|
|
|
+ :value="opt.value"
|
|
|
|
|
+ />
|
|
|
</el-select>
|
|
</el-select>
|
|
|
</el-form-item>
|
|
</el-form-item>
|
|
|
</el-col>
|
|
</el-col>
|
|
|
- <el-col :span="12"><el-form-item label="生效"><el-switch v-model="form.isActive" /></el-form-item></el-col>
|
|
|
|
|
- <el-col :span="12"><el-form-item label="来源表"><el-input v-model="form.sourceTable" /></el-form-item></el-col>
|
|
|
|
|
- <el-col :span="12"><el-form-item label="来源字段"><el-input v-model="form.sourceColumn" /></el-form-item></el-col>
|
|
|
|
|
- <el-col :span="12"><el-form-item label="来源类型"><el-input v-model="form.sourceType" /></el-form-item></el-col>
|
|
|
|
|
- <el-col :span="12"><el-form-item label="来源关联"><el-input v-model="form.sourceId" /></el-form-item></el-col>
|
|
|
|
|
- <el-col :span="12"><el-form-item label="工单字段 Value"><el-input v-model="form.value" /></el-form-item></el-col>
|
|
|
|
|
- <el-col :span="12"><el-form-item label="工单类型"><el-input v-model="form.valueType" /></el-form-item></el-col>
|
|
|
|
|
- <el-col :span="12"><el-form-item label="工单关联"><el-input v-model="form.valueId" /></el-form-item></el-col>
|
|
|
|
|
|
|
+ <el-col :span="12">
|
|
|
|
|
+ <el-form-item label="订单类型">
|
|
|
|
|
+ <el-select v-model="ruleForm.orderType" clearable placeholder="不限" style="width: 100%">
|
|
|
|
|
+ <el-option
|
|
|
|
|
+ v-for="opt in dictOptions.orderType"
|
|
|
|
|
+ :key="opt.value"
|
|
|
|
|
+ :label="opt.label"
|
|
|
|
|
+ :value="opt.value"
|
|
|
|
|
+ />
|
|
|
|
|
+ </el-select>
|
|
|
|
|
+ </el-form-item>
|
|
|
|
|
+ </el-col>
|
|
|
|
|
+ <el-col :span="12">
|
|
|
|
|
+ <el-form-item label="交期条件">
|
|
|
|
|
+ <el-select v-model="ruleForm.dueStatus" clearable placeholder="不限" style="width: 100%">
|
|
|
|
|
+ <el-option
|
|
|
|
|
+ v-for="opt in dictOptions.dueStatus"
|
|
|
|
|
+ :key="opt.value"
|
|
|
|
|
+ :label="opt.label"
|
|
|
|
|
+ :value="opt.value"
|
|
|
|
|
+ />
|
|
|
|
|
+ </el-select>
|
|
|
|
|
+ </el-form-item>
|
|
|
|
|
+ </el-col>
|
|
|
|
|
+ <el-col :span="12">
|
|
|
|
|
+ <el-form-item label="优先级" prop="priorityLevel">
|
|
|
|
|
+ <el-input-number v-model="ruleForm.priorityLevel" :min="1" style="width: 100%" controls-position="right" />
|
|
|
|
|
+ </el-form-item>
|
|
|
|
|
+ </el-col>
|
|
|
|
|
+ <el-col :span="12">
|
|
|
|
|
+ <el-form-item label="排序方向">
|
|
|
|
|
+ <el-select v-model="ruleForm.sortDirection" style="width: 100%">
|
|
|
|
|
+ <el-option label="升序 ASC" value="asc" />
|
|
|
|
|
+ <el-option label="降序 DESC" value="desc" />
|
|
|
|
|
+ </el-select>
|
|
|
|
|
+ </el-form-item>
|
|
|
|
|
+ </el-col>
|
|
|
|
|
+ <el-col :span="12">
|
|
|
|
|
+ <el-form-item label="是否生效">
|
|
|
|
|
+ <el-switch v-model="ruleForm.isEnabled" />
|
|
|
|
|
+ </el-form-item>
|
|
|
|
|
+ </el-col>
|
|
|
|
|
+ <el-col :span="24">
|
|
|
|
|
+ <el-form-item label="备注">
|
|
|
|
|
+ <el-input v-model="ruleForm.remark" type="textarea" :rows="2" />
|
|
|
|
|
+ </el-form-item>
|
|
|
|
|
+ </el-col>
|
|
|
</el-row>
|
|
</el-row>
|
|
|
</el-form>
|
|
</el-form>
|
|
|
<template #footer>
|
|
<template #footer>
|
|
|
- <el-button @click="dialogVisible = false">取消</el-button>
|
|
|
|
|
- <el-button type="primary" :loading="saving" @click="submitForm">保存</el-button>
|
|
|
|
|
|
|
+ <el-button @click="ruleDialogVisible = false">取消</el-button>
|
|
|
|
|
+ <el-button type="primary" :loading="ruleSaving" @click="submitRuleForm">保存</el-button>
|
|
|
</template>
|
|
</template>
|
|
|
</el-dialog>
|
|
</el-dialog>
|
|
|
|
|
+
|
|
|
|
|
+ <!-- ── 配置维护弹窗 ── -->
|
|
|
|
|
+ <el-dialog
|
|
|
|
|
+ v-model="configDialogVisible"
|
|
|
|
|
+ title="订单优先级配置维护"
|
|
|
|
|
+ width="860px"
|
|
|
|
|
+ destroy-on-close
|
|
|
|
|
+ @open="onConfigDialogOpen"
|
|
|
|
|
+ >
|
|
|
|
|
+ <el-tabs v-model="configActiveTab">
|
|
|
|
|
+ <!-- Tab 1: 客户类型 -->
|
|
|
|
|
+ <el-tab-pane label="客户类型" name="customerType">
|
|
|
|
|
+ <DictDataTab
|
|
|
|
|
+ dict-code="s0_order_priority_customer_type"
|
|
|
|
|
+ :rows="configTabs.customerType.rows"
|
|
|
|
|
+ :loading="configTabs.customerType.loading"
|
|
|
|
|
+ @reload="loadConfigTab('customerType')"
|
|
|
|
|
+ />
|
|
|
|
|
+ </el-tab-pane>
|
|
|
|
|
+
|
|
|
|
|
+ <!-- Tab 2: 订单类型 -->
|
|
|
|
|
+ <el-tab-pane label="订单类型" name="orderType">
|
|
|
|
|
+ <DictDataTab
|
|
|
|
|
+ dict-code="s0_order_type"
|
|
|
|
|
+ :rows="configTabs.orderType.rows"
|
|
|
|
|
+ :loading="configTabs.orderType.loading"
|
|
|
|
|
+ @reload="loadConfigTab('orderType')"
|
|
|
|
|
+ />
|
|
|
|
|
+ </el-tab-pane>
|
|
|
|
|
+
|
|
|
|
|
+ <!-- Tab 3: 交期规则 -->
|
|
|
|
|
+ <el-tab-pane label="交期规则" name="dueStatus">
|
|
|
|
|
+ <DictDataTab
|
|
|
|
|
+ dict-code="s0_due_status"
|
|
|
|
|
+ :rows="configTabs.dueStatus.rows"
|
|
|
|
|
+ :loading="configTabs.dueStatus.loading"
|
|
|
|
|
+ :allow-edit="true"
|
|
|
|
|
+ :allow-delete="false"
|
|
|
|
|
+ @reload="loadConfigTab('dueStatus')"
|
|
|
|
|
+ />
|
|
|
|
|
+ </el-tab-pane>
|
|
|
|
|
+
|
|
|
|
|
+ <!-- Tab 4: 字段映射 -->
|
|
|
|
|
+ <el-tab-pane label="字段映射" name="fieldMapping">
|
|
|
|
|
+ <div class="field-mapping-panel">
|
|
|
|
|
+ <el-alert
|
|
|
|
|
+ type="info"
|
|
|
|
|
+ :closable="false"
|
|
|
|
|
+ title="字段映射来源于现有优先级规则字段配置"
|
|
|
|
|
+ description="来源实体、来源字段、工单字段等字段映射信息在各条业务规则中独立维护,请通过「编辑规则」进行调整。"
|
|
|
|
|
+ />
|
|
|
|
|
+ <el-table
|
|
|
|
|
+ :data="fieldMappingRows"
|
|
|
|
|
+ v-loading="fieldMappingLoading"
|
|
|
|
|
+ border
|
|
|
|
|
+ stripe
|
|
|
|
|
+ size="small"
|
|
|
|
|
+ style="width: 100%; margin-top: 12px"
|
|
|
|
|
+ max-height="320px"
|
|
|
|
|
+ >
|
|
|
|
|
+ <el-table-column prop="name" label="规则名称" min-width="130" show-overflow-tooltip />
|
|
|
|
|
+ <el-table-column prop="sourceEntity" label="来源实体" width="130" show-overflow-tooltip />
|
|
|
|
|
+ <el-table-column prop="sourceField" label="来源字段" width="130" show-overflow-tooltip />
|
|
|
|
|
+ <el-table-column prop="workOrderField" label="工单字段" width="130" show-overflow-tooltip />
|
|
|
|
|
+ <el-table-column prop="workOrderFieldType" label="工单字段类型" width="120" show-overflow-tooltip />
|
|
|
|
|
+ </el-table>
|
|
|
|
|
+ <div v-if="!fieldMappingLoading && fieldMappingRows.length === 0" class="empty-hint">
|
|
|
|
|
+ 当前未维护字段映射
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </el-tab-pane>
|
|
|
|
|
+ </el-tabs>
|
|
|
|
|
+ </el-dialog>
|
|
|
</AidopDemoShell>
|
|
</AidopDemoShell>
|
|
|
</template>
|
|
</template>
|
|
|
|
|
|
|
@@ -119,75 +230,47 @@ import { useRoute } from 'vue-router';
|
|
|
import { ElMessage, ElMessageBox, type FormInstance, type FormRules } from 'element-plus';
|
|
import { ElMessage, ElMessageBox, type FormInstance, type FormRules } from 'element-plus';
|
|
|
import AidopDemoShell from '../../components/AidopDemoShell.vue';
|
|
import AidopDemoShell from '../../components/AidopDemoShell.vue';
|
|
|
import {
|
|
import {
|
|
|
- s0OrderPriorityRulesApi,
|
|
|
|
|
- type S0PriorityCodeRow,
|
|
|
|
|
- type S0PriorityCodeUpsert,
|
|
|
|
|
|
|
+ s0PriorityRulesApi,
|
|
|
|
|
+ type S0PriorityRuleRow,
|
|
|
|
|
+ type S0PriorityRuleUpsert,
|
|
|
|
|
+ loadDictOptions,
|
|
|
|
|
+ listDictDataByCode,
|
|
|
|
|
+ addDictData,
|
|
|
|
|
+ updateDictData,
|
|
|
|
|
+ deleteDictData,
|
|
|
|
|
+ setDictDataStatus,
|
|
|
|
|
+ getDictTypeIdByCode,
|
|
|
|
|
+ type SysDictData,
|
|
|
|
|
+ StatusEnum,
|
|
|
|
|
+ type OptionItem,
|
|
|
} from '../api/s0SalesApi';
|
|
} from '../api/s0SalesApi';
|
|
|
|
|
|
|
|
|
|
+// ── 旧 API 保留(不删除,不作为主列表数据源)──────────────────────────────
|
|
|
|
|
+// s0OrderPriorityRulesApi 仍在 s0SalesApi.ts 中导出,此处不需引用
|
|
|
|
|
+
|
|
|
const route = useRoute();
|
|
const route = useRoute();
|
|
|
const pageTitle = computed(() => (route.meta?.title as string) || '订单优先规则');
|
|
const pageTitle = computed(() => (route.meta?.title as string) || '订单优先规则');
|
|
|
|
|
|
|
|
|
|
+// ── 查询 ──────────────────────────────────────────────────────────────────
|
|
|
const query = reactive({
|
|
const query = reactive({
|
|
|
keyword: '',
|
|
keyword: '',
|
|
|
- domainCode: '',
|
|
|
|
|
- descr: '',
|
|
|
|
|
- priority: undefined as number | undefined,
|
|
|
|
|
- sourceTable: '',
|
|
|
|
|
- sourceColumn: '',
|
|
|
|
|
- value: '',
|
|
|
|
|
- isActive: undefined as boolean | undefined,
|
|
|
|
|
|
|
+ isEnabled: undefined as boolean | undefined,
|
|
|
page: 1,
|
|
page: 1,
|
|
|
pageSize: 20,
|
|
pageSize: 20,
|
|
|
});
|
|
});
|
|
|
|
|
|
|
|
const loading = ref(false);
|
|
const loading = ref(false);
|
|
|
-const rows = ref<S0PriorityCodeRow[]>([]);
|
|
|
|
|
|
|
+const rows = ref<S0PriorityRuleRow[]>([]);
|
|
|
const total = ref(0);
|
|
const total = ref(0);
|
|
|
-const dialogVisible = ref(false);
|
|
|
|
|
-const dialogTitle = ref('新增规则');
|
|
|
|
|
-const editingId = ref<string | null>(null);
|
|
|
|
|
-const saving = ref(false);
|
|
|
|
|
-const formRef = ref<FormInstance>();
|
|
|
|
|
-
|
|
|
|
|
-function emptyForm(): S0PriorityCodeUpsert {
|
|
|
|
|
- return {
|
|
|
|
|
- domainCode: '',
|
|
|
|
|
- descr: '',
|
|
|
|
|
- value: '',
|
|
|
|
|
- priority: 1,
|
|
|
|
|
- orderBy: true,
|
|
|
|
|
- sourceTable: '',
|
|
|
|
|
- sourceColumn: '',
|
|
|
|
|
- sourceType: '',
|
|
|
|
|
- sourceId: '',
|
|
|
|
|
- valueType: '',
|
|
|
|
|
- valueId: '',
|
|
|
|
|
- isActive: true,
|
|
|
|
|
- createUser: '',
|
|
|
|
|
- updateUser: '',
|
|
|
|
|
- };
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-const form = reactive<S0PriorityCodeUpsert>(emptyForm());
|
|
|
|
|
-
|
|
|
|
|
-const rules: FormRules = {
|
|
|
|
|
- descr: [{ required: true, message: '请填写名称', trigger: 'blur' }],
|
|
|
|
|
-};
|
|
|
|
|
|
|
|
|
|
async function loadList() {
|
|
async function loadList() {
|
|
|
loading.value = true;
|
|
loading.value = true;
|
|
|
try {
|
|
try {
|
|
|
- const data = await s0OrderPriorityRulesApi.list({
|
|
|
|
|
|
|
+ const data = await s0PriorityRulesApi.list({
|
|
|
page: query.page,
|
|
page: query.page,
|
|
|
pageSize: query.pageSize,
|
|
pageSize: query.pageSize,
|
|
|
keyword: query.keyword || undefined,
|
|
keyword: query.keyword || undefined,
|
|
|
- domainCode: query.domainCode || undefined,
|
|
|
|
|
- descr: query.descr || undefined,
|
|
|
|
|
- priority: query.priority,
|
|
|
|
|
- sourceTable: query.sourceTable || undefined,
|
|
|
|
|
- sourceColumn: query.sourceColumn || undefined,
|
|
|
|
|
- value: query.value || undefined,
|
|
|
|
|
- isActive: query.isActive,
|
|
|
|
|
|
|
+ isEnabled: query.isEnabled,
|
|
|
});
|
|
});
|
|
|
rows.value = data.list;
|
|
rows.value = data.list;
|
|
|
total.value = data.total;
|
|
total.value = data.total;
|
|
@@ -200,105 +283,375 @@ async function loadList() {
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
function resetQuery() {
|
|
function resetQuery() {
|
|
|
- Object.assign(query, {
|
|
|
|
|
- keyword: '',
|
|
|
|
|
- domainCode: '',
|
|
|
|
|
- descr: '',
|
|
|
|
|
- priority: undefined,
|
|
|
|
|
- sourceTable: '',
|
|
|
|
|
- sourceColumn: '',
|
|
|
|
|
- value: '',
|
|
|
|
|
- isActive: undefined,
|
|
|
|
|
- page: 1,
|
|
|
|
|
- });
|
|
|
|
|
|
|
+ Object.assign(query, { keyword: '', isEnabled: undefined, page: 1 });
|
|
|
void loadList();
|
|
void loadList();
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-function resetForm() {
|
|
|
|
|
- editingId.value = null;
|
|
|
|
|
- Object.assign(form, emptyForm());
|
|
|
|
|
- formRef.value?.clearValidate();
|
|
|
|
|
|
|
+// ── 字典选项 ──────────────────────────────────────────────────────────────
|
|
|
|
|
+const dictOptions = reactive({
|
|
|
|
|
+ customerType: [] as OptionItem[],
|
|
|
|
|
+ orderType: [] as OptionItem[],
|
|
|
|
|
+ dueStatus: [] as OptionItem[],
|
|
|
|
|
+});
|
|
|
|
|
+
|
|
|
|
|
+async function loadDictSelects() {
|
|
|
|
|
+ const [ct, ot, ds] = await Promise.all([
|
|
|
|
|
+ loadDictOptions('s0_order_priority_customer_type'),
|
|
|
|
|
+ loadDictOptions('s0_order_type'),
|
|
|
|
|
+ loadDictOptions('s0_due_status'),
|
|
|
|
|
+ ]);
|
|
|
|
|
+ dictOptions.customerType = ct;
|
|
|
|
|
+ dictOptions.orderType = ot;
|
|
|
|
|
+ dictOptions.dueStatus = ds;
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-function rowToForm(row: S0PriorityCodeRow) {
|
|
|
|
|
- Object.assign(form, {
|
|
|
|
|
- domainCode: row.domainCode ?? '',
|
|
|
|
|
- descr: row.descr,
|
|
|
|
|
- value: row.value ?? '',
|
|
|
|
|
- priority: row.priority,
|
|
|
|
|
- orderBy: row.orderBy ?? true,
|
|
|
|
|
- sourceTable: row.sourceTable ?? '',
|
|
|
|
|
- sourceColumn: row.sourceColumn ?? '',
|
|
|
|
|
- sourceType: row.sourceType ?? '',
|
|
|
|
|
- sourceId: row.sourceId ?? '',
|
|
|
|
|
- valueType: row.valueType ?? '',
|
|
|
|
|
- valueId: row.valueId ?? '',
|
|
|
|
|
- isActive: row.isActive,
|
|
|
|
|
- createUser: row.createUser ?? '',
|
|
|
|
|
- updateUser: row.updateUser ?? '',
|
|
|
|
|
- });
|
|
|
|
|
|
|
+// ── 规则表单 ──────────────────────────────────────────────────────────────
|
|
|
|
|
+const ruleDialogVisible = ref(false);
|
|
|
|
|
+const ruleDialogTitle = ref('新增规则');
|
|
|
|
|
+const editingId = ref<number | null>(null);
|
|
|
|
|
+const ruleSaving = ref(false);
|
|
|
|
|
+const ruleFormRef = ref<FormInstance>();
|
|
|
|
|
+
|
|
|
|
|
+function emptyRuleForm(): S0PriorityRuleUpsert & { customerType?: string; orderType?: string; dueStatus?: string } {
|
|
|
|
|
+ return {
|
|
|
|
|
+ companyRefId: 0,
|
|
|
|
|
+ factoryRefId: 0,
|
|
|
|
|
+ code: '',
|
|
|
|
|
+ name: '',
|
|
|
|
|
+ priorityLevel: 1,
|
|
|
|
|
+ sortDirection: 'asc',
|
|
|
|
|
+ customerType: undefined,
|
|
|
|
|
+ orderType: undefined,
|
|
|
|
|
+ dueStatus: undefined,
|
|
|
|
|
+ isEnabled: true,
|
|
|
|
|
+ remark: '',
|
|
|
|
|
+ };
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+const ruleForm = reactive(emptyRuleForm());
|
|
|
|
|
+
|
|
|
|
|
+const ruleFormRules: FormRules = {
|
|
|
|
|
+ code: [{ required: true, message: '请填写规则编码', trigger: 'blur' }],
|
|
|
|
|
+ name: [{ required: true, message: '请填写规则名称', trigger: 'blur' }],
|
|
|
|
|
+ priorityLevel: [{ required: true, message: '请填写优先级', trigger: 'change' }],
|
|
|
|
|
+};
|
|
|
|
|
+
|
|
|
|
|
+function resetRuleForm() {
|
|
|
|
|
+ editingId.value = null;
|
|
|
|
|
+ Object.assign(ruleForm, emptyRuleForm());
|
|
|
|
|
+ ruleFormRef.value?.clearValidate();
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
function openCreate() {
|
|
function openCreate() {
|
|
|
- resetForm();
|
|
|
|
|
- dialogTitle.value = '新增规则';
|
|
|
|
|
- dialogVisible.value = true;
|
|
|
|
|
|
|
+ resetRuleForm();
|
|
|
|
|
+ ruleDialogTitle.value = '新增规则';
|
|
|
|
|
+ ruleDialogVisible.value = true;
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-function openEdit(row: S0PriorityCodeRow) {
|
|
|
|
|
- resetForm();
|
|
|
|
|
|
|
+function parseRuleExpr(row: S0PriorityRuleRow): { customerType?: string; orderType?: string; dueStatus?: string } {
|
|
|
|
|
+ // 后端 IsIgnore 标签字段优先;fallback 解析 ruleExpr JSON
|
|
|
|
|
+ if (row.customerTypeLabel !== undefined || row.orderTypeLabel !== undefined || row.dueStatusLabel !== undefined) {
|
|
|
|
|
+ // 标签字段是展示用的,实际 value 需从 ruleExpr 解析
|
|
|
|
|
+ }
|
|
|
|
|
+ if (!row.ruleExpr) return {};
|
|
|
|
|
+ try {
|
|
|
|
|
+ const parsed = JSON.parse(row.ruleExpr) as Record<string, unknown>;
|
|
|
|
|
+ return {
|
|
|
|
|
+ customerType: typeof parsed.customerType === 'string' ? parsed.customerType : undefined,
|
|
|
|
|
+ orderType: typeof parsed.orderType === 'string' ? parsed.orderType : undefined,
|
|
|
|
|
+ dueStatus: typeof parsed.dueStatus === 'string' ? parsed.dueStatus : undefined,
|
|
|
|
|
+ };
|
|
|
|
|
+ } catch {
|
|
|
|
|
+ return {};
|
|
|
|
|
+ }
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+function openEdit(row: S0PriorityRuleRow) {
|
|
|
|
|
+ resetRuleForm();
|
|
|
editingId.value = row.id;
|
|
editingId.value = row.id;
|
|
|
- dialogTitle.value = `编辑规则 ${row.descr}`;
|
|
|
|
|
- rowToForm(row);
|
|
|
|
|
- dialogVisible.value = true;
|
|
|
|
|
|
|
+ ruleDialogTitle.value = `编辑规则 ${row.name}`;
|
|
|
|
|
+ const expr = parseRuleExpr(row);
|
|
|
|
|
+ Object.assign(ruleForm, {
|
|
|
|
|
+ companyRefId: row.companyRefId,
|
|
|
|
|
+ factoryRefId: row.factoryRefId,
|
|
|
|
|
+ code: row.code,
|
|
|
|
|
+ name: row.name,
|
|
|
|
|
+ priorityLevel: row.priorityLevel,
|
|
|
|
|
+ sortDirection: row.sortDirection,
|
|
|
|
|
+ customerType: expr.customerType,
|
|
|
|
|
+ orderType: expr.orderType,
|
|
|
|
|
+ dueStatus: expr.dueStatus,
|
|
|
|
|
+ sourceEntity: row.sourceEntity,
|
|
|
|
|
+ sourceField: row.sourceField,
|
|
|
|
|
+ sourceFieldType: row.sourceFieldType,
|
|
|
|
|
+ sourceLinkField: row.sourceLinkField,
|
|
|
|
|
+ workOrderField: row.workOrderField,
|
|
|
|
|
+ workOrderFieldType: row.workOrderFieldType,
|
|
|
|
|
+ workOrderLinkField: row.workOrderLinkField,
|
|
|
|
|
+ isEnabled: row.isEnabled,
|
|
|
|
|
+ remark: row.remark ?? '',
|
|
|
|
|
+ });
|
|
|
|
|
+ ruleDialogVisible.value = true;
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-async function submitForm() {
|
|
|
|
|
- await formRef.value?.validate();
|
|
|
|
|
- saving.value = true;
|
|
|
|
|
|
|
+async function submitRuleForm() {
|
|
|
|
|
+ await ruleFormRef.value?.validate();
|
|
|
|
|
+ ruleSaving.value = true;
|
|
|
try {
|
|
try {
|
|
|
- const payload: S0PriorityCodeUpsert = { ...form };
|
|
|
|
|
- if (editingId.value) {
|
|
|
|
|
- await s0OrderPriorityRulesApi.update(editingId.value, payload);
|
|
|
|
|
|
|
+ const payload: S0PriorityRuleUpsert = {
|
|
|
|
|
+ companyRefId: ruleForm.companyRefId,
|
|
|
|
|
+ factoryRefId: ruleForm.factoryRefId,
|
|
|
|
|
+ code: ruleForm.code,
|
|
|
|
|
+ name: ruleForm.name,
|
|
|
|
|
+ priorityLevel: ruleForm.priorityLevel,
|
|
|
|
|
+ sortDirection: ruleForm.sortDirection,
|
|
|
|
|
+ customerType: (ruleForm as any).customerType || undefined,
|
|
|
|
|
+ orderType: (ruleForm as any).orderType || undefined,
|
|
|
|
|
+ dueStatus: (ruleForm as any).dueStatus || undefined,
|
|
|
|
|
+ sourceEntity: ruleForm.sourceEntity,
|
|
|
|
|
+ sourceField: ruleForm.sourceField,
|
|
|
|
|
+ sourceFieldType: ruleForm.sourceFieldType,
|
|
|
|
|
+ sourceLinkField: ruleForm.sourceLinkField,
|
|
|
|
|
+ workOrderField: ruleForm.workOrderField,
|
|
|
|
|
+ workOrderFieldType: ruleForm.workOrderFieldType,
|
|
|
|
|
+ workOrderLinkField: ruleForm.workOrderLinkField,
|
|
|
|
|
+ isEnabled: ruleForm.isEnabled,
|
|
|
|
|
+ remark: ruleForm.remark,
|
|
|
|
|
+ };
|
|
|
|
|
+ if (editingId.value !== null) {
|
|
|
|
|
+ await s0PriorityRulesApi.update(editingId.value, payload);
|
|
|
ElMessage.success('已保存');
|
|
ElMessage.success('已保存');
|
|
|
} else {
|
|
} else {
|
|
|
- await s0OrderPriorityRulesApi.create(payload);
|
|
|
|
|
|
|
+ await s0PriorityRulesApi.create(payload);
|
|
|
ElMessage.success('已创建');
|
|
ElMessage.success('已创建');
|
|
|
}
|
|
}
|
|
|
- dialogVisible.value = false;
|
|
|
|
|
|
|
+ ruleDialogVisible.value = false;
|
|
|
await loadList();
|
|
await loadList();
|
|
|
|
|
+ } catch {
|
|
|
|
|
+ ElMessage.error('保存订单优先规则失败,请检查填写内容后重试');
|
|
|
} finally {
|
|
} finally {
|
|
|
- saving.value = false;
|
|
|
|
|
|
|
+ ruleSaving.value = false;
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-function onDelete(row: S0PriorityCodeRow) {
|
|
|
|
|
- ElMessageBox.confirm(`确定删除规则「${row.descr}」?`, '确认', { type: 'warning' })
|
|
|
|
|
|
|
+function onDelete(row: S0PriorityRuleRow) {
|
|
|
|
|
+ ElMessageBox.confirm(`确定删除规则「${row.name}」?`, '确认', { type: 'warning' })
|
|
|
.then(async () => {
|
|
.then(async () => {
|
|
|
- await s0OrderPriorityRulesApi.delete(row.id);
|
|
|
|
|
|
|
+ await s0PriorityRulesApi.delete(row.id);
|
|
|
ElMessage.success('已删除');
|
|
ElMessage.success('已删除');
|
|
|
await loadList();
|
|
await loadList();
|
|
|
})
|
|
})
|
|
|
.catch(() => {});
|
|
.catch(() => {});
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-function toggleActive(row: S0PriorityCodeRow) {
|
|
|
|
|
- const next = !row.isActive;
|
|
|
|
|
|
|
+function toggleEnabled(row: S0PriorityRuleRow) {
|
|
|
|
|
+ const next = !row.isEnabled;
|
|
|
const actionText = next ? '生效' : '停用';
|
|
const actionText = next ? '生效' : '停用';
|
|
|
- ElMessageBox.confirm(`确定${actionText}规则「${row.descr}」?`, '确认', { type: 'warning' })
|
|
|
|
|
|
|
+ ElMessageBox.confirm(`确定${actionText}规则「${row.name}」?`, '确认', { type: 'warning' })
|
|
|
.then(async () => {
|
|
.then(async () => {
|
|
|
- await s0OrderPriorityRulesApi.toggleEnabled(row.id, { isActive: next });
|
|
|
|
|
|
|
+ await s0PriorityRulesApi.toggleEnabled(row.id, { isEnabled: next });
|
|
|
ElMessage.success(`${actionText}成功`);
|
|
ElMessage.success(`${actionText}成功`);
|
|
|
await loadList();
|
|
await loadList();
|
|
|
})
|
|
})
|
|
|
.catch(() => {});
|
|
.catch(() => {});
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+// ── 配置维护弹窗 ──────────────────────────────────────────────────────────
|
|
|
|
|
+const configDialogVisible = ref(false);
|
|
|
|
|
+const configActiveTab = ref('customerType');
|
|
|
|
|
+
|
|
|
|
|
+type ConfigTabKey = 'customerType' | 'orderType' | 'dueStatus';
|
|
|
|
|
+const CONFIG_TAB_CODES: Record<ConfigTabKey, string> = {
|
|
|
|
|
+ customerType: 's0_order_priority_customer_type',
|
|
|
|
|
+ orderType: 's0_order_type',
|
|
|
|
|
+ dueStatus: 's0_due_status',
|
|
|
|
|
+};
|
|
|
|
|
+
|
|
|
|
|
+const configTabs = reactive<Record<ConfigTabKey, { rows: SysDictData[]; loading: boolean }>>({
|
|
|
|
|
+ customerType: { rows: [], loading: false },
|
|
|
|
|
+ orderType: { rows: [], loading: false },
|
|
|
|
|
+ dueStatus: { rows: [], loading: false },
|
|
|
|
|
+});
|
|
|
|
|
+
|
|
|
|
|
+async function loadConfigTab(tab: ConfigTabKey) {
|
|
|
|
|
+ configTabs[tab].loading = true;
|
|
|
|
|
+ try {
|
|
|
|
|
+ configTabs[tab].rows = await listDictDataByCode(CONFIG_TAB_CODES[tab]);
|
|
|
|
|
+ } finally {
|
|
|
|
|
+ configTabs[tab].loading = false;
|
|
|
|
|
+ }
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+async function onConfigDialogOpen() {
|
|
|
|
|
+ await Promise.all([
|
|
|
|
|
+ loadConfigTab('customerType'),
|
|
|
|
|
+ loadConfigTab('orderType'),
|
|
|
|
|
+ loadConfigTab('dueStatus'),
|
|
|
|
|
+ loadFieldMapping(),
|
|
|
|
|
+ ]);
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+watch(configActiveTab, (tab) => {
|
|
|
|
|
+ if (tab === 'fieldMapping') void loadFieldMapping();
|
|
|
|
|
+});
|
|
|
|
|
+
|
|
|
|
|
+// 字段映射 Tab
|
|
|
|
|
+const fieldMappingRows = ref<S0PriorityRuleRow[]>([]);
|
|
|
|
|
+const fieldMappingLoading = ref(false);
|
|
|
|
|
+
|
|
|
|
|
+async function loadFieldMapping() {
|
|
|
|
|
+ fieldMappingLoading.value = true;
|
|
|
|
|
+ try {
|
|
|
|
|
+ const data = await s0PriorityRulesApi.list({ page: 1, pageSize: 200 });
|
|
|
|
|
+ fieldMappingRows.value = data.list.filter(
|
|
|
|
|
+ (r) => r.sourceEntity || r.sourceField || r.workOrderField,
|
|
|
|
|
+ );
|
|
|
|
|
+ } catch {
|
|
|
|
|
+ fieldMappingRows.value = [];
|
|
|
|
|
+ } finally {
|
|
|
|
|
+ fieldMappingLoading.value = false;
|
|
|
|
|
+ }
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
onMounted(async () => {
|
|
onMounted(async () => {
|
|
|
- await loadList();
|
|
|
|
|
|
|
+ await Promise.all([loadList(), loadDictSelects()]);
|
|
|
});
|
|
});
|
|
|
</script>
|
|
</script>
|
|
|
|
|
|
|
|
|
|
+<!-- ── DictDataTab 子组件(inline defineComponent 风格,避免新建文件) ── -->
|
|
|
|
|
+<script lang="ts">
|
|
|
|
|
+import { defineComponent, toRefs } from 'vue';
|
|
|
|
|
+
|
|
|
|
|
+const DictDataTab = defineComponent({
|
|
|
|
|
+ name: 'DictDataTab',
|
|
|
|
|
+ props: {
|
|
|
|
|
+ dictCode: { type: String, required: true },
|
|
|
|
|
+ rows: { type: Array as () => SysDictData[], default: () => [] },
|
|
|
|
|
+ loading: { type: Boolean, default: false },
|
|
|
|
|
+ allowEdit: { type: Boolean, default: true },
|
|
|
|
|
+ allowDelete: { type: Boolean, default: true },
|
|
|
|
|
+ },
|
|
|
|
|
+ emits: ['reload'],
|
|
|
|
|
+ setup(props, { emit }) {
|
|
|
|
|
+ const editDialogVisible = ref(false);
|
|
|
|
|
+ const editForm = ref<{ id: number | null; label: string; value: string; orderNo: number }>({
|
|
|
|
|
+ id: null, label: '', value: '', orderNo: 100,
|
|
|
|
|
+ });
|
|
|
|
|
+ const editSaving = ref(false);
|
|
|
|
|
+ const dictTypeIdCache = ref<number | null>(null);
|
|
|
|
|
+
|
|
|
|
|
+ async function ensureDictTypeId(): Promise<number | null> {
|
|
|
|
|
+ if (dictTypeIdCache.value !== null) return dictTypeIdCache.value;
|
|
|
|
|
+ dictTypeIdCache.value = await getDictTypeIdByCode(props.dictCode);
|
|
|
|
|
+ return dictTypeIdCache.value;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ function openAdd() {
|
|
|
|
|
+ editForm.value = { id: null, label: '', value: '', orderNo: (props.rows.length + 1) * 10 };
|
|
|
|
|
+ editDialogVisible.value = true;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ function openEditRow(row: SysDictData) {
|
|
|
|
|
+ editForm.value = { id: row.id ?? null, label: row.label, value: row.value, orderNo: row.orderNo ?? 100 };
|
|
|
|
|
+ editDialogVisible.value = true;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ async function saveEdit() {
|
|
|
|
|
+ if (!editForm.value.label || !editForm.value.value) {
|
|
|
|
|
+ ElMessage.warning('名称和编码均为必填');
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
+ editSaving.value = true;
|
|
|
|
|
+ try {
|
|
|
|
|
+ if (editForm.value.id === null) {
|
|
|
|
|
+ const typeId = await ensureDictTypeId();
|
|
|
|
|
+ if (!typeId) { ElMessage.error('无法获取字典类型,请刷新后重试'); return; }
|
|
|
|
|
+ await addDictData({ dictTypeId: typeId, label: editForm.value.label, value: editForm.value.value, orderNo: editForm.value.orderNo });
|
|
|
|
|
+ ElMessage.success('已新增');
|
|
|
|
|
+ } else {
|
|
|
|
|
+ await updateDictData({ id: editForm.value.id, label: editForm.value.label, value: editForm.value.value, orderNo: editForm.value.orderNo });
|
|
|
|
|
+ ElMessage.success('已保存');
|
|
|
|
|
+ }
|
|
|
|
|
+ editDialogVisible.value = false;
|
|
|
|
|
+ emit('reload');
|
|
|
|
|
+ } catch {
|
|
|
|
|
+ ElMessage.error('保存失败,请稍后重试');
|
|
|
|
|
+ } finally {
|
|
|
|
|
+ editSaving.value = false;
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ async function toggleStatus(row: SysDictData) {
|
|
|
|
|
+ const isEnabled = row.status === StatusEnum.NUMBER_1;
|
|
|
|
|
+ const next = isEnabled ? StatusEnum.NUMBER_2 : StatusEnum.NUMBER_1;
|
|
|
|
|
+ const label = isEnabled ? '停用' : '启用';
|
|
|
|
|
+ await ElMessageBox.confirm(`确定${label}「${row.label}」?`, '确认', { type: 'warning' });
|
|
|
|
|
+ await setDictDataStatus(row.id!, next);
|
|
|
|
|
+ ElMessage.success(`已${label}`);
|
|
|
|
|
+ emit('reload');
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ async function doDelete(row: SysDictData) {
|
|
|
|
|
+ await ElMessageBox.confirm(`确定删除「${row.label}」?删除后不可恢复。`, '确认', { type: 'warning' });
|
|
|
|
|
+ await deleteDictData(row.id!);
|
|
|
|
|
+ ElMessage.success('已删除');
|
|
|
|
|
+ emit('reload');
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ function statusLabel(row: SysDictData) {
|
|
|
|
|
+ return row.status === StatusEnum.NUMBER_1 ? '启用' : '停用';
|
|
|
|
|
+ }
|
|
|
|
|
+ function statusType(row: SysDictData): 'success' | 'info' {
|
|
|
|
|
+ return row.status === StatusEnum.NUMBER_1 ? 'success' : 'info';
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ return {
|
|
|
|
|
+ editDialogVisible, editForm, editSaving,
|
|
|
|
|
+ openAdd, openEditRow, saveEdit, toggleStatus, doDelete,
|
|
|
|
|
+ statusLabel, statusType,
|
|
|
|
|
+ };
|
|
|
|
|
+ },
|
|
|
|
|
+ template: `
|
|
|
|
|
+ <div>
|
|
|
|
|
+ <div style="margin-bottom:10px" v-if="allowEdit">
|
|
|
|
|
+ <el-button size="small" type="primary" @click="openAdd">新增</el-button>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ <el-table :data="rows" v-loading="loading" border stripe size="small" max-height="320px">
|
|
|
|
|
+ <el-table-column prop="label" label="名称" min-width="120" />
|
|
|
|
|
+ <el-table-column prop="value" label="编码" min-width="120" />
|
|
|
|
|
+ <el-table-column label="状态" width="80" align="center">
|
|
|
|
|
+ <template #default="{ row }">
|
|
|
|
|
+ <el-tag :type="statusType(row)" size="small">{{ statusLabel(row) }}</el-tag>
|
|
|
|
|
+ </template>
|
|
|
|
|
+ </el-table-column>
|
|
|
|
|
+ <el-table-column label="操作" width="160" align="center">
|
|
|
|
|
+ <template #default="{ row }">
|
|
|
|
|
+ <el-button v-if="allowEdit" link type="primary" @click="openEditRow(row)">编辑</el-button>
|
|
|
|
|
+ <el-button link :type="row.status === 1 ? 'warning' : 'success'" @click="toggleStatus(row)">
|
|
|
|
|
+ {{ row.status === 1 ? '停用' : '启用' }}
|
|
|
|
|
+ </el-button>
|
|
|
|
|
+ <el-button v-if="allowDelete" link type="danger" @click="doDelete(row)">删除</el-button>
|
|
|
|
|
+ </template>
|
|
|
|
|
+ </el-table-column>
|
|
|
|
|
+ </el-table>
|
|
|
|
|
+ <el-dialog v-model="editDialogVisible" :title="editForm.id ? '编辑条目' : '新增条目'" width="420px" append-to-body destroy-on-close>
|
|
|
|
|
+ <el-form label-width="80px">
|
|
|
|
|
+ <el-form-item label="名称"><el-input v-model="editForm.label" /></el-form-item>
|
|
|
|
|
+ <el-form-item label="编码"><el-input v-model="editForm.value" /></el-form-item>
|
|
|
|
|
+ <el-form-item label="排序"><el-input-number v-model="editForm.orderNo" :min="1" controls-position="right" style="width:100%" /></el-form-item>
|
|
|
|
|
+ </el-form>
|
|
|
|
|
+ <template #footer>
|
|
|
|
|
+ <el-button @click="editDialogVisible = false">取消</el-button>
|
|
|
|
|
+ <el-button type="primary" :loading="editSaving" @click="saveEdit">保存</el-button>
|
|
|
|
|
+ </template>
|
|
|
|
|
+ </el-dialog>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ `,
|
|
|
|
|
+});
|
|
|
|
|
+
|
|
|
|
|
+export { DictDataTab };
|
|
|
|
|
+</script>
|
|
|
|
|
+
|
|
|
<style scoped lang="scss">
|
|
<style scoped lang="scss">
|
|
|
@import '/@/views/aidop/styles/aidop-demo.scss';
|
|
@import '/@/views/aidop/styles/aidop-demo.scss';
|
|
|
|
|
|
|
@@ -311,4 +664,13 @@ onMounted(async () => {
|
|
|
display: flex;
|
|
display: flex;
|
|
|
justify-content: flex-end;
|
|
justify-content: flex-end;
|
|
|
}
|
|
}
|
|
|
|
|
+
|
|
|
|
|
+.field-mapping-panel {
|
|
|
|
|
+ .empty-hint {
|
|
|
|
|
+ text-align: center;
|
|
|
|
|
+ color: #909399;
|
|
|
|
|
+ padding: 24px 0;
|
|
|
|
|
+ font-size: 13px;
|
|
|
|
|
+ }
|
|
|
|
|
+}
|
|
|
</style>
|
|
</style>
|