Project.Fengling.QoderVersion/docs/frontend/前端功能概览.md
sam 056eb9b6f9 feat: 实现完整的前后端功能
- 后端新增管理员、商品、分类聚合模型
- 实现积分规则、礼品、订单、会员等完整功能
- 添加管理员认证和权限管理
- 完善数据库迁移和实体配置
- 前端管理后台实现登录、仪表盘、积分规则、礼品、订单、会员等页面
- 集成shadcn-vue UI组件库
- 添加前后端功能文档和截图
2026-02-11 21:36:37 +08:00

383 lines
15 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

## 前端管理后台功能概览
> 本文档说明管理后台前端(Fengling.Backend.Admin)的技术实现与功能模块,便于后续开发和前后端联调。
> 最后更新时间2026-02-11
---
## 一、整体技术栈与架构
### 1.1 技术栈
- **Vue 3.5** - Composition API + `<script setup>` 语法
- **TypeScript 5.9** - 强类型,启用 `erasableSyntaxOnly`
- **Vite 7.3** - 构建工具,开发服务器端口 3000
- **pnpm** - 包管理器
- **shadcn-vue** - UI 组件库(基于 Radix Vue + Tailwind CSS v4
- **Vue Router 4** - 路由管理,支持路由守卫
- **Pinia 3** - 状态管理
- **Axios** - HTTP 客户端,含拦截器
- **lucide-vue-next** - 图标库
- **vue-sonner** - Toast 消息提示
### 1.2 架构风格
- **模块化目录结构**按功能模块组织页面、API、类型
- **API 服务层**:每个后端模块对应一个 `api/*.ts` 文件,统一解包 `ResponseData<T>`
- **类型安全**:所有后端 DTO 在 `types/` 中有对应 TypeScript 接口
- **路由懒加载**:所有页面组件使用 `() => import()` 动态导入
- **Mock 认证**:当前使用模拟 Token后端 JWT 完善后可无缝切换
---
## 二、项目结构
```
Frontend/Fengling.Backend.Admin/
├── src/
│ ├── api/ # API 服务层
│ │ ├── client.ts # Axios 实例 + 请求/响应拦截器
│ │ ├── gifts.ts # 礼品管理 API7 个函数)
│ │ ├── orders.ts # 订单管理 API5 个函数)
│ │ ├── marketing-codes.ts # 营销码 API
│ │ ├── points-rules.ts # 积分规则 API
│ │ └── members.ts # 会员查询 API
│ ├── components/
│ │ ├── layout/ # 布局组件
│ │ │ ├── AdminLayout.vue # 主布局(侧边栏 + Header + 内容区)
│ │ │ ├── Sidebar.vue # 左侧导航菜单
│ │ │ └── Header.vue # 顶部面包屑导航
│ │ └── ui/ # shadcn-vue 组件20+ 组件)
│ ├── lib/
│ │ ├── utils.ts # cn() class 合并工具
│ │ └── constants.ts # formatDate, truncateId, copyToClipboard 等工具函数
│ ├── pages/ # 页面组件9 个页面)
│ │ ├── auth/Login.vue
│ │ ├── dashboard/Dashboard.vue
│ │ ├── gifts/GiftList.vue, GiftForm.vue
│ │ ├── orders/OrderList.vue, OrderDetail.vue
│ │ ├── marketing-codes/MarketingCodes.vue
│ │ ├── points-rules/PointsRules.vue
│ │ └── members/MemberSearch.vue
│ ├── router/index.ts # 路由配置 + 认证守卫
│ ├── stores/auth.ts # Pinia 认证状态管理
│ ├── types/ # TypeScript 类型定义7 个文件)
│ │ ├── api.ts, enums.ts, gift.ts, order.ts
│ │ ├── member.ts, marketing-code.ts, points-rule.ts
│ ├── App.vue # 根组件RouterView + Toaster
│ ├── main.ts # 应用入口Pinia + Router
│ └── style.css # Tailwind CSS + CSS 变量主题
├── .env.development # 开发环境变量
├── .env.production # 生产环境变量
├── components.json # shadcn-vue 配置
├── vite.config.ts # Vite 配置Tailwind 插件 + 路径别名 + API 代理)
└── tsconfig.json / tsconfig.app.json
```
---
## 三、环境配置
### 3.1 环境变量
| 变量 | 开发环境 | 说明 |
|------|---------|------|
| `VITE_API_BASE_URL` | `http://localhost:5511` | 后端 API 基础地址 |
| `VITE_APP_TITLE` | `Fengling 管理后台` | 应用标题 |
### 3.2 Vite 代理
开发模式下,所有 `/api` 请求通过 Vite proxy 代理到后端 `http://localhost:5511`,无需处理 CORS。
### 3.3 运行命令
```bash
cd Frontend/Fengling.Backend.Admin
pnpm install # 安装依赖
pnpm dev # 启动开发服务器 → http://localhost:3000
pnpm build # 生产构建vue-tsc 类型检查 + vite build
pnpm preview # 预览生产构建
```
---
## 四、认证与路由
### 4.1 认证机制Mock
当前后端 JWT 认证尚未完全实现,前端采用 Mock Token 方式:
- **登录**:输入任意用户名密码,生成 `mock-admin-token-{username}-{timestamp}` 存入 `localStorage`
- **Token 注入**Axios 请求拦截器自动从 `localStorage` 读取 `admin_token` 并添加 `Authorization: Bearer {token}`
- **401 处理**:响应拦截器检测到 401 时自动清除 Token 并跳转登录页
- **切换真实认证**:修改 `stores/auth.ts``login()` 方法调用后端登录 API返回真实 JWT 即可
### 4.2 路由结构
| 路径 | 页面 | 说明 | 认证 |
|------|------|------|------|
| `/login` | Login.vue | 管理员登录 | 否 |
| `/dashboard` | Dashboard.vue | 仪表盘 | 是 |
| `/marketing-codes` | MarketingCodes.vue | 营销码管理 | 是 |
| `/gifts` | GiftList.vue | 礼品列表 | 是 |
| `/gifts/create` | GiftForm.vue | 创建礼品 | 是 |
| `/gifts/edit/:id` | GiftForm.vue | 编辑礼品 | 是 |
| `/orders` | OrderList.vue | 兑换订单列表 | 是 |
| `/orders/:id` | OrderDetail.vue | 订单详情 | 是 |
| `/points-rules` | PointsRules.vue | 积分规则管理 | 是 |
| `/members` | MemberSearch.vue | 会员查询 | 是 |
### 4.3 路由守卫
```
beforeEach:
未登录 + 访问受保护路由 → 重定向 /login
已登录 + 访问 /login → 重定向 /dashboard
```
---
## 五、API 服务层
### 5.1 Axios 客户端配置 (`api/client.ts`)
- **baseURL**:从 `VITE_API_BASE_URL` 环境变量读取
- **超时**15 秒
- **请求拦截器**:自动附加 Bearer Token
- **响应拦截器**
- 检查 `ResponseData.success` 字段,失败时 Toast 提示并 reject
- 401 错误清除 Token 跳转登录
- 网络错误友好提示
### 5.2 API 模块与后端端点对照
#### 礼品管理 (`api/gifts.ts`)
| 前端函数 | HTTP 方法 | 后端端点 |
|---------|----------|---------|
| `getGifts()` | GET | `/api/admin/gifts` |
| `getGiftById(id)` | GET | `/api/admin/gifts/{GiftId}` |
| `createGift(data)` | POST | `/api/admin/gifts` |
| `updateGift(id, data)` | PUT | `/api/admin/gifts/{GiftId}` |
| `putOnShelf(id)` | POST | `/api/admin/gifts/{GiftId}/putonshelf` |
| `putOffShelf(id)` | POST | `/api/admin/gifts/{GiftId}/putoffshelf` |
| `addGiftStock(id, quantity)` | POST | `/api/admin/gifts/{GiftId}/addstock` |
#### 订单管理 (`api/orders.ts`)
| 前端函数 | HTTP 方法 | 后端端点 |
|---------|----------|---------|
| `getOrders()` | GET | `/api/admin/redemption-orders` |
| `getOrderById(id)` | GET | `/api/admin/redemption-orders/{OrderId}` |
| `dispatchOrder(data)` | POST | `/api/admin/redemption-orders/{OrderId}/dispatch` |
| `completeOrder(orderId)` | POST | `/api/admin/redemption-orders/{OrderId}/complete` |
| `cancelOrder(data)` | POST | `/api/admin/redemption-orders/{OrderId}/cancel` |
#### 营销码管理 (`api/marketing-codes.ts`)
| 前端函数 | HTTP 方法 | 后端端点 |
|---------|----------|---------|
| `generateMarketingCodes(data)` | POST | `/api/admin/marketing-codes/generate` |
#### 积分规则 (`api/points-rules.ts`)
| 前端函数 | HTTP 方法 | 后端端点 |
|---------|----------|---------|
| `createPointsRule(data)` | POST | `/api/admin/points-rules` |
#### 会员查询 (`api/members.ts`)
| 前端函数 | HTTP 方法 | 后端端点 |
|---------|----------|---------|
| `getMemberById(memberId)` | GET | `/api/members/{MemberId}` |
---
## 六、类型定义
### 6.1 统一响应格式 (`types/api.ts`)
```typescript
interface ResponseData<T> {
success: boolean
code: number
message: string
data: T
}
```
### 6.2 枚举常量 (`types/enums.ts`)
由于 TypeScript `erasableSyntaxOnly` 限制,使用 `const as const` 模式定义枚举:
```typescript
// 礼品类型
GiftType.Physical = 1 // 实物
GiftType.Virtual = 2 // 虚拟
GiftType.Product = 3 // 自有产品
// 订单状态
OrderStatus.Pending = 1 // 待处理
OrderStatus.Dispatched = 2 // 已发货
OrderStatus.Delivered = 3 // 已送达
OrderStatus.Completed = 4 // 已完成
OrderStatus.Cancelled = 5 // 已取消
// 积分规则类型
PointsRuleType.Product = 1 // 产品规则
PointsRuleType.Time = 2 // 时间规则
PointsRuleType.MemberLevel = 3 // 会员等级规则
```
### 6.3 核心 DTO 类型
| 文件 | 接口 | 对应后端 DTO |
|------|------|-------------|
| `gift.ts` | `GiftDto` | 礼品列表/详情数据 |
| `gift.ts` | `CreateGiftRequest` | 创建礼品请求体 |
| `gift.ts` | `UpdateGiftRequest` | 更新礼品请求体 |
| `order.ts` | `RedemptionOrderDto` | 订单列表/详情数据 |
| `order.ts` | `RedemptionOrderAddressDto` | 收货地址 |
| `order.ts` | `DispatchOrderRequest` | 发货请求体 |
| `order.ts` | `CancelOrderRequest` | 取消订单请求体 |
| `member.ts` | `MemberDto` | 会员信息 |
| `marketing-code.ts` | `GenerateMarketingCodesRequest/Response` | 生成营销码请求/响应 |
| `points-rule.ts` | `CreatePointsRuleRequest/Response` | 创建积分规则请求/响应 |
---
## 七、页面功能详情
### 7.1 登录页 (`/login`)
- 居中卡片式表单,用户名 + 密码
- Mock 认证,成功后跳转仪表盘
- 表单验证:用户名和密码不为空
### 7.2 仪表盘 (`/dashboard`)
- **统计卡片**4 个):总礼品数 / 待处理订单 / 已上架礼品 / 已完成订单
- **近期订单表**:最新 5 条订单,显示订单号、礼品名、状态 Badge、时间
- **库存预警表**:可用库存 < 10 的上架礼品低库存红色高亮
- 数据来源并行调用 `getGifts()` + `getOrders()` 计算统计
### 7.3 礼品列表 (`/gifts`)
- **筛选栏**礼品类型 Select全部/实物/虚拟/产品+ 上架状态 Select全部/已上架/未上架
- **数据表格**名称类型 Badge所需积分总库存可用库存低库存高亮)、上架 Switch时间操作列
- **操作**
- 编辑按钮 跳转编辑页
- 上下架 Switch 调用 `putOnShelf/putOffShelf` + Toast 反馈
- 增加库存按钮 Dialog 输入数量 调用 `addGiftStock`
- **创建礼品按钮** 跳转创建页
### 7.4 礼品创建/编辑 (`/gifts/create` | `/gifts/edit/:id`)
- **表单字段**名称类型 Select编辑时禁用)、描述 Textarea图片 URL含预览)、所需积分总库存编辑时禁用)、每人限兑
- **表单验证**必填字段非空积分/库存为正数
- **模式判断**通过 `route.params.id` 区分创建/编辑编辑时自动加载礼品数据
### 7.5 订单列表 (`/orders`)
- **筛选**订单状态 Select全部/待处理/已发货/已送达/已完成/已取消
- **数据表格**订单号会员 ID截短)、礼品名数量消耗积分状态 Badge时间操作列
- **操作**根据状态动态显示
- 待处理 发货按钮Dialog 输入物流单号)、取消按钮
- 已发货/已送达 完成按钮取消按钮
- 所有状态 详情按钮
- **Dialog 交互**发货需输入物流单号可选)、取消需输入原因必填
### 7.6 订单详情 (`/orders/:id`)
- **订单信息卡片**订单号状态大 Badge创建/更新时间取消原因如有
- **礼品信息卡片**礼品名类型 Badge数量消耗积分
- **收货地址卡片**仅实物收货人电话地址物流单号
- **操作按钮**根据状态显示发货/完成/取消按钮 + 返回列表按钮
### 7.7 营销码管理 (`/marketing-codes`)
- **生成表单**批次号产品 ID产品名称生成数量1-10000)、过期时间可选
- **生成结果**显示批次号和数量Table 列出所有营销码等宽字体
- **操作**单个复制按钮复制全部按钮导出 CSV 按钮
### 7.8 积分规则管理 (`/points-rules`)
- **创建表单**规则名称规则类型 Select积分值奖励倍数默认 1.0)、开始/结束时间
- **动态条件字段**
- 产品规则 显示产品 ID + 品类 ID 输入框
- 会员等级规则 显示会员等级编码输入框
- 时间规则 无额外字段
- 创建成功后自动清空表单
### 7.9 会员查询 (`/members`)
- **搜索区域**会员 ID 输入框GUID 格式+ 查询按钮
- **结果展示**2x2 网格
- 基本信息ID手机号昵称
- 等级信息等级编码等级名称 Badge
- 积分信息累计总积分可用积分大号字体
- 账户状态正常/禁用 Badge注册时间
---
## 八、UI 组件使用
### 8.1 已安装的 shadcn-vue 组件
| 组件 | 用途 |
|------|------|
| Button | 操作按钮 |
| Input | 文本输入 |
| Textarea | 多行文本 |
| Label | 表单标签 |
| Select | 下拉选择筛选器类型选择 |
| Table | 数据表格 |
| Card | 卡片容器 |
| Dialog | 对话框发货/取消/库存 |
| Badge | 状态标签 |
| Switch | 开关上下架 |
| Tabs | 标签页 |
| Separator | 分隔线 |
| Avatar | 头像 |
| Breadcrumb | 面包屑导航 |
| Scroll Area | 滚动区域 |
| Sheet | 侧边抽屉 |
| Dropdown Menu | 下拉菜单 |
| Popover | 弹出框 |
| Tooltip | 工具提示 |
| Sonner | Toast 消息 |
### 8.2 添加新 shadcn-vue 组件
```bash
cd Frontend/Fengling.Backend.Admin
npx shadcn-vue@latest add [组件名]
```
---
## 九、当前状态与后续建议
### 9.1 当前状态
**已完成**
- 项目基础架构搭建Vite + Vue 3 + TypeScript + shadcn-vue
- 全部 9 个管理页面的 UI 与交互逻辑
- 覆盖后端全部 15 个管理端 API 端点
- 路由守卫 + Mock 认证
- `pnpm build` 通过无类型错误
- 生产构建产物约 155KB JS (gzip ~57KB)
**已知限制**
- 认证为 Mock 模式需后端 JWT 完善后对接
- 列表页无分页需后端添加分页接口后实现
- 表单验证为手动实现未使用 VeeValidate 等验证库
### 9.2 后续建议
#### 对接真实认证
1. 修改 `stores/auth.ts` `login()` 方法调用后端登录 API
2. 保存返回的 JWT Token localStorage
3. 无需修改 `api/client.ts`拦截器已适配 Bearer Token 模式
#### 功能增强
- **分页**后端添加分页支持后在列表页添加 Pagination 组件
- **积分规则列表**后端暴露查询端点后在积分规则页添加已有规则列表
- **营销码查询**后端添加查询端点后支持按批次号查看历史生成记录
- **数据导出**为订单列表礼品列表添加 Excel/CSV 导出功能
- **仪表盘图表**引入 ECharts/Chart.js 添加趋势图表
#### 技术优化
- 引入 VeeValidate 进行表单验证
- 大数据量场景引入虚拟滚动
- 添加 Vitest 单元测试