Răsfoiți Sursa

```
feat(delivery): 新增积分明细页面并更新相关配置

- 添加 delivery_ponits-details 页面路由配置
- 在国际化文件中添加积分明细相关词条
- 更新路由映射和类型定义
- 创建积分明细 API 接口文件
- 添加积分明细页面组件实现表格展示、搜索和导出功能

fix(goods): 修复商品管理页面字段映射和显示问题

- 将价格字段从 channelProdPrice 改为 price
- 使用 channelVOS 替代 channelProdList 进行数据渲染
- 添加商品状态显示和过滤功能
- 修复价格编辑和删除逻辑中的字段引用错误

refactor(normal-order): 注释掉待拆单状态选项

- 临时禁用 normal-order 页面中的待拆单状态筛选功能

chore(env): 更新测试环境服务基础URL

- 将测试环境的服务基础URL从旧地址切换到新地址
```

wenjie 1 săptămână în urmă
părinte
comite
b416c61e13

+ 1 - 1
.env.test

@@ -1,6 +1,6 @@
 # backend service base url, test environment
 # VITE_SERVICE_BASE_URL=http://74949mkfh190.vicp.fun
-# VITE_SERVICE_BASE_URL=http://22b0cfad.r36.cpolar.top #付
+# VITE_SERVICE_BASE_URL=http://69a076ff.r36.cpolar.top #付
 # VITE_SERVICE_BASE_URL=http://192.168.0.157:8114 #王
 # VITE_SERVICE_BASE_URL=http://89561bkaq794.vicp.fun:53846 #张
 # VITE_SERVICE_BASE_URL=http://192.168.1.66:8114 #邓

+ 2 - 1
src/locales/langs/en-us.ts

@@ -310,7 +310,8 @@ const local: App.I18n.Schema = {
     finance: '',
     'finance_commodity-freight': '',
     finance_summary: '',
-    config_dict: ''
+    config_dict: '',
+    'delivery_ponits-details': ''
   },
   page: {
     login: {

+ 2 - 1
src/locales/langs/zh-cn.ts

@@ -307,7 +307,8 @@ const local: App.I18n.Schema = {
     finance: '',
     'finance_commodity-freight': '',
     finance_summary: '',
-    config_dict: ''
+    config_dict: '',
+    'delivery_ponits-details': ''
   },
   page: {
     login: {

+ 1 - 0
src/router/elegant/imports.ts

@@ -26,6 +26,7 @@ export const views: Record<LastLevelRouteKey, RouteComponent | (() => Promise<Ro
   "config_order-split": () => import("@/views/config/order-split/index.vue"),
   "delivery_after-sales-order": () => import("@/views/delivery/after-sales-order/index.vue"),
   "delivery_normal-order": () => import("@/views/delivery/normal-order/index.vue"),
+  "delivery_ponits-details": () => import("@/views/delivery/ponits-details/index.vue"),
   "delivery_split-order-detail": () => import("@/views/delivery/split-order-detail/index.vue"),
   "delivery_split-order": () => import("@/views/delivery/split-order/index.vue"),
   "finance_commodity-freight": () => import("@/views/finance/commodity-freight/index.vue"),

+ 9 - 0
src/router/elegant/routes.ts

@@ -115,6 +115,15 @@ export const generatedRoutes: GeneratedRoute[] = [
           i18nKey: 'route.delivery_normal-order'
         }
       },
+      {
+        name: 'delivery_ponits-details',
+        path: '/delivery/ponits-details',
+        component: 'view.delivery_ponits-details',
+        meta: {
+          title: 'delivery_ponits-details',
+          i18nKey: 'route.delivery_ponits-details'
+        }
+      },
       {
         name: 'delivery_split-order',
         path: '/delivery/split-order',

+ 1 - 0
src/router/elegant/transform.ts

@@ -189,6 +189,7 @@ const routeMap: RouteMap = {
   "delivery": "/delivery",
   "delivery_after-sales-order": "/delivery/after-sales-order",
   "delivery_normal-order": "/delivery/normal-order",
+  "delivery_ponits-details": "/delivery/ponits-details",
   "delivery_split-order": "/delivery/split-order",
   "delivery_split-order-detail": "/delivery/split-order-detail",
   "finance": "/finance",

+ 13 - 0
src/service/api/delivery/ponits-details/index.ts

@@ -0,0 +1,13 @@
+import { request } from '@/service/request';
+/**
+ * 分页获取商品
+ * @param params
+ * @returns
+ */
+export function fetchList(data: any) {
+  return request({
+    url: '/platform/pointsRecord/backendPointsRecordList',
+    method: 'get',
+    params: data
+  });
+}

+ 2 - 0
src/typings/elegant-router.d.ts

@@ -43,6 +43,7 @@ declare module "@elegant-router/types" {
     "delivery": "/delivery";
     "delivery_after-sales-order": "/delivery/after-sales-order";
     "delivery_normal-order": "/delivery/normal-order";
+    "delivery_ponits-details": "/delivery/ponits-details";
     "delivery_split-order": "/delivery/split-order";
     "delivery_split-order-detail": "/delivery/split-order-detail";
     "finance": "/finance";
@@ -203,6 +204,7 @@ declare module "@elegant-router/types" {
     | "config_order-split"
     | "delivery_after-sales-order"
     | "delivery_normal-order"
+    | "delivery_ponits-details"
     | "delivery_split-order-detail"
     | "delivery_split-order"
     | "finance_commodity-freight"

+ 4 - 4
src/views/delivery/normal-order/index.vue

@@ -402,10 +402,10 @@ async function getNums() {
       label: '待支付',
       value: 'paddingPay'
     },
-    {
-      label: '待拆单',
-      value: 'split'
-    },
+    // {
+    //   label: '待拆单',
+    //   value: 'split'
+    // },
     {
       label: '待发货',
       value: 'paddingShipped'

+ 162 - 0
src/views/delivery/ponits-details/index.vue

@@ -0,0 +1,162 @@
+<script setup lang="tsx">
+// import dayjs from 'dayjs';
+// import { fetchGetStoreList } from '@/service/api/xsb-manage/store-info';
+import { computed } from 'vue';
+import { fetchList } from '@/service/api/delivery/ponits-details';
+import { commonExport } from '@/utils/common';
+import { useTable } from '@/components/zt/Table/hooks/useTable';
+
+const columns: NaiveUI.TableColumn<Api.goods.ShopSku>[] = [
+  {
+    key: 'orderNumber',
+    align: 'center',
+    title: '流水号'
+  },
+  {
+    key: 'realName',
+    title: '姓名',
+    align: 'center'
+  },
+  {
+    key: 'mobile',
+    title: '用户手机号',
+    align: 'center'
+  },
+  {
+    key: 'businessType',
+    title: '业务场景',
+    align: 'center'
+  },
+  {
+    key: 'variablePoints',
+    title: '变动积分',
+    align: 'center'
+  },
+  {
+    key: 'currentlyAvailablePoints',
+    title: '变动后积分',
+    align: 'center'
+  },
+  // {
+  //   key: 'receiveTime',
+  //   title: '变动前积分',
+  //   align: 'center',
+  //   width: 120,
+  //   ellipsis: {
+  //     tooltip: true
+  //   }
+  // },
+  {
+    key: 'creationDate',
+    title: '更新时间',
+    align: 'center'
+  }
+];
+
+const [registerTable, { getTableData, getSeachForm, setTableLoading }] = useTable({
+  searchFormConfig: {
+    schemas: [
+      {
+        label: '手机号',
+        component: 'NInput',
+        field: 'mobile'
+      },
+      {
+        label: '业务场景',
+        component: 'NSelect',
+        field: 'businessType',
+        componentProps: {
+          options: [
+            {
+              label: '充值',
+              value: 'CZ'
+            },
+            {
+              label: '过期',
+              value: 'GQ'
+            },
+            {
+              label: '退款过期',
+              value: 'TKGQ'
+            },
+            {
+              label: '退款',
+              value: 'TK'
+            },
+            {
+              label: '星闪豹',
+              value: 'XSB'
+            },
+            {
+              label: '充电',
+              value: 'CD'
+            },
+
+            {
+              label: '电影',
+              value: 'DYY'
+            },
+            {
+              label: '虚拟商品',
+              value: 'XNSP'
+            },
+            {
+              label: '大健康',
+              value: 'DJK'
+            }
+          ]
+        }
+      },
+
+      {
+        label: '更新时间',
+        component: 'NDatePicker',
+        field: 'createTime',
+        componentProps: {
+          type: 'datetimerange',
+          defaultTime: ['00:00:00', '23:59:59']
+        }
+      }
+    ],
+    inline: false,
+    size: 'small',
+    labelPlacement: 'left',
+    isFull: false
+  },
+  tableConfig: {
+    keyField: 'skuId',
+    title: '积分明细',
+    showAddButton: false,
+    fieldMapToTime: [['createTime', ['startTime', 'endTime']]]
+  }
+});
+
+const tableData = computed(() => {
+  return getTableData();
+});
+
+async function handleExport() {
+  setTableLoading(true);
+  try {
+    await commonExport('/platform/pointsRecord/backendPointsRecordListExport', getSeachForm(), '积分明细.xlsx');
+  } finally {
+    setTableLoading(false);
+  }
+}
+</script>
+
+<template>
+  <LayoutTable>
+    <ZTable :columns="columns" :show-table-action="false" :api="fetchList" @register="registerTable">
+      <template #prefix="{ loading }">
+        <NSpace>
+          <NButton size="small" :disabled="tableData.length == 0" :loading="loading" @click="handleExport">
+            导出全部
+          </NButton>
+        </NSpace>
+      </template>
+    </ZTable>
+  </LayoutTable>
+</template>
+
+<style scoped></style>

+ 130 - 40
src/views/goods/store-goods/index.vue

@@ -14,10 +14,11 @@ import { commonExport } from '@/utils/common';
 import { useTable } from '@/components/zt/Table/hooks/useTable';
 import SvgIcon from '@/components/custom/svg-icon.vue';
 import { useModal } from '@/components/zt/Modal/hooks/useModal';
-type Price = { channelId: number | undefined; channelProdPrice: number; id: number };
+type Price = { channelId: number | undefined; price: number; id: number };
 const importTemplateRef = useTemplateRef('importTemplateRef');
 const options = ref<Api.goods.Channel[]>([]);
 const TypeName = ['企业用户', 'B端用户', 'C端用户'];
+const statusList = ['商家下架', '上架', '违规下架', '平台审核'];
 
 const columns: NaiveUI.TableColumn<Api.goods.ShopSku>[] = [
   {
@@ -73,42 +74,62 @@ const columns: NaiveUI.TableColumn<Api.goods.ShopSku>[] = [
     align: 'center',
     width: 120
   },
-  {
-    key: 'purchasePrice',
-    title: '进货价(元)',
-    align: 'center',
-    width: 120,
-    render: row => {
-      if (!row.channelProdList?.length) return '--';
-      if (row.channelProdList) return <div>{row.channelProdList[0].purchasePrice || '--'}</div>;
-      return '--';
-    }
-  },
-  {
-    key: 'deliveryPrice',
-    title: '出货价/控制价(元)',
-    align: 'center',
-    width: 150,
-    render: row => {
-      if (!row.channelProdList?.length) return '--';
-      if (row.channelProdList) return <div>{row.channelProdList[0].deliveryPrice || '--'}</div>;
-      return '--';
-    }
-  },
+  // {
+  //   key: 'purchasePrice',
+  //   title: '进货价(元)',
+  //   align: 'center',
+  //   width: 120,
+  //   render: row => {
+  //     if (!row.channelVOS?.length) return '--';
+  //     if (row.channelVOS) return <div>{row.channelVOS[0].purchasePrice || '--'}</div>;
+  //     return '--';
+  //   }
+  // },
+  // {
+  //   key: 'deliveryPrice',
+  //   title: '出货价/控制价(元)',
+  //   align: 'center',
+  //   width: 150,
+  //   render: row => {
+  //     if (!row.channelVOS?.length) return '--';
+  //     if (row.channelVOS) return <div>{row.channelVOS[0].deliveryPrice || '--'}</div>;
+  //     return '--';
+  //   }
+  // },
   {
     key: 'name',
     title: '销售渠道及价格',
     align: 'center',
     width: 250,
     render: row => {
-      return row.channelProdList?.map(it => {
+      return row.channelVOS?.map((it: any) => {
         return (
           <div>
-            {TypeName[Number(it.channelId) - 1]} ({it.channelName || '--'}) : {it.channelProdPrice || '--'}
+            {TypeName[Number(it.channelId) - 1]} ({it.channelName || '--'}) : {it.price || '--'}
           </div>
         );
       });
     }
+  },
+  {
+    key: 'status',
+    title: '状态',
+    align: 'center',
+    width: 120,
+    render: (row: any) => {
+      return (
+        <div class="flex items-center justify-center">
+          <n-badge color={row.status == 1 ? 'green' : 'red'} value={row.status} dot />
+          <span class="ml-2">{statusList[row.status]}</span>
+        </div>
+      );
+    }
+  },
+  {
+    key: 'updateTime',
+    title: '更新时间',
+    align: 'center',
+    width: 120
   }
 ];
 const PriceColumns: NaiveUI.TableColumn<Price>[] = [
@@ -153,16 +174,16 @@ const PriceColumns: NaiveUI.TableColumn<Price>[] = [
   },
   {
     title: '售价(元)',
-    key: 'channelProdPrice',
+    key: 'price',
     align: 'center',
     width: 250,
     render: row => {
       return (
         <NInputNumber
-          value={row.channelProdPrice}
+          value={row.price}
           precision={2}
           onUpdate:value={value => {
-            row.channelProdPrice = Number(value);
+            row.price = Number(value);
           }}
           min={0}
         />
@@ -186,7 +207,7 @@ const PriceColumns: NaiveUI.TableColumn<Price>[] = [
     align: 'center',
     render: row => {
       return (
-        <div onClick={() => handleDelPrice(row.id)} class={'w-full flex items-center justify-center'}>
+        <div onClick={() => handleDelPrice(row.channelId as number)} class={'w-full flex items-center justify-center'}>
           <SvgIcon
             icon={'proicons:subtract-square'}
             class={'cursor-pointer text-24px'}
@@ -216,6 +237,69 @@ const [registerTable, { getTableCheckedRowKeys, refresh, getTableData, getSeachF
         label: '商品名称',
         component: 'NInput',
         field: 'skuName'
+      },
+      {
+        label: '关键词',
+        component: 'NInput',
+        field: 'keywords',
+        componentProps: {
+          placeholder: '请输入商品名称/海博商品ID'
+        }
+      },
+      {
+        label: '状态',
+        field: 'status',
+        component: 'NSelect',
+        componentProps: {
+          options: [
+            {
+              label: '商家下架',
+              value: 0
+            },
+            {
+              label: '上架',
+              value: 1
+            },
+            {
+              label: '违规下架',
+              value: 2
+            },
+            {
+              label: '平台审核',
+              value: 3
+            }
+          ]
+        }
+      },
+      {
+        label: '更新时间',
+        component: 'NDatePicker',
+        field: 'createTime',
+        componentProps: {
+          type: 'datetimerange',
+          defaultTime: ['00:00:00', '23:59:59']
+        }
+      },
+      {
+        label: '价格范围',
+        component: 'NInput',
+        field: 'price',
+        componentProps: {
+          separator: '-',
+          pair: true,
+          placeholder: ['最低价', '最高价'],
+          allowInput: (value: string) => !value || /^\d+$/.test(value)
+        }
+      },
+      {
+        label: '海博商品ID',
+        component: 'NInput',
+        field: 'hbSkuId'
+      },
+      {
+        label: '商品编码',
+        component: 'NInput',
+        field: 'skuCode'
       }
     ],
     inline: false,
@@ -227,7 +311,11 @@ const [registerTable, { getTableCheckedRowKeys, refresh, getTableData, getSeachF
     keyField: 'id',
     title: '商品列表',
     showAddButton: false,
-    scrollX: 1800
+    scrollX: 1800,
+    fieldMapToTime: [
+      ['price', ['minPrice', 'maxPrice']],
+      ['createTime', ['startTime', 'endTime']]
+    ]
   }
 });
 
@@ -260,8 +348,8 @@ function openImportModal() {
 function handleModalPrice(row: Api.goods.ShopSku) {
   selectData.value = row;
 
-  if (row.channelProdList) {
-    PriceData.value = row.channelProdList?.map(it => {
+  if (row.channelVOS) {
+    PriceData.value = row.channelVOS?.map((it: any) => {
       options.value.map(its => {
         if (its.id == it.channelId) {
           its.disabled = true;
@@ -271,7 +359,7 @@ function handleModalPrice(row: Api.goods.ShopSku) {
 
       return {
         channelId: Number(it.channelId),
-        channelProdPrice: Number(it.channelProdPrice),
+        price: Number(it.price),
         id: Number(it.id)
       };
     });
@@ -285,18 +373,20 @@ function handleAddPrice() {
   }
   PriceData.value.push({
     channelId: undefined,
-    channelProdPrice: 1,
+    price: 1,
     id: dayjs().valueOf()
   });
 }
 function handleDelPrice(id: number) {
-  PriceData.value = PriceData.value.filter(item => item.id != id);
+  console.log(id);
+
+  PriceData.value = PriceData.value.filter(item => item.channelId != id);
 }
 
 async function handleSubmitPrice() {
   if (!PriceData.value.length) {
-    window.$message?.error('最少填写一条数据');
-    return;
+    // window.$message?.error('最少填写一条数据');
+    // return;
   }
   if (!areAllItemsAllFieldsFilled(PriceData.value)) {
     window.$message?.error('请填写完整数据');
@@ -306,12 +396,12 @@ async function handleSubmitPrice() {
   const form = {
     shopId: selectData.value?.shopId,
     skuId: selectData.value?.skuId,
-    purchasePrice: selectData.value?.channelProdList?.length ? selectData.value.channelProdList[0].purchasePrice : null,
-    deliveryPrice: selectData.value?.channelProdList?.length ? selectData.value.channelProdList[0].deliveryPrice : null,
+    purchasePrice: selectData.value?.channelVOS?.length ? selectData.value.channelVOS[0].purchasePrice : null,
+    deliveryPrice: selectData.value?.channelVOS?.length ? selectData.value.channelVOS[0].deliveryPrice : null,
     setChannelPriceDtoList: PriceData.value.map(item => {
       return {
         channelId: item.channelId,
-        channelProdPrice: item.channelProdPrice
+        channelProdPrice: item.price
       };
     })
   };