txw/前端项目文档.md

661 lines
18 KiB
Markdown
Raw Permalink 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.

# 前端项目文档
## 目录
- [项目概览](#项目概览)
- [目录结构](#目录结构)
- [核心模块详解](#核心模块详解)
- [技术栈](#技术栈)
- [环境变量](#环境变量)
- [启动方式](#启动方式)
- [API 层](#api-层)
- [Mock 数据](#mock-数据)
- [各项目功能对比](#各项目功能对比)
---
## 项目概览
本项目是一个**多模块前后分离架构**的企业级应用,包含 6 个 Vue 前端项目和一个 Java 微服务后端。
### 前端项目列表
| 项目 | 访问路径 | 描述 |
|------|----------|------|
| txw-gxzx-web | /view/gxzx | 可信碳信息网(功能最丰富) |
| txw-mhzc-web | /view/mhzc | 苗栗县综合平台 |
| txw-tzzx-web | /view/tzzx | Topfans 投资资讯 |
| txw-ytzx-web | /view/ytzx | Topfans 媒体中心 |
| txw-yygl-web | /view/yygl | 运营管理系统 |
| txw-kxtfwzx-web | /view/kxtfwzx | 综合服务信息中心 |
### 技术架构
- **框架**: Vue 2.6 + Vue Router 3 + Vuex 3
- **UI 组件库**: TDesign Vue 1.4.0 + @gtff/tdesign-gt-vue
- **构建工具**: Vue CLI 4.5
- **HTTP 客户端**: Axios
- **图表库**: ECharts 5.5
- **样式预处理**: LESS
---
## 目录结构
```
<project>/
├── public/ # 静态资源(不经过 webpack 处理)
│ ├── index.html # 生产环境 HTML 模板
│ └── local.html # 本地开发 HTML 模板
├── src/
│ ├── core/ # 核心初始化模块(所有项目共享)
│ │ ├── index.js # Vue 插件注册、TDesign 组件库初始化
│ │ ├── request.js # Axios 封装(拦截器 + 4 种 fetch 函数)
│ │ └── download.js # 文件下载工具(含 IE 兼容)
│ ├── pages/
│ │ └── index/ # 主页面模块(所有业务代码)
│ │ ├── main.js # 入口文件
│ │ ├── app.vue # 根组件
│ │ ├── api/ # API 接口定义
│ │ ├── assets/ # 模块资源(图片、字体等)
│ │ ├── components/ # 业务组件
│ │ ├── config/ # 顶部/侧边栏配置
│ │ ├── router/ # 路由定义
│ │ │ ├── index.js # VueRouter 实例创建
│ │ │ └── routes.js # 路由表定义(懒加载)
│ │ ├── store/ # Vuex 状态管理
│ │ │ ├── index.js # Store 实例
│ │ │ └── modules/ # 状态模块
│ │ ├── styles/ # 模块级样式
│ │ └── views/ # 页面组件
│ ├── styles/ # 全局共享样式
│ │ ├── index.less
│ │ ├── index.css
│ │ ├── variables.less # LESS 变量(主题色、尺寸等)
│ │ └── span-btn.less
│ └── utils/ # 全局工具函数
│ ├── auth.js # Token 管理
│ ├── calc.js # 税费计算
│ ├── dateUtil.js # 日期工具
│ ├── numberUtils.js # 数字格式化
│ ├── eventBus.js # 事件总线
│ └── urlParams.js # URL 参数解析
├── mock/ # Mock 数据(开发环境)
│ ├── index.js # Mock 入口
│ ├── get/ # GET 请求 Mock
│ └── post/ # POST 请求 Mock
├── .env # 默认环境变量
├── .env.development # 开发环境变量
├── .env.production # 生产环境变量
├── .env.test # 测试环境变量
├── babel.config.js # Babel 转译配置
├── vue.config.js # Vue CLI Webpack 配置
├── proxy.js # 开发服务器代理配置
├── package.json
└── README.md
```
### 目录用途说明
| 目录/文件 | 用途 |
|-----------|------|
| `public/` | 不经过 webpack 处理的静态资源,直接复制到输出目录 |
| `src/core/` | 核心初始化代码,包括 Axios 封装、下载工具 |
| `src/pages/index/` | 所有业务代码API、组件、视图、路由、状态 |
| `src/styles/` | 全局样式和 LESS 变量 |
| `src/utils/` | 与业务无关的纯工具函数 |
| `mock/` | 前端 Mock 数据,用于独立开发 |
| `.env.*` | 环境差异化配置 |
---
## 核心模块详解
### 1. 入口文件 (`src/pages/index/main.js`)
```javascript
// 1. Polyfill 引入
import 'core-js/stable';
import 'regenerator-runtime/runtime';
// 2. 核心模块初始化
import core from '@/core/index.js';
// 3. Vue 实例创建
import Vue from 'vue';
import App from './app.vue';
// 4. 路由和状态管理
import router from './router/index.js';
import store from './store/index.js';
// 5. 创建并挂载 Vue 实例
new Vue({
router,
store,
render: h => h(App)
}).$mount('#app');
```
**主要职责**
- 初始化 polyfill
- 注册 Vue 插件和全局组件
- 整合 Router 和 Vuex Store
- 设置文档标题
- 注册全局事件(登录/登出)
### 2. Axios 封装 (`src/core/request.js`)
提供 4 种请求方法:
| 函数 | 用途 | BaseURL | 特殊 Header |
|------|------|---------|-------------|
| `fetch` | 普通业务 API | `API_PREFIX` | 无 |
| `fetchSso` | SSO 服务 | `SSO_PREFIX` | `TOKEN-TYPE: YW` |
| `fetchSso1` | SSO 服务 | `SSO_PREFIX` | `TOKEN-TYPE: STAR` |
| `fetchNoPrefix` | 无前缀调用 | 空 | 无 |
**请求拦截器**
- 自动添加时间戳防止缓存
- GET 请求参数映射到 URL query string
**响应拦截器**
- `code !== 1` 时显示错误信息
- `code === 401` 时跳转登录页
- 统一错误处理
### 3. 路由 (`src/pages/index/router/`)
**`index.js`** - VueRouter 实例:
```javascript
const router = new VueRouter({
mode: 'history', // 使用 History 模式
base: `${window.STATIC_ENV_CONFIG.ROUTER_PREFIX}/`, // 基础路径
routes: require('./routes').default
});
```
**`routes.js`** - 路由表(懒加载):
```javascript
export default [
{
path: '/login',
name: 'login',
component: () => import(/* webpackChunkName: "login" */ '@/pages/index/views/login/login.vue')
},
// ...其他路由
];
```
### 4. 状态管理 (`src/pages/index/store/`)
**`index.js`** - Store 实例创建:
```javascript
import Vue from 'vue';
import Vuex from 'vuex';
import user from './modules/user.js';
import mxuser from './modules/mxuser.js';
Vue.use(Vuex);
export default new Vuex.Store({
modules: {
user,
mxuser
}
});
```
**模块结构**
- `modules/user.js` - 用户信息、登录状态
- `modules/mxuser.js` - MX 用户状态
- 各业务模块的 store 在各自目录下
### 5. 文件下载 (`src/core/download.js`)
```javascript
// 普通浏览器下载
download(url, filename) {
const link = document.createElement('a');
link.href = url;
link.download = filename;
link.click();
}
// IE 兼容下载
downloadForIE(url, filename) {
const iframe = document.createElement('iframe');
iframe.style.display = 'none';
iframe.src = url;
document.body.appendChild(iframe);
}
```
---
## 技术栈
### 核心依赖
| 技术 | 版本 | 用途 |
|------|------|------|
| vue | ~2.6.11 | 前端框架 |
| vue-router | 3.2.0 | 路由管理 |
| vuex | ^3.4.0 | 状态管理 |
| tdesign-vue | 1.4.0 | TDesign UI 组件库 |
| @gtff/tdesign-gt-vue | 1.4.0 | 定制 TDesign 组件 |
| @gt4/common-front | 2.0.113 | 公共前端工具库 |
### HTTP 与数据处理
| 技术 | 版本 | 用途 |
|------|------|------|
| axios | ^0.21.1 | HTTP 客户端 |
| dayjs | ^1.10.4 | 日期处理(轻量级) |
| lodash-es | ^4.17.21 | JavaScript 工具库 |
### 可视化
| 技术 | 版本 | 用途 |
|------|------|------|
| echarts | ^5.5.0 | 图表库 |
| vue-echarts | ^6.6.9 | ECharts Vue 封装 |
| vue-pdf | ^4.3.0 | PDF 预览 |
### 构建与开发
| 技术 | 版本 | 用途 |
|------|------|------|
| @vue/cli-service | ~4.5.0 | Vue CLI 服务 |
| @wecity/static-env-config | 1.0.32 | 环境配置注入 |
| mockjs | ^1.1.0 | Mock 数据生成 |
| less | ^4.1.3 | LESS 预处理器 |
### 图标
| 技术 | 版本 | 用途 |
|------|------|------|
| tdesign-icons-vue | 0.0.8 | TDesign 图标 |
| @fortawesome/fontawesome-free | ^7.0.1 | Font Awesome 图标 |
---
## 环境变量
### `.env` 默认配置
```
VUE_APP_ENV=dev
VUE_APP_MODEL=local
VUE_APP_CDN_PATH=/view/<project>
VUE_APP_ROUTER_BASE=/view/<project>
VUE_APP_API_BASE_URL=
VUE_APP_API_TIMEOUT=15000
VUE_APP_CSS_EXTRACT=false
```
### `.env.development` 开发配置
```
VUE_APP_ENV=dev
VUE_APP_MODEL=local
VUE_APP_CDN_PATH=/view/<project>
VUE_APP_ROUTER_BASE=/view/<project>
VUE_APP_API_BASE_URL=
VUE_APP_DEV_SERVER_PORT=9002
VUE_APP_MOCK=true
VUE_APP_AUTO_ROUTER=false
```
### `.env.production` 生产配置
```
VUE_APP_ENV=prod
VUE_APP_MODEL=online
VUE_APP_CDN_PATH=/view/<project>
VUE_APP_ROUTER_BASE=/view/<project>
VUE_APP_API_BASE_URL=
VUE_APP_AUTO_ROUTER=false
```
### `.env.test` 测试配置
```
NODE_ENV=production
VUE_APP_ENV=beta
VUE_APP_MODEL=online
VUE_APP_CDN_PATH=/test
VUE_APP_ROUTER_BASE=/test
VUE_APP_API_BASE_URL=/test/api
VUE_APP_API_BASE_URL2=/test/api
```
### 变量说明
| 变量 | 说明 | 示例值 |
|------|------|--------|
| `VUE_APP_ENV` | 环境标识 | dev / prod / beta |
| `VUE_APP_MODEL` | 运行模式 | local本地/ online线上 |
| `VUE_APP_CDN_PATH` | 静态资源基础路径 | /view/gxzx |
| `VUE_APP_ROUTER_BASE` | Vue Router 基础路径 | /view/gxzx |
| `VUE_APP_API_BASE_URL` | API 请求前缀 | 空(使用网关) |
| `VUE_APP_DEV_SERVER_PORT` | 开发服务器端口 | 9002 |
| `VUE_APP_MOCK` | 是否启用 Mock 数据 | true / false |
| `VUE_APP_AUTO_ROUTER` | 是否启用自动路由 | false |
---
## 启动方式
### 前置条件
- Node.js >= 14.x
- Yarn 或 npm
### 安装依赖
```bash
cd txw-gxzx-web # 进入项目目录
yarn install # 安装依赖(推荐)
# 或 npm install
```
### 开发模式
```bash
# 普通开发模式
yarn dev
# 启用 Mock 数据模式(无需后端启动)
yarn dev:mock
# 使用 npm
npm run serve
```
### 构建打包
```bash
# 生产环境打包
yarn build
# 开发环境打包
yarn build:site:dev
# 测试环境打包
yarn build:site:test
# 指定环境打包
yarn build:site --mode development
```
### 代码检查
```bash
# ESLint 检查
yarn lint
# 样式检查
yarn lint:style
```
### 开发服务器
默认端口:`9002`(可通过 `VUE_APP_DEV_SERVER_PORT` 修改)
代理配置(`proxy.js`
```javascript
proxy: {
'/sso': { target: 'http://10.23.20.13:94/' },
'/mhzc': { target: 'http://10.23.20.13:94/' },
}
```
---
## API 层
### API 定义示例
`src/pages/index/api/` 目录下定义接口:
```javascript
// login.js
import { fetch, fetchSso } from '@/core/request.js';
export const login = (data) => fetch.post('/user/login', data);
export const logout = () => fetchSso.post('/sso/logout');
export const getUserInfo = () => fetch.get('/user/info');
```
### API 调用方式
```javascript
import { login, getUserInfo } from '../api/login.js';
// 登录
login({ username: 'admin', password: '123456' })
.then(res => {
if (res.code === 1) {
// 登录成功
}
});
// 获取用户信息
getUserInfo()
.then(res => console.log(res.data));
```
### 各项目 API 文件
| 项目 | API 文件 |
|------|----------|
| txw-gxzx-web | login.js, common.js, cjjpwh.js, ggwhglHtgl/index.js, gxzx/index.js, htgl.js, lsjr.js, lsjy.js, tjzsym.js, yhjfzsym.js |
| txw-mhzc-web | login.js, ggwhglHtgl/index.js, gxzx/index.js, htgl.js, yhzx/index.js |
| txw-tzzx-web | login.js, cjjpwh.js, common.js, ggwhglHtgl/index.js, htgl.js, tjzsym.js, yhjfzsym.js |
| txw-ytzx-web | login.js, cjjpwh.js, common.js, ggwhglHtgl/index.js, htgl.js, tjzsym.js, yhjfzsym.js |
| txw-yygl-web | login.js, cjjpwh.js, common.js, gggl/index.js, ggwhglHtgl/index.js, gxzx/index.js, htgl.js, lscp.js, tjzsym.js, yhjfzsym.js |
| txw-kxtfwzx-web | login.js, cjjpwh.js, common.js, ggwhglHtgl/index.js, htgl.js, tjzsym.js, yhjfzsym.js |
---
## Mock 数据
### Mock 目录结构
```
mock/
├── index.js # Mock 入口
├── get/ # GET 请求 Mock
│ ├── user_info.json # -> GET /user/info
│ └── user_list.json # -> GET /user/list
└── post/ # POST 请求 Mock
├── user_login.json # -> POST /user/login
└── user_logout.json # -> POST /user/logout
```
### 文件命名规则
Mock 文件名中的双下划线 `__` 会被映射为路径斜杠 `/`
| 文件名 | 映射路径 |
|--------|----------|
| `user_info.json` | `/user/info` |
| `user_bulk__delete.json` | `/user/bulk_delete` |
| `admin_role_list.json` | `/admin/role/list` |
### 启用 Mock
方式一:修改 `.env.development`
```
VUE_APP_MOCK=true
```
方式二:使用 dev:mock 命令
```bash
yarn dev:mock
```
### Mock 数据示例
```javascript
// mock/post/user_login.json
{
"code": 1,
"msg": "登录成功",
"data": {
"token": "mock_token_12345",
"userId": 1001,
"username": "admin"
}
}
```
---
## 各项目功能对比
| 项目 | 主要功能模块 | 特点 |
|------|-------------|------|
| **txw-gxzx-web** | 可信碳信息、绿色金融(lsjr)、绿色交易(lsjy)、绿色信贷(lsxd)、企业出海(qych)、碳能力平台(gxnlpt) | 功能最丰富,业务模块最多 |
| **txw-mhzc-web** | 登录、首页(mhNewMain/home/home2)、用户中心(yhzx)、新闻中心、授权(authorize)、论坛(zxym)、企业入驻(qyrz/qy-rz) | 多首页适配,屏幕适配(1895x953) |
| **txw-tzzx-web** | 登录、首页 | 简单结构,仅基础功能 |
| **txw-ytzx-web** | 登录、首页 | 简单结构,仅基础功能 |
| **txw-yygl-web** | 登录、用户中心、公告管理(gggl)、轮播图(banner)、企业入驻(qyrz/qysp)、历史产品(lscp)、数据概览(tjzsym) | 运营管理功能 |
| **txw-kxtfwzx-web** | 登录、首页 | 简单结构,仅基础功能 |
### 各项目 Views 目录结构
**txw-gxzx-web**:
```
views/gxzx/ # 可信碳信息
views/lsjr/ # 绿色金融
views/lsjy/ # 绿色交易
views/qych/ # 企业出海
views/transfer/ # 转让
```
**txw-mhzc-web**:
```
views/dddl/ # 订单
views/ggwhglHtgl/ # 公共管理
views/glxtSy/ # 管理平台首页
views/gxfb/ # 信息发布
views/gxnlpt/ # 能力平台
views/home/ # 首页
views/hyzt/ # 行业状态
views/login/ # 登录
views/lsjy/ # 历史交易
views/qy-rz/ # 企业入驻
views/qych/ # 企业出海
views/qyrz/ # 企业认证
views/zx/ # 资讯
```
**txw-yygl-web**:
```
views/banner/ # 轮播图管理
views/ggwhglHtgl/ # 公共管理
views/glxtSy/ # 管理平台首页
views/gxfb/ # 信息发布
views/login/ # 登录
views/lscp/ # 历史产品
views/lsjy/ # 历史交易
views/qyrz/ # 企业入驻
views/qysp/ # 企业审批
views/yhgl/ # 用户管理
```
---
## 公共组件
| 组件 | 路径 | 用途 |
|------|------|------|
| AddEditTable | `components/AddEditTable/` | 表格增删改一体 |
| all-select | `components/all-select/` | 自定义多选组件 |
| common-breadcrumb | `components/common-breadcrumb/` | 面包屑导航 |
| common-confirm | `components/common-confirm/` | 确认对话框 |
| commonCard | `components/commonCard/` | 卡片包装组件 |
| empty-placeholder | `components/empty-placeholder/` | 空状态占位 |
| footer | `components/footer/` | 页脚 |
| header-search | `components/header-search/` | 头部搜索 |
| ImportDialog | `components/ImportDialog/` | 文件导入弹窗 |
| nav | `components/nav/` | 导航组件 |
| pdf | `components/pdf/` | PDF 预览组件 |
| sbbBottomSubmit | `components/sbbBottomSubmit/` | 底部提交按钮 |
| search-control-panel | `components/search-control-panel/` | 搜索面板 |
| workflow | `components/workflow/` | 工作流组件 |
---
## 工具函数
| 文件 | 函数 | 用途 |
|------|------|------|
| **auth.js** | `getAccessToken()` | 获取 Access Token |
| | `setToken(token)` | 设置 Token |
| | `removeToken()` | 清除 Token |
| **dateUtil.js** | `getQuarter(date)` | 获取日期所在季度 |
| | `getMonthStartEndDay(date)` | 获取月份开始结束日期 |
| | `getThisMonthRange()` | 获取本月日期范围 |
| **calc.js** | 税费计算相关 | 税费计算工具 |
| **numberUtils.js** | 数字处理相关 | 数字格式化工具 |
| **eventBus.js** | `EventBus.$on()` | 监听事件 |
| | `EventBus.$emit()` | 触发事件 |
| **urlParams.js** | URL 参数解析 | 获取 URL 参数 |
---
## 部署说明
### 静态资源路径
每个项目部署后通过不同路径访问:
- `/view/gxzx` -> txw-gxzx-web
- `/view/mhzc` -> txw-mhzc-web
- `/view/tzzx` -> txw-tzzx-web
- `/view/ytzx` -> txw-ytzx-web
- `/view/yygl` -> txw-yygl-web
- `/view/kxtfwzx` -> txw-kxtfwzx-web
### 环境配置注入
构建时通过 `@wecity/static-env-config` 插件注入环境变量,生成 `env.config.js` 文件:
- 开发环境: `/view/<project>/env.config.js`
- 生产环境: `/view/<project>/env.config.js`
### Nginx 配置示例
```nginx
location /view/gxzx {
alias /usr/share/nginx/html/gxzx;
try_files $uri $uri/ /view/gxzx/index.html;
}
location /view/mhzc {
alias /usr/share/nginx/html/mhzc;
try_files $uri $uri/ /view/mhzc/index.html;
}
```
---
## 常见问题
### 1. 跨域问题
开发环境通过 `proxy.js` 配置代理解决。生产环境通过网关路由解决。
### 2. Mock 数据与实际接口切换
修改 `VUE_APP_MOCK` 环境变量即可切换。
### 3. 路由 404 问题
确保 Nginx 配置了 `try_files $uri $uri/ /index.html`,支持 History 模式的路由。
### 4. IE 浏览器兼容
已引入 `@wecity/tdesign-vue-ie` 和相关 polyfill但部分功能可能受限。
---
*文档生成时间: 2026-04-03*