最初我在项目中使用了 Spring Boot 1.2 和 Spring hateoas,我需要自定义错误消息。所以我创建了我们的类而不是原生的 VndErrors 和 VndError。
我创建了一个扩展 VndErrors.VndError 的类。
public class MyError extends VndErrors.VndError{
//add some my custom fields
}
还有另一个类来包装 MyError。
public class ErrorDetails{
int total;
@JsonProperty("_embedded")
Map<String, List<MyError>> errors;
public ErrorDetails(List<MyError> err){
this.total=err.size();
errors.put("errors", err);
}
}
所有异常都在一个@ContrllerAdvice
类中处理。我在我们的项目中使用了自定义Jackson2ObjectMapperBuilder
配置。ObjectMapper
当我使用 Spring 1.2 时,它按预期呈现。如下。
{
"total": 1,
"_embedded":{
"errors":[
{
//feilds,
_links:{
"self":""
}
}
]
}
}
但是当升级到 Spring Boot 1.3时,它不能正常工作。
_links呈现为links,并且内容类型是调试信息中的application /json。
阶段1:
我正在尝试使用 of 创建一个简单的 pojo List
,Link
但它不起作用。
public class ErrorDetails{}//pojo includes fields
public class MyError{
//add some my custom fields
@JsonUnwrapped
ErrorDetails content;
List<link> links;
}
public class ErrorResources{
int total;
@JsonProperty("_embedded")
Map<String, List<MyError>> errors;
public ErrorResources(List<MyError> err){
this.total=err.size();
errors.put("errors", err);
}
}
我在 Spring Hateoas 项目的 github 上发现了一些相关问题。
https://github.com/spring-projects/spring-hateoas/issues/279
https://github.com/spring-projects/spring-hateoas/issues/324
https://github.com/spring-projects/spring-hateoas/issues/288
在MyError 类@JsonSerialze(using=Jackson2HalModule.HalLinkListSerializer)
的链接上添加时,我尝试了上述问题的建议之一。
得到类似于找不到正确的 HttpMessageConverter的消息,结果的内容类型是application/ocect
(二进制)。
我也尝试将默认的 contentType 或默认的 viewResolver 设置为 MappingJackson2JsonView,都没有改变结果。
MappingJackson2HttpMessageConverter
当我在我的配置中添加了一个自定义:
@Bean
@Order(1)
public MappingJackson2HttpMessageConverter jacksonMessageConverter() {
ObjectMapper halObjectMapper=ctx.getBean("_halObjectMapper", ObjectMapper.class);
MappingJackson2HttpMessageConverter jacksonMessageConverter =
new MappingJackson2HttpMessageConverter();
jacksonMessageConverter.setObjectMapper(halObjectMapper);
jacksonMessageConverter.setSupportedMediaTypes(
Arrays.asList(MediaTypes.HAL_JSON, MediaType.APPLICATION_JSON_UTF8, MediaType.ALL));
return jacksonMessageConverter;
}
错误结果按预期呈现。但我不认为这是正确的方法,因为我MediaType.ALL
在这里使用过。它引起了另一个大问题。
我曾经TestRestTemplate
测试过我的其余 API。restTemplate 尝试将输入数据视为 XML。我在异常中看到它表明它试图调用 XmlHttpMessageConverter 来处理内容(它是 json),即使我已将接受标头设置为application/json
. 当然,在我升级到 Spring Boot 1.3 堆栈之前,它可以工作。
第 2 阶段:
我尝试使用Resources
并Resource
包装错误结果。
public class ErrorDetails{}//pojo includes error description fields
public class ErrorResource extends Resource<ErrorDetails>{
}
public class ErrorResources extends Resources<ErrorResource>{
}
public class ErrorMessage {
int total;
ErrorResources errors;
}
Spring仍然无法将错误结果呈现为hal格式,它是application/json。当我添加
类@JsonSerialze(using=Jackson2HalModule.HalResourcesSerializer)
时ErrorResources
,它引发了一个异常,抱怨HalResourcesSerializer
没有默认构造函数。
在 @ControllerAdvice 类中,我尝试将方法返回类型设置为 ErrorMessage 和一个 wrapper ResponseEntity
,但它不起作用。
最后,我的问题是如何使响应主体@ControllerAdvice
与正常的响应主体相同@RestController
?为什么它在课堂上不起作用@ControllerAdvice
?
这个问题有简单的解决方法吗?