为什么它们有时不一致?从服务器接收的 java.sql.Date 类型的值,然后由 google.gson 转换。从服务器发送的 json 字符串

问题描述 投票:0回答:1

问题

简介

为什么它们有时不一致?从服务器

java.sql.Date
接收的
Postman
类型的值然后由
com.google.gson.Gson
反序列化(在实例化 Gson 实例之前,我注册了两个适配器 - 一个用于反序列化
java.sql.Date
,另一个用于反序列化
java.sql.Time
。)。以及从服务器发送的 json 字符串。

我尝试从

Postman
发送请求到
Tomcat v9.0
,并将原始数据(这里是一个json字符串)反序列化到
DietDiary
对象,该对象包含两个类型为
java.sql.Date
java.sql.Time
的字段,使用
com.google.gson
包.

Postman
中请求原始数据的两个键。

    "createDate":"2022-05-05",
    "createTime":"12:00:00",  

request in Postman

但是 Eclipse 中的控制台会打印

Ready to deserialize.
dietDiary:DietDiary [diaryId=2, userId=2, createDate=2021-12-26, createTime=00:00:00, totalFat=2.52, totalCarbon=2.3, totalProtein=2.1, totalFiber=2.1, totalSugar=1.2, totalSodium=1.1, totalCalories=1.21]

不知道为什么?

欣赏

任何有关此问题的回复都将受到高度赞赏。

详细信息

这里有详细信息。

服务器

名字

Postman

请求

方法

GET

网址

http://localhost:8080/HealthHelper/dietDiary/test

原始数据

一个 json 字符串。

{
    "diaryId":2,
    "userId":2,
    "createDate":"2022-05-05",
    "createTime":"12:00:00",  
    "totalFat":2.52,
    "totalCarbon":2.3,
    "totalProtein":2.1,
    "totalFiber":2.1,
    "totalSugar":1.2,
    "totalSodium":1.1,
    "totalCalories":1.21 
}

客户

Tomcat
v9.0(版本9)

代码

/HealthHelper/src/main/java/controller/TestController.java

package controller;

import java.io.IOException;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.sql.Date;
import java.sql.Time;

import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonDeserializationContext;
import com.google.gson.JsonDeserializer;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import com.google.gson.JsonParseException;

import constant.SqlDatePattern;
import constant.SqlTimePattern;
import util.gson.GsonForSqlDateAndSqlTime;
import util.gson.deserializer.JsonDeserializerForSqTime;
import util.gson.deserializer.JsonDeserializerForSqlDate;
import vo.DietDiary;


@WebServlet("/dietDiary/test")
public class TestController extends HttpServlet {

    private static final long serialVersionUID = 1L;
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse res) throws IOException {  
        Gson gson = GsonForSqlDateAndSqlTime.gson;
        DietDiary dietDiary = gson.fromJson(req.getReader(), DietDiary.class);
        
        System.out.println("Ready to deserialize.");
        System.out.println("dietDiary:"+dietDiary);
    }
}

/HealthHelper/src/main/java/vo/DietDiary.java

满足JavaBean规则且不被污染的类。

package vo;

import java.sql.Date;
import java.sql.Time;

public class DietDiary {
    private int diaryId;
    private int userId;
    private Date createDate;
    private Time createTime;
    private Double totalFat;
    private Double totalCarbon;
    private Double totalProtein;
    private Double totalFiber;
    private Double totalSugar;
    private Double totalSodium;
    private Double totalCalories;
    
    public int getDiaryId() {
        return diaryId;
    }
    public void setDiaryId(int diaryId) {
        this.diaryId = diaryId;
    }
    public int getUserId() {
        return userId;
    }
    public void setUserId(int userId) {
        this.userId = userId;
    }
    public Date getCreateDate() {
        return createDate;
    }
    public void setCreateDate(Date createDate) {
        this.createDate = createDate;
    }
    public Time getCreateTime() {
        return createTime;
    }
    public void setCreateTime(Time createTime) {
        this.createTime = createTime;
    }
    public Double getTotalFat() {
        return totalFat;
    }
    public void setTotalFat(Double totalFat) {
        this.totalFat = totalFat;
    }
    public Double getTotalCarbon() {
        return totalCarbon;
    }
    public void setTotalCarbon(Double totalCarbon) {
        this.totalCarbon = totalCarbon;
    }
    public Double getTotalProtein() {
        return totalProtein;
    }
    public void setTotalProtein(Double totalProtein) {
        this.totalProtein = totalProtein;
    }
    public Double getTotalFiber() {
        return totalFiber;
    }
    public void setTotalFiber(Double totalFiber) {
        this.totalFiber = totalFiber;
    }
    public Double getTotalSugar() {
        return totalSugar;
    }
    public void setTotalSugar(Double totalSugar) {
        this.totalSugar = totalSugar;
    }
    public Double getTotalSodium() {
        return totalSodium;
    }
    public void setTotalSodium(Double totalSodium) {
        this.totalSodium = totalSodium;
    }
    public Double getTotalCalories() {
        return totalCalories;
    }
    public void setTotalCalories(Double totalCalories) {
        this.totalCalories = totalCalories;
    }
    
    public boolean equals(Object object) {
        if(object instanceof DietDiary) {
            return false;
        }
        
        DietDiary dietDiary = (DietDiary) object;
        
        if(!(this.getDiaryId() == dietDiary.getDiaryId())) {
            return false;
        }
        
        if(!(this.getUserId() == dietDiary.getUserId())) {
            return false;
        }
        
        if(!(this.getCreateDate() == dietDiary.getCreateDate())) {
            return false;
        }
        
        if(!(this.getCreateTime() == dietDiary.getCreateTime())) {
            return false;
        }
        
        return true;
    }
    
    @Override
    public String toString() {
        return "DietDiary [diaryId=" + diaryId + ", userId=" + userId + ", createDate=" + createDate + ", createTime="
                + createTime + ", totalFat=" + totalFat + ", totalCarbon=" + totalCarbon + ", totalProtein="
                + totalProtein + ", totalFiber=" + totalFiber + ", totalSugar=" + totalSugar + ", totalSodium="
                + totalSodium + ", totalCalories=" + totalCalories + "]";
    }

    
}

/HealthHelper/src/main/java/util/gson/GsonForSqlDateAndSqlTime.java

我在

java.sql.Date
公共类中放置了一个 gson 实例,其适配器已注册用于反序列化
java.sql.Time
GsonForSqlDateAndSqlTime

package util.gson;

import java.sql.Date;
import java.sql.Time;

import com.google.gson.Gson;
import com.google.gson.GsonBuilder;

import util.gson.deserializer.JsonDeserializerForSqTime;
import util.gson.deserializer.JsonDeserializerForSqlDate;

public class GsonForSqlDateAndSqlTime {
    public static Gson gson = new GsonBuilder()
            .registerTypeAdapter(Date.class, JsonDeserializerForSqlDate.dateDeserializer)
            .registerTypeAdapter(Time.class, JsonDeserializerForSqTime.timeDeserializer)
            .create();
}

/HealthHelper/src/main/java/util/gson/deserializer/JsonDeserializerForSqlDate.java

package util.gson.deserializer;

import java.lang.reflect.Type;
import java.sql.Date;
import java.text.ParseException;
import java.text.SimpleDateFormat;

import com.google.gson.JsonDeserializationContext;
import com.google.gson.JsonDeserializer;
import com.google.gson.JsonElement;
import com.google.gson.JsonParseException;

import constant.SqlDatePattern;

public class JsonDeserializerForSqlDate {
    public static JsonDeserializer<Date> dateDeserializer = new JsonDeserializer<Date>() {
        @Override
        public Date deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context)
                throws JsonParseException {
            SimpleDateFormat dateFormat = new SimpleDateFormat(SqlDatePattern.sqlDatePattern);
            try {
                return new Date(dateFormat.parse(json.getAsString()).getTime());
            } catch (ParseException e) {
                throw new JsonParseException(e);
            }
        }
    };
}

/HealthHelper/src/main/java/util/gson/deserializer/JsonDeserializerForSqTime.java

package util.gson.deserializer;

import java.lang.reflect.Type;
import java.sql.Time;
import java.text.ParseException;
import java.text.SimpleDateFormat;

import com.google.gson.JsonDeserializationContext;
import com.google.gson.JsonDeserializer;
import com.google.gson.JsonElement;
import com.google.gson.JsonParseException;

import constant.SqlTimePattern;

public class JsonDeserializerForSqTime {
    public static JsonDeserializer<Time> timeDeserializer = new JsonDeserializer<Time>() {
        @Override
        public Time deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context)
                throws JsonParseException {
            SimpleDateFormat timeFormat = new SimpleDateFormat(SqlTimePattern.sqlTimePattern);
            try {
                return new Time(timeFormat.parse(json.getAsString()).getTime());
            } catch (ParseException e) {
                throw new JsonParseException(e);
            }
        }
    };
}

我尝试了什么?

我已阅读这些文档。

  1. JsonDeserializer
    包中
    com.google.gson
    接口的API
java tomcat servlets gson
1个回答
0
投票

我知道为什么!!!

原因似乎很明显。

我滥用该标志来创建

java.text.SimpleDateFormat
实例(发生在
/HealthHelper/src/main/java/util/gson/deserializer/JsonDeserializerForSqlDate.java
中),因此
java.sql.Date
解析是错误的。

在此声明中

SimpleDateFormat dateFormat = new SimpleDateFormat(SqlDatePattern.sqlDatePattern);

静态字段

SqlDatePattern.sqlDatePattern
被分配给
yyyy-MM-DD

我把它改为

yyyy-MM-dd

我还将

SqlTimePattern.sqlTimePattern
hh:mm:ss
更改为
HH:mm:ss

在以下声明中。

SimpleDateFormat timeFormat = new SimpleDateFormat(SqlTimePattern.sqlTimePattern);

然后我再次测试,得到了预期的结果。

在 Eclipse 的控制台中,它打印

Ready to deserialize.
dietDiary:DietDiary [diaryId=2, userId=2, createDate=2022-05-05, createTime=12:00:00, totalFat=2.52, totalCarbon=2.3, totalProtein=2.1, totalFiber=2.1, totalSugar=1.2, totalSodium=1.1, totalCalories=1.21]
© www.soinside.com 2019 - 2024. All rights reserved.