Redis:Gson反序列化时间戳过长导致报错
问题描述
今天在用Gson进行反序列化json为Java Bean时,报Invalid time zone indicator
com.google.gson.JsonSyntaxException: 1631599981000 at com.google.gson.internal.bind.DateTypeAdapter.deserializeToDate(DateTypeAdapter.java:87) ~[gson-2.8.6.jar:na] at com.google.gson.internal.bind.DateTypeAdapter.read(DateTypeAdapter.java:75) ~[gson-2.8.6.jar:na] at com.google.gson.internal.bind.DateTypeAdapter.read(DateTypeAdapter.java:46) ~[gson-2.8.6.jar:na] at com.google.gson.internal.bind.ReflectiveTypeAdapterFactory$1.read(ReflectiveTypeAdapterFactory.java:131) ~[gson-2.8.6.jar:na] at com.google.gson.internal.bind.ReflectiveTypeAdapterFactory$Adapter.read(ReflectiveTypeAdapterFactory.java:222) ~[gson-2.8.6.jar:na] at com.google.gson.Gson.fromJson(Gson.java:932) ~[gson-2.8.6.jar:na] at com.google.gson.Gson.fromJson(Gson.java:897) ~[gson-2.8.6.jar:na] at com.google.gson.Gson.fromJson(Gson.java:846) ~[gson-2.8.6.jar:na] at com.google.gson.Gson.fromJson(Gson.java:817) ~[gson-2.8.6.jar:na] Caused by: java.text.ParseException: Failed to parse date ["1631599981000"]: Invalid time zone indicator 8 at com.google.gson.internal.bind.util.ISO8601Utils.parse(ISO8601Utils.java:274) ~[gson-2.8.6.jar:na] at com.google.gson.internal.bind.DateTypeAdapter.deserializeToDate(DateTypeAdapter.java:85) ~[gson-2.8.6.jar:na] ... 132 common frames omitted Caused by: java.lang.IndexOutOfBoundsException: Invalid time zone indicator 8 at com.google.gson.internal.bind.util.ISO8601Utils.parse(ISO8601Utils.java:245) ~[gson-2.8.6.jar:na] ... 133 common frames omitted
原因
实际上是因为Gson反序列化时间的时候没有设置时区,导致解析时间戳的时候转为Date类型报错,所以Gson无法解析位数太长的时间格式。
解决方式
- 更换序列化框架例如jackson,fastjson等
- 通过GsonBuilder生成注册Date类型的GSON(推荐)。
private final static Gson gson = new GsonBuilder().registerTypeAdapter(Date.class, new JsonDeserializer<Date>() { @Override public Date deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context) throws JsonParseException { return new Date(json.getAsJsonPrimitive().getAsLong()); } }).create(); /** * The Redis template. */ private RedisTemplate<Object, Object> redisTemplate; /** * Get t. * 解决时间戳过长无法转换Date * @param <T> the type parameter * @param key the key * @param clazz the clazz * @param expire the expire * @return the t */ public <T> T get(String key, Class<T> clazz) { Object value = get(key); return value == null ? null : gson.fromJson(JSON.toJSONString(value), clazz); } /** * 普通缓存获取 * * @param key 键 * @return 值 object */ public Object get(String key) { return key == null ? null : redisTemplate.opsForValue().get(key); }
下一篇:
MySQL 常用函数 - 数字函数