SpringBoot之使⽤Json详解
Spring Boot 之使⽤ Json 详解
简介
Spring Boot ⽀持的 Json 库
Spring Boot ⽀持三种 Json 库:
Gson
Jackson
JSON-B
Jackson 是 Spring Boot 官⽅推荐的默认库。
Spring Boot 提供了 Jackson 的⾃动配置,Jackson 是spring-boot-starter-json的⼀部分。当 Jackson 在类路径上时,会⾃动配置 ObjectMapper bean。
Spring Boot 提供了 Gson 的⾃动配置。当 Gson 在 classpath 上时,会⾃动配置 Gson bean。提供了⼏个spring.gson.*配置属性来⾃定义配置。为了获得更多控制,可以使⽤⼀个或多个GsonBuilderCustomizer bean。
Spring Boot 提供了 JSON-B 的⾃动配置。当 JSON-B API 在 classpath 上时,将⾃动配置 Jsonb bean。⾸选的 JSON-B 实现是 Apache Johnzon,它提供了依赖关系管理。Spring Web 中的序列化、反序列化
以下注解都是spring-web中提供的⽀持。
@ResponseBody
@Responsebody注解⽤于将 Controller 的⽅法返回的对象,通过适当的HttpMessageConverter转换为指定格式后,写⼊到 HTTP Response 对象的 body 数据区。⼀般在异步获取数据时使⽤。通常是在使⽤@RequestMapping后,返回值通常解析为跳转路径,加上 @Responsebody 后返回结果不会被解析为跳转路径,⽽是直接写⼊ HTTP 响应正⽂中。
⽰例:
@ResponseBody
@RequestMapping(name = "/getInfo", method = RequestMethod.GET)
public InfoDTO getInfo() {
return new InfoDTO();
}
@RequestBody
@RequestBody 注解⽤于读取 HTTP Request 请求的 body 部分数据,使⽤系统默认配置的HttpMessageConverter进⾏解析,然后把相应的数据绑定到要返回的对象上;再把HttpMessageConverter返回的对象数据绑定到 controller 中⽅法的参数上。
request 的 body 部分的数据编码格式由 header 部分的Content-Type指定。
⽰例:
@RequestMapping(name = "/postInfo", method = RequestMethod.POST)
public void postInfo(@RequestBody InfoDTO infoDTO) {
// ...
}
@RestController
Spring 4 以前:
如果需要返回到指定页⾯,则需要⽤@Controller配合视图解析器InternalResourceViewResolver。
如果需要返回 JSON,XML 或⾃定义 mediaType 内容到页⾯,则需要在对应的⽅法上加上@ResponseBody注解。
Spring 4 以后,新增了@RestController注解:
它相当于@Controller + @RequestBody。
如果使⽤@RestController注解 Controller,则 Controller 中的⽅法⽆法返回 jsp 页⾯,或者 html,配置的视图解析器InternalResourceViewResolver将不起作⽤,直接返回内容。
指定类的 Json 序列化、反序列化
如果使⽤ Jackson 序列化和反序列化 JSON 数据,您可能需要编写⾃⼰的JsonSerializer和JsonDeserializer类。⾃定义序列化程序通常通过模块向 Jackson 注册,但 Spring Boot 提供了另⼀种@JsonComponent注释,可以更容易地直接注册 Spring Beans。
您可以直接在JsonSerializer或JsonDeserializer实现上使⽤@JsonComponent注释。您还可以在包含序列化程序/反序列化程序作为内部类的类上使⽤它,如以下⽰例所⽰:
import java.io.*;
import com.*;
import com.fasterxml.jackson.databind.*;
import org.springframework.boot.jackson.*;
@JsonComponent
public class Example {
public static class Serializer extends JsonSerializer<SomeObject> {
/
/ ...
}
public static class Deserializer extends JsonDeserializer<SomeObject> {
// ...
}
}
ApplicationContext中的所有@JsonComponent bean 都会⾃动注册到 Jackson。因为@JsonComponent是使⽤@Component进⾏元注释的,所以通常的组件扫描规则适⽤。
Spring Boot 还提供了和基类,它们在序列化对象时提供了标准 Jackson 版本的有⽤替代⽅法。有关详细信息,请参阅 Javadoc 中的和。
@JsonTest
使⽤@JsonTest可以很⽅便的在 Spring Boot 中测试序列化、反序列化。
使⽤@JsonTest相当于使⽤以下⾃动配置:
org.springframework.boot.autoconfigure.cache.CacheAutoConfiguration org.springframework.boot.autoconfigure.gson.GsonAutoConfiguration org.springframework.boot.autoconfigure.jackson.JacksonAutoConfiguration org.springframework.boot.au @JsonTest使⽤⽰例:
想试试完整⽰例,可以参考:
@JsonTest
@RunWith(SpringRunner.class)
public class SimpleJsonTest {
private final Logger log = Class());
@Autowired
private JacksonTester<InfoDTO> json;
@Test
public void testSerialize() throws Exception {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
InfoDTO infoDTO = new InfoDTO("JSON测试应⽤", "1.0.0", sdf.parse("2019-01-01 12:00:00"));
JsonContent<InfoDTO> jsonContent = json.write(infoDTO);
log.info("json content: {}", Json());
// 或者使⽤基于JSON path的校验
assertThat(jsonContent).hasJsonPathStringValue("@.appName");
assertThat(jsonContent).extractingJsonPathStringValue("@.appName").isEqualTo("JSON测试应⽤");
assertThat(jsonContent).hasJsonPathStringValue("@.version");
assertThat(jsonContent).extractingJsonPathStringValue("@.version").isEqualTo("1.0.0");
assertThat(jsonContent).hasJsonPathStringValue("@.date");
assertThat(jsonContent).extractingJsonPathStringValue("@.date").isEqualTo("2019-01-01 12:00:00");
}
@Test
public void testDeserialize() throws Exception {
String content = "{\"appName\":\"JSON测试应⽤\",\"version\":\"1.0.0\",\"date\":\"2019-01-01\"}";
InfoDTO actual = json.parseObject(content);
AppName()).isEqualTo("JSON测试应⽤");
Version()).isEqualTo("1.0.0");
}
}
Spring Boot 中的 json 配置
Jackson 配置
当 Spring Boot 的 json 库为 jackson 时,可以使⽤以下配置属性(对应类):
spring.jackson.date-format= # Date format string or a fully-qualified date format class name. For instance, `yyyy-MM-dd HH:mm:ss`.
spring.jackson.default-property-inclusion= # Controls the inclusion of properties during serialization. Configured with one of the values in Jackson's JsonInclude.Include enumeration.
spring.jackson.deserialization.*= # Jackson on/off features that affect the way Java objects are deserialized.
ator.*= # Jackson on/off features for generators.
spring.jackson.joda-date-time-format= # Joda date time format string. If not configured, "date-format" is used as a fallback if it is configured with a format string.
spring.jackson.locale= # Locale used for formatting.
spring.jackson.mapper.*= # Jackson general purpose on/off features.
spring.jackson.parser.*= # Jackson on/off features for parsers.
spring.jackson.property-naming-strategy= # One of the constants on Jackson's PropertyNamingStrategy. Can also be a fully-qualified class name of a PropertyNamingStrategy subclass.
spring.jackson.serialization.*= # Jackson on/off features that affect the way Java objects are serialized.
spring.jackson.time-zone= # Time zone used when formatting dates. For instance, "America/Los_Angeles" or "GMT+10".
spring.jackson.visibility.*= # Jackson visibility thresholds that can be used to limit which methods (and fields) are auto-detected.
GSON 配置
当 Spring Boot 的 json 库为 gson 时,可以使⽤以下配置属性(对应类):
spring.gson.date-format= # Format to use when serializing Date objects.
spring.gson.disable-html-escaping= # Whether to disable the escaping of HTML characters such as '<', '>', etc.
spring.gson.disable-inner-class-serialization= # Whether to exclude inner classes during serialization.
able-complex-map-key-serialization= # Whether to enable serialization of complex map keys (i.e. non-primitives).
lude-fields-without-expose-annotation= # Whether to exclude all fields from consideration for serialization or deserialization that do not have the "Expose" annotation.
spring.gson.field-naming-policy= # Naming policy that should be applied to an object's field during serialization and deserialization.
ate-non-executable-json= # Whether to generate non executable JSON by prefixing the output with some special text.
spring.gson.lenient= # Whether to be lenient about parsing JSON that doesn't conform to RFC 4627.
spring.gson.long-serialization-policy= # Serialization policy for Long and long types.
spring.gson.pretty-printing= # Whether to output serialized JSON that fits in a page for pretty printing.
spring.gson.serialize-nulls= # Whether to serialize null fields.
Spring Boot 中使⽤ Fastjson
国内很多的 Java 程序员更喜欢使⽤阿⾥的 fastjson 作为 json lib。那么,如何在 Spring Boot 中将其替换默认的 jackson 库呢?
你需要做如下处理:
(1)引⼊ fastjson jar 包:
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.54</version>
</dependency>
(2)实现 WebMvcConfigurer 接⼝,⾃定义configureMessageConverters接⼝。如下所⽰:
@Configuration
public class WebMvcConfig implements WebMvcConfigurer {
private final Logger log = Class());
fastjson怎么用/**
* ⾃定义消息转换器
* @param converters
*/
@Override
public void configureMessageConverters(List<HttpMessageConverter<?>> converters) {
// 清除默认 Json 转换器
// 配置 FastJson
FastJsonConfig config = new FastJsonConfig();
config.setSerializerFeatures(SerializerFeature.QuoteFieldNames, SerializerFeature.WriteEnumUsingToString,
SerializerFeature.WriteMapNullValue, SerializerFeature.WriteDateUseDateFormat,
SerializerFeature.DisableCircularReferenceDetect);
// 添加 FastJsonHttpMessageConverter
FastJsonHttpMessageConverter fastJsonHttpMessageConverter = new FastJsonHttpMessageConverter();
fastJsonHttpMessageConverter.setFastJsonConfig(config);
List<MediaType> fastMediaTypes = new ArrayList<>();
fastMediaTypes.add(MediaType.APPLICATION_JSON_UTF8);
fastJsonHttpMessageConverter.setSupportedMediaTypes(fastMediaTypes);
converters.add(fastJsonHttpMessageConverter);
// 添加 StringHttpMessageConverter,解决中⽂乱码问题
StringHttpMessageConverter stringHttpMessageConverter = new StringHttpMessageConverter(Charset.forName("UTF-8")); converters.add(stringHttpMessageConverter);
}
// ...
}
⽰例源码
完整⽰例:
引申和引⽤
引申
引⽤
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论