模块: 11-产品管理
版本: v1.0
日期: 2025-10-03
关联文档:
- 需求文档:
docs/11-产品管理模块需求.md- 原型图:
yuanxing/09-产品管理原型图.md- 数据库:
sql/crm/11-crm_product.sql
接口地址: GET /crm/product/category/tree
接口描述: 获取产品分类树形结构,用于分类选择器和分类管理页面
权限标识: crm:product:category:list
请求参数: 无
返回示例:
{
"code": 200,
"msg": "操作成功",
"data": [
{
"id": 1,
"categoryName": "软件产品",
"parentId": 0,
"ancestors": "0",
"sort": 1,
"status": "0",
"children": [
{
"id": 11,
"categoryName": "CRM系统",
"parentId": 1,
"ancestors": "0,1",
"sort": 1,
"status": "0",
"children": [
{
"id": 111,
"categoryName": "标准版",
"parentId": 11,
"ancestors": "0,1,11",
"sort": 1,
"status": "0"
}
]
}
]
}
]
}
接口地址: GET /crm/product/category/{id}
接口描述: 根据ID查询分类详细信息
权限标识: crm:product:category:query
请求参数: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | id | Long | 是 | 分类ID |
返回示例:
{
"code": 200,
"msg": "操作成功",
"data": {
"id": 1,
"categoryName": "软件产品",
"parentId": 0,
"ancestors": "0",
"sort": 1,
"status": "0",
"createTime": "2025-01-01 10:00:00",
"remark": "软件类产品分类"
}
}
接口地址: POST /crm/product/category
接口描述: 新增产品分类
权限标识: crm:product:category:add
请求体:
{
"categoryName": "软件产品",
"parentId": 0,
"sort": 1,
"status": "0",
"remark": "软件类产品分类"
}
请求参数说明: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | categoryName | String | 是 | 分类名称,最大100字符 | | parentId | Long | 否 | 父级分类ID,默认0(顶级) | | sort | Integer | 否 | 显示顺序,默认0 | | status | String | 否 | 状态:0-正常 1-停用,默认0 | | remark | String | 否 | 备注,最大500字符 |
返回示例:
{
"code": 200,
"msg": "操作成功"
}
接口地址: PUT /crm/product/category
接口描述: 修改产品分类信息
权限标识: crm:product:category:edit
请求体:
{
"id": 1,
"categoryName": "软件产品",
"parentId": 0,
"sort": 1,
"status": "0",
"remark": "软件类产品分类"
}
请求参数说明: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | id | Long | 是 | 分类ID | | categoryName | String | 是 | 分类名称 | | parentId | Long | 否 | 父级分类ID | | sort | Integer | 否 | 显示顺序 | | status | String | 否 | 状态 | | remark | String | 否 | 备注 |
返回示例:
{
"code": 200,
"msg": "操作成功"
}
接口地址: DELETE /crm/product/category/{ids}
接口描述: 删除产品分类(支持批量)
权限标识: crm:product:category:remove
请求参数: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | ids | Long[] | 是 | 分类ID数组,多个用逗号分隔 |
业务规则:
返回示例:
{
"code": 200,
"msg": "操作成功"
}
接口地址: GET /crm/product/list
接口描述: 分页查询产品列表,支持多条件筛选
权限标识: crm:product:list
请求参数: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | pageNum | Integer | 否 | 页码,默认1 | | pageSize | Integer | 否 | 每页条数,默认10 | | productName | String | 否 | 产品名称(模糊查询) | | productNo | String | 否 | 产品编号(模糊查询) | | categoryId | Long | 否 | 分类ID | | status | String | 否 | 状态:on-上架 off-下架 | | minPrice | BigDecimal | 否 | 最低价格 | | maxPrice | BigDecimal | 否 | 最高价格 | | minSaleCount | Integer | 否 | 最小销量 | | maxSaleCount | Integer | 否 | 最大销量 | | beginTime | String | 否 | 开始时间 yyyy-MM-dd HH:mm:ss | | endTime | String | 否 | 结束时间 yyyy-MM-dd HH:mm:ss |
返回示例:
{
"code": 200,
"msg": "查询成功",
"rows": [
{
"id": 1,
"productNo": "PRD20250101001",
"productName": "CRM系统标准版",
"categoryId": 11,
"categoryName": "CRM系统",
"model": "V5.4.0",
"unit": "套",
"barcode": "6901234567890",
"price": 12800.00,
"cost": 8000.00,
"minPrice": 10000.00,
"stock": 100,
"lowStock": 10,
"status": "on",
"description": "适合中小企业的CRM系统",
"images": "/upload/product/001.jpg,/upload/product/002.jpg",
"saleCount": 156,
"createTime": "2025-01-01 10:00:00",
"updateTime": "2025-01-15 16:30:00",
"remark": ""
}
],
"total": 89
}
接口地址: GET /crm/product/{id}
接口描述: 根据ID查询产品详细信息
权限标识: crm:product:query
请求参数: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | id | Long | 是 | 产品ID |
返回示例:
{
"code": 200,
"msg": "操作成功",
"data": {
"id": 1,
"productNo": "PRD20250101001",
"productName": "CRM系统标准版",
"categoryId": 11,
"categoryName": "CRM系统",
"model": "V5.4.0",
"unit": "套",
"barcode": "6901234567890",
"price": 12800.00,
"cost": 8000.00,
"minPrice": 10000.00,
"stock": 100,
"lowStock": 10,
"status": "on",
"description": "适合中小企业的CRM系统,包含客户管理、销售管理、数据分析等功能",
"images": "/upload/product/001.jpg,/upload/product/002.jpg",
"saleCount": 156,
"createTime": "2025-01-01 10:00:00",
"createBy": 1,
"updateTime": "2025-01-15 16:30:00",
"updateBy": 1,
"remark": "标准版产品"
}
}
接口地址: POST /crm/product
接口描述: 新增产品信息
权限标识: crm:product:add
请求体:
{
"productNo": "PRD20250101001",
"productName": "CRM系统标准版",
"categoryId": 11,
"model": "V5.4.0",
"unit": "套",
"barcode": "6901234567890",
"price": 12800.00,
"cost": 8000.00,
"minPrice": 10000.00,
"stock": 100,
"lowStock": 10,
"status": "on",
"description": "适合中小企业的CRM系统",
"images": "/upload/product/001.jpg,/upload/product/002.jpg",
"remark": "标准版产品"
}
请求参数说明: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | productNo | String | 是 | 产品编号,唯一,最大50字符 | | productName | String | 是 | 产品名称,最大200字符 | | categoryId | Long | 否 | 分类ID | | model | String | 否 | 型号/规格,最大100字符 | | unit | String | 否 | 单位,默认"个",最大20字符 | | barcode | String | 否 | 条码,最大100字符 | | price | BigDecimal | 是 | 标准价格,保留2位小数 | | cost | BigDecimal | 否 | 成本价,保留2位小数 | | minPrice | BigDecimal | 否 | 最低价格,保留2位小数 | | stock | Integer | 否 | 库存数量,默认0 | | lowStock | Integer | 否 | 库存预警值,默认10 | | status | String | 否 | 状态:on-上架 off-下架,默认on | | description | String | 否 | 产品描述,文本类型 | | images | String | 否 | 产品图片,多个用逗号分隔 | | remark | String | 否 | 备注,最大500字符 |
校验规则:
返回示例:
{
"code": 200,
"msg": "操作成功"
}
接口地址: PUT /crm/product
接口描述: 修改产品信息
权限标识: crm:product:edit
请求体:
{
"id": 1,
"productNo": "PRD20250101001",
"productName": "CRM系统标准版",
"categoryId": 11,
"model": "V5.4.0",
"unit": "套",
"barcode": "6901234567890",
"price": 12800.00,
"cost": 8000.00,
"minPrice": 10000.00,
"stock": 100,
"lowStock": 10,
"status": "on",
"description": "适合中小企业的CRM系统",
"images": "/upload/product/001.jpg,/upload/product/002.jpg",
"remark": "标准版产品"
}
请求参数说明: 同新增接口,但需要传入id
返回示例:
{
"code": 200,
"msg": "操作成功"
}
接口地址: DELETE /crm/product/{ids}
接口描述: 删除产品(支持批量)
权限标识: crm:product:remove
请求参数: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | ids | Long[] | 是 | 产品ID数组,多个用逗号分隔 |
业务规则:
返回示例:
{
"code": 200,
"msg": "操作成功"
}
接口地址: PUT /crm/product/status
接口描述: 批量修改产品状态(上架/下架)
权限标识: crm:product:edit
请求体:
{
"ids": [1, 2, 3],
"status": "on"
}
请求参数说明: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | ids | Long[] | 是 | 产品ID数组 | | status | String | 是 | 状态:on-上架 off-下架 |
返回示例:
{
"code": 200,
"msg": "操作成功"
}
接口地址: PUT /crm/product/price
接口描述: 批量调整产品价格
权限标识: crm:product:edit
请求体:
{
"ids": [1, 2, 3],
"priceType": "price",
"adjustType": "percent",
"adjustValue": 10.0,
"remark": "年度调价"
}
请求参数说明: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | ids | Long[] | 是 | 产品ID数组 | | priceType | String | 是 | 价格类型:price-标准价 cost-成本价 minPrice-最低价 | | adjustType | String | 是 | 调整方式:percent-百分比 fixed-固定金额 | | adjustValue | BigDecimal | 是 | 调整值(百分比或固定金额) | | remark | String | 否 | 调价备注 |
返回示例:
{
"code": 200,
"msg": "操作成功"
}
接口地址: POST /crm/product/export
接口描述: 导出产品数据到Excel
权限标识: crm:product:export
请求体: 查询参数同2.1列表查询接口
返回: Excel文件流
接口地址: POST /crm/product/import
接口描述: 批量导入产品数据
权限标识: crm:product:import
请求参数: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | file | MultipartFile | 是 | Excel文件 | | updateSupport | Boolean | 否 | 是否更新已存在的产品,默认false |
返回示例:
{
"code": 200,
"msg": "操作成功",
"data": {
"total": 100,
"success": 95,
"fail": 5,
"errors": [
{
"row": 3,
"error": "产品编号已存在"
},
{
"row": 7,
"error": "分类不存在"
}
]
}
}
接口地址: POST /crm/product/importTemplate
接口描述: 下载产品导入Excel模板
权限标识: crm:product:import
请求参数: 无
返回: Excel文件流
接口地址: GET /crm/product/no/{productNo}
接口描述: 根据产品编号查询产品信息
权限标识: crm:product:query
请求参数: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | productNo | String | 是 | 产品编号 |
返回示例: 同2.2查询详情接口
接口地址: GET /crm/product/search
接口描述: 根据关键词搜索产品,用于产品选择器
权限标识: crm:product:list
请求参数: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | keyword | String | 否 | 搜索关键词(产品名称/编号) | | categoryId | Long | 否 | 分类ID | | status | String | 否 | 状态,默认只查询上架产品 | | limit | Integer | 否 | 返回条数,默认10 |
返回示例:
{
"code": 200,
"msg": "查询成功",
"data": [
{
"id": 1,
"productNo": "PRD20250101001",
"productName": "CRM系统标准版",
"categoryName": "CRM系统",
"price": 12800.00,
"unit": "套",
"stock": 100
}
]
}
接口地址: GET /crm/product/stockAlert
接口描述: 查询库存低于预警值的产品列表
权限标识: crm:product:list
请求参数: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | pageNum | Integer | 否 | 页码,默认1 | | pageSize | Integer | 否 | 每页条数,默认10 |
返回示例:
{
"code": 200,
"msg": "查询成功",
"rows": [
{
"id": 1,
"productNo": "PRD20250101001",
"productName": "CRM系统标准版",
"stock": 5,
"lowStock": 10,
"alertLevel": "warning"
}
],
"total": 8
}
接口地址: GET /crm/product/statistics/overview
接口描述: 获取产品统计概览数据
权限标识: crm:product:list
请求参数: 无
返回示例:
{
"code": 200,
"msg": "查询成功",
"data": {
"totalCount": 89,
"onlineCount": 76,
"offlineCount": 13,
"totalSaleCount": 1256,
"monthAddCount": 5,
"alertCount": 8
}
}
接口地址: GET /crm/product/statistics/hot
接口描述: 获取热销产品排行榜
权限标识: crm:product:list
请求参数: | 参数名 | 类型 | 必填 | 说明 | |--------|------|------|------| | limit | Integer | 否 | 返回条数,默认10 |
返回示例:
{
"code": 200,
"msg": "查询成功",
"data": [
{
"id": 3,
"productNo": "PRD20250101003",
"productName": "办公自动化系统",
"saleCount": 234,
"totalAmount": 2059200.00
}
]
}
接口地址: GET /crm/product/statistics/category
接口描述: 按分类统计产品数量和销量
权限标识: crm:product:list
请求参数: 无
返回示例:
{
"code": 200,
"msg": "查询成功",
"data": [
{
"categoryId": 1,
"categoryName": "软件产品",
"productCount": 45,
"saleCount": 856,
"totalAmount": 12500000.00
}
]
}
public class CrmProductCategoryBo extends BaseEntity {
/** 主键ID */
@NotNull(message = "主键不能为空", groups = { EditGroup.class })
private Long id;
/** 分类名称 */
@NotBlank(message = "分类名称不能为空", groups = { AddGroup.class, EditGroup.class })
private String categoryName;
/** 父级ID */
private Long parentId;
/** 祖级列表 */
private String ancestors;
/** 显示顺序 */
private Integer sort;
/** 状态 */
private String status;
/** 备注 */
private String remark;
}
public class CrmProductCategoryVo implements Serializable {
/** 主键ID */
@ExcelProperty(value = "ID")
private Long id;
/** 分类名称 */
@ExcelProperty(value = "分类名称")
private String categoryName;
/** 父级ID */
private Long parentId;
/** 祖级列表 */
private String ancestors;
/** 显示顺序 */
@ExcelProperty(value = "显示顺序")
private Integer sort;
/** 状态 */
@ExcelProperty(value = "状态", converter = ExcelDictConvert.class)
@ExcelDictFormat(dictType = "sys_normal_disable")
private String status;
/** 创建时间 */
@ExcelProperty(value = "创建时间")
private LocalDateTime createTime;
/** 备注 */
@ExcelProperty(value = "备注")
private String remark;
/** 子分类列表 */
private List<CrmProductCategoryVo> children;
}
public class CrmProductBo extends BaseEntity {
/** 主键ID */
@NotNull(message = "主键不能为空", groups = { EditGroup.class })
private Long id;
/** 产品编号 */
@NotBlank(message = "产品编号不能为空", groups = { AddGroup.class, EditGroup.class })
private String productNo;
/** 产品名称 */
@NotBlank(message = "产品名称不能为空", groups = { AddGroup.class, EditGroup.class })
private String productName;
/** 分类ID */
private Long categoryId;
/** 型号/规格 */
private String model;
/** 单位 */
private String unit;
/** 条码 */
private String barcode;
/** 标准价格 */
@NotNull(message = "标准价格不能为空", groups = { AddGroup.class, EditGroup.class })
private BigDecimal price;
/** 成本价 */
private BigDecimal cost;
/** 最低价格 */
private BigDecimal minPrice;
/** 库存数量 */
private Integer stock;
/** 库存预警值 */
private Integer lowStock;
/** 状态 */
private String status;
/** 产品描述 */
private String description;
/** 产品图片 */
private String images;
/** 备注 */
private String remark;
}
public class CrmProductVo implements Serializable {
/** 主键ID */
@ExcelProperty(value = "ID")
private Long id;
/** 产品编号 */
@ExcelProperty(value = "产品编号")
private String productNo;
/** 产品名称 */
@ExcelProperty(value = "产品名称")
private String productName;
/** 分类ID */
private Long categoryId;
/** 分类名称 */
@ExcelProperty(value = "产品分类")
private String categoryName;
/** 型号/规格 */
@ExcelProperty(value = "型号/规格")
private String model;
/** 单位 */
@ExcelProperty(value = "单位")
private String unit;
/** 条码 */
@ExcelProperty(value = "条码")
private String barcode;
/** 标准价格 */
@ExcelProperty(value = "标准价格")
private BigDecimal price;
/** 成本价 */
@ExcelProperty(value = "成本价")
private BigDecimal cost;
/** 最低价格 */
@ExcelProperty(value = "最低价格")
private BigDecimal minPrice;
/** 库存数量 */
@ExcelProperty(value = "库存数量")
private Integer stock;
/** 库存预警值 */
@ExcelProperty(value = "库存预警值")
private Integer lowStock;
/** 状态 */
@ExcelProperty(value = "状态", converter = ExcelDictConvert.class)
@ExcelDictFormat(dictType = "crm_product_status")
private String status;
/** 产品描述 */
private String description;
/** 产品图片 */
private String images;
/** 销售次数 */
@ExcelProperty(value = "销售次数")
private Integer saleCount;
/** 创建时间 */
@ExcelProperty(value = "创建时间")
private LocalDateTime createTime;
/** 更新时间 */
@ExcelProperty(value = "更新时间")
private LocalDateTime updateTime;
/** 备注 */
@ExcelProperty(value = "备注")
private String remark;
}
| 字典值 | 字典标签 | 说明 |
|---|---|---|
| on | 上架 | 产品可销售 |
| off | 下架 | 产品不可销售 |
| 权限标识 | 说明 |
|---|---|
| crm:product:category:list | 产品分类列表查询 |
| crm:product:category:query | 产品分类详情查询 |
| crm:product:category:add | 产品分类新增 |
| crm:product:category:edit | 产品分类修改 |
| crm:product:category:remove | 产品分类删除 |
| crm:product:list | 产品列表查询 |
| crm:product:query | 产品详情查询 |
| crm:product:add | 产品新增 |
| crm:product:edit | 产品修改 |
| crm:product:remove | 产品删除 |
| crm:product:export | 产品导出 |
| crm:product:import | 产品导入 |
文档结束