SpringMVC接受数组类型的参数

spring接受数组类型和普通类型有点区别,虽然之前也接收过这样的参数,但是由于前后端分离,参数前端传递的方式不一样,所以需要一点额外的操作。

References:

首先能想到的解决方法就是直接把参数改为数组类型:

@ResponseBody
@PostMapping("/listDetails.do")
public ResultDTO listDetails(
        @RequestParam(name="accountNumber", required=false) String accountNumber,
        @RequestParam(name="currency", required=false) String currency,
        @RequestParam(name="operationTypes", required=false) String[] operationTypes,
        @RequestParam(name="statuses", required=false) String[] statuses,
        @RequestParam(name="timeFrom", required=false) Date timeFrom,
        @RequestParam(name="timeTill", required=false) Date timeTill,
        @RequestParam(name="pageSize", required=false, defaultValue="15") Integer pageSize,
        @RequestParam(name="pageNo", required=false, defaultValue="1") Integer pageNo) {
}

如上代码中的operationTypes和statuses,之前直接这样加就可以了。这次不知道为什么不行,死活数据传的不对。例如传递的参数为“[DEBIT,CREDIT]”,接受后就变成了一个字符串,而不是两个元素。在网上搜到的方法也基本都是在接受参数名字后面加上[],例如:name="operationTypes"改为name="operationTypes[]",但是使用后发现并不起作用,甚至前端需要改变传递的key,后台才能接受到这个参数,而且也没有分割成数组,依然是一个字符串。要不就是把参数封装成对象,不过我并不喜欢对象当成参数,一来不清晰,不能一眼看到接口需要哪些参数,二来控制required有点繁琐,需要框架(如validator)的支持。甚至有通过@RequestBody的方式,前端将参数转成json传递,后端接受json的参数,不过这需要将这一次请求全部的参数都转成json,而不能部分转换。

分析传递的参数后发现,Ajax传递的数组类似/listDetails.do?operationTypes=DEBIT&operationTypes=CREDIT这样的,即多个同名参数一起发送,但是值不一样,经过postman手动测试,这样传递参数,后台确实可以接受到。但是前端现在用的是form表单的方式提交,参数格式就是operationTypes: [DEBIT,CREDIT]这样。我个人也倾向于这种方式。

找了一会后放弃了,换种方式接收参数,通过注册自定义请求参数编辑器的方式,即@InitBinder。没错,可能你已经想到我要干什么了。

@InitBinder这里就不多介绍了,参考链接或者自行搜索。通常这个注解被使用最多的就是日期处理,即接口直接接收日期类型。下面贴下日期和数组的转换:

@InitBinder
public void initBinder(WebDataBinder binder) {
    // 此controller所有日期类型都会被转换
    SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
    dateFormat.setLenient(false);
    binder.registerCustomEditor(Date.class, new CustomDateEditor(dateFormat, true)); // true:允许输入空值,false:不能为空值
    
    // 所有的String数组类型都会按逗号分割
    binder.registerCustomEditor(String[].class, new StringArrayPropertyEditor(","));
}

这个方法放在Controller中某个位置即可,第一个CustomEditor指明了,如果接受了yyyy-MM-dd HH:mm:ss格式的时间,就转成Date类型。第二个CustomEditor就是我们需要的,将String数组类型都按照,分割。这样只要加一段代码就行了,原来的代码不用变。

注:
SpringMVC接收日期类型除了上面的方式,还有一种方式,使用@DateTimeFormat注解。可参考此链接

标签: none

添加新评论

ali-01.gifali-58.gifali-09.gifali-23.gifali-04.gifali-46.gifali-57.gifali-22.gifali-38.gifali-13.gifali-10.gifali-34.gifali-06.gifali-37.gifali-42.gifali-35.gifali-12.gifali-30.gifali-16.gifali-54.gifali-55.gifali-59.gif

加载中……