houyaf 3 years ago
parent
commit
3e7bd49ec2

+ 0 - 77
src/api/system/entCatApi.ts

@@ -1,77 +0,0 @@
-import apiRequest from '@/network/http/apiRequest'
-
-/**
- * 获取Ent Category分页
- * @param data
- * @returns
- */
-export function getEntCatByPage(data: any) {
-  return apiRequest({
-    url: '/ent/cat/page',
-    method: 'GET',
-    params: data,
-  })
-}
-
-/**
- * 获取Ent Category列表
- * @param data
- * @returns
- */
-export function getEntCatByList(data: any) {
-  return apiRequest({
-    url: '/ent/cat',
-    method: 'GET',
-    params: data,
-  })
-}
-
-/**
- * 根据Id获取Ent Category
- * @returns
- * @param id
- */
-export function getEntCatById(id: number) {
-  return apiRequest({
-    url: `/ent/cat/${id}`,
-    method: 'GET',
-  })
-}
-
-/**
- * 添加Ent Category
- * @param data
- * @returns
- */
-export function createEntCat(data: any) {
-  return apiRequest({
-    url: '/ent/cat/add',
-    method: 'post',
-    data,
-  })
-}
-
-/**
- * 更新Ent Category
- * @param data
- * @returns
- */
-export function updateEntCat(data: any) {
-  return apiRequest({
-    url: '/ent/cat/update',
-    method: 'PUT',
-    data,
-  })
-}
-
-/**
- * 删除Ent Type
- * @returns
- * @param id
- */
-export function deleteEntCatById(id: number) {
-  return apiRequest({
-    url: `/ent/cat/${id}`,
-    method: 'DELETE',
-  })
-}

+ 127 - 0
src/api/system/ocApi.ts

@@ -12,3 +12,130 @@ export function getOcByList(data: any) {
     params: data,
   })
 }
+
+/**
+ * 获取列表
+ * @param data
+ * @returns
+ */
+export function getOcByPage(data: any) {
+  return apiRequest({
+    url: '/oc/page',
+    method: 'GET',
+    params: data,
+  })
+}
+
+/**
+ * 获取管理员
+ * @param ocId
+ * @returns
+ */
+export function getOcAdmin(ocId: number) {
+  return apiRequest({
+    url: `/oc/getAdmin/${ocId}`,
+    method: 'GET',
+  })
+}
+
+/**
+ * 新增管理员
+ * @param data
+ * @returns
+ */
+export function createOcAdmin(data: any) {
+  return apiRequest({
+    url: '/oc/addAdmin',
+    method: 'POST',
+    data,
+  })
+}
+
+/**
+ * 更新管理员
+ * @param data
+ * @returns
+ */
+export function updateOcAdmin(data: any) {
+  return apiRequest({
+    url: '/oc/updateAdmin',
+    method: 'PUT',
+    data,
+  })
+}
+
+/**
+ * 重置管理员密码
+ * @returns
+ * @param ocId
+ * @param adminId
+ */
+export function resetAdminPwd(ocId: number, adminId: number) {
+  return apiRequest({
+    url: `/oc/resetAdminPwd/${ocId}/${adminId}`,
+    method: 'PUT',
+  })
+}
+
+/**
+ * 根据ID获取单位信息
+ * @returns
+ * @param ocId
+ */
+export function getOcById(ocId: number) {
+  return apiRequest({
+    url: `/oc/${ocId}`,
+    method: 'GET',
+  })
+}
+
+/**
+ * 添加单位
+ * @param data
+ * @returns
+ */
+export function createOc(data: any) {
+  return apiRequest({
+    url: '/oc/add',
+    method: 'POST',
+    data,
+  })
+}
+
+/**
+ * 更新单位
+ * @param data
+ * @returns
+ */
+export function updateOc(data: any) {
+  return apiRequest({
+    url: '/oc/update',
+    method: 'PUT',
+    data,
+  })
+}
+
+/**
+ * 删除单位
+ * @returns
+ * @param ocId
+ */
+export function deleteOcById(ocId: number) {
+  return apiRequest({
+    url: `/oc/${ocId}`,
+    method: 'DELETE',
+  })
+}
+
+/**
+ * 更新单位状态
+ * @returns
+ * @param ocId
+ * @param status
+ */
+export function updateOcStatus(ocId: number, status: number) {
+  return apiRequest({
+    url: `/oc/updateStatus/${ocId}/${status}`,
+    method: 'PUT',
+  })
+}

+ 91 - 0
src/api/system/ocCatApi.ts

@@ -0,0 +1,91 @@
+import apiRequest from '@/network/http/apiRequest'
+
+/**
+ * 获取Oc Category分页
+ * @param data
+ * @returns
+ */
+export function getOcCatByPage(data: any) {
+  return apiRequest({
+    url: '/oc/cat/page',
+    method: 'GET',
+    params: data,
+  })
+}
+
+/**
+ * 获取Oc Category列表
+ * @param data
+ * @returns
+ */
+export function getOcCatByList(data: any) {
+  return apiRequest({
+    url: '/oc/cat',
+    method: 'GET',
+    params: data,
+  })
+}
+
+/**
+ * 根据Id获取OC Category
+ * @returns
+ * @param ocTypeId
+ * @param ocCatId
+ */
+export function getOcCatById(ocTypeId: number, ocCatId: number) {
+  return apiRequest({
+    url: `/oc/cat/${ocTypeId}/${ocCatId}`,
+    method: 'GET',
+  })
+}
+
+/**
+ * 根据Id获取OC Category
+ * @returns
+ * @param ocTypeId
+ */
+export function getOcCatListById(ocTypeId: number) {
+  return apiRequest({
+    url: `/oc/cat/${ocTypeId}`,
+    method: 'GET',
+  })
+}
+
+/**
+ * 添加Oc Category
+ * @param data
+ * @returns
+ */
+export function createOcCat(data: any) {
+  return apiRequest({
+    url: '/oc/cat/add',
+    method: 'post',
+    data,
+  })
+}
+
+/**
+ * 更新Oc Category
+ * @param data
+ * @returns
+ */
+export function updateOcCat(data: any) {
+  return apiRequest({
+    url: '/oc/cat/update',
+    method: 'PUT',
+    data,
+  })
+}
+
+/**
+ * 删除Oc Type
+ * @returns
+ * @param ocTypeId
+ * @param ocCatId
+ */
+export function deleteOcCatById(ocTypeId: number, ocCatId: number) {
+  return apiRequest({
+    url: `/oc/cat/${ocTypeId}/${ocCatId}`,
+    method: 'DELETE',
+  })
+}

+ 65 - 0
src/api/system/ocTypeApi.ts

@@ -0,0 +1,65 @@
+import apiRequest from '@/network/http/apiRequest'
+
+/**
+ * 获取Oc Type列表
+ * @param data
+ * @returns
+ */
+export function getOcTypeByList(data: any) {
+  return apiRequest({
+    url: '/oc/type',
+    method: 'GET',
+    params: data,
+  })
+}
+
+/**
+ * 根据Id获取OC Type
+ * @returns
+ * @param ocTypeId
+ * @param ocTypeId
+ */
+export function getOcTypeById(ocTypeId: number) {
+  return apiRequest({
+    url: `/oc/type/${ocTypeId}`,
+    method: 'GET',
+  })
+}
+
+/**
+ * 添加Oc Type
+ * @param data
+ * @returns
+ */
+export function createOcType(data: any) {
+  return apiRequest({
+    url: '/oc/type/add',
+    method: 'POST',
+    data,
+  })
+}
+
+/**
+ * 更新Oc Type
+ * @param data
+ * @returns
+ */
+export function updateOcType(data: any) {
+  return apiRequest({
+    url: '/oc/type/update',
+    method: 'PUT',
+    data,
+  })
+}
+
+/**
+ * 删除Oc Type
+ * @returns
+ * @param ocTypeId
+ */
+export function deleteOcTypeById(ocTypeId: number) {
+  return apiRequest({
+    url: `/oc/type/${ocTypeId}`,
+    method: 'DELETE',
+  })
+}

+ 1 - 0
src/router/index.ts

@@ -49,6 +49,7 @@ router.beforeEach(async (to, from, next) => {
         })
         iframeStore.generateList(iframeList)
       }
+
       // 导航栏如果不是 single 模式,则需要根据 path 定位主导航的选中状态
       settingsStore.settings.menu.menuMode !== 'single' && menuStore.setActived(to.path)
       // 如果已登录状态下,进入登录页会强制跳转到主页

+ 7 - 15
src/router/modules/system.ts

@@ -11,7 +11,7 @@ const routes: RouteRecordRaw[] = [
     meta: {
       title: '组织管理',
       i18n: 'system.company',
-      icon: 'ic:twotone-double-arrow',
+      icon: 'ep:office-building',
     },
     children: [
       {
@@ -47,7 +47,7 @@ const routes: RouteRecordRaw[] = [
     name: 'system_role',
     meta: {
       title: '角色管理',
-      icon: 'bx:bxs-component',
+      icon: 'ep:pointer',
     },
     children: [
       {
@@ -70,23 +70,15 @@ const routes: RouteRecordRaw[] = [
     name: 'system-setting',
     meta: {
       title: '系统配置',
-      icon: 'ic:twotone-double-arrow',
+      icon: 'ep:setting',
     },
     children: [
       {
-        path: 'ent-cat',
-        name: 'ent_cat',
-        component: () => import('@/views/system/setting/ent_cat/index.vue'),
+        path: 'oc-cat',
+        name: 'oc_cat',
+        component: () => import('@/views/system/setting/oc_cat/index.vue'),
         meta: {
-          title: '企业分类',
-        },
-      },
-      {
-        path: 'partner-cat',
-        name: 'partner_cat',
-        component: () => import('@/views/system/setting/partner_cat/index.vue'),
-        meta: {
-          title: '合作伙伴分类',
+          title: '客户分类',
         },
       },
       {

+ 37 - 24
src/views/system/setting/partner_cat/components/PartnerCat.vue → src/views/customer/components/Oc.vue

@@ -3,19 +3,23 @@ meta:
   enabled: false
 </route>
 
-<script lang="ts" setup>
+<script lang="ts" setup name="Oc">
 import { ElMessage } from 'element-plus'
 import type { FormInstance, FormRules } from 'element-plus'
-import { createPartnerCat, getPartnerCatById, updatePartnerCat } from '@/api/system/partnerCatApi'
+import { createOc, getOcById, updateOc } from '@/api/system/ocApi'
+import OcCatSelector from '@/views/customer/components/OcCatSelector.vue'
 const emit = defineEmits(['success'])
 
 const formRef = ref<FormInstance>()
 const formRules = ref<FormRules>({
-  partnerCatTitle: [
+  ocName: [
     { required: true, message: '请输入标题', trigger: 'blur' },
   ],
-  partnerCatDesc: [
-    { required: false, message: '请输入描述', trigger: 'blur' },
+  ocTypeId: [
+    { required: true, message: '请输入类型', trigger: 'blur' },
+  ],
+  ocCatId: [
+    { required: true, message: '请输入分类', trigger: 'blur' },
   ],
 })
 
@@ -24,18 +28,20 @@ const state = reactive({
   dialogVisible: false,
   loading: false,
   formData: {
-    partnerCatId: 0,
-    partnerCatTitle: '',
-    partnerCatDesc: '',
+    ocId: 0,
+    ocName: '',
+    ocTypeId: 0,
+    ocCatId: 0,
+    ocRemark: '',
   },
   actionType: 1,
 })
 
 onMounted(() => {})
 
-const getData = async (partnerCatId: number) => {
+const getData = async (ocId: number) => {
   state.loading = true
-  const { data } = await getPartnerCatById(partnerCatId)
+  const { data } = await getOcById(ocId)
   state.loading = false
   state.formData = data
 }
@@ -44,12 +50,12 @@ function onSubmit() {
   formRef.value && formRef.value.validate(async (valid) => {
     if (valid) {
       if (state.actionType === 1) {
-        await createPartnerCat(state.formData)
+        await createOc(state.formData)
         state.dialogVisible = false
         emit('success')
       }
       else {
-        await updatePartnerCat(state.formData)
+        await updateOc(state.formData)
         state.dialogVisible = false
         emit('success')
       }
@@ -67,25 +73,28 @@ function onCancel() {
 
 function resetFormData() {
   state.formData = {
-    partnerCatId: 0,
-    partnerCatTitle: '',
-    partnerCatDesc: '',
+    ocId: 0,
+    ocName: '',
+    ocTypeId: 0,
+    ocCatId: 0,
+    ocRemark: '',
   }
 }
 
 defineExpose({
-  showAddModel() {
+  showAddModel(ocTypeId: number){
     resetFormData()
-    state.title = '新增'
+    state.title = '新增岗位'
     state.actionType = 1
+    state.formData.ocTypeId = ocTypeId
     state.dialogVisible = true
   },
-  showEditModel(partnerCatId: number) {
+  showEditModel(ocId: number) {
     resetFormData()
-    state.title = '编辑'
+    state.title = '编辑岗位'
     state.actionType = 2
     state.dialogVisible = true
-    getData(partnerCatId)
+    getData(ocId)
   },
 
 })
@@ -94,12 +103,16 @@ defineExpose({
 <template>
   <el-drawer v-model="state.dialogVisible" :title="state.title" width="600px" :close-on-click-modal="false" append-to-body destroy-on-close>
     <el-form ref="formRef" :model="state.formData" :rules="formRules" label-width="120px" label-suffix=":">
-      <el-form-item label="分类名称" prop="partnerCatTitle">
-        <el-input v-model="state.formData.partnerCatTitle" placeholder="请输入标题" />
+      <el-form-item label="单位名称" prop="ocName">
+        <el-input v-model="state.formData.positionName" placeholder="请输入标题" />
+      </el-form-item>
+
+      <el-form-item label="分类" prop="ocName">
+        <OcCatSelector v-model="state.formData.ocCatId" :oc-type-id="state.formData.ocTypeId" placeholder="请输入标题" />
       </el-form-item>
 
-      <el-form-item label="简要说明" prop="partnerCatDesc">
-        <el-input v-model="state.formData.partnerCatDesc" type="textarea" rows="10" placeholder="请输入简要说明" />
+      <el-form-item label="备注" prop="ocRemark">
+        <el-input v-model="state.formData.ocRemark" type="textarea" rows="10" placeholder="请输入标题" />
       </el-form-item>
     </el-form>
 

+ 0 - 0
src/views/customer/components/OcAdmin.vue


+ 50 - 0
src/views/customer/components/OcCatSelector.vue

@@ -0,0 +1,50 @@
+<script lang="ts" setup name="OcCatSelector">
+import { getOcCatListById } from '@/api/system/ocCatApi'
+const props = withDefaults(defineProps<{
+  ocTypeId: number
+  modelValue: number
+}>(), {
+  ocTypeId: 0,
+  modelValue: 0,
+})
+const emit = defineEmits(['update:modelValue'])
+interface OcCat {
+  ocCatId: number
+  ocCatTitle: string
+}
+const ocCatId = computed({
+  get: () => {
+    return props.modelValue
+  },
+  set: (val) => {
+    emit('update:modelValue', val)
+  },
+})
+const state = reactive({
+  loading: false,
+  dataList: [] as OcCat[],
+})
+
+const getData = async () => {
+  state.loading = true
+  const ocTypeId = props.ocTypeId
+  const { data } = await getOcCatListById(ocTypeId)
+  state.loading = false
+  state.dataList = data
+}
+onMounted(() => {
+  getData ()
+})
+</script>
+
+<template>
+  <el-select v-model="ocCatId" v-loading="state.loading" style="width: 100%" filterable placeholder="请选择分类" value-key="ocCatId">
+    <el-option key="0" label="请选择" :value="0" disabled />
+    <el-option
+      v-for="item in state.dataList"
+      :key="item.ocCatId"
+      :label="item.ocCatTitle"
+      :value="item.ocCatId"
+    />
+  </el-select>
+</template>

+ 47 - 0
src/views/customer/components/OcTypeSelector.vue

@@ -0,0 +1,47 @@
+<script lang="ts" setup name="OcTypeSelector">
+import { getOcTypeByList } from '@/api/system/ocTypeApi'
+const props = withDefaults(defineProps<{
+  modelValue: number
+}>(), {
+  modelValue: 0,
+})
+const emit = defineEmits(['update:modelValue'])
+interface OcType {
+  ocTypeId: number
+  ocTypeTitle: string
+}
+const ocTypeId = computed({
+  get: () => {
+    return props.modelValue
+  },
+  set: (val) => {
+    emit('update:modelValue', val)
+  },
+})
+const state = reactive({
+  loading: false,
+  dataList: [] as OcType[],
+})
+
+const getData = async () => {
+  state.loading = true
+  const { data } = await getOcTypeByList({})
+  state.loading = false
+  state.dataList = data
+}
+onMounted(() => {
+  getData ()
+})
+</script>
+
+<template>
+  <el-select v-model="ocTypeId" v-loading="state.loading" style="width: 100%" filterable placeholder="请选择分类" value-key="ocTypeId">
+    <el-option key="0" label="请选择" :value="0" disabled />
+    <el-option
+      v-for="item in state.dataList"
+      :key="item.ocTypeId"
+      :label="item.ocTypeTitle"
+      :value="item.ocTypeId"
+    />
+  </el-select>
+</template>

+ 174 - 21
src/views/customer/ent/index.vue

@@ -1,27 +1,180 @@
-<route lang="yaml">
-meta:
-  enabled: false
-</route>
-
-<script lang="ts" setup>
-const value = ref(true)
-const value1 = ref(true)
-const value2 = ref(true)
-const value3 = ref(false)
+<script lang="ts" setup name="positionIndex">
+import { ElMessage, ElMessageBox } from 'element-plus'
+import OcComponent from '../components/Oc.vue'
+import { deleteOcById, getOcByList } from '@/api/system/ocApi'
+
+const state = reactive({
+  loading: false,
+  // 表格是否自适应高度
+  tableAutoHeight: false,
+  // 搜索
+  search: {
+    ocTypeId: 2,
+    keywords: '',
+  },
+  // 列表数据
+  dataList: [],
+})
+
+const ocRef = ref()
+
+const getDataList = async () => {
+  state.loading = true
+  const { data } = await getOcByList(state.search)
+  state.dataList = data
+  state.loading = false
+}
+
+onMounted(() => {
+  getDataList()
+})
+
+function onSearch() {
+  getDataList()
+}
+
+function onOcAdd() {
+  const ocTypeId = state.search.ocTypeId
+  ocRef.value.showAddModel(ocTypeId)
+}
+
+function onOcEdit(row: any) {
+  const ocId = row.ocId
+  ocRef.value.showEditModel(ocId)
+}
+
+function onOcDel(row: any) {
+  ElMessageBox.confirm(`确认删除「${row.ocName}」吗?`, '确认信息').then(async () => {
+    await deleteOcById(row.ocId)
+    await getDataList()
+    ElMessage.success({
+      message: '删除成功',
+      center: true,
+    })
+  }).catch(() => {})
+}
+
+const adminRef = ref()
+// 添加管理员账号
+function onAdminAdd(row: any) {
+  const { ocId } = row
+  adminRef.value.showAddModel(ocId)
+}
+
+// 修改管理员账号
+function onAdminEdit(row: any) {
+  const { ocId } = row
+  adminRef.value.showEditModel(ocId)
+}
+
 </script>
 
 <template>
-  <div>
-    <page-header title="开关" />
-    <page-main title="基础用法" class="demo">
-      <el-switch v-model="value" active-color="#13ce66" inactive-color="#ff4949" />
-    </page-main>
-    <page-main title="文字描述" class="demo">
-      <el-switch v-model="value1" active-text="按月付费" inactive-text="按年付费" />
-    </page-main>
-    <page-main title="禁用状态" class="demo">
-      <el-switch v-model="value2" disabled style="margin-right: 10px;" />
-      <el-switch v-model="value3" disabled />
+  <div :class="{ 'absolute-container': state.tableAutoHeight }">
+    <page-header title="企业单位管理">
+    </page-header>
+
+    <page-main>
+
+      <tool-bar>
+        <template #right>
+          <el-input v-model="state.search.keywords" placeholder="请输入名称,支持模糊查询" style="padding-right: 10px;" clearable />
+          <el-button type="primary" @click="onSearch">
+            <template #icon>
+              <el-icon>
+                <svg-icon name="i-ep:search" />
+              </el-icon>
+            </template>
+          </el-button>
+
+          <el-button size="default" @click.stop="onOcAdd">
+            <template #icon>
+              <el-icon>
+                <svg-icon name="i-ep:plus" />
+              </el-icon>
+            </template>
+            公司单位
+          </el-button>
+        </template>
+      </tool-bar>
+      <el-table v-loading="state.loading" class="list-table" :data="state.dataList" size="small" border stripe highlight-current-row height="100%">
+        <el-table-column type="index" label="序号" width="60" header-align="center" align="center" />
+
+        <el-table-column prop="ocName" label="名称" header-align="center" align="center" width="200">
+          <template #default="scope">
+            <span>{{ scope.row.ocName }}</span>
+          </template>
+        </el-table-column>
+
+        <el-table-column prop="ocTypeId" label="类型">
+          <template #default="scope">
+            <span>{{ scope.row.ocTypeId }}</span>
+          </template>
+        </el-table-column>
+
+        <el-table-column prop="ocCatId" label="分类">
+          <template #default="scope">scope.
+            <span>{{ scope.row.ocCatTitle }}</span>
+          </template>
+        </el-table-column>
+
+        <el-table-column label="管理员账号" width="250" align="center" header-align="center">
+          <template #default="scope">
+            <div>
+              <el-tag v-if="scope.row.adminId > 0" @click="onAdminEdit(scope.row)">
+                {{ scope.row.adminName }}
+              </el-tag>
+              <el-tag v-else @click="onAdminAdd(scope.row)">
+                <i class="el-icon-plus" /> 管理员账号
+              </el-tag>
+            </div>
+          </template>
+        </el-table-column>
+
+        <el-table-column prop="ocRemark" label="备注">
+          <template #default="scope">
+            <span>{{ scope.row.ocRemark }}</span>
+          </template>
+        </el-table-column>
+
+        <el-table-column label="操作" width="250" align="center" fixed="right">
+          <template #default="scope">
+            <el-button type="primary" size="small" plain @click="onOcEdit(scope.row)">
+              编辑
+            </el-button>
+            <el-button v-if="!scope.row.isFixed" type="danger" size="small" plain @click="onOcDel(scope.row)">
+              删除
+            </el-button>
+          </template>
+        </el-table-column>
+      </el-table>
     </page-main>
+    <OcComponent ref="ocRef" @success="getDataList" />
   </div>
 </template>
+
+<style lang="scss" scoped>
+.absolute-container {
+  position: absolute;
+  width: 100%;
+  height: 100%;
+  display: flex;
+  flex-direction: column;
+
+  .page-header {
+    margin-bottom: 0;
+  }
+
+  .page-main {
+    // 让 page-main 的高度自适应
+    flex: 1;
+    overflow: auto;
+    display: flex;
+    flex-direction: column;
+
+    .search-container {
+      margin-bottom: 0;
+    }
+  }
+}
+</style>

+ 0 - 121
src/views/system/setting/ent_cat/index.vue

@@ -1,121 +0,0 @@
-<script lang="ts" setup name="EntCatIndex">
-import { ElMessage, ElMessageBox } from 'element-plus'
-import EntCat from './components/EntCat.vue'
-import { deleteEntCatById, getEntCatByList } from '@/api/system/entCatApi'
-
-const state = reactive({
-  loading: false,
-  // 表格是否自适应高度
-  tableAutoHeight: false,
-  // 搜索
-  search: {
-    keywords: '',
-  },
-  // 列表数据
-  dataList: [],
-})
-
-const entCatRef = ref()
-
-const getDataList = async () => {
-  state.loading = true
-  const { data } = await getEntCatByList({})
-  state.dataList = data
-  state.loading = false
-}
-
-onMounted(() => {
-  getDataList()
-})
-
-function onEntCatAdd() {
-  entCatRef.value.showAddModel()
-}
-
-function onEntCatEdit(row: any) {
-  const entCatId = row.entCatId
-  entCatRef.value.showEditModel(entCatId)
-}
-
-function onEntCatDel(row: any) {
-  ElMessageBox.confirm(`确认删除「${row.entCatTitle}」吗?`, '确认信息').then(async () => {
-    await deleteEntCatById(row.entCatId)
-    await getDataList()
-    ElMessage.success({
-      message: '删除成功',
-      center: true,
-    })
-  }).catch(() => {})
-}
-</script>
-
-<template>
-  <div :class="{ 'absolute-container': state.tableAutoHeight }">
-    <page-header title="企业分类">
-      <template #content>
-        <div>
-          系统支持基于企业客户的分类管理
-        </div>
-      </template>
-
-      <el-button-group>
-        <el-button type="primary" size="large" @click="onEntCatAdd">
-          <template #icon>
-            <el-icon>
-              <svg-icon name="ep:plus" />
-            </el-icon>
-          </template>
-          新增
-        </el-button>
-      </el-button-group>
-    </page-header>
-
-    <page-main>
-      <el-table v-loading="state.loading" class="list-table" :data="state.dataList" border stripe highlight-current-row height="100%">
-        <el-table-column type="index" label="序号" width="60" header-align="center" align="center" />
-
-        <el-table-column prop="entCatTitle" label="名称" header-align="center" align="center" width="200" />
-
-        <el-table-column prop="entCatDesc" label="说明" />
-
-        <el-table-column label="操作" width="250" align="center" fixed="right">
-          <template #default="scope">
-            <el-button type="primary" size="small" plain @click="onEntCatEdit(scope.row)">
-              编辑
-            </el-button>
-            <el-button v-if="!scope.row.isFixed" type="danger" size="small" plain @click="onEntCatDel(scope.row)">
-              删除
-            </el-button>
-          </template>
-        </el-table-column>
-      </el-table>
-    </page-main>
-    <EntCat ref="entCatRef" @success="getDataList" />
-  </div>
-</template>
-
-<style lang="scss" scoped>
-.absolute-container {
-  position: absolute;
-  width: 100%;
-  height: 100%;
-  display: flex;
-  flex-direction: column;
-
-  .page-header {
-    margin-bottom: 0;
-  }
-
-  .page-main {
-    // 让 page-main 的高度自适应
-    flex: 1;
-    overflow: auto;
-    display: flex;
-    flex-direction: column;
-
-    .search-container {
-      margin-bottom: 0;
-    }
-  }
-}
-</style>

+ 23 - 20
src/views/system/setting/ent_cat/components/EntCat.vue → src/views/system/setting/oc_cat/components/OcCat.vue

@@ -6,15 +6,15 @@ meta:
 <script lang="ts" setup>
 import { ElMessage } from 'element-plus'
 import type { FormInstance, FormRules } from 'element-plus'
-import { createEntCat, getEntCatById, updateEntCat } from '@/api/system/entCatApi'
+import { createOcCat, getOcCatById, updateOcCat } from '@/api/system/ocCatApi'
 const emit = defineEmits(['success'])
 
 const formRef = ref<FormInstance>()
 const formRules = ref<FormRules>({
-  entCatTitle: [
+  ocCatTitle: [
     { required: true, message: '请输入标题', trigger: 'blur' },
   ],
-  entCatDesc: [
+  ocCatDesc: [
     { required: false, message: '请输入描述', trigger: 'blur' },
   ],
 })
@@ -24,18 +24,19 @@ const state = reactive({
   dialogVisible: false,
   loading: false,
   formData: {
-    entCatId: 0,
-    entCatTitle: '',
-    entCatDesc: '',
+    ocTypeId: 0,
+    ocCatId: 0,
+    ocCatTitle: '',
+    ocCatDesc: '',
   },
   actionType: 1,
 })
 
 onMounted(() => {})
 
-const getData = async (entCatId: number) => {
+const getData = async (ocTypeId: number, ocCatId: number) => {
   state.loading = true
-  const { data } = await getEntCatById(entCatId)
+  const { data } = await getOcCatById(ocTypeId, ocCatId)
   state.loading = false
   state.formData = data
 }
@@ -44,12 +45,12 @@ function onSubmit() {
   formRef.value && formRef.value.validate(async (valid) => {
     if (valid) {
       if (state.actionType === 1) {
-        await createEntCat(state.formData)
+        await createOcCat(state.formData)
         state.dialogVisible = false
         emit('success')
       }
       else {
-        await updateEntCat(state.formData)
+        await updateOcCat(state.formData)
         state.dialogVisible = false
         emit('success')
       }
@@ -67,25 +68,27 @@ function onCancel() {
 
 function resetFormData() {
   state.formData = {
-    entCatId: 0,
-    entCatTitle: '',
-    entCatDesc: '',
+    ocTypeId: 0,
+    ocCatId: 0,
+    ocCatTitle: '',
+    ocCatDesc: '',
   }
 }
 
 defineExpose({
-  showAddModel() {
+  showAddModel(ocTypeId: number) {
     resetFormData()
     state.title = '新增'
     state.actionType = 1
+    state.formData.ocTypeId = ocTypeId
     state.dialogVisible = true
   },
-  showEditModel(entCatId: number) {
+  showEditModel(ocTypeId: number, ocCatId: number) {
     resetFormData()
     state.title = '编辑'
     state.actionType = 2
     state.dialogVisible = true
-    getData(entCatId)
+    getData(ocTypeId, ocCatId)
   },
 
 })
@@ -94,12 +97,12 @@ defineExpose({
 <template>
   <el-drawer v-model="state.dialogVisible" :title="state.title" width="600px" :close-on-click-modal="false" append-to-body destroy-on-close>
     <el-form ref="formRef" :model="state.formData" :rules="formRules" label-width="120px" label-suffix=":">
-      <el-form-item label="分类名称" prop="entCatTitle">
-        <el-input v-model="state.formData.entCatTitle" placeholder="请输入标题" />
+      <el-form-item label="分类名称" prop="ocCatTitle">
+        <el-input v-model="state.formData.ocCatTitle" placeholder="请输入标题" />
       </el-form-item>
 
-      <el-form-item label="简要说明" prop="entCatDesc">
-        <el-input v-model="state.formData.entCatDesc" type="textarea" rows="10" placeholder="请输入简要说明" />
+      <el-form-item label="简要说明" prop="ocCatDesc">
+        <el-input v-model="state.formData.ocCatDesc" type="textarea" rows="10" placeholder="请输入简要说明" />
       </el-form-item>
     </el-form>
 

+ 279 - 0
src/views/system/setting/oc_cat/index.vue

@@ -0,0 +1,279 @@
+<script lang="ts" setup name="oc_cat_List">
+import { ElMessage, ElMessageBox } from 'element-plus'
+import OcCatComponent from './components/OcCat.vue'
+
+import { getOcTypeByList } from '@/api/system/ocTypeApi'
+import { deleteOcCatById, getOcCatListById } from '@/api/system/ocCatApi'
+
+interface TreeNode {
+  label: string
+  isLeaf: boolean
+  ocTypeId: number
+  children?: TreeNode[]
+}
+
+interface Object {
+  modelId: number
+  objectId: number
+  objectTitle: string
+  objectCode: string
+  comment: string
+}
+
+const state = reactive({
+  loading: false,
+  keywords: '',
+  treeData: [] as TreeNode[],
+  curOcTypeId: 0,
+  ocCatList: [] as Object[],
+  dialogState: 1,
+  search: {
+    keywords: '',
+  },
+})
+
+const leftTreeRef = ref()
+const getOcCatData = async () => {
+  const curOcTypeId = state.curOcTypeId
+  if (curOcTypeId > 0) {
+    state.loading = true
+    const { data } = await getOcCatListById(curOcTypeId)
+    state.ocCatList = data
+    state.loading = false
+  }
+}
+
+const getOcTypeData = async () => {
+  const { data } = await getOcTypeByList({})
+  const children: TreeNode[] = []
+  data.forEach((item: any) => {
+    return children.push({
+      label: item.ocTypeTitle,
+      ocTypeId: item.ocTypeId,
+      isLeaf: true,
+    })
+  })
+  state.treeData = [
+    {
+      label: '客户类型',
+      isLeaf: false,
+      ocTypeId: -1,
+      children,
+    },
+  ]
+
+  if (data && data.length > 0) {
+    state.curOcTypeId = data[0].ocTypeId
+    nextTick(() => {
+      leftTreeRef.value.setCurrentKey(data[0].ocTypeId)
+    })
+    await getOcCatData()
+  }
+}
+
+onMounted(() => {
+  getOcTypeData()
+})
+
+// 模型选择
+const onTreeNodeClick = (node: TreeNode) => {
+  if (node.isLeaf) {
+    state.curOcTypeId = node.ocTypeId
+    getOcCatData()
+  }
+}
+
+const ocCatTableRef = ref()
+const ocCatRef = ref()
+
+// 检索对象
+const onSearch = () => {
+  getOcCatData()
+}
+
+// 新增
+const onOcCatAdd = () => {
+  const ocTypeId = state.curOcTypeId
+  if (ocTypeId > 0) {
+    ocCatRef.value.showAddModel(ocTypeId)
+  }
+}
+
+// 编辑
+const onOcCatEdit = (row: { ocCatId: number }) => {
+  const ocTypeId = state.curOcTypeId
+  if (ocTypeId > 0) {
+    ocCatRef.value.showEditModel(ocTypeId, row.ocCatId)
+  }
+}
+
+// 删除对象
+const onOcCatDelete = (row: any) => {
+  const { ocTypeId, ocCatId, ocCatTitle } = row
+  ElMessageBox.confirm(`确认删除「${ocCatTitle}」吗?`, '确认信息').then(async () => {
+    await deleteOcCatById(ocTypeId, ocCatId)
+    await getOcCatData()
+    ElMessage.success({
+      message: '删除成功',
+      center: true,
+    })
+  })
+}
+</script>
+
+<template>
+  <div class="absolute-container">
+    <tool-header title="客户分类" />
+
+    <div class="page-main">
+      <LayoutContainer left-side-width="250px" hide-left-side-toggle>
+        <template #leftSide>
+          <el-scrollbar class="tree">
+            <ElTree ref="leftTreeRef" :data="state.treeData" default-expand-all node-key="modelId" @node-click="onTreeNodeClick">
+              <template #default="{ node, data }">
+                <div class="custom-tree-node">
+                  <div class="label" :title="node.label">
+                    <el-icon v-if="data.isLeaf" size="16px" style="margin-right: 5px;">
+                      <svg-icon name="ep:office-building" />
+                    </el-icon>
+                    <div class="text">
+                      {{ data.label }}
+                    </div>
+                  </div>
+                </div>
+              </template>
+            </ElTree>
+          </el-scrollbar>
+        </template>
+
+        <div class="container">
+          <tool-bar>
+            <template #right>
+              <el-input v-model="state.search.keywords" placeholder="请输入名称,支持模糊查询" style="padding-right: 10px;" clearable />
+              <el-button type="primary" @click="onSearch">
+                <template #icon>
+                  <el-icon>
+                    <svg-icon name="i-ep:search" />
+                  </el-icon>
+                </template>
+              </el-button>
+
+              <el-button size="default" @click.stop="onOcCatAdd">
+                <template #icon>
+                  <el-icon>
+                    <svg-icon name="i-ep:plus" />
+                  </el-icon>
+                </template>
+                客户分类
+              </el-button>
+            </template>
+          </tool-bar>
+
+          <el-table ref="ocCatTableRef" v-loading="state.loading" class="list-table" :data="state.ocCatList" size="small" border stripe highlight-current-row height="100%">
+            <el-table-column type="index" label="序号" header-align="center" align="center" width="60" />
+
+            <el-table-column prop="ocCatTitle" label="名称" header-align="center" align="center" width="200">
+              <template #default="scope">
+                <span>{{ scope.row.ocCatTitle }}</span>
+              </template>
+            </el-table-column>
+
+            <el-table-column prop="ocCatDesc" label="说明" header-align="center" align="left">
+              <template #default="scope">
+                <span>{{ scope.row.ocCatDesc }}</span>
+              </template>
+            </el-table-column>
+
+            <el-table-column label="操作" header-align="center" align="center" width="220">
+              <template #default="scope">
+                <el-button type="warning" size="small" plain @click="onOcCatEdit(scope.row)">编辑</el-button>
+                <el-button v-if="scope.row.isFixed <= 0" type="danger" size="small" plain @click="onOcCatDelete(scope.row)">删除</el-button>
+              </template>
+            </el-table-column>
+          </el-table>
+        </div>
+      </LayoutContainer>
+    </div>
+    <OcCatComponent ref="ocCatRef" @success="getOcCatData" />
+  </div>
+</template>
+
+<style lang="scss" scoped>
+.container {
+  height: 100%;
+  display: flex;
+  flex-direction: column;
+}
+
+.absolute-container {
+  :deep(.left-side) {
+    display: flex;
+    flex-direction: column;
+    height: 100%;
+
+    .btns {
+      display: inline-flex;
+      width: 100%;
+      margin-bottom: var(--container-padding);
+
+      .add {
+        width: 100%;
+      }
+    }
+
+    .tree {
+      flex: 1;
+      overflow-y: auto;
+
+      .el-tree {
+        .el-tree-node__content {
+          height: 40px;
+        }
+
+        .is-current > .el-tree-node__content {
+          background-color: var(--el-color-primary-light-9);
+        }
+
+        .custom-tree-node {
+          flex: 1;
+          position: relative;
+          width: 0;
+          height: 100%;
+          display: flex;
+          flex-direction: column;
+          justify-content: center;
+
+          .label {
+            display: inline-flex;
+            align-items: center;
+            width: calc(100% - 10px);
+            color: var(--el-text-color-primary);
+
+            .text {
+              @include text-overflow;
+            }
+          }
+
+          &:hover {
+            .actions {
+              display: block;
+            }
+          }
+
+          .actions {
+            display: none;
+            position: absolute;
+            right: 10px;
+            top: 50%;
+            transform: translateY(-50%);
+
+            .el-button {
+              padding: 5px 8px;
+            }
+          }
+        }
+      }
+    }
+  }
+}
+</style>

+ 0 - 129
src/views/system/setting/partner_cat/index.vue

@@ -1,129 +0,0 @@
-<script lang="ts" setup name="PartnerCatIndex">
-import { ElMessage, ElMessageBox } from 'element-plus'
-import PartnerCat from './components/PartnerCat.vue'
-import { deletePartnerCatById, getPartnerCatByList } from '@/api/system/partnerCatApi'
-
-const state = reactive({
-  loading: false,
-  // 表格是否自适应高度
-  tableAutoHeight: false,
-  // 搜索
-  search: {
-    keywords: '',
-  },
-  // 列表数据
-  dataList: [],
-})
-
-const partnerCatRef = ref()
-
-const getDataList = async () => {
-  state.loading = true
-  const { data } = await getPartnerCatByList({})
-  state.dataList = data
-  state.loading = false
-}
-
-onMounted(() => {
-  getDataList()
-})
-
-function onPartnerCatAdd() {
-  partnerCatRef.value.showAddModel()
-}
-
-function onPartnerCatEdit(row: any) {
-  const partnerCatId = row.partnerCatId
-  partnerCatRef.value.showEditModel(partnerCatId)
-}
-
-function onPartnerCatDel(row: any) {
-  ElMessageBox.confirm(`确认删除「${row.partnerCatTitle}」吗?`, '确认信息').then(async () => {
-    await deletePartnerCatById(row.partnerCatId)
-    await getDataList()
-    ElMessage.success({
-      message: '删除成功',
-      center: true,
-    })
-  }).catch(() => {})
-}
-</script>
-
-<template>
-  <div :class="{ 'absolute-container': state.tableAutoHeight }">
-    <page-header title="合作伙伴分类">
-      <template #content>
-        <div>
-          系统支持基于合作伙伴的分类管理
-        </div>
-      </template>
-
-      <el-button-group>
-        <el-button type="primary" size="large" @click="onPartnerCatAdd">
-          <template #icon>
-            <el-icon>
-              <svg-icon name="ep:plus" />
-            </el-icon>
-          </template>
-          新增
-        </el-button>
-      </el-button-group>
-    </page-header>
-
-    <page-main>
-      <el-table v-loading="state.loading" class="list-table" :data="state.dataList" border stripe highlight-current-row height="100%">
-        <el-table-column type="index" label="序号" width="60" header-align="center" align="center" />
-
-        <el-table-column prop="partnerCatTitle" label="名称" header-align="center" align="center" width="200">
-          <template #default="scope">
-            <span>{{ scope.row.partnerCatTitle }}</span>
-          </template>
-        </el-table-column>
-
-        <el-table-column prop="partnerCatDesc" label="说明">
-          <template #default="scope">
-            <span>{{ scope.row.partnerCatDesc }}</span>
-          </template>
-        </el-table-column>
-
-        <el-table-column label="操作" width="200" align="center" fixed="right">
-          <template #default="scope">
-            <el-button type="primary" size="small" plain @click="onPartnerCatEdit(scope.row)">
-              编辑
-            </el-button>
-            <el-button v-if="!scope.row.isFixed" type="danger" size="small" plain @click="onPartnerCatDel(scope.row)">
-              删除
-            </el-button>
-          </template>
-        </el-table-column>
-      </el-table>
-    </page-main>
-    <PartnerCat ref="partnerCatRef" @success="getDataList" />
-  </div>
-</template>
-
-<style lang="scss" scoped>
-.absolute-container {
-  position: absolute;
-  width: 100%;
-  height: 100%;
-  display: flex;
-  flex-direction: column;
-
-  .page-header {
-    margin-bottom: 0;
-  }
-
-  .page-main {
-    // 让 page-main 的高度自适应
-    flex: 1;
-    overflow: auto;
-    display: flex;
-    flex-direction: column;
-
-    .search-container {
-      margin-bottom: 0;
-    }
-  }
-}
-</style>