17 KiB
17 KiB
采购管理模块 - 前端开发规范
本文档为采购管理模块的前端开发技术规范,包含UI组件规范、字段验证、API接口等内容。
1. 技术栈
| 技术 | 版本 | 说明 |
|---|---|---|
| Vue | 2.x | 前端框架 |
| Element UI | 2.x | UI组件库 |
| Axios | - | HTTP请求库 |
| Vue Router | 3.x | 路由管理 |
| Vuex | 3.x | 状态管理 |
2. 设计规范
2.1 颜色规范
| 用途 | 色值 | 说明 |
|---|---|---|
| 主色 | #409EFF | 按钮、链接等 |
| 成功色 | #67C23A | 成功状态 |
| 警告色 | #E6A23C | 警告状态 |
| 危险色 | #F56C6C | 错误、删除 |
| 信息色 | #909399 | 次要信息 |
| 背景色 | #F5F7FA | 页面背景 |
| 边框色 | #DCDFE6 | 表格边框 |
2.2 状态标签颜色
| 状态 | 颜色类型 | Element Type |
|---|---|---|
| 开立 | 信息 | info |
| 审核 | 成功 | success |
| 关闭 | 默认 | - |
| 退回 | 警告 | warning |
| 入账 | 成功 | success |
2.3 字体规范
| 用途 | 字号 | 字重 |
|---|---|---|
| 页面标题 | 20px | 500 |
| 模块标题 | 16px | 500 |
| 正文 | 14px | 400 |
| 辅助文字 | 12px | 400 |
| 表格文字 | 14px | 400 |
2.4 间距规范
| 用途 | 间距 |
|---|---|
| 页面边距 | 20px |
| 模块间距 | 20px |
| 表单行间距 | 22px |
| 按钮间距 | 10px |
| 表格单元格内边距 | 12px 0 |
3. 通用组件规范
3.1 表格组件
<el-table
:data="tableData"
border
stripe
style="width: 100%"
:header-cell-style="{ background: '#f5f7fa', color: '#606266' }"
@row-click="handleRowClick"
>
<el-table-column type="index" label="序号" width="60" align="center" />
<el-table-column prop="code" label="单据编码" min-width="120" />
<el-table-column prop="status" label="状态" width="80" align="center">
<template slot-scope="scope">
<el-tag :type="getStatusType(scope.row.status)">
{{ scope.row.status }}
</el-tag>
</template>
</el-table-column>
<el-table-column label="操作" width="150" fixed="right">
<template slot-scope="scope">
<el-button type="text" @click="handleView(scope.row)">查看</el-button>
<el-button type="text" @click="handleEdit(scope.row)">修改</el-button>
<el-button type="text" class="danger-text" @click="handleDelete(scope.row)">删除</el-button>
</template>
</el-table-column>
</el-table>
3.2 查询表单
<el-form :inline="true" :model="queryParams" class="query-form">
<el-form-item label="供应商名称">
<el-input v-model="queryParams.supplierName" placeholder="请输入" clearable />
</el-form-item>
<el-form-item label="单据日期">
<el-date-picker
v-model="queryParams.dateRange"
type="daterange"
range-separator="-"
start-placeholder="开始日期"
end-placeholder="结束日期"
value-format="yyyy-MM-dd"
/>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="el-icon-search" @click="handleQuery">搜索</el-button>
</el-form-item>
</el-form>
3.3 弹窗组件
<el-dialog
:title="dialogTitle"
:visible.sync="dialogVisible"
width="800px"
:close-on-click-modal="false"
@close="handleClose"
>
<el-form ref="formRef" :model="form" :rules="rules" label-width="100px">
<!-- 表单内容 -->
</el-form>
<span slot="footer" class="dialog-footer">
<el-button @click="dialogVisible = false">取 消</el-button>
<el-button type="primary" @click="handleSubmit">确 定</el-button>
</span>
</el-dialog>
3.4 分页组件
<el-pagination
background
:current-page="queryParams.pageNum"
:page-size="queryParams.pageSize"
:page-sizes="[10, 20, 50, 100]"
:total="total"
layout="total, sizes, prev, pager, next, jumper"
@size-change="handleSizeChange"
@current-change="handleCurrentChange"
/>
4. 数据字典
4.1 单据状态(status)
| 值 | 显示名称 | 说明 |
|---|---|---|
| DRAFT | 开立 | 草稿状态 |
| APPROVED | 审核 | 已审核 |
| CLOSED | 关闭 | 已关闭 |
| RETURNED | 退回 | 已退回 |
4.2 业务类型(businessType)
| 值 | 显示名称 |
|---|---|
| RAW_MATERIAL | 原材料 |
| PARTS | 零部件 |
| ASSEMBLY | 装配件 |
| FINISHED | 成品 |
| HARDWARE | 五金件 |
| PACKAGING | 包装物 |
4.3 财务状态(financeStatus)
| 值 | 显示名称 |
|---|---|
| RECORDED | 录入 |
| ENTERED | 入账 |
4.4 用料需求(materialNeed)
| 值 | 显示名称 |
|---|---|
| ORDER_USE | 订单用料 |
| STOCK_USE | 备库用料 |
4.5 供应商状态(enableFlag)
| 值 | 显示名称 |
|---|---|
| Y | 正常 |
| N | 停用 |
4.6 供应商等级(supplierLevel)
| 值 | 显示名称 |
|---|---|
| A | A级 |
| B | B级 |
| C | C级 |
| D | D级 |
5. 表单字段规范
5.1 原料供应商表单
| 字段名 | 字段key | 类型 | 必填 | 验证规则 |
|---|---|---|---|---|
| 供应商名称 | supplierName | String | 是 | 最大100字符 |
| 供应商别名 | supplierAlias | String | 否 | 最大100字符 |
| 简称 | supplierNick | String | 否 | 最大50字符 |
| 所属省/市 | provinceCity | Array | 否 | 级联选择 |
| 供应料品 | supplyItems | Array | 否 | 多选 |
| 供应商分类 | supplierType | String | 否 | 单选 |
| 供应商等级 | supplierLevel | String | 否 | A/B/C/D |
| 公司地址 | address | String | 否 | 最大200字符 |
| 邮编 | zipCode | String | 否 | 6位数字 |
| 电话 | tel | String | 否 | 电话格式 |
| 备注 | remark | String | 否 | 最大500字符 |
| 状态 | enableFlag | String | 否 | Y/N |
| 开户行 | bankName | String | 否 | 最大100字符 |
| 地址电话 | bankAddress | String | 否 | 最大200字符 |
| 账号 | bankAccount | String | 否 | 最大30字符 |
| 税号 | taxNo | String | 否 | 最大30字符 |
| 业务联系人 | contact1 | String | 否 | 最大50字符 |
| 业务手机 | contact1Tel | String | 否 | 手机格式 |
| 财务联系人 | contact2 | String | 否 | 最大50字符 |
| 财务手机 | contact2Tel | String | 否 | 手机格式 |
5.2 采购订单表单
| 字段名 | 字段key | 类型 | 必填 | 验证规则 |
|---|---|---|---|---|
| 单据编码 | orderCode | String | 自动 | 系统生成 |
| 单据日期 | orderDate | Date | 是 | 日期格式 |
| 业务类型 | businessType | String | 是 | 必选 |
| 单据类型 | orderType | String | 是 | 固定值 |
| 采购部门 | deptId | Integer | 否 | 部门选择 |
| 采购人员 | userId | Integer | 否 | 人员选择 |
| 用料需求 | materialNeed | String | 是 | 必选 |
| 供方 | supplierId | Integer | 否 | 供应商选择 |
| 到货日期 | deliveryDate | Date | 否 | 日期格式 |
| 合同号 | contractNo | String | 否 | 最大50字符 |
| 备注信息 | remark | String | 否 | 最大500字符 |
5.3 采购订单明细
| 字段名 | 字段key | 类型 | 必填 | 验证规则 |
|---|---|---|---|---|
| 物料编码 | itemCode | String | 是 | 物料选择 |
| 物料名称 | itemName | String | - | 自动带出 |
| 型号规格 | specification | String | - | 自动带出 |
| 主计量 | unitName | String | - | 自动带出 |
| 需求日期 | needDate | Date | 否 | 日期格式 |
| 数量 | quantity | Decimal | 是 | >0 |
| 单价 | unitPrice | Decimal | 否 | >=0 |
| 金额 | amount | Decimal | - | 自动计算 |
| 采购说明 | remark | String | 否 | 最大200字符 |
6. API 接口规范
Base URL:
https://demo.rsun.vip/prod-api
6.1 接口基础规范
请求格式
// Content-Type: application/json
// 字符编码: UTF-8
// GET 请求 - 查询列表
axios.get('/po/supplier', { params: queryParams })
// GET 请求 - 获取详情
axios.get('/po/supplier/' + supplierId)
// POST 请求 - 新增
axios.post('/po/supplier', formData)
// PUT 请求 - 更新
axios.put('/po/supplier', formData)
// DELETE 请求 - 删除(支持批量,逗号分隔)
axios.delete('/po/supplier/' + supplierIds)
响应格式
// 通用响应 (AjaxResult)
{
"code": 200, // 状态码:200成功
"msg": "操作成功", // 提示信息
"data": { ... } // 返回数据
}
// 分页响应 (TableDataInfo)
{
"total": 100, // 总条数
"rows": [ ... ], // 数据列表
"code": 200,
"msg": "查询成功"
}
6.2 供应商接口 (/po/supplier)
| 接口 | 方法 | 路径 | 说明 |
|---|---|---|---|
| 分页列表 | GET | /po/supplier/list | 查询供应商列表 |
| 详情 | GET | /po/supplier/{supplierId} | 获取供应商详情 |
| 新增 | POST | /po/supplier | 新增供应商 |
| 更新 | PUT | /po/supplier | 更新供应商 |
| 删除 | DELETE | /po/supplier/{supplierIds} | 批量删除 |
| 导出 | POST | /po/supplier/export | 导出Excel |
查询参数
| 参数名 | 类型 | 必填 | 说明 |
|---|---|---|---|
| supplierName | String | 否 | 供应商名称 |
| contact1 | String | 否 | 业务联系人 |
| supplyItem | String | 否 | 供应料品 |
| pageNum | Integer | 否 | 页码,默认1 |
| pageSize | Integer | 否 | 每页条数,默认10 |
6.3 采购订单接口 (/po/order)
| 接口 | 方法 | 路径 | 说明 |
|---|---|---|---|
| 分页列表 | GET | /po/order/list | 查询订单列表 |
| 详情 | GET | /po/order/{orderId} | 获取订单详情 |
| 新增 | POST | /po/order | 新增订单 |
| 更新 | PUT | /po/order | 更新订单 |
| 删除 | DELETE | /po/order/{orderIds} | 批量删除 |
| 审核 | PUT | /po/order/approve | 审核订单 |
| 反审核 | PUT | /po/order/unapprove | 反审核订单 |
| 导出 | POST | /po/order/export | 导出Excel |
查询参数
| 参数名 | 类型 | 必填 | 说明 |
|---|---|---|---|
| trackCode | String | 否 | 跟单编号 |
| orderCode | String | 否 | 单据编码 |
| supplierName | String | 否 | 供应商名称 |
| itemCode | String | 否 | 物料编码 |
| itemName | String | 否 | 物料名称 |
| beginDate | String | 否 | 开始日期 |
| endDate | String | 否 | 结束日期 |
| pageNum | Integer | 否 | 页码 |
| pageSize | Integer | 否 | 每页条数 |
6.4 采购到货单接口 (/po/checkin)
| 接口 | 方法 | 路径 | 说明 |
|---|---|---|---|
| 分页列表 | GET | /po/checkin/list | 查询到货单列表 |
| 详情 | GET | /po/checkin/{checkinId} | 获取到货单详情 |
| 新增 | POST | /po/checkin | 新增到货单 |
| 更新 | PUT | /po/checkin | 更新到货单 |
| 删除 | DELETE | /po/checkin/{checkinIds} | 批量删除 |
| 审核 | PUT | /po/checkin/approve | 审核 |
| 导出 | POST | /po/checkin/export | 导出Excel |
6.5 采购发票接口 (/po/invoice)
| 接口 | 方法 | 路径 | 说明 |
|---|---|---|---|
| 分页列表 | GET | /po/invoice/list | 查询发票列表 |
| 详情 | GET | /po/invoice/{invoiceId} | 获取发票详情 |
| 新增 | POST | /po/invoice | 新增发票 |
| 更新 | PUT | /po/invoice | 更新发票 |
| 删除 | DELETE | /po/invoice/{invoiceIds} | 批量删除 |
| 审核 | PUT | /po/invoice/approve | 审核 |
| 入账 | PUT | /po/invoice/enter | 入账 |
| 导出 | POST | /po/invoice/export | 导出Excel |
6.6 采购退货单接口 (/po/reject)
| 接口 | 方法 | 路径 | 说明 |
|---|---|---|---|
| 分页列表 | GET | /po/reject/list | 查询退货单列表 |
| 详情 | GET | /po/reject/{rejectId} | 获取退货单详情 |
| 新增 | POST | /po/reject | 新增退货单 |
| 更新 | PUT | /po/reject | 更新退货单 |
| 删除 | DELETE | /po/reject/{rejectIds} | 批量删除 |
| 审核 | PUT | /po/reject/approve | 审核 |
| 导出 | POST | /po/reject/export | 导出Excel |
7. 业务逻辑
7.1 金额计算
// 采购订单明细金额计算
function calculateAmount(quantity, unitPrice) {
if (!quantity || !unitPrice) return 0;
return (parseFloat(quantity) * parseFloat(unitPrice)).toFixed(2);
}
// 发票税额计算
function calculateTax(amount, taxRate) {
if (!amount || !taxRate) return 0;
return (parseFloat(amount) * parseFloat(taxRate) / 100).toFixed(2);
}
// 价税合计
function calculateTotal(amount, tax) {
return (parseFloat(amount || 0) + parseFloat(tax || 0)).toFixed(2);
}
7.2 按钮权限控制
// 按钮显示逻辑
const buttonPermissions = {
// 审核按钮:开立状态可见
approve: (status) => status === 'DRAFT',
// 反审核按钮:审核状态可见
unapprove: (status) => status === 'APPROVED',
// 编辑按钮:开立状态可见
edit: (status) => status === 'DRAFT',
// 删除按钮:开立状态可见
delete: (status) => status === 'DRAFT',
// 入账按钮:审核状态可见(发票)
enter: (status) => status === 'APPROVED'
};
7.3 字段联动
// 采购部门 -> 采购人员联动
watch: {
'form.deptId': function(newVal) {
if (newVal) {
this.getUsersByDept(newVal);
} else {
this.userOptions = [];
this.form.userId = null;
}
}
}
// 物料选择后自动带出信息
function onItemSelect(item) {
this.form.itemCode = item.itemCode;
this.form.itemName = item.itemName;
this.form.specification = item.specification;
this.form.unitName = item.unitName;
this.form.unitPrice = item.purchasePrice || 0;
}
8. 文件目录结构
src/
├── views/
│ └── po/ # 采购管理模块
│ ├── supplier/ # 供应商管理
│ │ └── index.vue
│ ├── order/ # 采购订单
│ │ ├── index.vue # 列表页
│ │ └── form.vue # 新增/编辑页
│ ├── checkin/ # 采购到货
│ │ ├── index.vue
│ │ └── form.vue
│ ├── invoice/ # 采购发票
│ │ ├── index.vue
│ │ └── form.vue
│ ├── reject/ # 采购退货
│ │ ├── index.vue
│ │ └── form.vue
│ └── report/ # 报表
│ ├── detail.vue # 执行明细表
│ ├── total.vue # 执行汇总表
│ ├── line.vue # 到货明细表
│ └── fapiaoreport.vue # 发票明细表
├── api/
│ └── po/
│ ├── supplier.js # 供应商接口
│ ├── order.js # 采购订单接口
│ ├── checkin.js # 到货单接口
│ ├── invoice.js # 发票接口
│ └── reject.js # 退货单接口
└── components/
└── po/
├── SupplierSelect.vue # 供应商选择组件
├── ItemSelect.vue # 物料选择组件
└── PlanImport.vue # 计划引入组件
9. 路由配置
{
path: '/po',
component: Layout,
redirect: '/po/supplier',
name: 'Po',
meta: { title: '采购管理', icon: 'shopping' },
children: [
{
path: 'supplier',
component: () => import('@/views/po/supplier/index'),
name: 'PoSupplier',
meta: { title: '原料供应商' }
},
{
path: 'order',
component: () => import('@/views/po/order/index'),
name: 'PoOrder',
meta: { title: '采购订单' }
},
{
path: 'order/add',
component: () => import('@/views/po/order/form'),
name: 'PoOrderAdd',
meta: { title: '新增采购订单', activeMenu: '/po/order' },
hidden: true
},
{
path: 'order/edit/:id',
component: () => import('@/views/po/order/form'),
name: 'PoOrderEdit',
meta: { title: '编辑采购订单', activeMenu: '/po/order' },
hidden: true
},
{
path: 'checkin',
component: () => import('@/views/po/checkin/index'),
name: 'PoCheckin',
meta: { title: '采购到货单' }
},
{
path: 'invoice',
component: () => import('@/views/po/invoice/index'),
name: 'PoInvoice',
meta: { title: '采购发票' }
},
{
path: 'reject',
component: () => import('@/views/po/reject/index'),
name: 'PoReject',
meta: { title: '采购退货单' }
},
{
path: 'report/detail',
component: () => import('@/views/po/report/detail'),
name: 'PoReportDetail',
meta: { title: '采购执行明细表' }
},
{
path: 'report/total',
component: () => import('@/views/po/report/total'),
name: 'PoReportTotal',
meta: { title: '采购执行汇总表' }
},
{
path: 'report/line',
component: () => import('@/views/po/report/line'),
name: 'PoReportLine',
meta: { title: '采购到货明细表' }
},
{
path: 'report/fapiao',
component: () => import('@/views/po/report/fapiaoreport'),
name: 'PoReportFapiao',
meta: { title: '采购发票明细表' }
}
]
}