有时候参数的传递还需要更多的参数,比如一个获取用户信息的请求中既有用户ID等基本参数,还要求对查询结果进行分页,针对这种场景,一般都会将分页参数封装成一个对象,然后将它和基本参数一起传给控制器,为了控制器方便接受,我们可以将这些所有的请求参数封装成一个json对象进行传递。现在我进行一个以下场景的实例:通过页面输入参数id和名称,然后从param表中获取id大于参数id,名称中包含参数名称字样的结果,并将结果分页,只获取20条数据。我已经在数据库中插入了相关数据,并且只有ID不一致,其他的都一样,如下图所示:
下面创建代码
1、创建前端页面
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%> <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"> <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> <% String root = request.getContextPath(); String basePath = request.getScheme() + "://" + request.getServerName() + ":" + request.getServerPort() + root + "/"; %> <script type="text/javascript" src="<%=basePath%>jslib/jquery-1.8.3.min.js"></script> <script type="text/javascript" src="<%=basePath%>jslib/jquery.form.js"></script> <script type="text/javascript" src="<%=basePath%>js/param.js"></script> <link href="<%=basePath%>css/param.css" type="text/css" rel="stylesheet"> <title>Insert title here</title> </head> <body> <div class="param"> <!--使用JSON传递参数 --> <div class="public json"> <p style="text-align: center;">JSON方式传递参数</p> <form id="jsonForm"> <table id="jsonTable"> <tr> <td>id:</td> <td><input type="text" name="id" value=""></td> </tr> <tr> <td>名称:</td> <td><input type="text" name="name" value=""></td> </tr> <tr> <td></td> <td style="text-align: right;"><input type="button" value="提交" id="setJsonParam"></td> </tr> </table> </form> </div> </body> </html>
页面效果如下:
2、给提交按钮绑定事件
点击提交的时候,向后台发起请求,请求的参数是一个json;
$(function() { /* json方式传递数据 */ /* 注意⚠️:json参数必须和类PageParam的属性一一对应 */ $("#setJsonParam").click(function() { var data = { paramId : $("#jsonForm input[name=id]").val(), paramName : $("#jsonForm input[name=name]").val(), page : { start : 0, limit : 20 } } $.ajax({ url : "./jsonParam", type : "POST", /* 此处需要定义传递参数的类型为json */ contentType : "application/json", /* 将json转化为字符串 */ data : JSON.stringify(data), success : function(data) { var size = data.paramList.length; var html = "<tr><td>总数:</td><td>" + size + "</td></tr>"; $("#jsonTable").append(html); } }); }); });
注意上面代码中加粗标红的部分:
- 变量data是个json数据,它有三个属性分别是paramId、paramName、page,而page又有两个属性start和limit,代表起始页和该页的数量;
- ajax请求的时候,数据类型需要定义为json格式;
- 传递参数时需要将json转化为字符串
根据上面的介绍,下一步需要创建json类。
3、创建json参数类
需要两步:
1⃣️创建分页类
package com.mvc.pojo; /* * 分页类 */ public class Page { public int start; public int limit; public int getStart() { return start; } public void setStart(int start) { this.start = start; } public int getLimit() { return limit; } public void setLimit(int limit) { this.limit = limit; } }
2⃣️封装所有参数类
该类中包含参数paramId、paramName和page
package com.mvc.pojo; /* * 分页参数类 */ public class PageParam { private int paramId; private String paramName; private Page page; public Page getPage() { return page; } public void setPage(Page page) { this.page = page; } public int getParamId() { return paramId; } public void setParamId(int paramId) { this.paramId = paramId; } public String getParamName() { return paramName; } public void setParamName(String paramName) { this.paramName = paramName; } }
通过上面两步就封装好了请求参数,下面需要创建控制器进行获取。
4、创建控制器
@Controller @RequestMapping("/param") public class ParamController { @Autowired @Qualifier("paramService") ParamService paramService = null; /** * 通过json获取参数 * * @param id * @param name * @return */ @RequestMapping(value = "jsonParam") public ModelAndView getParamByJson(@RequestBody PageParam pageParam) { ModelAndView mv = new ModelAndView(); List<Param> paramList = paramService.getParam(pageParam); mv.addObject(paramList); mv.setView(new MappingJackson2JsonView()); return mv; } }
上面代码中红色加粗部分:
- 注解RequestBody用来接受json参数
- paramService.getParam(pageParam);封装了一个从数据库中查询的方式,相当于服务端分页,具体的代码不贴了,看一下关键SQL吧:
<select id="getParamByPaging" parameterType="com.mvc.pojo.PageParam" resultMap="BaseResultMap"> SELECT * FROM param WHERE param_id > #{paramId,jdbcType=INTEGER} AND param_name like concat('%',#{paramName,jdbcType=VARCHAR},'%') LIMIT #{page.limit,jdbcType=INTEGER} OFFSET #{page.start,jdbcType=INTEGER} </select>
上面代码中红色加粗的部分:
- 参数类型,就是刚才封装的哪个分页参数类;
- 基本参数就是类中的参数名;
- 针对分页参数,获取其属性值的时候,不需要get方式,直接通过*.*的方式,前一个星号表示传递过来的封装类中的对象属性,后一个参数是这个对象属性中的属性值,比如分页类Page中的页数start和页大小limit
至此,所有代码已经完成,下面进行测试。
5、测试
在页面输入如下参数
点击提交之后的结果如下:
这里直接打印的是总的查询结果,为了验证是否正确在数据库中执行SQL看一下,执行之前先看一下传递的参数值是多少:
从控制台可以看出各个参数,SQL语句及执行结果如下:
可以看到和页面显示的是一致的,所以说控制器获取参数成功。
六、总结
使用JSON传递参数时需要注意以下几点:
- 传递的json数据需要和对应参数的pojo保持一致。其实这种类型跟pojo方式很像,只不过pojo方式中参数对应的pojo没有引用类型的属性罢了。
- 在请求的时候要告知请求的参数类型为JSON;
- 传递参数时需要将JSON数据转化成字符串;
- 在mapper中获取参数值时,基本类型引用的参数名就是pojo中的参数,而引用类型中的参数只需要通过pojo中的引用变量名.属性名的方式,而不是对应的get方法;