【发布时间】:2019-08-08 09:23:21
【问题描述】:
我有这个 InstantDesrializer
@Slf4j
public class InstantDeserializer extends StdDeserializer<Instant> {
public InstantDeserializer() {
this(null);
}
public InstantDeserializer(Class<?> vc) {
super(vc);
}
@Override
public Instant deserialize(JsonParser jp, DeserializationContext ctxt)
throws IOException, JsonProcessingException {
JsonNode node = jp.getCodec().readTree(jp);
log.info(node.asText());
TemporalAccessor parse = null;
DateTimeFormatter dateTimeFormatter = DateTimeFormatter.ofPattern(Constants.DATE_TIME_FORMAT).withZone(ZoneOffset.UTC);
try {
parse = dateTimeFormatter.parse(node.asText());
} catch (Exception e) {
e.printStackTrace();
throw new IOException();
}
log.info(Instant.from(parse).toString());
return Instant.from(parse);
}
}
然后在@ControllerAdvice中对应IOException
@ExceptionHandler(IOException.class)
public ResponseEntity<String> handleIOException(IOException e) {
return ResponseEntity.status(422).build();
}
这在我的 DTO 中:
@NotNull
@JsonDeserialize(using = InstantDeserializer.class)
// @DateTimeFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss.SSS'Z'")
private Instant timestamp;
即使未注释 @DateTimeFormat,它也不起作用
理想情况下,它应该返回 422 状态。但是,它返回 400。
也许我只是错过了一些我无法弄清楚的小东西。
这里建议使用这种方法: Throw custom exception while deserializing the Date field using jackson in java
【问题讨论】:
-
第一个猜测:您得到 400 是因为您将 json 作为 post 或 put 的主体发送,您的 Web 服务框架(spring mvc?)尝试反序列化 json 并失败。无论最初的原因如何,它都会生成 400,因为预期的输入是无效的,这可能在将请求路由到您的代码之前发生。您的处理程序可能看不到异常。我建议放置一个断点或登录你的处理程序,看看它是否被调用过。
-
于是,我在Deserializer中添加了日志,日志进入catch语句。
-
你登录处理程序了吗,处理程序是否被调用过?
-
Jackson 反序列化失败时,您希望在最终响应中显示 422 而不是 400 的状态吗?
标签: java spring spring-boot exception jackson