当前位置: 首页 > news >正文

9 前后端数据处理格式的注意事项

目录

9 前后端数据处理格式的注意事项

9.1 后端 JSON 序列化字段不一致问题

(1)修改变量名

(2)@JsonProperty指定 JSON 字段名

(3)隐藏敏感字段(如 password)

(4)空值字段不返回前端

9.2 前端响应格式适配问题

9.3 后端请求参数接收规范(DTO vs Map)

(1)数据类职责划分(强制)

(2)参数接收规范

(3)代码示例(规范 DTO 用法)


9 前后端数据处理格式的注意事项

9.1 后端 JSON 序列化字段不一致问题

  1. 问题表现
后端 VO 类变量名与接口文档约定的 JSON 字段名不匹配(如接口定义meta,后端写metaVo),导致 Jackson 序列化后 JSON 字段名错误,前端无法解析数据。
  1. 底层原理
SpringMVC 通过 Jackson 将 Java 对象序列化为 JSON,核心规则如下:
  • Jackson 序列化时,不直接读取 Java 变量名,而是通过解析类的getter方法名来生成 JSON 字段名,推导规则固定:
  • 第一步:去掉getter方法名的get前缀(如getMeta()去掉get→Meta,getMetaVo()去掉get→MetaVo);
  • 第二步:将剩余部分的首字母小写,得到最终 JSON 字段名(Meta→meta,MetaVo→metaVo)。
  • IDEA 手动生成 getter、@Data(Lombok)自动生成 getter都是get + 变量名首字母大写 + 变量剩余部分
  • JSON 字段名大小写敏感,需与前端完全一致。
  1. 解决方案及拓展
(1)修改变量名
  • 解决方案:变量名严格对齐接口文档 JSON 字段名
  • 代码示例:
//假设接口文档中对应的变量名是meta // 错误写法 // private MetaVO metaVo; // 正确写法 private MetaVO meta;
  • 原理说明:保证getter生成的字段名与接口一致
(2)@JsonProperty指定 JSON 字段名
  • 解决方案:使用@JsonProperty指定 JSON 字段名
  • 代码示例:
@JsonProperty("user_id") private Long userId;
原理说明:覆盖 Jackson 默认规则,强制定义字段名
(3)隐藏敏感字段(如 password)
  • 解决方案:使用@JsonIgnore注解
  • 代码示例:
@JsonIgnore private String password;
  • 原理说明:序列化时跳过该字段,JSON 中不生成对应键值对
(4)空值字段不返回前端
  • 解决方案:全局配置(application.yml)或@JsonInclude注解
  • 代码示例(全局配置):
spring: jackson: default-property-inclusion: non_null
  • 原理说明:控制空值(null / 空字符串 / 空集合)是否序列化

9.2 前端响应格式适配问题

  1. 问题表现
  • 后端成功传参,但是前端就是拿不到值
  • 前处理的字段名和后端处理的字段名不一致
  1. 原因
  • 前端可能封装统一 axios 工具类,拦截响应自动解析data
代码示例:
响应拦截器会拦截所有的响应,处理数据后再统一返回,此时我前端调后端接口拿到的数据就是我响应拦截器处理后的数据不是后端返回的原始数据。
import axios from 'axios' const request = axios.create({ baseURL: '/api' }) // 响应拦截器:自动提取Result<T>中的data request.interceptors.response.use( res => res.data, // 直接返回data字段,业务层无需再res.data error => { console.error('请求失败:', error) return Promise.reject(error) } )
// 修正后的购物车数量更新方法 const updateCartCount = async () => { try { // 拦截器已解析data,直接获取业务数据 const cartItems = await request.get('/cart/items') cartItemCount.value = Array.isArray(cartItems) ? cartItems.reduce((total, item) => total + item.quantity, 0) : 0 } catch (error) { cartItemCount.value = 0 } }
  1. 解决方案
  • 前后端字段名不一致
解决方案:前端手动映射字段名(临时方案),优先后端用@JsonProperty对齐(长期方案)
代码示例(前端映射):
解构后端数据并重命名字段,适配前端变量命名习惯
// 后端字段itemName/unitPrice → 前端name/price const mappedItems = items.map(item => ({ ...item, name: item.itemName, price: item.unitPrice, unitPrice: item.unitPrice, totalPrice: item.totalPrice }))

9.3 后端请求参数接收规范(DTO vs Map)

  1. 问题表现
  • 使用Map接收表单参数时,会包含按钮、隐藏域等无关字段,需手动过滤;
  • 未按规范使用 DTO 接收参数,导致参数校验、类型安全无法保障;
  • 混淆 DTO(接收参数)、VO(返回数据)、Entity(数据库映射)的职责,数据类使用混乱。
  1. 底层原理
  • SpringMVC 参数绑定规则:DTO 按字段名匹配赋值(自动过滤无关参数),Map存储全量键值对;
  • DTO 为强类型(编译期校验),Map为弱类型(运行期报错);
  • 不同数据类有明确职责边界,混用会导致数据泄露、校验缺失。
  1. DTO 与 Map 详细对比
对比维度
专用 DTO 类接收
Map 集合接收
核心影响
字段过滤
自动过滤无关参数(如表单按钮)
接收所有参数(含无关字段)
Map 需手动过滤,易遗漏;DTO 无需额外处理
类型安全
编译期校验(如 String→Integer 报错)
运行期类型转换异常
DTO 提前暴露错误,Map 线上才会发现问题
参数校验
支持
@NotBlank
/
@NotNull
等注解
需手动编写校验逻辑
DTO 简化校验,Map 增加冗余代码
可读性
字段显性定义,易协作
字段隐性存储,需查文档
DTO 降低团队沟通成本,Map 易导致理解偏差
适用场景
表单 / 接口参数接收(90% 场景)
临时调试、动态参数(极少场景)
DTO 适配结构化参数,Map 仅用于非结构化场景
  1. 规范要求
(1)数据类职责划分(强制)
数据类类型
核心职责
禁用场景
Entity
对应数据库表,仅用于数据层
直接接收前端参数、返回给前端
DTO
接收前端参数,含参数校验,仅存必要字段
映射数据库、返回给前端(特殊场景除外)
VO
返回前端数据,隐藏敏感字段
接收前端参数、映射数据库
(2)参数接收规范
  • 所有表单 / 接口参数强制使用 DTO 接收(如UserLoginDTO、CartAddDTO),仅包含接口所需字段;
  • 禁止业务接口用Map接收 / 返回参数(临时调试除外);
  • DTO 需添加参数校验注解(如@NotBlank校验非空、@Pattern校验格式),替代手动校验。
(3)代码示例(规范 DTO 用法)
// 购物车添加参数DTO(仅含必要字段) @Data public class CartAddDTO { @NotNull(message = "商品ID不能为空") private Long productId; @Min(value = 1, message = "数量不能小于1") private Integer quantity; // 仅包含接口所需字段,自动过滤表单无关参数(如按钮、隐藏域) } // Controller接收参数(自动过滤无关字段+校验) @PostMapping("/cart/add") public Result<Void> addCart(@Valid @RequestBody CartAddDTO cartAddDTO) { cartService.addCart(cartAddDTO); return Result.success(); }
http://www.jsqmd.com/news/95995/

相关文章:

  • 近红外光谱数据集实战手册:5大核心应用场景深度解析
  • Windows网络性能终极测试指南:iperf3完整使用教程
  • 7个关键步骤掌握智能API网关:多模型管理开源工具实战指南
  • 终极指南:Kafka Exporter实时监控全解析
  • ZonyLrcToolsX:终极音乐歌词管理解决方案完整指南 [特殊字符]
  • 终极指南:3D打印GPS自行车码表外壳制作全流程
  • 知识星球内容归档终极方案:5步实现自动化PDF制作
  • 廊坊市广告公司供应商
  • 如何快速解决ustcthesis参考文献格式更新问题:本科论文终极指南
  • 暗黑破坏神II存档编辑器:多版本兼容的角色定制解决方案
  • 如何快速实现前端Word文档生成:DOCX.js完整使用手册
  • 10分钟精通MTKClient:小白也能上手的联发科设备调试全攻略
  • Joy-Con Toolkit终极指南:如何轻松自定义你的游戏手柄
  • Ice:Mac菜单栏终极整理指南,彻底告别拥挤混乱
  • 终极标签打印解决方案:LPrint让你的跨平台打印变得如此简单
  • Poppler Windows版:终极PDF处理工具完整指南 [特殊字符]
  • GHelper完全攻略:华硕笔记本硬件控制与性能优化终极指南
  • 15、基于梯度的图像对齐方法及深度估计技术解析
  • 百度网盘秒传脚本终极完整使用指南
  • Python中华历史故事展播系统的设计与实现_6s872fp0_pycharm Vue django flask项目源码
  • Python医疗设备维护平台_医院设备维修系统za112o22--pycharm Vue django flask项目源码
  • 10、密集分割感知描述符:原理、方法与实验评估
  • Python医院就诊管理系统_j1xc967h_在线问诊系统
  • 3步搞定Vue即时通讯:chat-uikit-vue实战避坑指南
  • 11、图像特征描述符的高效解决方案:从密集分割感知到SIFTpack
  • Python协同过滤算法 音乐推荐系统_731w447o 论坛 浏览历史
  • 厦门大学LaTeX论文模板:学术写作的智能排版助手
  • Apk Pure评论摘要提取:LLama-Factory训练信息抽取模型
  • Vue大屏自适应终极解决方案:v-scale-screen组件深度解析
  • 函数C++