Browse Source

联系人等

lipenghui 5 months ago
parent
commit
73012a87ae

+ 58 - 0
src/api/supplier/base/index.ts

@@ -0,0 +1,58 @@
+import request from '@/config/axios'
+
+// 供应商主数据 VO
+export interface SupplierVO {
+  id: number // 主键
+  code: string // 供应商编号 自动生成
+  name: string // 供应商名称
+  classification: string // 供应商分类
+  type: string // 公司类型
+  nature: string // 供应商性质
+  creditCode: string // 社会信用代码
+  tin: string // 纳税人识别号
+  corporation: string // 法人
+  incorporationDate: Date // 成立日期
+  address: string // 公司地址
+  bizScope: string // 经营范围
+  registeredCapital: number // 注册资金 单位:万元
+  annualTurnove: number // 年营业额 单位:万元
+  size: string // 公司规模 数据字典
+  status: number // 商品状态: 1 草稿 2活动 3 关闭
+  remark: string // 备注
+}
+
+// 供应商主数据 API
+export const Api = {
+  // 查询供应商主数据分页
+  getPage: async (params: any) => {
+    return await request.get({ url: `/supplier/base/page`, params })
+  },
+
+  // 查询供应商主数据详情
+  get: async (id: number) => {
+    return await request.get({ url: `/supplier/base/get?id=` + id })
+  },
+
+  // 新增供应商主数据
+  create: async (data: SupplierVO) => {
+    return await request.post({ url: `/supplier/base/create`, data })
+  },
+
+  // 修改供应商主数据
+  update: async (data: SupplierVO) => {
+    return await request.put({ url: `/supplier/base/update`, data })
+  },
+
+  // 删除供应商主数据
+  delete: async (id: number) => {
+    return await request.delete({ url: `/supplier/base/delete?id=` + id })
+  },
+
+  // 导出供应商主数据 Excel
+  export: async (params) => {
+    return await request.download({ url: `/supplier/base/export-excel`, params })
+  },
+  getAll: async () =>{
+    return await request.get({ url: `/supplier/base/all` })
+  }
+}

+ 47 - 0
src/api/supplier/connect/index.ts

@@ -0,0 +1,47 @@
+import request from '@/config/axios'
+
+// 供应商联系记录 VO
+export interface ConnectRecordVO {
+  id: number // 主键
+  supplierId: number // 供应商id
+  userId: number // 我方联系人id
+  username: string // 我方联系人姓名
+  contactId: number // 供应商联系人id
+  contactName: string // 供应商联系人姓名
+  reason: string // 联系原因
+  content: string // 交流内容
+  urls: string // 附件
+}
+
+// 供应商联系记录 API
+export const ConnectRecordApi = {
+  // 查询供应商联系记录分页
+  getConnectRecordPage: async (params: any) => {
+    return await request.get({ url: `/supplier/connect-record/page`, params })
+  },
+
+  // 查询供应商联系记录详情
+  getConnectRecord: async (id: number) => {
+    return await request.get({ url: `/supplier/connect-record/get?id=` + id })
+  },
+
+  // 新增供应商联系记录
+  createConnectRecord: async (data: ConnectRecordVO) => {
+    return await request.post({ url: `/supplier/connect-record/create`, data })
+  },
+
+  // 修改供应商联系记录
+  updateConnectRecord: async (data: ConnectRecordVO) => {
+    return await request.put({ url: `/supplier/connect-record/update`, data })
+  },
+
+  // 删除供应商联系记录
+  deleteConnectRecord: async (id: number) => {
+    return await request.delete({ url: `/supplier/connect-record/delete?id=` + id })
+  },
+
+  // 导出供应商联系记录 Excel
+  exportConnectRecord: async (params) => {
+    return await request.download({ url: `/supplier/connect-record/export-excel`, params })
+  },
+}

+ 47 - 0
src/api/supplier/contact/index.ts

@@ -0,0 +1,47 @@
+import request from '@/config/axios'
+
+// 供应商联系人 VO
+export interface ContactVO {
+  id: number // 主键
+  supplierId: number // 供应商id
+  name: string // 姓名
+  position: string // 职务
+  telephone: string // 电话
+  email: string // 邮箱
+  productIds: number // 联系人负责的产品/业务模块  关联产品id 逗号分隔
+  productNames: string // 联系人负责的产品/业务模块  关联产品名称 逗号分隔
+  remark: string // 备注
+}
+
+// 供应商联系人 API
+export const ContactApi = {
+  // 查询供应商联系人分页
+  getContactPage: async (params: any) => {
+    return await request.get({ url: `/supplier/contact/page`, params })
+  },
+
+  // 查询供应商联系人详情
+  getContact: async (id: number) => {
+    return await request.get({ url: `/supplier/contact/get?id=` + id })
+  },
+
+  // 新增供应商联系人
+  createContact: async (data: ContactVO) => {
+    return await request.post({ url: `/supplier/contact/create`, data })
+  },
+
+  // 修改供应商联系人
+  updateContact: async (data: ContactVO) => {
+    return await request.put({ url: `/supplier/contact/update`, data })
+  },
+
+  // 删除供应商联系人
+  deleteContact: async (id: number) => {
+    return await request.delete({ url: `/supplier/contact/delete?id=` + id })
+  },
+
+  // 导出供应商联系人 Excel
+  exportContact: async (params) => {
+    return await request.download({ url: `/supplier/contact/export-excel`, params })
+  },
+}

+ 43 - 0
src/api/supplier/coreproduct/index.ts

@@ -0,0 +1,43 @@
+import request from '@/config/axios'
+
+// 供应商核心产品 VO
+export interface CoreProductVO {
+  id: number // 主键
+  supplierId: number // 供应商id
+  productId: number // 产品id
+  productName: string // 产品名称
+  advantage: string // 优势介绍
+}
+
+// 供应商核心产品 API
+export const CoreProductApi = {
+  // 查询供应商核心产品分页
+  getCoreProductPage: async (params: any) => {
+    return await request.get({ url: `/supplier/core-product/page`, params })
+  },
+
+  // 查询供应商核心产品详情
+  getCoreProduct: async (id: number) => {
+    return await request.get({ url: `/supplier/core-product/get?id=` + id })
+  },
+
+  // 新增供应商核心产品
+  createCoreProduct: async (data: CoreProductVO) => {
+    return await request.post({ url: `/supplier/core-product/create`, data })
+  },
+
+  // 修改供应商核心产品
+  updateCoreProduct: async (data: CoreProductVO) => {
+    return await request.put({ url: `/supplier/core-product/update`, data })
+  },
+
+  // 删除供应商核心产品
+  deleteCoreProduct: async (id: number) => {
+    return await request.delete({ url: `/supplier/core-product/delete?id=` + id })
+  },
+
+  // 导出供应商核心产品 Excel
+  exportCoreProduct: async (params) => {
+    return await request.download({ url: `/supplier/core-product/export-excel`, params })
+  },
+}

+ 6 - 1
src/utils/dict.ts

@@ -112,7 +112,12 @@ export enum DICT_TYPE {
   COMMON_STATUS = 'common_status',
   TERMINAL = 'terminal', // 终端
   DATE_INTERVAL = 'date_interval', // 数据间隔
-
+// ========== supplier 模块 ==========
+  SUPPLIER_TYPE = "supplier_classification",
+  SUPPLIER_COMPANY_TYPE = "supplier_type",
+  SUPPLIER_NATURE = "supplier_nature",
+  SUPPLIER_STATUS = "supplier_status",
+  SUPPLIER_SIZE = "supplier_size",
   // ========== SYSTEM 模块 ==========
   SYSTEM_USER_SEX = 'system_user_sex',
   SYSTEM_MENU_TYPE = 'system_menu_type',

+ 229 - 0
src/views/supplier/base/Form.vue

@@ -0,0 +1,229 @@
+<template>
+  <Dialog :title="dialogTitle" v-model="dialogVisible">
+    <el-form
+      ref="formRef"
+      :model="formData"
+      :rules="formRules"
+      label-width="100px"
+      v-loading="formLoading"
+    >
+<!--      <el-form-item label="供应商编号" prop="code">-->
+<!--        <el-input v-model="formData.code" placeholder="请输入供应商编号" />-->
+<!--      </el-form-item>-->
+      <el-form-item label="供应商名称" prop="name">
+        <el-input v-model="formData.name" placeholder="请输入供应商名称" />
+      </el-form-item>
+<!--      <el-form-item label="供应商分类" prop="classification">-->
+<!--        <el-input v-model="formData.classification" placeholder="请输入供应商分类" />-->
+<!--      </el-form-item>-->
+      <el-form-item label="供应商分类">
+        <el-select v-model="formData.name" placeholder="请选择">
+          <el-option
+            v-for="dict in getIntDictOptions(DICT_TYPE.SUPPLIER_TYPE)"
+            :key="dict.value"
+            :label="dict.label"
+            :value="dict.value"
+          />
+        </el-select>
+      </el-form-item>
+<!--      <el-form-item label="公司类型" prop="type">-->
+<!--        <el-select v-model="formData.type" placeholder="请选择公司类型">-->
+<!--          <el-option label="请选择字典生成" value="" />-->
+<!--        </el-select>-->
+<!--      </el-form-item>-->
+      <el-form-item label="公司类型">
+        <el-select v-model="formData.type" placeholder="请选择">
+          <el-option
+            v-for="dict in getIntDictOptions(DICT_TYPE.SUPPLIER_COMPANY_TYPE)"
+            :key="dict.value"
+            :label="dict.label"
+            :value="dict.value"
+          />
+        </el-select>
+      </el-form-item>
+<!--      <el-form-item label="供应商性质" prop="nature">-->
+<!--        <el-input v-model="formData.nature" placeholder="请输入供应商性质" />-->
+<!--      </el-form-item>-->
+      <el-form-item label="供应商性质">
+        <el-select v-model="formData.nature" placeholder="请选择">
+          <el-option
+            v-for="dict in getIntDictOptions(DICT_TYPE.SUPPLIER_NATURE)"
+            :key="dict.value"
+            :label="dict.label"
+            :value="dict.value"
+          />
+        </el-select>
+      </el-form-item>
+      <el-form-item label="公司规模">
+        <el-select v-model="formData.size" placeholder="请选择">
+          <el-option
+            v-for="dict in getIntDictOptions(DICT_TYPE.SUPPLIER_NATURE)"
+            :key="dict.value"
+            :label="dict.label"
+            :value="dict.value"
+          />
+        </el-select>
+      </el-form-item>
+      <el-form-item label="社会信用代码" prop="creditCode">
+        <el-input v-model="formData.creditCode" placeholder="请输入社会信用代码" />
+      </el-form-item>
+      <el-form-item label="纳税人识别号" prop="tin">
+        <el-input v-model="formData.tin" placeholder="请输入纳税人识别号" />
+      </el-form-item>
+      <el-form-item label="法人" prop="corporation">
+        <el-input v-model="formData.corporation" placeholder="请输入法人" />
+      </el-form-item>
+      <el-form-item label="成立日期" prop="incorporationDate">
+        <el-date-picker
+          v-model="formData.incorporationDate"
+          type="date"
+          value-format="x"
+          placeholder="选择成立日期"
+        />
+      </el-form-item>
+      <el-form-item label="公司地址" prop="address">
+        <el-input v-model="formData.address" placeholder="请输入公司地址" />
+      </el-form-item>
+      <el-form-item label="经营范围" prop="bizScope">
+        <el-input type="textarea" v-model="formData.bizScope" placeholder="请输入经营范围" />
+      </el-form-item>
+      <el-form-item label="注册资金" prop="registeredCapital">
+        <el-input type="number" v-model="formData.registeredCapital" placeholder="请输入注册资金 单位:万元" />
+      </el-form-item>
+      <el-form-item label="年营业额" prop="annualTurnove">
+        <el-input type="number" v-model="formData.annualTurnove" placeholder="请输入年营业额 单位:万元" />
+      </el-form-item>
+      <el-form-item label="供应商性质">
+        <el-select v-model="formData.size" placeholder="请选择">
+          <el-option
+            v-for="dict in getIntDictOptions(DICT_TYPE.SUPPLIER_NATURE)"
+            :key="dict.value"
+            :label="dict.label"
+            :value="dict.value"
+          />
+        </el-select>
+      </el-form-item>
+      <el-form-item label="状态">
+        <el-select v-model="formData.status" placeholder="请选择">
+          <el-option
+            v-for="dict in getIntDictOptions(DICT_TYPE.SUPPLIER_STATUS)"
+            :key="dict.value"
+            :label="dict.label"
+            :value="dict.value"
+          />
+        </el-select>
+      </el-form-item>
+      <el-form-item label="备注" prop="remark">
+        <el-input v-model="formData.remark" placeholder="请输入备注" />
+      </el-form-item>
+    </el-form>
+    <template #footer>
+      <el-button @click="submitForm" type="primary" :disabled="formLoading">确 定</el-button>
+      <el-button @click="dialogVisible = false">取 消</el-button>
+    </template>
+  </Dialog>
+</template>
+<script setup lang="ts">
+import { Api, SupplierVO } from '@/api/supplier/base'
+import {DICT_TYPE, getIntDictOptions} from "@/utils/dict";
+
+/** 供应商主数据 表单 */
+defineOptions({ name: 'SupplierForm' })
+
+const { t } = useI18n() // 国际化
+const message = useMessage() // 消息弹窗
+
+const dialogVisible = ref(false) // 弹窗的是否展示
+const dialogTitle = ref('') // 弹窗的标题
+const formLoading = ref(false) // 表单的加载中:1)修改时的数据加载;2)提交的按钮禁用
+const formType = ref('') // 表单的类型:create - 新增;update - 修改
+const formData = ref({
+  id: undefined,
+  code: undefined,
+  name: undefined,
+  classification: undefined,
+  type: undefined,
+  nature: undefined,
+  creditCode: undefined,
+  tin: undefined,
+  corporation: undefined,
+  incorporationDate: undefined,
+  address: undefined,
+  bizScope: undefined,
+  registeredCapital: undefined,
+  annualTurnove: undefined,
+  size: undefined,
+  status: undefined,
+  remark: undefined,
+})
+const formRules = reactive({
+  status: [{ required: true, message: '状态不能为空', trigger: 'blur' }],
+})
+const formRef = ref() // 表单 Ref
+
+/** 打开弹窗 */
+const open = async (type: string, id?: number) => {
+  dialogVisible.value = true
+  dialogTitle.value = t('action.' + type)
+  formType.value = type
+  resetForm()
+  // 修改时,设置数据
+  if (id) {
+    formLoading.value = true
+    try {
+      formData.value = await Api.get(id)
+    } finally {
+      formLoading.value = false
+    }
+  }
+}
+defineExpose({ open }) // 提供 open 方法,用于打开弹窗
+
+/** 提交表单 */
+const emit = defineEmits(['success']) // 定义 success 事件,用于操作成功后的回调
+const submitForm = async () => {
+  // 校验表单
+  await formRef.value.validate()
+  // 提交请求
+  formLoading.value = true
+  try {
+    const data = formData.value as unknown as SupplierVO
+    if (formType.value === 'create') {
+      await Api.create(data)
+      message.success(t('common.createSuccess'))
+    } else {
+      await Api.update(data)
+      message.success(t('common.updateSuccess'))
+    }
+    dialogVisible.value = false
+    // 发送操作成功的事件
+    emit('success')
+  } finally {
+    formLoading.value = false
+  }
+}
+
+/** 重置表单 */
+const resetForm = () => {
+  formData.value = {
+    id: undefined,
+    code: undefined,
+    name: undefined,
+    classification: undefined,
+    type: undefined,
+    nature: undefined,
+    creditCode: undefined,
+    tin: undefined,
+    corporation: undefined,
+    incorporationDate: undefined,
+    address: undefined,
+    bizScope: undefined,
+    registeredCapital: undefined,
+    annualTurnove: undefined,
+    size: undefined,
+    status: undefined,
+    remark: undefined,
+  }
+  formRef.value?.resetFields()
+}
+</script>

+ 306 - 0
src/views/supplier/base/index.vue

@@ -0,0 +1,306 @@
+<template>
+  <ContentWrap>
+    <!-- 搜索工作栏 -->
+    <el-form
+      class="-mb-15px"
+      :model="queryParams"
+      ref="queryFormRef"
+      :inline="true"
+      label-width="68px"
+    >
+      <el-form-item label="供应商编号" label-width="85px" prop="code">
+        <el-input
+          v-model="queryParams.code"
+          placeholder="请输入供应商编号"
+          clearable
+          @keyup.enter="handleQuery"
+          class="!w-240px"
+        />
+      </el-form-item>
+      <el-form-item label="供应商名称" label-width="85px"  prop="name">
+        <el-input
+          v-model="queryParams.name"
+          placeholder="请输入供应商名称"
+          clearable
+          @keyup.enter="handleQuery"
+          class="!w-240px"
+        />
+      </el-form-item>
+      <el-form-item label="供应商分类" label-width="85px"  prop="classification">
+        <el-select
+          v-model="queryParams.classification"
+          placeholder="供应商分类"
+          clearable
+          class="!w-240px"
+        >
+          <el-option
+            v-for="dict in getIntDictOptions(DICT_TYPE.SUPPLIER_TYPE)"
+            :key="dict.value"
+            :label="dict.label"
+            :value="dict.value"
+          />
+        </el-select>
+      </el-form-item>
+      <el-form-item label="公司类型" label-width="85px"  prop="type">
+        <el-select
+          v-model="queryParams.type"
+          placeholder="公司类型"
+          clearable
+          class="!w-240px"
+        >
+          <el-option
+            v-for="dict in getIntDictOptions(DICT_TYPE.SUPPLIER_COMPANY_TYPE)"
+            :key="dict.value"
+            :label="dict.label"
+            :value="dict.value"
+          />
+        </el-select>
+      </el-form-item>
+      <el-form-item label="供应商性质" label-width="85px"  prop="nature">
+        <el-select
+          v-model="queryParams.nature"
+          placeholder="供应商性质"
+          clearable
+          class="!w-240px"
+        >
+          <el-option
+            v-for="dict in getIntDictOptions(DICT_TYPE.SUPPLIER_NATURE)"
+            :key="dict.value"
+            :label="dict.label"
+            :value="dict.value"
+          />
+        </el-select>
+      </el-form-item>
+      <el-form-item label="社会信用代码" label-width="98px"  prop="creditCode">
+        <el-input
+          v-model="queryParams.creditCode"
+          placeholder="请输入社会信用代码"
+          clearable
+          @keyup.enter="handleQuery"
+          class="!w-240px"
+        />
+      </el-form-item>
+      <el-form-item label="状态:" prop="status">
+        <el-select
+          v-model="queryParams.status"
+          placeholder="状态"
+          clearable
+          class="!w-240px"
+        >
+          <el-option
+            v-for="dict in getIntDictOptions(DICT_TYPE.SUPPLIER_STATUS)"
+            :key="dict.value"
+            :label="dict.label"
+            :value="dict.value"
+          />
+        </el-select>
+      </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('create')"
+        >
+          <Icon icon="ep:plus" class="mr-5px" /> 新增
+        </el-button>
+        <el-button
+          type="success"
+          plain
+          @click="handleExport"
+          :loading="exportLoading"
+          v-hasPermi="['supplier::export']"
+        >
+          <Icon icon="ep:download" class="mr-5px" /> 导出
+        </el-button>
+      </el-form-item>
+    </el-form>
+  </ContentWrap>
+
+  <!-- 列表 -->
+  <ContentWrap>
+    <el-table v-loading="loading" :data="list" :stripe="true" :show-overflow-tooltip="true">
+      <el-table-column label="供应商编号" align="center" prop="code" />
+      <el-table-column label="供应商名称" align="center" prop="name" />
+      <el-table-column label="供应商分类" align="center" prop="classification" >
+        <template #default="scope">
+          <dict-tag :type="DICT_TYPE.SUPPLIER_TYPE" :value="scope.row.classification" />
+        </template>
+      </el-table-column>
+      <el-table-column label="公司类型" align="center" prop="type" >
+        <template #default="scope">
+          <dict-tag :type="DICT_TYPE.SUPPLIER_COMPANY_TYPE" :value="scope.row.type" />
+        </template>
+      </el-table-column>
+      <el-table-column label="供应商性质" align="center" prop="nature" >
+        <template #default="scope">
+          <dict-tag :type="DICT_TYPE.SUPPLIER_NATURE" :value="scope.row.nature" />
+        </template>
+      </el-table-column>
+      <el-table-column label="社会信用代码" align="center" prop="creditCode" />
+<!--      <el-table-column label="纳税人识别号" align="center" prop="tin" />-->
+      <el-table-column label="法人" align="center" prop="corporation" />
+      <el-table-column
+        label="成立日期"
+        align="center"
+        prop="incorporationDate"
+        :formatter="dateFormatter"
+        width="180px"
+      />
+<!--      <el-table-column label="公司地址" align="center" prop="address" />-->
+<!--      <el-table-column label="经营范围" align="center" prop="bizScope" />-->
+<!--      <el-table-column label="注册资金(万元)" align="center" prop="registeredCapital" />-->
+<!--      <el-table-column label="年营业额(万元)" align="center" prop="annualTurnove" />-->
+      <el-table-column label="公司规模" align="center" prop="size" >
+        <template #default="scope">
+          <dict-tag :type="DICT_TYPE.SUPPLIER_SIZE" :value="scope.row.size" />
+        </template>
+      </el-table-column>
+      <el-table-column label="状态" align="center" prop="status" >
+        <template #default="scope">
+          <dict-tag :type="DICT_TYPE.SUPPLIER_STATUS" :value="scope.row.status" />
+        </template>
+      </el-table-column>
+      <el-table-column
+        label="创建时间"
+        align="center"
+        prop="createTime"
+        :formatter="dateFormatter"
+        width="180px"
+      />
+      <el-table-column label="操作" align="center" min-width="120px">
+        <template #default="scope">
+          <el-button
+            link
+            type="primary"
+            @click="openForm('update', scope.row.id)"
+          >
+            编辑
+          </el-button>
+          <el-button
+            link
+            type="danger"
+            @click="handleDelete(scope.row.id)"
+          >
+            删除
+          </el-button>
+        </template>
+      </el-table-column>
+    </el-table>
+    <!-- 分页 -->
+    <Pagination
+      :total="total"
+      v-model:page="queryParams.pageNo"
+      v-model:limit="queryParams.pageSize"
+      @pagination="getList"
+    />
+  </ContentWrap>
+
+  <!-- 表单弹窗:添加/修改 -->
+  <Form ref="formRef" @success="getList" />
+</template>
+
+<script setup lang="ts">
+import { dateFormatter } from '@/utils/formatTime'
+import download from '@/utils/download'
+import { Api, VO } from '@/api/supplier/base'
+import Form from './Form.vue'
+import {DICT_TYPE, getIntDictOptions} from "@/utils/dict";
+
+/** 供应商主数据 列表 */
+defineOptions({ name: 'Suppliers' })
+
+const message = useMessage() // 消息弹窗
+const { t } = useI18n() // 国际化
+
+const loading = ref(true) // 列表的加载中
+const list = ref<VO[]>([]) // 列表的数据
+const total = ref(0) // 列表的总页数
+const queryParams = reactive({
+  pageNo: 1,
+  pageSize: 10,
+  code: undefined,
+  name: undefined,
+  classification: undefined,
+  type: undefined,
+  nature: undefined,
+  creditCode: undefined,
+  tin: undefined,
+  corporation: undefined,
+  incorporationDate: [],
+  address: undefined,
+  bizScope: undefined,
+  registeredCapital: undefined,
+  annualTurnove: undefined,
+  size: undefined,
+  status: undefined,
+  remark: undefined,
+  createTime: [],
+})
+const queryFormRef = ref() // 搜索的表单
+const exportLoading = ref(false) // 导出的加载中
+
+/** 查询列表 */
+const getList = async () => {
+  loading.value = true
+  try {
+    const data = await Api.getPage(queryParams)
+    list.value = data.list
+    total.value = data.total
+  } finally {
+    loading.value = false
+  }
+}
+
+/** 搜索按钮操作 */
+const handleQuery = () => {
+  queryParams.pageNo = 1
+  getList()
+}
+
+/** 重置按钮操作 */
+const resetQuery = () => {
+  queryFormRef.value.resetFields()
+  handleQuery()
+}
+
+/** 添加/修改操作 */
+const formRef = ref()
+const openForm = (type: string, id?: number) => {
+  formRef.value.open(type, id)
+}
+
+/** 删除按钮操作 */
+const handleDelete = async (id: number) => {
+  try {
+    // 删除的二次确认
+    await message.delConfirm()
+    // 发起删除
+    await Api.delete(id)
+    message.success(t('common.delSuccess'))
+    // 刷新列表
+    await getList()
+  } catch {}
+}
+
+/** 导出按钮操作 */
+const handleExport = async () => {
+  try {
+    // 导出的二次确认
+    await message.exportConfirm()
+    // 发起导出
+    exportLoading.value = true
+    const data = await Api.export(queryParams)
+    download.excel(data, '供应商主数据.xls')
+  } catch {
+  } finally {
+    exportLoading.value = false
+  }
+}
+
+/** 初始化 **/
+onMounted(() => {
+  getList()
+})
+</script>

+ 132 - 0
src/views/supplier/connect/ConnectRecordForm.vue

@@ -0,0 +1,132 @@
+<template>
+  <Dialog :title="dialogTitle" v-model="dialogVisible">
+    <el-form
+      ref="formRef"
+      :model="formData"
+      :rules="formRules"
+      label-width="100px"
+      v-loading="formLoading"
+    >
+      <el-form-item label="供应商">
+        <el-select v-model="formData.supplierId" placeholder="请选择">
+          <el-option
+            v-for="dict in supplierList"
+            :key="dict.value"
+            :label="dict.label"
+            :value="dict.value"
+          />
+        </el-select>
+      </el-form-item>
+<!--      <el-form-item label="我方联系人" prop="username">-->
+<!--        <el-input v-model="formData.username" placeholder="请输入我方联系人姓名" />-->
+<!--      </el-form-item>-->
+      <el-form-item label="供应商联系人" prop="contactName">
+        <el-input v-model="formData.contactName" placeholder="请输入供应商联系人姓名" />
+      </el-form-item>
+      <el-form-item label="联系原因" prop="reason">
+        <el-input v-model="formData.reason" placeholder="请输入联系原因" />
+      </el-form-item>
+      <el-form-item label="交流内容" prop="content">
+        <Editor v-model="formData.content" height="150px" />
+      </el-form-item>
+      <el-form-item label="附件" prop="urls">
+        <el-input v-model="formData.urls" placeholder="请输入附件" />
+      </el-form-item>
+    </el-form>
+    <template #footer>
+      <el-button @click="submitForm" type="primary" :disabled="formLoading">确 定</el-button>
+      <el-button @click="dialogVisible = false">取 消</el-button>
+    </template>
+  </Dialog>
+</template>
+<script setup lang="ts">
+import { ConnectRecordApi, ConnectRecordVO } from '@/api/supplier/connect'
+import {DICT_TYPE, getIntDictOptions} from "@/utils/dict";
+import {onMounted} from "vue";
+import * as SupplierBaseApi from '@/api/supplier/base/index'
+import * as SupplierProductCategoryApi from "@/api/supplier/product/category";
+/** 供应商联系记录 表单 */
+defineOptions({ name: 'ConnectRecordForm' })
+
+const { t } = useI18n() // 国际化
+const message = useMessage() // 消息弹窗
+const supplierList = ref<any[]>([]) // 供应商
+const dialogVisible = ref(false) // 弹窗的是否展示
+const dialogTitle = ref('') // 弹窗的标题
+const formLoading = ref(false) // 表单的加载中:1)修改时的数据加载;2)提交的按钮禁用
+const formType = ref('') // 表单的类型:create - 新增;update - 修改
+const formData = ref({
+  id: undefined,
+  supplierId: undefined,
+  userId: undefined,
+  username: undefined,
+  contactId: undefined,
+  contactName: undefined,
+  reason: undefined,
+  content: undefined,
+  urls: undefined,
+})
+const formRules = reactive({
+})
+const formRef = ref() // 表单 Ref
+
+/** 打开弹窗 */
+const open = async (type: string, id?: number) => {
+  dialogVisible.value = true
+  dialogTitle.value = t('action.' + type)
+  formType.value = type
+  resetForm()
+  // 修改时,设置数据
+  if (id) {
+    formLoading.value = true
+    try {
+      formData.value = await ConnectRecordApi.getConnectRecord(id)
+    } finally {
+      formLoading.value = false
+    }
+  }
+}
+defineExpose({ open }) // 提供 open 方法,用于打开弹窗
+
+/** 提交表单 */
+const emit = defineEmits(['success']) // 定义 success 事件,用于操作成功后的回调
+const submitForm = async () => {
+  // 校验表单
+  await formRef.value.validate()
+  // 提交请求
+  formLoading.value = true
+  try {
+    const data = formData.value as unknown as ConnectRecordVO
+    if (formType.value === 'create') {
+      await ConnectRecordApi.createConnectRecord(data)
+      message.success(t('common.createSuccess'))
+    } else {
+      await ConnectRecordApi.updateConnectRecord(data)
+      message.success(t('common.updateSuccess'))
+    }
+    dialogVisible.value = false
+    // 发送操作成功的事件
+    emit('success')
+  } finally {
+    formLoading.value = false
+  }
+}
+onMounted(()=>{
+  supplierList.value = await SupplierBaseApi.Api.getAll();
+})
+/** 重置表单 */
+const resetForm = () => {
+  formData.value = {
+    id: undefined,
+    supplierId: undefined,
+    userId: undefined,
+    username: undefined,
+    contactId: undefined,
+    contactName: undefined,
+    reason: undefined,
+    content: undefined,
+    urls: undefined,
+  }
+  formRef.value?.resetFields()
+}
+</script>

+ 203 - 0
src/views/supplier/connect/index.vue

@@ -0,0 +1,203 @@
+<template>
+  <ContentWrap>
+    <!-- 搜索工作栏 -->
+    <el-form
+      class="-mb-15px"
+      :model="queryParams"
+      ref="queryFormRef"
+      :inline="true"
+      label-width="68px"
+    >
+      <el-form-item label="供应商" prop="supplierId">
+        <el-input
+          v-model="queryParams.supplierId"
+          placeholder="请输入供应商"
+          clearable
+          @keyup.enter="handleQuery"
+          class="!w-240px"
+        />
+      </el-form-item>
+      <el-form-item label="我方联系人" prop="username">
+        <el-input
+          v-model="queryParams.username"
+          placeholder="请输入我方联系人"
+          clearable
+          @keyup.enter="handleQuery"
+          class="!w-240px"
+        />
+      </el-form-item>
+      <el-form-item label="供应商联系人" prop="contactName">
+        <el-input
+          v-model="queryParams.contactName"
+          placeholder="请输入供应商联系人"
+          clearable
+          @keyup.enter="handleQuery"
+          class="!w-240px"
+        />
+      </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('create')"
+
+        >
+          <Icon icon="ep:plus" class="mr-5px" /> 新增
+        </el-button>
+        <el-button
+          type="success"
+          plain
+          @click="handleExport"
+          :loading="exportLoading"
+          v-hasPermi="['supplier:connect-record:export']"
+        >
+          <Icon icon="ep:download" class="mr-5px" /> 导出
+        </el-button>
+      </el-form-item>
+    </el-form>
+  </ContentWrap>
+
+  <!-- 列表 -->
+  <ContentWrap>
+    <el-table v-loading="loading" :data="list" :stripe="true" :show-overflow-tooltip="true">
+      <el-table-column label="供应商" align="center" prop="supplierId" />
+      <el-table-column label="我方联系人姓名" align="center" prop="username" />
+      <el-table-column label="供应商联系人姓名" align="center" prop="contactName" />
+      <el-table-column label="联系原因" align="center" prop="reason" />
+      <el-table-column label="交流内容" align="center" prop="content" />
+      <el-table-column label="附件" align="center" prop="urls" />
+      <el-table-column
+        label="创建时间"
+        align="center"
+        prop="createTime"
+        :formatter="dateFormatter"
+        width="180px"
+      />
+      <el-table-column label="操作" align="center" min-width="120px">
+        <template #default="scope">
+          <el-button
+            link
+            type="primary"
+            @click="openForm('update', scope.row.id)"
+          >
+            编辑
+          </el-button>
+          <el-button
+            link
+            type="danger"
+            @click="handleDelete(scope.row.id)"
+          >
+            删除
+          </el-button>
+        </template>
+      </el-table-column>
+    </el-table>
+    <!-- 分页 -->
+    <Pagination
+      :total="total"
+      v-model:page="queryParams.pageNo"
+      v-model:limit="queryParams.pageSize"
+      @pagination="getList"
+    />
+  </ContentWrap>
+
+  <!-- 表单弹窗:添加/修改 -->
+  <ConnectRecordForm ref="formRef" @success="getList" />
+</template>
+
+<script setup lang="ts">
+import { dateFormatter } from '@/utils/formatTime'
+import download from '@/utils/download'
+import { ConnectRecordApi, ConnectRecordVO } from '@/api/supplier/connect/index'
+import ConnectRecordForm from './ConnectRecordForm.vue'
+
+/** 供应商联系记录 列表 */
+defineOptions({ name: 'ConnectRecord' })
+
+const message = useMessage() // 消息弹窗
+const { t } = useI18n() // 国际化
+
+const loading = ref(true) // 列表的加载中
+const list = ref<ConnectRecordVO[]>([]) // 列表的数据
+const total = ref(0) // 列表的总页数
+const queryParams = reactive({
+  pageNo: 1,
+  pageSize: 10,
+  supplierId: undefined,
+  userId: undefined,
+  username: undefined,
+  contactId: undefined,
+  contactName: undefined,
+  reason: undefined,
+  content: undefined,
+  urls: undefined,
+  createTime: [],
+})
+const queryFormRef = ref() // 搜索的表单
+const exportLoading = ref(false) // 导出的加载中
+
+/** 查询列表 */
+const getList = async () => {
+  loading.value = true
+  try {
+    const data = await ConnectRecordApi.getConnectRecordPage(queryParams)
+    list.value = data.list
+    total.value = data.total
+  } finally {
+    loading.value = false
+  }
+}
+
+/** 搜索按钮操作 */
+const handleQuery = () => {
+  queryParams.pageNo = 1
+  getList()
+}
+
+/** 重置按钮操作 */
+const resetQuery = () => {
+  queryFormRef.value.resetFields()
+  handleQuery()
+}
+
+/** 添加/修改操作 */
+const formRef = ref()
+const openForm = (type: string, id?: number) => {
+  formRef.value.open(type, id)
+}
+
+/** 删除按钮操作 */
+const handleDelete = async (id: number) => {
+  try {
+    // 删除的二次确认
+    await message.delConfirm()
+    // 发起删除
+    await ConnectRecordApi.deleteConnectRecord(id)
+    message.success(t('common.delSuccess'))
+    // 刷新列表
+    await getList()
+  } catch {}
+}
+
+/** 导出按钮操作 */
+const handleExport = async () => {
+  try {
+    // 导出的二次确认
+    await message.exportConfirm()
+    // 发起导出
+    exportLoading.value = true
+    const data = await ConnectRecordApi.exportConnectRecord(queryParams)
+    download.excel(data, '供应商联系记录.xls')
+  } catch {
+  } finally {
+    exportLoading.value = false
+  }
+}
+
+/** 初始化 **/
+onMounted(() => {
+  getList()
+})
+</script>

+ 126 - 0
src/views/supplier/contact/ContactForm.vue

@@ -0,0 +1,126 @@
+<template>
+  <Dialog :title="dialogTitle" v-model="dialogVisible">
+    <el-form
+      ref="formRef"
+      :model="formData"
+      :rules="formRules"
+      label-width="100px"
+      v-loading="formLoading"
+    >
+      <el-form-item label="供应商" prop="supplierId">
+        <el-input v-model="formData.supplierId" placeholder="请输入供应商" />
+      </el-form-item>
+      <el-form-item label="姓名" prop="name">
+        <el-input v-model="formData.name" placeholder="请输入姓名" />
+      </el-form-item>
+      <el-form-item label="职务" prop="position">
+        <el-input v-model="formData.position" placeholder="请输入职务" />
+      </el-form-item>
+      <el-form-item label="电话" prop="telephone">
+        <el-input v-model="formData.telephone" placeholder="请输入电话" />
+      </el-form-item>
+      <el-form-item label="邮箱" prop="email">
+        <el-input v-model="formData.email" placeholder="请输入邮箱" />
+      </el-form-item>
+<!--      <el-form-item label="产品/业务模块" prop="productIds">-->
+<!--        <el-input v-model="formData.productIds" placeholder="请输入联系人负责的产品/业务模块" />-->
+<!--      </el-form-item>-->
+      <el-form-item label="产品业务模块" prop="productIds">
+        <el-input v-model="formData.productIds" placeholder="请输入联系人负责的产品/业务模块" />
+      </el-form-item>
+      <el-form-item label="备注" prop="remark">
+        <el-input v-model="formData.remark" placeholder="请输入备注" />
+      </el-form-item>
+    </el-form>
+    <template #footer>
+      <el-button @click="submitForm" type="primary" :disabled="formLoading">确 定</el-button>
+      <el-button @click="dialogVisible = false">取 消</el-button>
+    </template>
+  </Dialog>
+</template>
+<script setup lang="ts">
+import { ContactApi, ContactVO } from '@/api/supplier/contact'
+import Supplier from '@/views/supplier/base/index.vue'
+/** 供应商联系人 表单 */
+defineOptions({ name: 'ContactForm' })
+
+const { t } = useI18n() // 国际化
+const message = useMessage() // 消息弹窗
+
+const dialogVisible = ref(false) // 弹窗的是否展示
+const dialogTitle = ref('') // 弹窗的标题
+const formLoading = ref(false) // 表单的加载中:1)修改时的数据加载;2)提交的按钮禁用
+const formType = ref('') // 表单的类型:create - 新增;update - 修改
+const formData = ref({
+  id: undefined,
+  supplierId: undefined,
+  name: undefined,
+  position: undefined,
+  telephone: undefined,
+  email: undefined,
+  productIds: undefined,
+  productNames: undefined,
+  remark: undefined,
+})
+const formRules = reactive({
+})
+const formRef = ref() // 表单 Ref
+
+/** 打开弹窗 */
+const open = async (type: string, id?: number) => {
+  dialogVisible.value = true
+  dialogTitle.value = t('action.' + type)
+  formType.value = type
+  resetForm()
+  // 修改时,设置数据
+  if (id) {
+    formLoading.value = true
+    try {
+      formData.value = await ContactApi.getContact(id)
+    } finally {
+      formLoading.value = false
+    }
+  }
+}
+defineExpose({ open }) // 提供 open 方法,用于打开弹窗
+
+/** 提交表单 */
+const emit = defineEmits(['success']) // 定义 success 事件,用于操作成功后的回调
+const submitForm = async () => {
+  // 校验表单
+  await formRef.value.validate()
+  // 提交请求
+  formLoading.value = true
+  try {
+    const data = formData.value as unknown as ContactVO
+    if (formType.value === 'create') {
+      await ContactApi.createContact(data)
+      message.success(t('common.createSuccess'))
+    } else {
+      await ContactApi.updateContact(data)
+      message.success(t('common.updateSuccess'))
+    }
+    dialogVisible.value = false
+    // 发送操作成功的事件
+    emit('success')
+  } finally {
+    formLoading.value = false
+  }
+}
+
+/** 重置表单 */
+const resetForm = () => {
+  formData.value = {
+    id: undefined,
+    supplierId: undefined,
+    name: undefined,
+    position: undefined,
+    telephone: undefined,
+    email: undefined,
+    productIds: undefined,
+    productNames: undefined,
+    remark: undefined,
+  }
+  formRef.value?.resetFields()
+}
+</script>

+ 206 - 0
src/views/supplier/contact/index.vue

@@ -0,0 +1,206 @@
+<template>
+  <ContentWrap>
+    <!-- 搜索工作栏 -->
+    <el-form
+      class="-mb-15px"
+      :model="queryParams"
+      ref="queryFormRef"
+      :inline="true"
+      label-width="68px"
+    >
+      <el-form-item label="姓名" prop="name">
+        <el-input
+          v-model="queryParams.name"
+          placeholder="请输入姓名"
+          clearable
+          @keyup.enter="handleQuery"
+          class="!w-240px"
+        />
+      </el-form-item>
+      <el-form-item label="职务" prop="position">
+        <el-input
+          v-model="queryParams.position"
+          placeholder="请输入职务"
+          clearable
+          @keyup.enter="handleQuery"
+          class="!w-240px"
+        />
+      </el-form-item>
+      <el-form-item label="电话" prop="telephone">
+        <el-input
+          v-model="queryParams.telephone"
+          placeholder="请输入电话"
+          clearable
+          @keyup.enter="handleQuery"
+          class="!w-240px"
+        />
+      </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('create')"
+        >
+          <Icon icon="ep:plus" class="mr-5px" /> 新增
+        </el-button>
+        <el-button
+          type="success"
+          plain
+          @click="handleExport"
+          :loading="exportLoading"
+          v-hasPermi="['supplier:contact:export']"
+        >
+          <Icon icon="ep:download" class="mr-5px" /> 导出
+        </el-button>
+      </el-form-item>
+    </el-form>
+  </ContentWrap>
+
+  <!-- 列表 -->
+  <ContentWrap>
+    <el-table v-loading="loading" :data="list" :stripe="true" :show-overflow-tooltip="true">
+      <el-table-column label="供应商" align="center" prop="supplierName" />
+      <el-table-column label="姓名" align="center" prop="name" />
+      <el-table-column label="职务" align="center" prop="position" />
+      <el-table-column label="电话" align="center" prop="telephone" />
+      <el-table-column label="邮箱" align="center" prop="email" />
+      <el-table-column label="联系人负责的产品/业务模块" align="center" prop="productIds" />
+      <el-table-column label="联系人负责的产品/业务模块" align="center" prop="productNames" />
+      <el-table-column label="备注" align="center" prop="remark" />
+      <el-table-column
+        label="创建时间"
+        align="center"
+        prop="createTime"
+        :formatter="dateFormatter"
+        width="180px"
+      />
+      <el-table-column label="操作" align="center" min-width="120px">
+        <template #default="scope">
+          <el-button
+            link
+            type="primary"
+            @click="openForm('update', scope.row.id)"
+
+          >
+            编辑
+          </el-button>
+          <el-button
+            link
+            type="danger"
+            @click="handleDelete(scope.row.id)"
+
+          >
+            删除
+          </el-button>
+        </template>
+      </el-table-column>
+    </el-table>
+    <!-- 分页 -->
+    <Pagination
+      :total="total"
+      v-model:page="queryParams.pageNo"
+      v-model:limit="queryParams.pageSize"
+      @pagination="getList"
+    />
+  </ContentWrap>
+
+  <!-- 表单弹窗:添加/修改 -->
+  <ContactForm ref="formRef" @success="getList" />
+</template>
+
+<script setup lang="ts">
+import { dateFormatter } from '@/utils/formatTime'
+import download from '@/utils/download'
+import { ContactApi, ContactVO } from '@/api/supplier/contact'
+import ContactForm from './ContactForm.vue'
+
+/** 供应商联系人 列表 */
+defineOptions({ name: 'SupplierContact' })
+
+const message = useMessage() // 消息弹窗
+const { t } = useI18n() // 国际化
+
+const loading = ref(true) // 列表的加载中
+const list = ref<ContactVO[]>([]) // 列表的数据
+const total = ref(0) // 列表的总页数
+const queryParams = reactive({
+  pageNo: 1,
+  pageSize: 10,
+  supplierId: undefined,
+  name: undefined,
+  position: undefined,
+  telephone: undefined,
+  email: undefined,
+  productIds: undefined,
+  productNames: undefined,
+  remark: undefined,
+  createTime: [],
+})
+const queryFormRef = ref() // 搜索的表单
+const exportLoading = ref(false) // 导出的加载中
+
+/** 查询列表 */
+const getList = async () => {
+  loading.value = true
+  try {
+    const data = await ContactApi.getContactPage(queryParams)
+    list.value = data.list
+    total.value = data.total
+  } finally {
+    loading.value = false
+  }
+}
+
+/** 搜索按钮操作 */
+const handleQuery = () => {
+  queryParams.pageNo = 1
+  getList()
+}
+
+/** 重置按钮操作 */
+const resetQuery = () => {
+  queryFormRef.value.resetFields()
+  handleQuery()
+}
+
+/** 添加/修改操作 */
+const formRef = ref()
+const openForm = (type: string, id?: number) => {
+  formRef.value.open(type, id)
+}
+
+/** 删除按钮操作 */
+const handleDelete = async (id: number) => {
+  try {
+    // 删除的二次确认
+    await message.delConfirm()
+    // 发起删除
+    await ContactApi.deleteContact(id)
+    message.success(t('common.delSuccess'))
+    // 刷新列表
+    await getList()
+  } catch {}
+}
+
+/** 导出按钮操作 */
+const handleExport = async () => {
+  try {
+    // 导出的二次确认
+    await message.exportConfirm()
+    // 发起导出
+    exportLoading.value = true
+    const data = await ContactApi.exportContact(queryParams)
+    download.excel(data, '供应商联系人.xls')
+  } catch {
+  } finally {
+    exportLoading.value = false
+  }
+}
+
+/** 初始化 **/
+onMounted(() => {
+  getList()
+})
+</script>

+ 106 - 0
src/views/supplier/coreproduct/CoreProductForm.vue

@@ -0,0 +1,106 @@
+<template>
+  <Dialog :title="dialogTitle" v-model="dialogVisible">
+    <el-form
+      ref="formRef"
+      :model="formData"
+      :rules="formRules"
+      label-width="100px"
+      v-loading="formLoading"
+    >
+      <el-form-item label="供应商id" prop="supplierId">
+        <el-input v-model="formData.supplierId" placeholder="请输入供应商id" />
+      </el-form-item>
+      <el-form-item label="产品id" prop="productId">
+        <el-input v-model="formData.productId" placeholder="请输入产品id" />
+      </el-form-item>
+      <el-form-item label="产品名称" prop="productName">
+        <el-input v-model="formData.productName" placeholder="请输入产品名称" />
+      </el-form-item>
+      <el-form-item label="优势介绍" prop="advantage">
+        <el-input v-model="formData.advantage" placeholder="请输入优势介绍" />
+      </el-form-item>
+    </el-form>
+    <template #footer>
+      <el-button @click="submitForm" type="primary" :disabled="formLoading">确 定</el-button>
+      <el-button @click="dialogVisible = false">取 消</el-button>
+    </template>
+  </Dialog>
+</template>
+<script setup lang="ts">
+import { CoreProductApi, CoreProductVO } from '@/api/supplier/coreproduct'
+
+/** 供应商核心产品 表单 */
+defineOptions({ name: 'CoreProductForm' })
+
+const { t } = useI18n() // 国际化
+const message = useMessage() // 消息弹窗
+
+const dialogVisible = ref(false) // 弹窗的是否展示
+const dialogTitle = ref('') // 弹窗的标题
+const formLoading = ref(false) // 表单的加载中:1)修改时的数据加载;2)提交的按钮禁用
+const formType = ref('') // 表单的类型:create - 新增;update - 修改
+const formData = ref({
+  id: undefined,
+  supplierId: undefined,
+  productId: undefined,
+  productName: undefined,
+  advantage: undefined,
+})
+const formRules = reactive({
+})
+const formRef = ref() // 表单 Ref
+
+/** 打开弹窗 */
+const open = async (type: string, id?: number) => {
+  dialogVisible.value = true
+  dialogTitle.value = t('action.' + type)
+  formType.value = type
+  resetForm()
+  // 修改时,设置数据
+  if (id) {
+    formLoading.value = true
+    try {
+      formData.value = await CoreProductApi.getCoreProduct(id)
+    } finally {
+      formLoading.value = false
+    }
+  }
+}
+defineExpose({ open }) // 提供 open 方法,用于打开弹窗
+
+/** 提交表单 */
+const emit = defineEmits(['success']) // 定义 success 事件,用于操作成功后的回调
+const submitForm = async () => {
+  // 校验表单
+  await formRef.value.validate()
+  // 提交请求
+  formLoading.value = true
+  try {
+    const data = formData.value as unknown as CoreProductVO
+    if (formType.value === 'create') {
+      await CoreProductApi.createCoreProduct(data)
+      message.success(t('common.createSuccess'))
+    } else {
+      await CoreProductApi.updateCoreProduct(data)
+      message.success(t('common.updateSuccess'))
+    }
+    dialogVisible.value = false
+    // 发送操作成功的事件
+    emit('success')
+  } finally {
+    formLoading.value = false
+  }
+}
+
+/** 重置表单 */
+const resetForm = () => {
+  formData.value = {
+    id: undefined,
+    supplierId: undefined,
+    productId: undefined,
+    productName: undefined,
+    advantage: undefined,
+  }
+  formRef.value?.resetFields()
+}
+</script>

+ 190 - 0
src/views/supplier/coreproduct/index.vue

@@ -0,0 +1,190 @@
+<template>
+  <ContentWrap>
+    <!-- 搜索工作栏 -->
+    <el-form
+      class="-mb-15px"
+      :model="queryParams"
+      ref="queryFormRef"
+      :inline="true"
+      label-width="68px"
+    >
+      <el-form-item label="产品名称" prop="productName">
+        <el-input
+          v-model="queryParams.productName"
+          placeholder="请输入产品名称"
+          clearable
+          @keyup.enter="handleQuery"
+          class="!w-240px"
+        />
+      </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-220px"
+        />
+      </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('create')"
+        >
+          <Icon icon="ep:plus" class="mr-5px" /> 新增
+        </el-button>
+        <el-button
+          type="success"
+          plain
+          @click="handleExport"
+          :loading="exportLoading"
+          v-hasPermi="['supplier:core-product:export']"
+        >
+          <Icon icon="ep:download" class="mr-5px" /> 导出
+        </el-button>
+      </el-form-item>
+    </el-form>
+  </ContentWrap>
+
+  <!-- 列表 -->
+  <ContentWrap>
+    <el-table v-loading="loading" :data="list" :stripe="true" :show-overflow-tooltip="true">
+      <el-table-column label="供应商id" align="center" prop="supplierId" />
+      <el-table-column label="产品名称" align="center" prop="productName" />
+      <el-table-column label="优势介绍" align="center" prop="advantage" />
+      <el-table-column
+        label="创建时间"
+        align="center"
+        prop="createTime"
+        :formatter="dateFormatter"
+        width="180px"
+      />
+      <el-table-column label="操作" align="center" min-width="120px">
+        <template #default="scope">
+          <el-button
+            link
+            type="primary"
+            @click="openForm('update', scope.row.id)"
+
+          >
+            编辑
+          </el-button>
+          <el-button
+            link
+            type="danger"
+            @click="handleDelete(scope.row.id)"
+
+          >
+            删除
+          </el-button>
+        </template>
+      </el-table-column>
+    </el-table>
+    <!-- 分页 -->
+    <Pagination
+      :total="total"
+      v-model:page="queryParams.pageNo"
+      v-model:limit="queryParams.pageSize"
+      @pagination="getList"
+    />
+  </ContentWrap>
+
+  <!-- 表单弹窗:添加/修改 -->
+  <CoreProductForm ref="formRef" @success="getList" />
+</template>
+
+<script setup lang="ts">
+import { dateFormatter } from '@/utils/formatTime'
+import download from '@/utils/download'
+import { CoreProductApi, CoreProductVO } from '@/api/supplier/coreproduct'
+import CoreProductForm from './CoreProductForm.vue'
+
+/** 供应商核心产品 列表 */
+defineOptions({ name: 'CoreProduct' })
+
+const message = useMessage() // 消息弹窗
+const { t } = useI18n() // 国际化
+
+const loading = ref(true) // 列表的加载中
+const list = ref<CoreProductVO[]>([]) // 列表的数据
+const total = ref(0) // 列表的总页数
+const queryParams = reactive({
+  pageNo: 1,
+  pageSize: 10,
+  supplierId: undefined,
+  productId: undefined,
+  productName: undefined,
+  advantage: undefined,
+  createTime: [],
+})
+const queryFormRef = ref() // 搜索的表单
+const exportLoading = ref(false) // 导出的加载中
+
+/** 查询列表 */
+const getList = async () => {
+  loading.value = true
+  try {
+    const data = await CoreProductApi.getCoreProductPage(queryParams)
+    list.value = data.list
+    total.value = data.total
+  } finally {
+    loading.value = false
+  }
+}
+
+/** 搜索按钮操作 */
+const handleQuery = () => {
+  queryParams.pageNo = 1
+  getList()
+}
+
+/** 重置按钮操作 */
+const resetQuery = () => {
+  queryFormRef.value.resetFields()
+  handleQuery()
+}
+
+/** 添加/修改操作 */
+const formRef = ref()
+const openForm = (type: string, id?: number) => {
+  formRef.value.open(type, id)
+}
+
+/** 删除按钮操作 */
+const handleDelete = async (id: number) => {
+  try {
+    // 删除的二次确认
+    await message.delConfirm()
+    // 发起删除
+    await CoreProductApi.deleteCoreProduct(id)
+    message.success(t('common.delSuccess'))
+    // 刷新列表
+    await getList()
+  } catch {}
+}
+
+/** 导出按钮操作 */
+const handleExport = async () => {
+  try {
+    // 导出的二次确认
+    await message.exportConfirm()
+    // 发起导出
+    exportLoading.value = true
+    const data = await CoreProductApi.exportCoreProduct(queryParams)
+    download.excel(data, '供应商核心产品.xls')
+  } catch {
+  } finally {
+    exportLoading.value = false
+  }
+}
+
+/** 初始化 **/
+onMounted(() => {
+  getList()
+})
+</script>