1.测试postman 向数据库添加优惠券信息报错
原始Body:
{
"shopId": 1,
"title": "100元代金券",
"subTitle": "周一至周五均可使用",
"rules": "全场通用\\n无需预约\\n可无限叠加\\n不兑现、不找零\\n仅限堂食",
"payValue": 8000,
"actualValue": 10000,
"type": 1,
"stock": 100,
"beginTime": "2022-01-26T10:09:17",
"endTime": "2022-01-26T24:09:04"
}
20:51:11.991 ERROR 22384 — [nio-8081-exec-2] com.hmdp.config.WebExceptionAdvice : org.springframework.http.converter.HttpMessageNotReadableException: JSON parse error: Current token (VALUE_STRING) not numeric, can not use numeric value accessors; nested exception is com.fasterxml.jackson.databind.JsonMappingException: Current token (VALUE_STRING) not numeric, can not use numeric value accessors
at [Source: (PushbackInputStream); line: 10, column: 17] (through reference chain: com.hmdp.entity.Voucher[“beginTime”])
原因是我们在JacksonConfig.java中配置了
// 从 JSON 中读取时间戳(毫秒值)
long timestamp = p.getLongValue();// 前端要传时间戳是Long
原来是要传时间戳,不能传"2022-01-26T10:09:17"这个日期了。
修改body为:
{
"shopId": 1,
"title": "100元代金券",
"subTitle": "周一至周五均可使用",
"rules": "全场通用\\n无需预约\\n可无限叠加\\n不兑现、不找零\\n仅限堂食",
"payValue": 8000,
"actualValue": 10000,
"type": 1,
"stock": 100,
"beginTime": 1643162400000,
"endTime": 1643209200000
}
成功效果
2.注意,此时只是添加到数据库中,可以前端访问时,优惠券显示会出现异常情况NaNa。可能业务需求必须传字符串时间而不是时间戳,这时候我们最好都能满足系统的要求。
2.1 在config包配置 FlexibleLocalDateTimeDeserializer
前端格式:“yyyy-MM-dd’T’HH:mm:ss”
package com.hmdp.config;
import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.core.JsonToken;
import com.fasterxml.jackson.databind.DeserializationContext;
import com.fasterxml.jackson.databind.JsonDeserializer;
import java.io.IOException;
import java.time.Instant;
import java.time.LocalDateTime;
import java.time.ZoneId;
import java.time.format.DateTimeFormatter;
public class FlexibleLocalDateTimeDeserializer extends JsonDeserializer<LocalDateTime> {
private static final DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ss");
@Override
public LocalDateTime deserialize(JsonParser p, DeserializationContext ctxt) throws IOException {
JsonToken token = p.currentToken();
if (token == JsonToken.VALUE_NUMBER_INT) {
// 时间戳(毫秒)
long timestamp = p.getLongValue();
return LocalDateTime.ofInstant(Instant.ofEpochMilli(timestamp), ZoneId.systemDefault());
} else if (token == JsonToken.VALUE_STRING) {
String value = p.getText().trim();
if (value.isEmpty()) return null;
try {
return LocalDateTime.parse(value, formatter);
} catch (Exception e) {
throw new IOException("无法解析 LocalDateTime 格式:" + value, e);
}
}
throw new IOException("不支持的时间格式:" + token);
}
}
2.2 修改 JacksonConfig
import java.time.LocalDateTime;
/**
* 为了解决时间戳反序列化对象设置的
*/
@Configuration
public class JacksonConfig {
@Bean
public ObjectMapper objectMapper() {
ObjectMapper mapper = new ObjectMapper();
JavaTimeModule timeModule = new JavaTimeModule();
timeModule.addDeserializer(LocalDateTime.class, new FlexibleLocalDateTimeDeserializer());
mapper.registerModule(timeModule);
mapper.disable(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS);
return mapper;
}
}
3.前端测试
注意时间不能过期(必须在此时后面),否则无法显示
{
"shopId": 1,
"title": "100元代金券",
"subTitle": "周一至周五均可使用",
"rules": "全场通用\\n无需预约\\n可无限叠加\\n不兑现、不找零\\n仅限堂食",
"payValue": 7000,
"actualValue": 10000,
"type": 1,
"stock": 100,
"beginTime": "2025-05-26T10:00:00",
"endTime": "2025-05-26T23:00:00"
}
现在就可以正常展示了