3 Commits 7659a03fba ... 7962a78103

Author SHA1 Message Date
  skyline 7962a78103 feat: 分页组件每页条数选项统一改为 10/20/50/100 4 days ago
  skyline cd201a7a9f feat: 门店操作按钮2×2布局 + 菜单图标补充 + 补货员管理入口隐藏 4 days ago
  skyline 906a7b5fd9 feat: vue-pure-admin升级至7.0.0 + 订单列表列合并优化 4 days ago

+ 7 - 1
haha-admin-web/build/plugins.ts

@@ -12,6 +12,7 @@ import { visualizer } from "rollup-plugin-visualizer";
 import removeConsole from "vite-plugin-remove-console";
 import VueI18nPlugin from "@intlify/unplugin-vue-i18n/vite";
 import { codeInspectorPlugin } from "code-inspector-plugin";
+import { vitePluginFakeServer } from "vite-plugin-fake-server";
 
 
 export async function getPluginsList(
@@ -51,7 +52,12 @@ export async function getPluginsList(
      * vite-plugin-router-warn只在开发环境下启用,只处理vue-router文件并且只在服务启动或重启时运行一次,性能消耗可忽略不计
      */
     removeNoMatch(),
-
+    vitePluginFakeServer({
+      logger: false,
+      include: "mock",
+      infixName: false,
+      enableProd: true
+    }),
     // svg组件化支持
     svgLoader(),
     // 自动按需加载图标

+ 18 - 4
haha-admin-web/eslint.config.js

@@ -5,6 +5,7 @@ import * as parserVue from "vue-eslint-parser";
 import configPrettier from "eslint-config-prettier";
 import pluginPrettier from "eslint-plugin-prettier";
 import { defineConfig, globalIgnores } from "eslint/config";
+import eslintPluginBetterTailwindcss from "eslint-plugin-better-tailwindcss";
 
 export default defineConfig([
   globalIgnores([
@@ -108,10 +109,7 @@ export default defineConfig([
   {
     files: ["**/*.d.ts"],
     rules: {
-      "eslint-comments/no-unlimited-disable": "off",
-      "import/no-duplicates": "off",
-      "no-restricted-syntax": "off",
-      "unused-imports/no-unused-vars": "off"
+      "no-restricted-syntax": "off"
     }
   },
   {
@@ -171,5 +169,21 @@ export default defineConfig([
         }
       ]
     }
+  },
+  {
+    files: ["**/*.vue", "**/*.tsx"],
+    plugins: {
+      "better-tailwindcss": eslintPluginBetterTailwindcss
+    },
+    rules: {
+      "better-tailwindcss/enforce-consistent-variable-syntax": "warn",
+      "better-tailwindcss/enforce-canonical-classes": "warn"
+    },
+    settings: {
+      "better-tailwindcss": {
+        entryPoint: "src/style/tailwind.css",
+        rootFontSize: 16
+      }
+    }
   }
 ]);

+ 12 - 0
haha-admin-web/mock/asyncRoutes.ts

@@ -0,0 +1,12 @@
+export default [
+  {
+    url: "/asyncRoutes",
+    method: "get",
+    response: () => {
+      return {
+        success: true,
+        data: []
+      };
+    }
+  }
+];

+ 44 - 41
haha-admin-web/package.json

@@ -49,14 +49,14 @@
     "@amap/amap-jsapi-loader": "^1.0.1",
     "@howdyjs/mouse-menu": "^2.1.7",
     "@infectoone/vue-ganttastic": "^2.3.2",
-    "@logicflow/core": "^1.2.28",
-    "@logicflow/extension": "^1.2.28",
+    "@logicflow/core": "^2.2.3",
+    "@logicflow/extension": "^2.2.3",
     "@pureadmin/descriptions": "^1.2.1",
     "@pureadmin/table": "^3.3.0",
     "@pureadmin/utils": "^2.6.4",
     "@vue-flow/background": "^1.3.2",
     "@vue-flow/core": "^1.48.2",
-    "@vueuse/core": "^14.2.1",
+    "@vueuse/core": "^14.3.0",
     "@vueuse/motion": "^3.0.3",
     "@wangeditor/editor": "^5.1.23",
     "@wangeditor/editor-for-vue": "^5.1.12",
@@ -68,14 +68,14 @@
     "codemirror": "^5.65.21",
     "codemirror-editor-vue3": "^2.8.0",
     "cropperjs": "^1.6.2",
-    "dayjs": "^1.11.20",
+    "dayjs": "^1.11.21",
     "deep-chat": "^2.4.2",
-    "echarts": "^6.0.0",
+    "echarts": "^6.1.0",
     "el-table-infinite-scroll": "^3.0.8",
-    "element-plus": "^2.13.7",
+    "element-plus": "^2.14.1",
     "highlight.js": "^11.11.1",
     "intro.js": "^7.2.0",
-    "js-cookie": "^3.0.5",
+    "js-cookie": "^3.0.8",
     "jsbarcode": "^3.12.3",
     "localforage": "^1.10.0",
     "mint-filter": "^4.0.3",
@@ -85,97 +85,99 @@
     "path-browserify": "^1.0.1",
     "pinia": "^3.0.4",
     "pinyin-pro": "^3.28.1",
-    "plus-pro-components": "^0.1.30",
+    "plus-pro-components": "^0.1.31",
     "qrcode": "^1.5.4",
-    "qs": "^6.15.1",
+    "qs": "^6.15.2",
     "responsive-storage": "^2.2.0",
     "sortablejs": "^1.15.7",
-    "swiper": "^12.1.3",
+    "swiper": "^14.0.1",
     "typeit": "^8.8.7",
     "v-contextmenu": "^3.2.0",
     "vditor": "^3.11.2",
     "version-rocket": "^1.7.4",
-    "vue": "^3.5.33",
-    "vue-i18n": "^11.4.0",
+    "vue": "^3.5.35",
+    "vue-i18n": "^11.4.4",
     "vue-json-pretty": "^2.6.0",
     "vue-pdf-embed": "^2.1.4",
-    "vue-router": "^5.0.6",
+    "vue-router": "^5.1.0",
     "vue-tippy": "^6.7.1",
     "vue-types": "^6.0.0",
-    "vue-virtual-scroller": "2.0.0-beta.10",
+    "vue-virtual-scroller": "^3.0.4",
     "vue-waterfall-plugin-next": "^2.6.9",
     "vue3-danmaku": "^1.6.7",
     "vue3-puzzle-vcode": "^1.1.7",
     "vuedraggable": "^4.1.0",
     "vxe-table": "4.6.25",
-    "wavesurfer.js": "^7.12.6",
+    "wavesurfer.js": "^7.12.7",
     "xgplayer": "^3.0.24",
     "xlsx": "^0.18.5"
   },
   "devDependencies": {
-    "@commitlint/cli": "^20.5.2",
-    "@commitlint/config-conventional": "^20.5.0",
-    "@commitlint/types": "^20.5.0",
+    "@commitlint/cli": "^21.0.2",
+    "@commitlint/config-conventional": "^21.0.2",
+    "@commitlint/types": "^21.0.1",
     "@eslint/js": "^10.0.1",
-    "@iconify/json": "^2.2.467",
+    "@faker-js/faker": "^10.4.0",
+    "@iconify/json": "^2.2.481",
     "@iconify/vue": "4.2.0",
-    "@intlify/unplugin-vue-i18n": "^11.1.2",
-    "@tailwindcss/vite": "^4.2.4",
+    "@intlify/unplugin-vue-i18n": "^11.2.3",
+    "@tailwindcss/vite": "^4.3.0",
     "@types/ali-oss": "^6.23.3",
     "@types/codemirror": "^5.60.17",
     "@types/dagre": "^0.7.54",
     "@types/intro.js": "^5.1.5",
     "@types/js-cookie": "^3.0.6",
-    "@types/node": "^20.19.39",
+    "@types/node": "^20.19.41",
     "@types/nprogress": "^0.2.3",
     "@types/path-browserify": "^1.0.3",
     "@types/qrcode": "^1.5.6",
-    "@types/qs": "^6.15.0",
+    "@types/qs": "^6.15.1",
     "@types/sortablejs": "^1.15.9",
-    "@vitejs/plugin-vue": "^6.0.6",
+    "@vitejs/plugin-vue": "^6.0.7",
     "@vitejs/plugin-vue-jsx": "^5.1.5",
     "boxen": "^8.0.1",
     "code-inspector-plugin": "^1.5.1",
-    "cssnano": "^7.1.7",
+    "cssnano": "^8.0.1",
     "dagre": "^0.8.5",
-    "eslint": "^10.2.1",
+    "eslint": "^10.4.1",
     "eslint-config-prettier": "^10.1.8",
-    "eslint-plugin-better-tailwindcss": "^4.4.1",
-    "eslint-plugin-prettier": "^5.5.5",
-    "eslint-plugin-vue": "^10.9.0",
+    "eslint-plugin-better-tailwindcss": "^4.5.0",
+    "eslint-plugin-prettier": "^5.5.6",
+    "eslint-plugin-vue": "^10.9.2",
     "gradient-string": "^3.0.0",
     "husky": "^9.1.7",
-    "lint-staged": "^16.4.0",
-    "postcss": "^8.5.12",
+    "lint-staged": "^17.0.7",
+    "postcss": "^8.5.15",
     "postcss-html": "^1.8.1",
     "postcss-load-config": "^6.0.1",
     "postcss-scss": "^4.0.9",
     "prettier": "^3.8.3",
     "rimraf": "^6.1.3",
-    "rollup-plugin-visualizer": "^6.0.11",
-    "sass": "^1.99.0",
-    "stylelint": "^17.9.1",
+    "rollup-plugin-visualizer": "^7.0.1",
+    "sass": "^1.100.0",
+    "stylelint": "^17.12.0",
     "stylelint-config-recess-order": "^7.7.0",
     "stylelint-config-recommended-vue": "^1.6.1",
     "stylelint-config-standard-scss": "^17.0.0",
     "stylelint-prettier": "^5.0.3",
     "svgo": "^4.0.1",
-    "tailwindcss": "^4.2.4",
+    "tailwindcss": "^4.3.0",
     "typescript": "^6.0.3",
-    "typescript-eslint": "^8.59.1",
+    "typescript-eslint": "^8.60.1",
     "unplugin-icons": "^23.0.1",
-    "vite": "^8.0.10",
+    "vite": "8.0.10",
     "vite-plugin-cdn-import": "^1.0.1",
     "vite-plugin-compression": "^0.5.1",
+    "vite-plugin-fake-server": "^2.2.4",
     "vite-plugin-remove-console": "^2.2.0",
     "vite-plugin-router-warn": "^2.0.0",
     "vite-svg-loader": "^5.1.1",
-    "vue-eslint-parser": "^10.4.0",
-    "vue-tsc": "^3.2.7"
+    "vue-eslint-parser": "^10.4.1",
+    "vue-tsc": "^3.3.3"
   },
   "engines": {
-    "node": "^20.19.0 || >=22.13.0",
-    "pnpm": ">=9"
+    "node": ">=22.22.1",
+    "pnpm": ">=10"
   },
   "pnpm": {
     "allowedDeprecatedVersions": {
@@ -193,6 +195,7 @@
       "glob": "*"
     },
     "onlyBuiltDependencies": [
+      "@logicflow/core",
       "@parcel/watcher",
       "core-js",
       "es5-ext",

File diff suppressed because it is too large
+ 305 - 271
haha-admin-web/pnpm-lock.yaml


+ 11 - 9
haha-admin-web/src/router/modules/operation.ts

@@ -35,20 +35,22 @@ export default {
         title: "门店分布地图"
       }
     },
-    {
-      path: "/operation/replenisher",
-      name: "ReplenisherList",
-      component: () => import("@/views/replenisher/index.vue"),
-      meta: {
-        icon: "ri:user-star-line",
-        title: "补货员管理"
-      }
-    },
+    // 补货员管理(暂时隐藏入口)
+    // {
+    //   path: "/operation/replenisher",
+    //   name: "ReplenisherList",
+    //   component: () => import("@/views/replenisher/index.vue"),
+    //   meta: {
+    //     icon: "ri:user-star-line",
+    //     title: "补货员管理"
+    //   }
+    // },
     {
       path: "/operation/erp-shop",
       name: "ErpShopList",
       component: () => import("@/views/erp-shop/index.vue"),
       meta: {
+        icon: "ri:store-2-line",
         title: "ERP店铺管理"
       }
     },

+ 1 - 0
haha-admin-web/src/router/modules/product.ts

@@ -40,6 +40,7 @@ export default {
       name: "ErpGoodsList",
       component: () => import("@/views/erp-goods/index.vue"),
       meta: {
+        icon: "ri:links-line",
         title: "ERP商品关联"
       }
     }

+ 1 - 0
haha-admin-web/src/utils/paginationHelper.ts

@@ -14,6 +14,7 @@ export function initPagination(): PaginationProps {
     pageSize: 10,
     currentPage: 1,
     background: true,
+    pageSizes: [10, 20, 50, 100],
     layout: "total, sizes, prev, pager, next, jumper"
   };
 }

+ 1 - 1
haha-admin-web/src/views/erp-goods/index.vue

@@ -320,7 +320,7 @@ onMounted(() => {
           v-model:current-page="pagination.currentPage"
           v-model:page-size="pagination.pageSize"
           :total="total"
-          :page-sizes="[10, 20, 50]"
+          :page-sizes="[10, 20, 50, 100]"
           layout="total, sizes, prev, pager, next, jumper"
           background
           @current-change="handlePageChange"

+ 1 - 1
haha-admin-web/src/views/erp-shop/index.vue

@@ -274,7 +274,7 @@ onMounted(() => {
           v-model:current-page="pagination.currentPage"
           v-model:page-size="pagination.pageSize"
           :total="total"
-          :page-sizes="[10, 20, 50]"
+          :page-sizes="[10, 20, 50, 100]"
           layout="total, sizes, prev, pager, next, jumper"
           background
           @current-change="handlePageChange"

+ 1 - 1
haha-admin-web/src/views/order/refund/utils/hook.tsx

@@ -157,7 +157,7 @@ export function useRefund(tableRef: Ref) {
             <div style="font-size: 15px; font-weight: 600; margin-bottom: 10px; color: var(--el-text-color-primary);">基本信息</div>
             <ElDescriptions column={2} border size="small">
               <ElDescriptionsItem label="订单编号">{order.orderNo || "-"}</ElDescriptionsItem>
-              <ElDescriptionsItem label="支付订单号">{order.outTradeNo || "-"}</ElDescriptionsItem>
+              <ElDescriptionsItem label="支付订单号">{order.transactionId || "-"}</ElDescriptionsItem>
               <ElDescriptionsItem label="用户ID">{order.userId || "-"}</ElDescriptionsItem>
               <ElDescriptionsItem label="手机号">{order.phone || "-"}</ElDescriptionsItem>
               <ElDescriptionsItem label="订单总金额">

+ 32 - 32
haha-admin-web/src/views/order/utils/hook.tsx

@@ -54,34 +54,34 @@ export function useOrder(tableRef: Ref) {
 
   const columns: TableColumnList = [
     {
-      label: "订单编号",
+      label: "订单编号 / 活动ID",
       prop: "orderNo",
-      minWidth: 160,
-      formatter: ({ orderNo }) => orderNo || "-"
-    },
-    {
-      label: "活动ID",
-      prop: "activityId",
-      minWidth: 120,
-      formatter: ({ activityId }) => activityId || "-"
+      minWidth: 180,
+      cellRenderer: ({ row }) => (
+        <div style="line-height: 1.6">
+          <div>{row.orderNo || "-"}</div>
+          <div style="border-top: 1px solid var(--el-border-color-light); margin: 2px 0"></div>
+          <div style="color: var(--el-text-color-regular); font-size: 14px">{row.activityId || "-"}</div>
+        </div>
+      )
     },
     {
       label: "支付订单号",
-      prop: "outTradeNo",
+      prop: "transactionId",
       minWidth: 150,
-      formatter: ({ outTradeNo }) => outTradeNo || "-"
+      formatter: ({ transactionId }) => transactionId || "-"
     },
     {
-      label: "用户 ID",
+      label: "用户ID / 手机号",
       prop: "userId",
-      minWidth: 80,
-      formatter: ({ userId }) => userId || "-"
-    },
-    {
-      label: "手机号",
-      prop: "phone",
-      minWidth: 120,
-      formatter: ({ phone }) => phone || "-"
+      minWidth: 140,
+      cellRenderer: ({ row }) => (
+        <div style="line-height: 1.6">
+          <div>{row.userId || "-"}</div>
+          <div style="border-top: 1px solid var(--el-border-color-light); margin: 2px 0"></div>
+          <div style="color: var(--el-text-color-regular); font-size: 14px">{row.phone || "-"}</div>
+        </div>
+      )
     },
     {
       label: "门店名称",
@@ -191,18 +191,18 @@ export function useOrder(tableRef: Ref) {
       }
     },
     {
-      label: "下单时间",
+      label: "下单时间 / 支付时间",
       prop: "createTime",
-      minWidth: 160,
-      formatter: ({ createTime }) =>
-        createTime ? dayjs(createTime).format("YYYY-MM-DD HH:mm:ss") : "-"
-    },
-    {
-      label: "支付时间",
-      prop: "payTime",
-      minWidth: 160,
-      formatter: ({ payTime }) =>
-        payTime ? dayjs(payTime).format("YYYY-MM-DD HH:mm:ss") : "-"
+      minWidth: 180,
+      cellRenderer: ({ row }) => (
+        <div style="line-height: 1.6">
+          <div>{row.createTime ? dayjs(row.createTime).format("YYYY-MM-DD HH:mm:ss") : "-"}</div>
+          <div style="border-top: 1px solid var(--el-border-color-light); margin: 2px 0"></div>
+          <div style="color: var(--el-text-color-regular); font-size: 14px">
+            {row.payTime ? dayjs(row.payTime).format("YYYY-MM-DD HH:mm:ss") : "-"}
+          </div>
+        </div>
+      )
     },
     {
       label: "操作",
@@ -353,7 +353,7 @@ export function useOrder(tableRef: Ref) {
             <ElDescriptions column={3} border size="small">
               <ElDescriptionsItem label="订单编号" span={2}>{order.orderNo}</ElDescriptionsItem>
               <ElDescriptionsItem label="门店名称">{order.shopName || "-"}</ElDescriptionsItem>
-              <ElDescriptionsItem label="支付订单号" span={2}>{order.outTradeNo || "-"}</ElDescriptionsItem>
+              <ElDescriptionsItem label="支付订单号" span={2}>{order.transactionId || "-"}</ElDescriptionsItem>
               <ElDescriptionsItem label="设备 ID">{order.deviceId || "-"}</ElDescriptionsItem>
               <ElDescriptionsItem label="活动 ID" span={2}>{order.activityId || "-"}</ElDescriptionsItem>
               <ElDescriptionsItem label="用户 ID">{order.userId || "-"}</ElDescriptionsItem>

+ 1 - 1
haha-admin-web/src/views/order/utils/types.ts

@@ -3,7 +3,7 @@ export interface OrderItem {
   id: number;
   orderNo: string;
   orderName?: string;
-  outTradeNo?: string;
+  transactionId?: string;
   activityId?: string;
   userId: number;
   phone?: string;

+ 46 - 50
haha-admin-web/src/views/shop/index.vue

@@ -123,62 +123,58 @@ const {
           @page-current-change="handleCurrentChange"
         >
           <template #operation="{ row }">
-            <el-button
-              class="reset-margin"
-              link
-              type="primary"
-              :size="size"
-              :icon="useRenderIcon(EditPen)"
-              @click="openDialog('修改', row)"
-            >
-              编辑
-            </el-button>
-            <el-button
-              class="reset-margin"
-              link
-              type="primary"
-              :size="size"
-              :icon="useRenderIcon(Link)"
-              @click="handleDevices(row)"
-            >
-              设备
-            </el-button>
-            <el-button
-              class="reset-margin"
-              link
-              type="primary"
-              :size="size"
-              :icon="useRenderIcon(User)"
-              @click="handleReplenishers(row)"
-            >
-              补货员
-            </el-button>
-            <el-button
-              class="reset-margin"
-              link
-              :type="row.status === 1 ? 'danger' : 'success'"
-              :size="size"
-              :icon="useRenderIcon(row.status === 1 ? Lock : Unlock)"
-              @click="handleToggleStatus(row)"
-            >
-              {{ row.status === 1 ? "停业" : "营业" }}
-            </el-button>
-            <el-popconfirm
-              :title="`是否确认删除门店 ${row.name}?`"
-              @confirm="handleDelete(row)"
-            >
-              <template #reference>
+            <div style="display:flex;flex-direction:column;align-items:center;gap:2px">
+              <div style="display:flex;align-items:center;justify-content:center;gap:2px">
                 <el-button
                   class="reset-margin"
                   link
-                  type="danger"
+                  type="primary"
                   :size="size"
-                  :icon="useRenderIcon(Delete)"
+                  :icon="useRenderIcon(EditPen)"
+                  @click="openDialog('修改', row)"
                 >
-                  删除
+                  编辑
                 </el-button>
-              </template>
-            </el-popconfirm>
+                <el-button
+                  class="reset-margin"
+                  link
+                  type="primary"
+                  :size="size"
+                  :icon="useRenderIcon(Link)"
+                  @click="handleDevices(row)"
+                >
+                  设备
+                </el-button>
+              </div>
+              <div style="display:flex;align-items:center;gap:2px">
+                <el-button
+                  class="reset-margin"
+                  link
+                  :type="row.status === 1 ? 'danger' : 'success'"
+                  :size="size"
+                  :icon="useRenderIcon(row.status === 1 ? Lock : Unlock)"
+                  @click="handleToggleStatus(row)"
+                >
+                  {{ row.status === 1 ? "停业" : "营业" }}
+                </el-button>
+                <el-popconfirm
+                  :title="`是否确认删除门店 ${row.name}?`"
+                  @confirm="handleDelete(row)"
+                >
+                  <template #reference>
+                    <el-button
+                      class="reset-margin"
+                      link
+                      type="danger"
+                      :size="size"
+                      :icon="useRenderIcon(Delete)"
+                    >
+                      删除
+                    </el-button>
+                  </template>
+                </el-popconfirm>
+              </div>
+            </div>
           </template>
         </pure-table>
       </template>

Some files were not shown because too many files changed in this diff