# CNC机床数据采集系统 - 前端全局规范 > 最后更新:2026-04-25 > 状态:设计中 --- ## 说明 本文档为**全局规范汇总**,定义所有页面通用的技术规则。各模块的页面设计(布局、字段、交互流程等)见 `docs/02-功能清单/管理后台/` 和 `docs/02-功能清单/大屏/` 对应模块子文件。 --- ## 全局规范 ### 组件规范 | 组件 | 用途 | 配置参数 | |------|------|---------| | el-table | 列表展示 | border, stripe, size=default, header-cell-style背景#f5f7fa | | el-table-column | 列定义 | show-overflow-tooltip=true 默认开启 | | el-pagination | 分页 | page-sizes=[20,50,100], background=true, layout=total,sizes,prev,pager,next,jumper | | el-form | 表单 | label-width=120px, label-position=right, size=default | | el-dialog | 弹窗 | close-on-click-modal=false, close-on-press-escape=true, destroy-on-close=true | | el-select | 下拉 | filterable=true, clearable=true | | el-date-picker | 日期 | type=daterange, value-format=YYYY-MM-DD, clearable=true | | el-input | 输入 | clearable=true, maxlength按字段定义 | | el-button | 按钮 | size=default, 操作类type=primary, 危险类type=danger | | el-message | 轻提示 | 成功success, 失败error, 警告warning | | el-message-box | 确认框 | type=warning | | el-tag | 状态标签 | size=small, 按状态配color | | el-tooltip | 提示 | placement=top | ### 防重复请求 - 所有写操作按钮点击后立即loading=true+disabled=true - 请求锁requestLock指令,同一按钮1秒内不可重复点击 - axios拦截器,相同URL+参数的请求500ms内自动去重 ### 超时与加载反馈 - API超时30秒(可配置) - 列表页v-loading指令 - 弹窗提交按钮loading+弹窗内遮罩 - 超时提示el-message error ### 操作确认机制 - 删除:确定删除【{name}】?此操作不可恢复。 - 停用/启用:确定{操作}? - 批量操作:确定对选中的{N}项执行{操作}? - 产量修正:确定修正产量?修正后将记录审计日志。 ### 脏数据检测 - 编辑弹窗关闭时:若表单有未保存修改,弹出确认 - 表单组件内维护isDirty状态,对比初始值与当前值 - 路由切换时:beforeRouteLeave守卫 ### 操作结果反馈 | 场景 | 反馈方式 | 持续时间 | |------|---------|---------| | 创建成功 | el-message success {资源}创建成功 | 3秒 | | 修改成功 | el-message success 保存成功 | 3秒 | | 删除成功 | el-message success {资源}已删除 | 3秒 | | 操作失败 | el-message error {具体错误信息} | 5秒 | | 批量操作 | el-message info 已{操作}{N}项 | 3秒 | ### 校验规则 | 字段类型 | 规则 | 错误提示 | 触发时机 | |---------|------|---------|---------| | 必填 | required | 此项为必填 | blur | | IP地址 | pattern正则 | 请输入正确的IP地址 | blur | | URL | pattern正则 | 请输入正确的HTTP地址 | blur | | 数字 | type:number | 请输入数字 | blur | | 正整数 | pattern正则 | 请输入正整数 | blur | | 长度限制 | maxlength | 最多{N}个字符 | input | | 编码唯一 | async validator API调用 | 此{字段}已存在 | blur | ### Mock数据规格 成功响应: code=0, message=success, data=对象 分页列表: code=0, data={items:[], total:160, page:1, pageSize:20} 失败响应: code=40001, message=具体错误, data=null ### 空状态设计 | 场景 | 展示 | |------|------| | 列表无数据 | el-empty description=暂无数据 image-size=120 | | 查询无结果 | el-empty description=未找到匹配的数据,请调整查询条件 | | 图表无数据 | 居中显示暂无数据灰色文字 | ### 错误码处理 | 错误码 | 含义 | 前端处理 | |--------|------|---------| | 0 | 成功 | 正常处理data | | 40001 | 参数校验失败 | el-message error显示message | | 40002 | 资源不存在 | el-message warning+刷新列表 | | 40003 | 资源已存在 | el-message error+聚焦冲突字段 | | 40101 | Token无效/过期 | 清除Token跳转登录页 | | 50001 | 服务器内部错误 | el-message error服务器错误 | | 50002 | 采集服务不可达 | el-message warning采集服务未响应 | ### 管理后台Layout ``` ┌──────────────────────────────────────────────────────────┐ │ [顶部栏] height=48px │ │ 左:系统名称「CNC机床数据采集系统」 │ │ 右:管理员 ▼ → [修改密码] [退出登录] │ ├────────┬─────────────────────────────────────────────────┤ │ [侧边栏]│ [内容区] padding=20px │ │ width= │ │ │ 200px │ │ │ │ │ │ 仪表盘 │ │ │ 设备管理│ │ │ 品牌模板│ │ │ 采集地址│ │ │ 员工管理│ │ │ 产量报表│ │ │ 告警中心│ │ │ 系统设置│ │ │ 操作日志│ │ │ 大屏配置│ │ ├────────┤ │ │ [折叠] │ │ └────────┴─────────────────────────────────────────────────┘ ``` **顶部栏规范:** - 高度48px,背景色#409EFF(Element Plus primary),文字白色 - 左侧:系统名称,font-size=16px,font-weight=bold - 右侧:管理员下拉菜单,el-dropdown,trigger=click - [修改密码]:打开修改密码弹窗(见09-系统设置) - [退出登录]:确认"确定退出登录?" → 清除Token → 跳转/login **侧边栏规范:** - 宽度200px,可折叠至64px(仅图标) - 折叠按钮:底部,el-icon Fold/Expand - 菜单项:el-menu,background=#304156,text=#bfcbd9,active-text=#409EFF - 当前路由自动高亮,使用 el-menu 的 default-active 绑定当前路由path - 菜单项无子菜单(均为一级),无折叠子菜单 **侧边栏菜单项与路由映射:** | 菜单名称 | 路由 | 图标(el-icon) | |---------|------|-------------| | 仪表盘 | /dashboard | Odometer | | 设备管理 | /machine | Monitor | | 品牌模板 | /brand | PriceTag | | 采集地址 | /collect-address | Link | | 员工管理 | /worker | User | | 产量报表 | /production | DataAnalysis | | 告警中心 | /alert | Bell | | 系统设置 | /settings | Setting | | 操作日志 | /log | Document | | 大屏配置 | /screen-config | Monitor |(注意:与设备管理图标不同,用View或FullScreen) **内容区规范:** - padding=20px - 最大宽度不限(全宽) - 背景#f0f2f5 - 面包屑在内容区顶部,非顶部栏中 ### 路由总表 | 路由 | 组件 | 权限 | 需Token | 重定向/备注 | |------|------|------|---------|------------| | /login | LoginPage | 无 | 否 | 登录页,独立Layout(无侧边栏) | | / | Layout | admin | 是 | 管理后台框架,重定向→/dashboard | | /dashboard | DashboardPage | admin | 是 | 嵌套在Layout内 | | /machine | MachineListPage | admin | 是 | 嵌套在Layout内 | | /machine/:id | MachineDetailPage | admin | 是 | 嵌套在Layout内 | | /brand | BrandListPage | admin | 是 | 嵌套在Layout内 | | /brand/create | BrandEditPage | admin | 是 | 新增品牌 | | /brand/:id/edit | BrandEditPage | admin | 是 | 编辑品牌(复用同一组件) | | /collect-address | CollectAddressListPage | admin | 是 | 嵌套在Layout内 | | /collect-address/:id | CollectAddressDetailPage | admin | 是 | 嵌套在Layout内 | | /worker | WorkerListPage | admin | 是 | 嵌套在Layout内 | | /worker/:id | WorkerDetailPage | admin | 是 | 嵌套在Layout内 | | /production | ProductionPage | admin | 是 | 嵌套在Layout内 | | /alert | AlertPage | admin | 是 | 嵌套在Layout内 | | /settings | SettingsPage | admin | 是 | 嵌套在Layout内 | | /log | LogPage | admin | 是 | 嵌套在Layout内 | | /screen-config | ScreenConfigPage | admin | 是 | 嵌套在Layout内 | | /screen | ScreenPage | 无 | 否 | 大屏看板,独立Layout(全屏,无侧边栏) | ### axios封装与路由守卫 **axios实例配置:** - baseURL:'/'(同IIS站点,无跨域) - timeout:30000(30秒,可通过cnc_sys_config配置) - 请求拦截:自动添加 `Authorization: Bearer {token}` header(从localStorage取token) - 响应拦截: - code=0 → 正常返回data - code=40101 → 清除localStorage.token → router.push('/login') → 弹出el-message warning"登录已过期" - code=40001/40002/40003/50001/50002 → 按错误码处理表执行 - HTTP状态码非200 → el-message error "网络异常" **路由守卫(router.beforeEach):** - 访问/login → 如果localStorage有token → 重定向/dashboard - 访问/api/admin/**路由 → 如果localStorage无token → 重定向/login?redirect=当前路由 - 访问/screen → 放行(免认证) - 其他 → 放行 **Token管理:** - 存储:localStorage.setItem('token', value) - 读取:localStorage.getItem('token') - 清除:localStorage.removeItem('token') - 登录成功后跳转:redirect参数存在则跳redirect,否则跳/dashboard --- ## 前端工程开发规范 > 最后更新:2026-04-26 > 本章节为1:1可交互界面生成的工程实现规范 ### 技术栈 | 类别 | 选型 | 版本要求 | |------|------|---------| | 框架 | Vue3 | >=3.4 | | 构建工具 | Vite | >=5.0 | | 语言 | TypeScript | >=5.0 | | UI组件库 | Element Plus | >=2.5 | | 路由 | Vue Router 4 | >=4.3 | | HTTP | Axios | >=1.6 | | 图表 | ECharts | >=5.5 | | Mock | vite-plugin-mock | >=3.0 | ### 项目目录 ``` D:\opencode\haoliang\frontend\ ├── index.html ├── package.json ├── tsconfig.json ├── vite.config.ts # mock插件 + proxy配置 ├── mock/ # Mock数据定义(按模块拆分) │ ├── login.ts │ ├── dashboard.ts │ ├── machine.ts │ ├── brand.ts │ ├── collect-address.ts │ ├── worker.ts │ ├── production.ts │ ├── alert.ts │ ├── settings.ts │ ├── log.ts │ └── screen.ts └── src/ ├── main.ts ├── App.vue ├── router/ │ └── index.ts # 路由定义(双套:正常路由 + /mock前缀路由) ├── composables/ │ └── useMockMode.ts # Mock模式检测 ├── utils/ │ └── request.ts # axios封装(根据mock模式切换baseURL) ├── layouts/ │ ├── AdminLayout.vue # 管理后台Layout(顶部栏+侧边栏+内容区) │ └── ScreenLayout.vue # 大屏Layout(全屏独立) ├── views/ # 页面组件(按模块目录) │ ├── login/ │ ├── dashboard/ │ ├── machine/ │ ├── brand/ │ ├── collect-address/ │ ├── worker/ │ ├── production/ │ ├── alert/ │ ├── settings/ │ ├── log/ │ ├── screen-config/ │ └── screen/ ├── styles/ │ ├── admin.scss # 管理后台全局样式 │ └── screen.scss # 大屏深色主题样式 └── types/ # TypeScript类型定义 ``` ### Mock方案:URL前缀切换 **核心规则:** 同一组件、同一套交互逻辑,仅axios请求路径不同。 ``` /mock/dashboard → axios请求走 /mock-api/** → vite-plugin-mock拦截返回Mock JSON /dashboard → axios请求走 /api/** → Vite proxy转发到真实后端 ``` #### 使用体验 | 阶段 | URL | 行为 | |------|-----|------| | 开发阶段(后端未就绪) | `http://localhost:5173/mock/dashboard` | Mock数据完整展示 | | 开发阶段(后端未就绪) | `http://localhost:5173/dashboard` | 界面正常,API请求404 | | 后端就绪后 | `http://localhost:5173/dashboard` | 直接对接真实API | | 后端就绪后 | `http://localhost:5173/mock/dashboard` | 仍可切回Mock对比 | #### 双列URL使用规则 接口文档(`docs/03-API接口设计.md` §3.1~3.13)中每个端点同时列出两列URL: | 列名 | 用途 | HTTP方法 | URL风格 | |------|------|---------|---------| | **Mock URL 列** | 前端Mock开发阶段使用 | 全部POST(简化) | `/xxx/update`、`/xxx/delete`、`/xxx/detail?id=` | | **正式API 列** | 前端正式联调使用 | RESTful(GET/POST/PUT/DELETE) | `/xxx/{id}` 路径参数 | **前端开发者必须遵守**: - Mock 开发阶段(`/mock/` 路径访问):按 Mock URL 列调用,全部用 POST - 正式联调阶段(`/` 路径访问):按正式API列调用,写操作用 PUT/DELETE,id放URL路径 - 切换时机:后端接口开发完成并可联调时,逐个接口从Mock风格切换到RESTful风格 - 禁止在正式环境中残留Mock风格的URL调用 #### Mock模式检测 ```typescript // src/composables/useMockMode.ts // 根据 route.path.startsWith('/mock') 判断是否为Mock模式 // 返回 computed isMock ``` #### axios baseURL切换 ```typescript // src/utils/request.ts // if (isMock) baseURL = '/mock-api' // else baseURL = '/api' // 其余拦截逻辑不变(Token/错误码/超时等) ``` #### 路由定义 ```typescript // src/router/index.ts // 函数生成两套路由: // 1. 正常路由:/dashboard, /machine, /login ... // 2. Mock前缀路由:/mock/dashboard, /mock/machine, /mock/login ... // 两套路由复用同一组件,Mock路由额外注入mock标识 ``` #### Mock数据文件 ``` mock/*.ts 文件内容来源: - 各页面.md中的Mock数据章节 - 数据结构严格匹配页面.md中定义的JSON - 一个模块一个文件,按API路径组织 ``` #### Vite配置 ```typescript // vite.config.ts // 1. vite-plugin-mock 配置 mock/**.ts // 2. proxy 配置: // /mock-api/** → mock插件拦截(开发环境) // /api/** → proxy到后端(可配置target,默认http://localhost:5800) ``` ### CSS规范 - 方案:Element Plus默认主题 + 局部scoped样式 - 管理后台:Element Plus默认蓝色主题(#409EFF),背景#f0f2f5 - 大屏看板:独立深色主题(#0f0f1a背景/#1a1a2e卡片),样式文件 `styles/screen.scss` - 不引入Tailwind CSS ### 大屏独立规范 - 独立Layout:`ScreenLayout.vue`(全屏,无侧边栏/面包屑) - 独立路由:`/screen` 和 `/mock/screen` - 独立主题:深色背景,通过 `screen.scss` 覆盖Element Plus默认样式 - 免认证:`/api/screen/**` 不需要Token - 自动刷新:定时器按卡片配置的刷新策略轮询 ### 强制要求 - **思考过程使用中文**:所有AI助手的推理、分析、思考过程必须使用中文输出 - **控制台输出中文**:所有控制台输出、日志、提示信息使用中文,不得出现乱码 - **所有文档使用中文**:项目内所有文档、注释、界面文案使用中文 - **组件文案中文**:所有界面文字(按钮/标签/提示/空状态/确认框)必须使用中文 - **代码注释中文**:所有代码注释使用中文 --- ## CRUD页面必填项 > 页面文件完整模板见 `功能清单文件夹创建规范.md` 第五节(共20项)。以下为本项目CRUD页面的**最小必填项**——20项的子集。未列出的项,若本模块有特殊需求则补充填写,无特殊需求则省略(继承全局规范即可)。 **默认继承全局规范、页面文件无需重复填写的项目:** - 防重复请求(8)、超时与加载反馈(9)、操作确认机制(10)、操作结果反馈(12)、校验规则(14)、响应式布局(15)、空状态设计(18)、错误码处理(19)、安全规范(20) - 仅当本页面有**不同于全局规范**的特殊逻辑时,才在页面文件中补充对应项 ### 列表页必填项 | 序号 | 必填项 | 说明 | |------|--------|------| | 1 | 基本信息 | 路由、权限、入口、面包屑 | | 2 | 界面布局 | ASCII图 | | 3 | 查询条件 | 字段/控件/必填/默认值/校验/联动,无筛选则写"无" | | 4 | 列表字段 | 字段名/列宽/排序/筛选/固定/超长处理/对齐 | | 5 | 操作按钮 | 名称/权限编码/位置/显示条件/点击行为 | | 6 | 弹窗规格 | 弹窗宽度/遮罩/ESC/表单字段定义,无弹窗则写"无" | | 7 | 状态机 | 状态值/颜色/可用操作,无状态则写"无" | | 8 | 交互流程 | 每个操作的主流程+异常处理 | | 9 | 空状态 | 列表无数据/查询无结果的展示 | **弹窗表单字段必填列:** | 列 | 说明 | |----|------| | 字段 | 中文名 | | 控件 | el-input/el-select等+具体参数 | | 必填 | 是/否 | | 默认值 | 无则写"-" | | 校验 | 必填/格式/唯一性等,无则写"-" | | 联动 | 值变化时影响哪些字段,无则写"-" | ### 详情页必填项 | 序号 | 必填项 | 说明 | |------|--------|------| | 1 | 基本信息 | 路由(含参数)、权限、入口、面包屑 | | 2 | 界面布局 | ASCII图 | | 3 | 数据区块 | 每个区块的展示字段+控件类型 | | 4 | 操作按钮 | 名称/位置/行为 | | 5 | 交互流程 | 加载/刷新/跳转 | ### 统计/仪表盘页必填项 | 序号 | 必填项 | 说明 | |------|--------|------| | 1 | 基本信息 | 路由、权限、入口、面包屑 | | 2 | 界面布局 | ASCII图(统计卡片+表格/图表区域) | | 3 | 数据区块 | 每个区块的数据来源API+刷新策略 | | 4 | 操作按钮 | 名称/位置/行为 | | 5 | 状态机 | 状态值/颜色(如有) | | 6 | 交互流程 | 加载/自动刷新/跳转 | | 7 | 空状态 | 各区块无数据的展示 | ### 登录/特殊页必填项 | 序号 | 必填项 | 说明 | |------|--------|------| | 1 | 基本信息 | 路由、入口 | | 2 | 界面布局 | ASCII图 | | 3 | 表单字段 | 字段/控件/校验(如有表单) | | 4 | 操作按钮 | 名称/行为 | | 5 | 交互流程 | 成功/失败/跳转 | | 6 | 安全规范 | Token存储/过期/登出策略 | --- ## 模块设计进度 > 具体页面设计见 `docs/02-功能清单/管理后台/{编号}-{模块名}/` 对应子文件 | 编号 | 模块 | 页面数 | 设计状态 | 备注 | |------|------|--------|---------|------| | 01 | 登录 | 1 | ✅ 已设计 | 见 `管理后台/01-登录/01-01-登录页面.md` | | 02 | 仪表盘 | 1 | ✅ 已设计 | 见 `管理后台/02-仪表盘/02-01-仪表盘页面.md` | | 03 | 设备管理 | 2 | ✅ 已设计 | 列表页+详情页,见 `管理后台/03-设备管理/` | | 04 | 品牌模板 | 2 | ✅ 已设计 | 列表页+编辑页,见 `管理后台/04-品牌模板/` | | 05 | 采集地址 | 2 | ✅ 已设计 | 列表页+详情页(采集历史+原始JSON),见 `管理后台/05-采集地址/` | | 06 | 员工管理 | 2 | ✅ 已设计 | 列表页+详情页,见 `管理后台/06-员工管理/` | | 07 | 产量报表 | 1 | ✅ 已设计 | 含修正+导出+数据缺失标记,见 `管理后台/07-产量报表/` | | 08 | 告警中心 | 1 | ✅ 已设计 | 含批量标记+统计,见 `管理后台/08-告警中心/` | | 09 | 系统设置 | 1 | ✅ 已设计 | 3Tab:配置项+车间管理+修改密码,见 `管理后台/09-系统设置/` | | 10 | 车间管理 | - | 🔀 已合并 | 合并至09-系统设置 | | 11 | 操作日志 | 1 | ✅ 已设计 | 双Tab:修正审计日志+系统运行日志,见 `管理后台/11-操作日志/` | | 12 | 大屏配置 | 1 | ✅ 已设计 | 见 `管理后台/12-大屏配置/12-01-大屏配置页面.md` | **大屏模块:** | 编号 | 模块 | 页面数 | 设计状态 | 备注 | |------|------|--------|---------|------| | 大屏-01 | 大屏看板 | 1 | ✅ 已设计 | 免认证,深色主题,卡片式自动刷新,见 `大屏/01-01-大屏看板页面.md` |