Springboot官网学习(7、Web应用程序【七Spring Web MVC 之WebMvcConfigurer(configureContentNegotiation方法,内容协商机制)】)

今天来说说内容协商机制。
内容协商机制这个太专业的名称,说下来,头一次听的话,估计是无法理解他其中的含义的。
那么我这里就用大白话说一下吧。
就是客户端向服务端发送一个请求,然后服务端给客户端返回什么格式的数据的,是需要两端进行协商的,既然是协商,那么他们有什么协议或者规则呢?
下面一探究竟:
一般现在服务端返回的数据基本都是json格式的数据,以前返回的是xml,那么现在如果要返回xml格式的数据,springmvc也是提供得有方法的。
@RequestMapping系列注解中produces可以指定返回得格式,(@GetMapping是@RequestMapping得一种变形)
写法:
@GetMapping(value = “xxx”,produces = MediaType.APPLICATION_XML_VALUE)

注意:在返回的实体中指定**@XmlRootElement(name = “xxx”)**,指定xml的根元素。即可

	@GetMapping(value = "getUser",produces = MediaType.APPLICATION_XML_VALUE)
    public User getUser(){
        User user = new User();
        user.setName("我是admin用户");
        return user;
    }
package com.osy.entity;

import javax.xml.bind.annotation.XmlRootElement;

@XmlRootElement(name = "user")
public class User {

    private String name;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

}

最后得到的结果就是

<user>
	<name>我是admin用户name>
user>

但是这只是服务端指定的,客户端不能够决定,如果客户端请求这个路径需要换成json格式的数据,那么是做不到的,所以就有了内容协商机制,也就是可以相互协商,客户端需要什么杨的格式,给个参数说明,服务端就可以返回客户端需要的数据了。

在springmvc中,我们需要需要达到内容协商机制,那么就需要覆盖WebMvcConfigurer中的configureContentNegotiation方法,(注释里讲得很详细)

package com.osy.config;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.ContentNegotiationConfigurer;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;

@Configuration
public class WebMvcConfiguration {

    @Bean
    public WebMvcConfigurer webMvcConfigurer() {
        return new WebMvcConfigurer() {
           @Override
            public void configureContentNegotiation(ContentNegotiationConfigurer configurer) {
                // 是否通过请求参数来决定返回数据,默认为false
                configurer.favorParameter(true)
                        .ignoreAcceptHeader(true) // 不检查Accept请求头
                        .parameterName("zyMediaType")// 参数名称,就是通过什么样的参数来获取返回值
                        .defaultContentType(MediaType.APPLICATION_JSON)
                        .mediaType("json",MediaType.APPLICATION_JSON)
                        .mediaType("xml",MediaType.APPLICATION_XML);
                        // mediaType此方法是从请求参数扩展名(也就是最后一个.后面的值),
                        // 然后绑定在parameterName上面,比如/admin/getUser.xml  等同于/admin/getUser?zyMediaType=xml
                        // 如果不需要这种后缀的,那么就是全部通过参数的方式传递到后台

            }

        };
    }
}

然后我们启动项目测试一下吧:
随意创建一个控制器:(注意,返回的实体中,在类上面必须打上@XmlRootElement注解,不然在请求xml格式的时候会报错)

	@GetMapping(value = "testMediaType")
    public User testMediaType(){
        User user = new User();
        user.setName("testMediaType");
        return user;
    }

实体还是上面的实体,
然后访问:
1、先通过url扩展名的方式访问
http://localhost:8080/admin/testMediaType.json

{"name":"testMediaType"}

http://localhost:8080/admin/testMediaType.xml

<user>
	<name>testMediaTypename>
user>

证明后缀是可以的,然后通过参数来测试一下:(注意参数名是你自己定义的,不一定都是我这个)

http://localhost:8080/admin/testMediaType?zyMediaType=json
http://localhost:8080/admin/testMediaType?zyMediaType=xml
两个地址访问和上面的结果是一样的,这里就不贴出结果了。
虽然xml格式的数据现在很少用了,但是有些特殊的场景还是需要的,get这么一个技能,就可以写一个接口符合两种场景了,就无需为某一种格式的数据单独的写接口了。

你可能感兴趣的:(springMvc,Springboot,spring)