赞
踩
入参出参dto里,有时候会看到@DateTimeFormat或@JsonFormat,代码如下。
- public class XXXdto{
-
- @DateTimeFormat(pattern = "yyyy-MM-dd")
- private Date startDate;
- }
-
- public class XXXdto{
- @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
- private Date startDate;
- }
加@DateTimeFormat注解的目的:将字符串的时间转换成Date类型。此注解只能用于form表单请求和get请求。
加@JsonFormat注解的目的:将字符串的时间转换成Date类型。此注解只能用于json请求。在Controller层入参处需要用@RequestBody
补充:@DataTimeFormat用于前端传后端,@JsonFormat用于后端传前端,这种说法是错误的。@JsonFormat前传后、后传前都可以用。
使用方法:加在时间类型的变量上。
这是为了入参可以是日期时间格式(年月日时分秒)的值。如 {"startDate":"2022-01-01 01:02:02"}。
如果没有加注解@DateTimeFormat,会报错:
- Invalid JSON input:
- Cannot deserialize value of type `java.util.Date` from String "2023-02-01 01:02:03": not a valid representation (error: Failed to parse Date value '2023-02-01 01:02:03': Cannot parse date "2023-02-01 01:02:03": while it seems to fit format 'yyyy-MM-dd'T'HH:mm:ss.SSSZ', parsing fails (leniency? null));
- nested exception is com.fasterxml.jackson.databind.exc.InvalidFormatException:
- Cannot deserialize value of type `java.util.Date` from String "2023-02-01 01:02:03": not a valid representation (error: Failed to parse Date value '2023-02-01 01:02:03': Cannot parse date "2023-02-01 01:02:03": while it seems to fit format 'yyyy-MM-dd'T'HH:mm:ss.SSSZ', parsing fails (leniency? null))
根据报错信息,while it seems to fit format 'yyyy-MM-dd'T'HH:mm:ss.SSSZ',判断传入的值日期格式有问题。
正确时间格式:2023-02-01T00:00:00.000+0800,即前端传参: {"startDate":"2023-02-01T00:00:00.000+0800"}。
由于前端通常也是直接使用时间组件生成的值,时间组件生成的就是正确的时间格式,所以通常后端不需要加@DateTimeFormat。
但如果前端传的是自定义的值,例如:2023-01-01 01:01:01,即年月日时分秒,由于这个值不是正确的时间格式,这时候,后端没有加注解就会报错。
在没有注解的年代,会用SimpleDateFormat做转换。代码如下
- public class XXXdto{
-
- private String startDate;
-
- public Date getStartDate(){
- return new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").parse(startDate);
- }
- }
但@DataTimeFormat不如@JsonFormat好用。另,如果值是纯日期,例如2022-01-01,也不需要用注解。
com.fasterxml.jackson.annotation.JsonFormat;
- public class XXXdto{
- @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
- private Date startDate;
- }
@JsonFormat 默认的时区是 Greenwich Time, 格林威治时间,而我们是在东八区。查到的时间可能会比数据库中的时间少八个小时。所以需要加上timezone="GMT+8"
org.springframework.format.annotation.DateTimeFormat
- public class XXXdto{
- @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
- private Date startDate;
- }
@JsonFormat | @DateTimeFormat | |
转换前端传入后端的时间格式的值 | √ | √ |
约束后端响应前端的时间类型的值 | √ | × |
数据类型(前端提交到后端) | 必须json 用@RequestBody | 必须form表单 不用@RequestBody |
时区 | √ | × 响应给前端的时间会比实际时间晚8个小时 |
1.前端传值给后端,后端接收到的都是字符串。
2.前端传日期格式的值,如果形如yyyy-MM-dd,即{"startDate":"2023-01-02"},不需要用@DataTimeFormat和@JsonFormat,框架会帮你转。
各种情况测试对比
无@RequestBody 无@DateTimeFormat | 无@RequestBody 有@DateTimeFormat | |
form表单提交 | 报错,见报错1。因为传的值是字符串,而后端的变量是Date类型 | 时间格式匹配对,则不会报错。例如:2022-01-01 匹配错则报错,见报错2。例如:2022-01-01 10:01:01 因为注解中模板是"yyyy-MM-dd",而传的值是年月日时分秒 |
json提交 | 不报错。入参变量startDate的值是null,说明没有赋值操作。意味着没有@RequestBody,json提交后端接收不到值;form表单提交,后端才能接收到值 | 不报错。同前面 |
- 报错1
- Field error in object 'safescoreHomePageQueryParam' on field 'startTime': rejected value [2023-02-01 01:01:01];Failed to convert property value of type 'java.lang.String' to required type 'java.util.Date' for property 'endTime';nested exception is java.lang.IllegalArgumentException
- 报错2
- nested exception is java.lang.IllegalArgumentException: Invalid format: "2023-02-01 01:01:01" is malformed at " 01:01:01"
使用@RequestBody,form表单提交会报错如下
Content type 'multipart/form-data;boundary=--------------------------590532731747110494187237;charset=UTF-8' not supported
使用@RequestBody,JSON提交,使用@JsonFormat,入参如果写20220101报错如下。
入参2022-01-01 10:01:01不会报错。时分秒写错不会报错
- Invalid JSON input: Cannot deserialize value of type `java.util.Date` from String "20220101": expected format "yyyy-MM-dd"; nested exception is com.fasterxml.jackson.databind.exc.InvalidFormatException: Cannot deserialize value of type `java.util.Date` from String "20220101": expected format "yyyy-MM-dd"
- at [Source: (PushbackInputStream); line: 1, column: 14] (through reference chain: com.xxx.dto.xxx.xxxDTO["startTime"])
使用@RequestBody,JSON提交,不使用@JsonFormat,入参2022-01-01 10:01:01报错如下。入参2022-01-01不会报错。
- Invalid JSON input: Cannot deserialize value of type `java.util.Date` from String "2022-01-01 10:01:01": not a valid representation (error: Failed to parse Date value '2022-01-01 10:01:01': Cannot parse date "2022-01-01 10:01:01": while it seems to fit format 'yyyy-MM-dd'T'HH:mm:ss.SSSZ', parsing fails (leniency? null)); nested exception is com.fasterxml.jackson.databind.exc.InvalidFormatException: Cannot deserialize value of type `java.util.Date` from String "2022-01-01 10:01:01": not a valid representation (error: Failed to parse Date value '2022-01-01 10:01:01': Cannot parse date "2022-01-01 10:01:01": while it seems to fit format 'yyyy-MM-dd'T'HH:mm:ss.SSSZ', parsing fails (leniency? null))
- at [Source: (PushbackInputStream); line: 1, column: 14] (through reference chain: com.xxx.dto.xxx.xxxDTO["startTime"])
不要在听大坑们@DateTimeFormat 和 @JsonFormat只是前后端传参的区别了_*阿莫西林*的博客-CSDN博客
=====================分割线=======================
文章到此已经结束,以下是紫薯布丁
public class XXXdto{
@DateTimeFormat(pattern = "yyyy-MM-dd")
private Date startDate;
}
public class XXXdto{
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
private Date startDate;
}
Invalid JSON input:
Cannot deserialize value of type `java.util.Date` from String "2023-02-01 01:02:03": not a valid representation (error: Failed to parse Date value '2023-02-01 01:02:03': Cannot parse date "2023-02-01 01:02:03": while it seems to fit format 'yyyy-MM-dd'T'HH:mm:ss.SSSZ', parsing fails (leniency? null));
nested exception is com.fasterxml.jackson.databind.exc.InvalidFormatException:
Cannot deserialize value of type `java.util.Date` from String "2023-02-01 01:02:03": not a valid representation (error: Failed to parse Date value '2023-02-01 01:02:03': Cannot parse date "2023-02-01 01:02:03": while it seems to fit format 'yyyy-MM-dd'T'HH:mm:ss.SSSZ', parsing fails (leniency? null))
public class XXXdto{
private String startDate;
public Date getStartDate(){
return new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").parse(startDate);
}
}
public class XXXdto{
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
private Date startDate;
}
public class XXXdto{
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
private Date startDate;
}
报错1
Field error in object 'safescoreHomePageQueryParam' on field 'startTime': rejected value [2023-02-01 01:01:01];Failed to convert property value of type 'java.lang.String' to required type 'java.util.Date' for property 'endTime';nested exception is java.lang.IllegalArgumentException
报错2
nested exception is java.lang.IllegalArgumentException: Invalid format: "2023-02-01 01:01:01" is malformed at " 01:01:01"
Content type 'multipart/form-data;boundary=--------------------------590532731747110494187237;charset=UTF-8' not supported
Invalid JSON input: Cannot deserialize value of type `java.util.Date` from String "20220101": expected format "yyyy-MM-dd"; nested exception is com.fasterxml.jackson.databind.exc.InvalidFormatException: Cannot deserialize value of type `java.util.Date` from String "20220101": expected format "yyyy-MM-dd"
at [Source: (PushbackInputStream); line: 1, column: 14] (through reference chain: com.xxx.dto.xxx.xxxDTO["startTime"])
Invalid JSON input: Cannot deserialize value of type `java.util.Date` from String "2022-01-01 10:01:01": not a valid representation (error: Failed to parse Date value '2022-01-01 10:01:01': Cannot parse date "2022-01-01 10:01:01": while it seems to fit format 'yyyy-MM-dd'T'HH:mm:ss.SSSZ', parsing fails (leniency? null)); nested exception is com.fasterxml.jackson.databind.exc.InvalidFormatException: Cannot deserialize value of type `java.util.Date` from String "2022-01-01 10:01:01": not a valid representation (error: Failed to parse Date value '2022-01-01 10:01:01': Cannot parse date "2022-01-01 10:01:01": while it seems to fit format 'yyyy-MM-dd'T'HH:mm:ss.SSSZ', parsing fails (leniency? null))
at [Source: (PushbackInputStream); line: 1, column: 14] (through reference chain: com.xxx.dto.xxx.xxxDTO["startTime"])
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。