zoukankan      html  css  js  c++  java
  • SpringBoot16 MockMvc的使用、JsonPath的使用、请求参数问题、JsonView、分页查询参数、JsonProperty

    1 MockMvc的使用

      利用MockMvc可以快速实现MVC测试

      坑01:利用MockMvc进行测试时应用上下文路径是不包含在请求路径中的

      1.1 创建一个SpringBoot项目

        项目脚手架

      1.2 创建一个用户实体类

    package cn.test.demo.base_demo.entity.po;
    
    import java.util.Date;
    
    /**
     * @author 王杨帅
     * @create 2018-05-05 22:03
     * @desc 用户实体类
     **/
    public class User {
        private Integer userId;
        private String userName;
        private String password;
        private Date birthday;
    
        public Integer getUserId() {
            return userId;
        }
    
        public void setUserId(Integer userId) {
            this.userId = userId;
        }
    
        public String getUserName() {
            return userName;
        }
    
        public void setUserName(String userName) {
            this.userName = userName;
        }
    
        public String getPassword() {
            return password;
        }
    
        public void setPassword(String password) {
            this.password = password;
        }
    
        public Date getBirthday() {
            return birthday;
        }
    
        public void setBirthday(Date birthday) {
            this.birthday = birthday;
        }
    }
    User.java

      1.3 创建一个用户控制类

    package cn.test.demo.base_demo.controller;
    
    import cn.test.demo.base_demo.entity.po.User;
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RestController;
    
    import java.util.ArrayList;
    import java.util.List;
    
    /**
     * @author 王杨帅
     * @create 2018-05-05 22:02
     * @desc 用户模块控制层
     **/
    @RestController
    @RequestMapping(value = "/user")
    public class UserController {
    
        @GetMapping
        public List<User> queryList() {
            List<User> userList = new ArrayList<>();
            userList.add(new User());
            userList.add(new User());
            userList.add(new User());
            return userList;
        }
    
    }
    UserController.java

      1.4 创建一个测试类

        该测试类主要测试用户控制类中的相关方法

        1.4.1 引入测试类注解以及日志注解

    @RunWith(SpringRunner.class)
    @SpringBootTest
    @Slf4j

        1.4.2 依赖注入WebApplicationContext

        @Autowired
        private WebApplicationContext wac;

        1.4.3 实例化MockMvc

        private MockMvc mockMvc;
    
        @Before
        public void setup() {
            mockMvc = MockMvcBuilders.webAppContextSetup(wac).build();
        }

        1.4.4 利用MockMvc对象模拟HTTP请求

        @Test
        public void queryList() throws Exception {
            String result = mockMvc.perform(
                        MockMvcRequestBuilders.get("/user")
                        .contentType(MediaType.APPLICATION_JSON_UTF8)
                    )
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andReturn().getResponse().getContentAsString();
            log.info("===/" + className + "/queryList===" + result);
        }

        1.4.5 测试类代码汇总

    package cn.test.demo.base_demo.controller;
    
    import lombok.extern.slf4j.Slf4j;
    import org.junit.Before;
    import org.junit.Test;
    import org.junit.runner.RunWith;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.boot.test.context.SpringBootTest;
    import org.springframework.http.MediaType;
    import org.springframework.test.context.junit4.SpringRunner;
    import org.springframework.test.web.servlet.MockMvc;
    import org.springframework.test.web.servlet.MockMvcBuilder;
    import org.springframework.test.web.servlet.request.MockMvcRequestBuilders;
    import org.springframework.test.web.servlet.result.MockMvcResultMatchers;
    import org.springframework.test.web.servlet.setup.MockMvcBuilders;
    import org.springframework.web.context.WebApplicationContext;
    
    import static org.junit.Assert.*;
    
    @RunWith(SpringRunner.class)
    @SpringBootTest
    @Slf4j
    public class UserControllerTest {
    
        private final String className = getClass().getName();
    
        @Autowired
        private WebApplicationContext wac;
    
        private MockMvc mockMvc;
    
        @Before
        public void setup() {
            mockMvc = MockMvcBuilders.webAppContextSetup(wac).build();
        }
    
        @Test
        public void queryList() throws Exception {
            String result = mockMvc.perform(
                        MockMvcRequestBuilders.get("/user")
                        .contentType(MediaType.APPLICATION_JSON_UTF8)
                    )
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andReturn().getResponse().getContentAsString();
            log.info("===/" + className + "/queryList===" + result);
        }
    
    }
    View Code

    2 JsonPath

      JsonPath是GitHub上的一个开源项目,主要用来对Json格式的数据进行一些处理

      技巧:jsonPath是MockMvcResultMatchers中的一个静态方法

      具体使用:点击前往

      2.1 简单实例

        @Test
        public void test01() throws Exception {
            mockMvc.perform(
                            MockMvcRequestBuilders.get("/user")
                                .contentType(MediaType.APPLICATION_JSON_UTF8)
                    )
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andExpect(MockMvcResultMatchers.jsonPath("$.length()").value(3));
        }

    3 请求参数

      3.1 PathVarible

        主要获取请求路径中的数据

        技巧01:PathVarible获取到的数据是请求路径的一部分

        技巧02:@PathVariable注解中的name和value两个成员的作用是一样的,是用来解决路径名和请求处理方法形参名不一致的问题

        技巧03:@PathVariable支持正则表达式,如果路径参数不满足正则表达式就会匹配失败;参考博文

    //
    // Source code recreated from a .class file by IntelliJ IDEA
    // (powered by Fernflower decompiler)
    //
    
    package org.springframework.web.bind.annotation;
    
    import java.lang.annotation.Documented;
    import java.lang.annotation.ElementType;
    import java.lang.annotation.Retention;
    import java.lang.annotation.RetentionPolicy;
    import java.lang.annotation.Target;
    import org.springframework.core.annotation.AliasFor;
    
    @Target({ElementType.PARAMETER})
    @Retention(RetentionPolicy.RUNTIME)
    @Documented
    public @interface PathVariable {
        @AliasFor("name")
        String value() default "";
    
        @AliasFor("value")
        String name() default "";
    
        boolean required() default true;
    }
    PathVariable.java

        

        3.1.1 控制类

    package cn.test.demo.base_demo.controller;
    
    import cn.test.demo.base_demo.entity.po.User;
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.PathVariable;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RestController;
    
    import java.util.ArrayList;
    import java.util.List;
    
    /**
     * @author 王杨帅
     * @create 2018-05-05 22:02
     * @desc 用户模块控制层
     **/
    @RestController
    @RequestMapping(value = "/user")
    @Slf4j
    public class UserController {
    
        private final String className = getClass().getName();
    
        @GetMapping
        public List<User> queryList() {
            List<User> userList = new ArrayList<>();
            userList.add(new User());
            userList.add(new User());
            userList.add(new User());
            return userList;
        }
    
        @GetMapping(value = "/{id}")
        public User queryInfoByUserId(
                @PathVariable(name = "id") String userId
        ) {
            System.out.println("===路径参数:" + userId);
    //        log.info("===/" + className + "/queryInfoByUserId===路径参数为:{}", userId);
            User user = new User();
            return user;
        }
    
    }
    UserController.java

        3.1.2 测试类

    package cn.test.demo.base_demo.controller;
    
            import lombok.extern.slf4j.Slf4j;
            import org.junit.Before;
            import org.junit.Test;
            import org.junit.runner.RunWith;
            import org.springframework.beans.factory.annotation.Autowired;
            import org.springframework.boot.test.context.SpringBootTest;
            import org.springframework.http.MediaType;
            import org.springframework.test.context.junit4.SpringRunner;
            import org.springframework.test.web.servlet.MockMvc;
            import org.springframework.test.web.servlet.MockMvcBuilder;
            import org.springframework.test.web.servlet.request.MockMvcRequestBuilders;
            import org.springframework.test.web.servlet.result.MockMvcResultMatchers;
            import org.springframework.test.web.servlet.setup.MockMvcBuilders;
            import org.springframework.web.context.WebApplicationContext;
    
            import static org.junit.Assert.*;
    
    @RunWith(SpringRunner.class)
    @SpringBootTest
    @Slf4j
    public class UserControllerTest {
    
        private final String className = getClass().getName();
    
        @Autowired
        private WebApplicationContext wac;
    
        private MockMvc mockMvc;
    
        @Before
        public void setup() {
            mockMvc = MockMvcBuilders.webAppContextSetup(wac).build();
        }
    
        @Test
        public void queryList() throws Exception {
            String result = mockMvc.perform(
                    MockMvcRequestBuilders.get("/user")
                            .contentType(MediaType.APPLICATION_JSON_UTF8)
            )
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andReturn().getResponse().getContentAsString();
            log.info("===/" + className + "/queryList===" + result);
        }
    
        /**
         * 测试JosnPath
         * @throws Exception
         */
        @Test
        public void test01() throws Exception {
            mockMvc.perform(
                            MockMvcRequestBuilders.get("/user")
                                .contentType(MediaType.APPLICATION_JSON_UTF8)
                    )
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andExpect(MockMvcResultMatchers.jsonPath("$.length()").value(3));
        }
    
        /**
         * 测试:路径参数
         * @throws Exception
         */
        @Test
        public void test02() throws Exception {
            String result =  mockMvc.perform(
                            MockMvcRequestBuilders.get("/user/123")
                                .contentType(MediaType.APPLICATION_JSON_UTF8)
                    )
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andReturn().getResponse().getContentAsString();
            System.out.println("====/" + result );
        }
    
    }
    UserControllerTest.java

      3.2 RequestParam

        主要获取请求路径后面的 K-V 键值对

        技巧01:@RequestParam注解中的name和value属性的作用都是一样的,都是为了解决前端变量名和后台请求处理方法形参不一致的问题

        技巧02:@RequestParam 可以指定默认值(即:指定了默认之后,即使前端不传入参数也不会报400错误,而是采用设定的默认值)

    //
    // Source code recreated from a .class file by IntelliJ IDEA
    // (powered by Fernflower decompiler)
    //
    
    package org.springframework.web.bind.annotation;
    
    import java.lang.annotation.Documented;
    import java.lang.annotation.ElementType;
    import java.lang.annotation.Retention;
    import java.lang.annotation.RetentionPolicy;
    import java.lang.annotation.Target;
    import org.springframework.core.annotation.AliasFor;
    
    @Target({ElementType.PARAMETER})
    @Retention(RetentionPolicy.RUNTIME)
    @Documented
    public @interface RequestParam {
        @AliasFor("name")
        String value() default "";
    
        @AliasFor("value")
        String name() default "";
    
        boolean required() default true;
    
        String defaultValue() default "
    		
    		
    ue000ue001ue002
    				
    ";
    }
    RequestParam.java

        3.2.1 控制类

          

    package cn.test.demo.base_demo.controller;
    
    import cn.test.demo.base_demo.entity.po.User;
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.web.bind.annotation.*;
    
    import java.util.ArrayList;
    import java.util.List;
    
    /**
     * @author 王杨帅
     * @create 2018-05-05 22:02
     * @desc 用户模块控制层
     **/
    @RestController
    @RequestMapping(value = "/user")
    @Slf4j
    public class UserController {
    
        private final String className = getClass().getName();
    
        @GetMapping
        public List<User> queryList() {
            List<User> userList = new ArrayList<>();
            userList.add(new User());
            userList.add(new User());
            userList.add(new User());
            return userList;
        }
    
        /**
         * 路径参数
         * @param userId
         * @return
         */
        @GetMapping(value = "/{id}")
        public User queryInfoByUserId(
                @PathVariable(name = "id") String userId
        ) {
            System.out.println("===路径参数:" + userId);
    //        log.info("===/" + className + "/queryInfoByUserId===路径参数为:{}", userId);
            User user = new User();
            return user;
        }
    
        @GetMapping(value = "/findByName")
        public void findByName(
                @RequestParam(value = "name") String username
        ) {
            System.out.println("===请求参数为:/" + username);
    
        }
    
    }
    UserController.java

        3.2.2 测试类

          

    package cn.test.demo.base_demo.controller;
    
            import lombok.extern.slf4j.Slf4j;
            import org.junit.Before;
            import org.junit.Test;
            import org.junit.runner.RunWith;
            import org.springframework.beans.factory.annotation.Autowired;
            import org.springframework.boot.test.context.SpringBootTest;
            import org.springframework.http.MediaType;
            import org.springframework.test.context.junit4.SpringRunner;
            import org.springframework.test.web.servlet.MockMvc;
            import org.springframework.test.web.servlet.MockMvcBuilder;
            import org.springframework.test.web.servlet.request.MockMvcRequestBuilders;
            import org.springframework.test.web.servlet.result.MockMvcResultMatchers;
            import org.springframework.test.web.servlet.setup.MockMvcBuilders;
            import org.springframework.web.context.WebApplicationContext;
    
            import static org.junit.Assert.*;
    
    @RunWith(SpringRunner.class)
    @SpringBootTest
    @Slf4j
    public class UserControllerTest {
    
        private final String className = getClass().getName();
    
        @Autowired
        private WebApplicationContext wac;
    
        private MockMvc mockMvc;
    
        @Before
        public void setup() {
            mockMvc = MockMvcBuilders.webAppContextSetup(wac).build();
        }
    
        @Test
        public void queryList() throws Exception {
            String result = mockMvc.perform(
                    MockMvcRequestBuilders.get("/user")
                            .contentType(MediaType.APPLICATION_JSON_UTF8)
            )
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andReturn().getResponse().getContentAsString();
            log.info("===/" + className + "/queryList===" + result);
        }
    
        /**
         * 测试JosnPath
         * @throws Exception
         */
        @Test
        public void test01() throws Exception {
            mockMvc.perform(
                            MockMvcRequestBuilders.get("/user")
                                .contentType(MediaType.APPLICATION_JSON_UTF8)
                    )
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andExpect(MockMvcResultMatchers.jsonPath("$.length()").value(3));
        }
    
        /**
         * 测试:路径参数
         * @throws Exception
         */
        @Test
        public void test02() throws Exception {
            String result =  mockMvc.perform(
                            MockMvcRequestBuilders.get("/user/123")
                                .contentType(MediaType.APPLICATION_JSON_UTF8)
                    )
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andReturn().getResponse().getContentAsString();
            System.out.println("====/" + result );
        }
    
        @Test
        public void test03() throws Exception {
            mockMvc.perform(
                        MockMvcRequestBuilders.get("/user/findByName")
                                .param("username", "王杨帅")
                                .contentType(MediaType.APPLICATION_JSON_UTF8)
                    )
                    .andExpect(MockMvcResultMatchers.status().isOk());
        }
    
    }
    UserControllerTest.java

      3.3 RequestBody

        可以将前端参数封装成一个对象传到后台

        技巧01:请求体中的数据会自动转化成字符串进行传输

        3.3.1 新建一个数据传输类

          该类主要用于整合前端传过来的数据

    package cn.test.demo.base_demo.entity.dto;
    
    public class UserQueryCondition {
    
        private String username;
        private Integer age;
        private Integer ageTo;
        private String xxx;
    
        public String getUsername() {
            return username;
        }
        public void setUsername(String username) {
            this.username = username;
        }
        public Integer getAge() {
            return age;
        }
        public void setAge(Integer age) {
            this.age = age;
        }
        public Integer getAgeTo() {
            return ageTo;
        }
        public void setAgeTo(Integer ageTo) {
            this.ageTo = ageTo;
        }
        public String getXxx() {
            return xxx;
        }
        public void setXxx(String xxx) {
            this.xxx = xxx;
        }
        
        @Override
        public String toString() {
            return "UserQueryCondition [username=" + username + ", age=" + age + ", ageTo=" + ageTo + ", xxx=" + xxx + "]";
        }
        
    }
    UserQueryCondition.java

        3.3.2 控制类

          

    package cn.test.demo.base_demo.controller;
    
    import cn.test.demo.base_demo.entity.dto.UserQueryCondition;
    import cn.test.demo.base_demo.entity.po.User;
    import com.fasterxml.jackson.annotation.JsonView;
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.web.bind.annotation.*;
    
    import java.util.ArrayList;
    import java.util.List;
    
    /**
     * @author 王杨帅
     * @create 2018-05-05 22:02
     * @desc 用户模块控制层
     **/
    @RestController
    @RequestMapping(value = "/user")
    @Slf4j
    public class UserController {
    
        private final String className = getClass().getName();
    
        @GetMapping
        @JsonView(value = User.UserSimple.class)
        public List<User> queryList() {
            List<User> userList = new ArrayList<>();
            userList.add(new User());
            userList.add(new User());
            userList.add(new User());
            return userList;
        }
    
        /**
         * 路径参数
         * @param userId
         * @return
         */
        @GetMapping(value = "/{id}")
        public User queryInfoByUserId(
                @PathVariable(name = "id") String userId
        ) {
            System.out.println("===路径参数:" + userId);
    //        log.info("===/" + className + "/queryInfoByUserId===路径参数为:{}", userId);
            User user = new User();
            return user;
        }
    
        /**
         * 请求参数
         * @param username
         */
        @GetMapping(value = "/findByName")
        public void findByName(
                @RequestParam(value = "name") String username
        ) {
            System.out.println("===请求参数为:/" + username);
    
        }
    
        /**
         * 请求体
         * @param userQueryCondition
         */
        @PostMapping()
        public void create(
                @RequestBody UserQueryCondition userQueryCondition
                ) {
            System.out.println("===前端获取到的数据为:" + userQueryCondition);
        }
    
    }
    UserController.java

        3.3.3 测试类

          

    package cn.test.demo.base_demo.controller;
    
            import lombok.extern.slf4j.Slf4j;
            import org.junit.Before;
            import org.junit.Test;
            import org.junit.runner.RunWith;
            import org.springframework.beans.factory.annotation.Autowired;
            import org.springframework.boot.test.context.SpringBootTest;
            import org.springframework.http.MediaType;
            import org.springframework.test.context.junit4.SpringRunner;
            import org.springframework.test.web.servlet.MockMvc;
            import org.springframework.test.web.servlet.MockMvcBuilder;
            import org.springframework.test.web.servlet.request.MockMvcRequestBuilders;
            import org.springframework.test.web.servlet.result.MockMvcResultMatchers;
            import org.springframework.test.web.servlet.setup.MockMvcBuilders;
            import org.springframework.web.context.WebApplicationContext;
    
            import static org.junit.Assert.*;
    
    @RunWith(SpringRunner.class)
    @SpringBootTest
    @Slf4j
    public class UserControllerTest {
    
        private final String className = getClass().getName();
    
        @Autowired
        private WebApplicationContext wac;
    
        private MockMvc mockMvc;
    
        @Before
        public void setup() {
            mockMvc = MockMvcBuilders.webAppContextSetup(wac).build();
        }
    
        @Test
        public void queryList() throws Exception {
            String result = mockMvc.perform(
                    MockMvcRequestBuilders.get("/user")
                            .contentType(MediaType.APPLICATION_JSON_UTF8)
            )
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andReturn().getResponse().getContentAsString();
    //        log.info("===/" + className + "/queryList===" + result);
            System.out.println("===/结果为:" + result);
        }
    
        /**
         * 测试JosnPath
         * @throws Exception
         */
        @Test
        public void test01() throws Exception {
            mockMvc.perform(
                            MockMvcRequestBuilders.get("/user")
                                .contentType(MediaType.APPLICATION_JSON_UTF8)
                    )
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andExpect(MockMvcResultMatchers.jsonPath("$.length()").value(3));
        }
    
        /**
         * 测试:路径参数
         * @throws Exception
         */
        @Test
        public void test02() throws Exception {
            String result =  mockMvc.perform(
                            MockMvcRequestBuilders.get("/user/123")
                                .contentType(MediaType.APPLICATION_JSON_UTF8)
                    )
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andReturn().getResponse().getContentAsString();
            System.out.println("====/" + result );
        }
    
        /**
         * 测试:请求参数
         * @throws Exception
         */
        @Test
        public void test03() throws Exception {
            mockMvc.perform(
                        MockMvcRequestBuilders.get("/user/findByName")
                                .param("name", "王杨帅")
                                .contentType(MediaType.APPLICATION_JSON_UTF8)
                    )
                    .andExpect(MockMvcResultMatchers.status().isOk());
        }
    
        @Test
        public void test04() throws Exception {
    
            String content = "{"username":"王杨帅","age":"24"}";
            mockMvc.perform(
                        MockMvcRequestBuilders.post("/user")
                                .content(content)
                                .contentType(MediaType.APPLICATION_JSON_UTF8)
                    )
                    .andExpect(MockMvcResultMatchers.status().isOk());
        }
    
    }
    UserControllerTest.java

        3.3.4 参数验证

          参考博文:点击前往

     4 JsonView

      需求:有的请求需要返回一个实体对象的全部字段,而有的请求只需要返回一个实体对象的部分字段;但是两个请求的数据都来自同一个实体类,怎么样才可以避免实体类重复定义

      JsonView可以通过一个实体类实现多种视图显示

      4.1 声明多个视图

        在一个实体类中利用接口实现声明多个视图

        技巧01:视图之间可以继承,如果视图A继承了视图B,那么在利用视图A进行显示时视图B对应的字段也会被显示出来

        

      4.2 设置实例属性

        在实例变量的Get方法上设置视图

        

    package cn.test.demo.base_demo.entity.po;
    
    import com.fasterxml.jackson.annotation.JsonView;
    
    import java.util.Date;
    
    /**
     * @author 王杨帅
     * @create 2018-05-05 22:03
     * @desc 用户实体类
     **/
    public class User {
    
        public interface UserSimple {};
        public interface UserDetail extends UserSimple {};
    
        private Integer userId;
        private String userName;
        private String password;
        private Date birthday;
    
        @JsonView(value = UserSimple.class)
        public Integer getUserId() {
            return userId;
        }
    
        public void setUserId(Integer userId) {
            this.userId = userId;
        }
    
        @JsonView(value = UserSimple.class)
        public String getUserName() {
            return userName;
        }
    
        public void setUserName(String userName) {
            this.userName = userName;
        }
    
        @JsonView(value = UserDetail.class)
        public String getPassword() {
            return password;
        }
    
        public void setPassword(String password) {
            this.password = password;
        }
    
        @JsonView(value = UserDetail.class)
        public Date getBirthday() {
            return birthday;
        }
    
        public void setBirthday(Date birthday) {
            this.birthday = birthday;
        }
    }
    User.java

      4.3 设置响应视图

        在控制类中方法中设置响应视图

          

    package cn.test.demo.base_demo.controller;
    
    import cn.test.demo.base_demo.entity.po.User;
    import com.fasterxml.jackson.annotation.JsonView;
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.web.bind.annotation.*;
    
    import java.util.ArrayList;
    import java.util.List;
    
    /**
     * @author 王杨帅
     * @create 2018-05-05 22:02
     * @desc 用户模块控制层
     **/
    @RestController
    @RequestMapping(value = "/user")
    @Slf4j
    public class UserController {
    
        private final String className = getClass().getName();
    
        @GetMapping
        @JsonView(value = User.UserSimple.class)
        public List<User> queryList() {
            List<User> userList = new ArrayList<>();
            userList.add(new User());
            userList.add(new User());
            userList.add(new User());
            return userList;
        }
    
        /**
         * 路径参数
         * @param userId
         * @return
         */
        @GetMapping(value = "/{id}")
        public User queryInfoByUserId(
                @PathVariable(name = "id") String userId
        ) {
            System.out.println("===路径参数:" + userId);
    //        log.info("===/" + className + "/queryInfoByUserId===路径参数为:{}", userId);
            User user = new User();
            return user;
        }
    
        @GetMapping(value = "/findByName")
        public void findByName(
                @RequestParam(value = "name") String username
        ) {
            System.out.println("===请求参数为:/" + username);
    
        }
    
    }
    UserController.java

    5 分页查询参数

      5.1 控制方法形参类型

        在controller层的控制方法中利用 Pageable 对象去接收前端传过来的路径参数

        技巧01:在springBoot项目中需要引入 spring-boot-starter-data-jpa 相关jar包才可以使用 Pageable 去接收分页查询参数

            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-data-jpa</artifactId>
            </dependency>

        技巧02:Pageable 所在的包名为:import org.springframework.data.domain.Pageable;

        技巧03:如果前端没有传入先关的参数,Pageable 是有默认值的,即使不用 @PageableDefault 指定默认值也是可以的(如果不指定:默认页码为第一页,默认每页记录数为20)

        技巧04:Pagealbe 可以利用 @PageableDefault 设置默认值(即:前端不传入任何参数,直接使用开发者指定的数值),例如:

    @PageableDefault(size = 14, page = 14, sort = "username", direction = Direction.DESC) Pageable pageable

        

      5.2 前端传参

        在前端直接在请求路径中利用 k-v 键值对传入即可,形如

        技巧01:分页查询的参数变量必须是page、size、sort,分别代表页码、每页记录数、排序字段及其升降序;前端传入这三个参数,后台会自动封装到 Pageable 对象中

    http://127.0.0.1:9999/test/page?page=12&size=23&sort=name,asc

         疑惑01:后台明明时利用 Pageable 去接收前端的参数,为什么打印出来的日志信息却是一个 Page 对象;(理解:SpringMVC框架对Pageable进行了一次封装)

          

      5.3 SpringJPA 中有直接进行分页查询的接口

        参考文档:点击前往

    6  JsonProperty

    6.1 需求

      当后台响应实体类的变量名和前台的需要的不一致时该如何解决;前端需要按照前端的变量规则来传,后端按照后端的变量规则来传,如何保证前后端的数据对应;例如:

      》前端要求的对象格式

      》后端要求的对象格式

    6.2 解决办法

      在定义后端的实体对象时利用 @JsonProperty 指定前端的变量名,例如:

    package cn.xiangxu.product.VO;
    
    import com.fasterxml.jackson.annotation.JsonProperty;
    import lombok.Data;
    
    import javax.persistence.Column;
    import java.util.List;
    
    /**
     * @author 王杨帅
     * @create 2018-07-23 14:22
     * @desc 商品类型视图
     **/
    @Data
    public class CategoryVO {
    
        /**
         * 类目名字
         */
        @JsonProperty(value = "name")
        private String categoryName;
        /**
         * 类目编号
         */
        @JsonProperty(value = "type")
        private Integer categoryType;
    
        /** 商品视图列表 */
        @JsonProperty(value = "foods")
        private List<ProductVO> productVOList;
    
    }
    View Code

      6.3 测试

        6.3.1 准备

          》创建一个SpringBoot项目,并引入lombok、spring-boot-starter-web依赖

            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-web</artifactId>
            </dependency>
    
            <!--日志、getset	oString satrt-->
            <dependency>
                <groupId>org.projectlombok</groupId>
                <artifactId>lombok</artifactId>
                <!--<version>1.18.0</version>-->
                <!--<scope>provided</scope>-->
            </dependency>
            <!--日志、getset	oString end-->
    View Code

          》编写视图类和视图类工具

            》》响应视图类

              技巧01:@Data注解的目的是自动生成getset oString等方法

              坑01:利用IDEA开发时就算引入了lombok依赖,也在相关类中添加了@Data注解,但是启动应用时会报错;因为lombok会在应用打包时自动给我们生成相关方法,直接利用IDEA启动应用时那些方法还没有生成,所以会报错;解决办法是在IDEA中安装一个lombok插件

    package cn.xiangxu.product.VO;
    
    import lombok.Data;
    
    /**
     * @author 王杨帅
     * @create 2018-07-23 13:58
     * @desc 数据封装视图
     **/
    @Data
    public class ResultVO<T> {
        private Integer code;
        private String msg;
        private T data;
    }
    ResultVO

            》》响应视图类工具

    package cn.xiangxu.product.utils;
    
    import cn.xiangxu.product.VO.ResultVO;
    
    /**
     * @author 王杨帅
     * @create 2018-07-23 14:06
     * @desc 响应视图工具类
     **/
    public class ResultVoUtil {
    
        public static ResultVO success(Object data) {
    
            ResultVO resultVO = new ResultVO();
            resultVO.setCode(0);
            resultVO.setMsg("请求成功");
            resultVO.setData(data);
    
            return resultVO;
        }
    
    }
    View Code

            》》数据视图类

    package cn.xiangxu.product.VO;
    
    import com.fasterxml.jackson.annotation.JsonProperty;
    import lombok.Data;
    
    import javax.persistence.Column;
    import java.util.List;
    
    /**
     * @author 王杨帅
     * @create 2018-07-23 14:22
     * @desc 商品类型视图
     **/
    @Data
    public class CategoryVO {
    
        /**
         * 类目名字
         */
        @JsonProperty(value = "name")
        private String categoryName;
        /**
         * 类目编号
         */
        @JsonProperty(value = "type")
        private Integer categoryType;
    
        /** 商品视图列表 */
        @JsonProperty(value = "foods")
        private List<ProductVO> productVOList;
    
    }
    View Code

        6.3.2 测试Get请求

        6.3.3 测试POST请求

        6.3.4 代码汇总

    package cn.xiangxu.product.controller;
    
    import cn.xiangxu.product.VO.CategoryVO;
    import cn.xiangxu.product.VO.ResultVO;
    import cn.xiangxu.product.utils.ResultVoUtil;
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.web.bind.annotation.*;
    
    /**
     * @author 王杨帅
     * @create 2018-07-23 15:51
     * @desc 测试控制层
     **/
    @RestController
    @RequestMapping(value = "/test")
    @Slf4j
    public class TestController {
    
        @GetMapping(value = "/connect")
        public ResultVO connect() {
            String result = "前后台连接成功";
            log.info(result);
            return ResultVoUtil.success(result);
        }
    
        @GetMapping(value = "/test01")
        public ResultVO test01() {
    
            CategoryVO categoryVO = new CategoryVO();
            categoryVO.setCategoryName("熟食");
            categoryVO.setCategoryType(2);
            categoryVO.setProductVOList(null);
    
            return ResultVoUtil.success(categoryVO);
        }
    
        @PostMapping(value = "/test02")
        public ResultVO test02(
                @RequestBody CategoryVO categoryVO
        ) {
            log.info("前端传过来的参数信息为:" + categoryVO);
    
            return ResultVoUtil.success(categoryVO);
        }
    
    }
    View Code

        

        

        

     

  • 相关阅读:
    iOS resign code with App Store profile and post to AppStore
    HTTPS科普扫盲帖 对称加密 非对称加密
    appid 评价
    使用Carthage安装第三方Swift库
    AngularJS:何时应该使用Directive、Controller、Service?
    xcode7 The operation couldn't be completed.
    cocoapods pod install 安装报错 is not used in any concrete target
    xcode7 NSAppTransportSecurity
    learning uboot how to set ddr parameter in qca4531 cpu
    learning uboot enable protect console
  • 原文地址:https://www.cnblogs.com/NeverCtrl-C/p/8996564.html
Copyright © 2011-2022 走看看