Spring MVC中AJAX POST请求无法填充@ModelAttribute对象问题
问题分析与解决方案
你遇到的核心问题是请求的Content-Type和实际发送的数据格式不匹配,导致Spring MVC无法正确绑定到@ModelAttribute的Product对象上:
- 表单提交时,默认的Content-Type是
application/x-www-form-urlencoded,和表单序列化后的url编码格式数据匹配,Spring能自动解析绑定。 - 但你在AJAX里设置了
contentType:"application/json",却发送了$("#productForm").serialize()生成的name=test_name&brand=test_brand...这种url编码字符串,Spring接收到后会按照JSON格式去解析,自然无法匹配Product对象的字段。
下面给你两种可行的解决方案:
方案一:修改AJAX的Content-Type匹配表单编码格式
这种方式最简单,不需要改动数据结构,只需要调整AJAX的Content-Type设置,让它和发送的数据格式一致:
function saveWithAjaxPost(){ var params = $("#productForm").serialize(); $.ajax({ url:"/saveWithAjaxPost", type:"POST", // 要么直接去掉contentType(jQuery会自动设置为表单编码格式),要么显式指定 contentType:"application/x-www-form-urlencoded; charset=UTF-8", data:params, async:true, dataType:"json", success:function(response){ $('#productsListDiv').empty(); getAllProcucts(); }, error:function(response){ alert(response.message); } }); }
控制器代码不需要做任何改动,保持原来的@ModelAttribute即可,Spring会正常解析表单编码格式的数据并填充Product对象。
方案二:转成JSON格式数据发送(更规范的前后端JSON交互)
如果希望前后端统一用JSON格式交互,需要把表单数据转换为JSON对象,再转成字符串发送,同时调整控制器的注解:
第一步:修改JavaScript代码,生成JSON格式数据
function saveWithAjaxPost(){ // 先把表单数据转成键值对数组,再转换成JSON对象 var formArray = $("#productForm").serializeArray(); var productData = {}; $.each(formArray, function(idx, item) { productData[item.name] = item.value; }); $.ajax({ url:"/saveWithAjaxPost", type:"POST", contentType:"application/json", // 把JSON对象转成字符串作为请求体发送 data: JSON.stringify(productData), async:true, dataType:"json", success:function(response){ $('#productsListDiv').empty(); getAllProcucts(); }, error:function(response){ alert(response.message); } }); }
第二步:调整控制器方法的注解
把@ModelAttribute改成@RequestBody,因为@RequestBody专门用来解析请求体中的JSON数据并绑定到Java对象:
@RequestMapping(value = "/saveWithAjaxPost", method = RequestMethod.POST) @ResponseBody public ModelMap saveWithAjaxPost(@RequestBody Product product) { ModelMap model = new ModelMap(); service.saveProduct(product); model.put("MESSAGE", "Success"); return model; }
两种方案都能解决你的问题,选哪种取决于你的项目交互规范——方案一快速兼容原有逻辑,方案二更贴合现代前后端分离的JSON交互模式。
内容的提问来源于stack exchange,提问作者Chamithra Thenuwara
相关产品推荐
相关产品推荐

