两个Java应用程序之间的Java spring boot JSON时间戳转换问题

两个Java应用程序之间的Java spring boot JSON时间戳转换问题,java,json,spring-boot,timestamp,jackson2,Java,Json,Spring Boot,Timestamp,Jackson2,我正在开发两个相互通信的java应用程序(“后端1”和“后端2”)。 我得到了这个错误: [{ "status": "BAD_REQUEST", "timestamp": "2018-07-11 02:54:28", "message": "Malformed JSON request", "debugMessage": "JSON parse error: Cannot deserialize value of type `java.sql.Timestamp`

我正在开发两个相互通信的java应用程序(“后端1”和“后端2”)。 我得到了这个错误:

[{
    "status": "BAD_REQUEST",
    "timestamp": "2018-07-11 02:54:28",
    "message": "Malformed JSON request",
    "debugMessage": "JSON parse error: Cannot deserialize value of type `java.sql.Timestamp` from String \"Jul 11, 2018 9:32:10 AM\": not a valid representation (error: Failed to parse Date value 'Jul 11, 2018 9:32:10 AM': Cannot parse date \"Jul 11, 2018 9:32:10 AM\": not compatible with any of standard forms (\"yyyy-MM-dd'T'HH:mm:ss.SSSZ\", \"yyyy-MM-dd'T'HH:mm:ss.SSS\", \"EEE, dd MMM yyyy HH:mm:ss zzz\", \"yyyy-MM-dd\")); nested exception is com.fasterxml.jackson.databind.exc.InvalidFormatException: Cannot deserialize value of type `java.sql.Timestamp` from String \"Jul 11, 2018 9:32:10 AM\": not a valid representation (error: Failed to parse Date value 'Jul 11, 2018 9:32:10 AM': Cannot parse date \"Jul 11, 2018 9:32:10 AM\": not compatible with any of standard forms (\"yyyy-MM-dd'T'HH:mm:ss.SSSZ\", \"yyyy-MM-dd'T'HH:mm:ss.SSS\", \"EEE, dd MMM yyyy HH:mm:ss zzz\", \"yyyy-MM-dd\"))\n at [Source: (PushbackInputStream); line: 1, column: 166] (through reference chain: java.util.ArrayList[0]->com.irm.api.automata.response.AutomataDeliveryNoteModel[\"createdAt\"])",
    "code": null,
    "subErrors": null
}]
我在backend1中的一个函数调用backend2控制器,其中 后端1代码:

Call<List<DeliverynotesEntity>> deliverynotesEntityCall = commonFunction.retrofitBuilder(commonFunction.getBaseURL()).create(ISendDeliveryNoteCall.class).sendDeliveryNotes(
        commonFunction.getToken(),
        deliverynotesEntities
    );
这里的createdAt导致了问题。这很奇怪,因为如果我使用postman调用带有url的控制器函数,代码是完美的、有效的,但是backend1函数调用backend2控制器,我会得到这个异常

下面是我在backend1中使用的deliverynote实体

package com.irmmat.backend.entity.object;

import com.fasterxml.jackson.annotation.JsonFormat;
import org.hibernate.annotations.CreationTimestamp;

import javax.persistence.*;
import java.io.Serializable;
import java.sql.Timestamp;
import java.util.Objects;

@Entity
@Table(name = "delivery_notes", schema = "irmmat")
public class DeliverynotesEntity implements Serializable {
  private Integer id;
  private Integer serpaCostCenterId;
  private Integer serpaProductId;
  private Integer productQuantity;
  private Integer direction;
  private Integer requesterEmployeeId;
  private Integer supervisorId;
  private Integer serpaSequenceId;
  @JsonFormat(shape = JsonFormat.Shape.NUMBER_FLOAT)
  private Timestamp createdAt;
  private String sessionId;

  @Id
  @GeneratedValue(strategy = GenerationType.IDENTITY)
  @Column(name = "id", nullable = false)
  public Integer getId() {
    return id;
  }

  public void setId(Integer id) {
    this.id = id;
  }

  @Basic
  @Column(name = "serpa_cost_center_id")
  public Integer getSerpaCostCenterId() {
    return serpaCostCenterId;
  }

  public void setSerpaCostCenterId(Integer serpaCostCenterId) {
    this.serpaCostCenterId = serpaCostCenterId;
  }

  @Basic
  @Column(name = "serpa_product_id", nullable = false)
  public Integer getSerpaProductId() {
    return serpaProductId;
  }

  public void setSerpaProductId(Integer serpaProductId) {
    this.serpaProductId = serpaProductId;
  }

  @Basic
  @Column(name = "product_quantity", nullable = false)
  public Integer getProductQuantity() {
    return productQuantity;
  }

  public void setProductQuantity(Integer productQuantity) {
    this.productQuantity = productQuantity;
  }

  @Basic
  @Column(name = "direction", nullable = false)
  public Integer getDirection() {
    return direction;
  }

  public void setDirection(Integer direction) {
    this.direction = direction;
  }

  @Basic
  @Column(name = "requester_employee_id", nullable = false)
  public Integer getRequesterEmployeeId() {
    return requesterEmployeeId;
  }

  public void setRequesterEmployeeId(Integer requesterEmployeeId) {
    this.requesterEmployeeId = requesterEmployeeId;
  }

  @Basic
  @Column(name = "supervisor_id", nullable = false)
  public Integer getSupervisorId() {
    return supervisorId;
  }

  public void setSupervisorId(Integer supervisorId) {
    this.supervisorId = supervisorId;
  }

  @Basic
  @Column(name = "serpa_sequence_id", nullable = false)
  public Integer getSerpaSequenceId() {
    return serpaSequenceId;
  }

  public void setSerpaSequenceId(Integer serpaSequenceId) {
    this.serpaSequenceId = serpaSequenceId;
  }

  @Basic
  @CreationTimestamp
  @Column(name = "created_at", nullable = false, updatable = false)
  public Timestamp getCreatedAt() {
    return createdAt;
  }

  public void setCreatedAt(Timestamp createdAt) {
    this.createdAt = createdAt;
  }

  @Basic
  @Column(name = "session_id", nullable = false)
  public String getSessionId() {
    return sessionId;
  }

  public void setSessionId(String sessionId) {
    this.sessionId = sessionId;
  }

  @Override
  public boolean equals(Object o) {
    if (this == o) return true;
    if (o == null || getClass() != o.getClass()) return false;
    DeliverynotesEntity that = (DeliverynotesEntity) o;
    return Objects.equals(id, that.id) &&
        Objects.equals(serpaCostCenterId, that.serpaCostCenterId) &&
        Objects.equals(serpaProductId, that.serpaProductId) &&
        Objects.equals(productQuantity, that.productQuantity) &&
        Objects.equals(direction, that.direction) &&
        Objects.equals(requesterEmployeeId, that.requesterEmployeeId) &&
        Objects.equals(supervisorId, that.supervisorId) &&
        Objects.equals(serpaSequenceId, that.serpaSequenceId) &&
        Objects.equals(createdAt, that.createdAt) &&
        Objects.equals(sessionId, that.sessionId);
  }

  @Override
  public int hashCode() {

    return Objects.hash(id, serpaCostCenterId, serpaProductId, productQuantity, direction, requesterEmployeeId, supervisorId, serpaSequenceId, createdAt, sessionId);
  }

}
这是我在后端2的模型

package com.irm.api.automata.response;

import com.fasterxml.jackson.annotation.JsonFormat;

import java.sql.Timestamp;

public class AutomataDeliveryNoteModel {
  private Integer id;
  private Integer serpaCostCenterId;
  private Integer serpaProductId;
  private Integer productQuantity;
  private Integer direction;
  private Integer requesterEmployeeId;
  private Integer supervisorId;
  private Integer serpaSequenceId;
  @JsonFormat(shape = JsonFormat.Shape.NUMBER_FLOAT)
  private Timestamp createdAt;
  private String sessionId;

  public Integer getId() {
    return id;
  }

  public void setId(Integer id) {
    this.id = id;
  }

  public Integer getSerpaCostCenterId() {
    return serpaCostCenterId;
  }

  public void setSerpaCostCenterId(Integer serpaCostCenterId) {
    this.serpaCostCenterId = serpaCostCenterId;
  }

  public Integer getSerpaProductId() {
    return serpaProductId;
  }

  public void setSerpaProductId(Integer serpaProductId) {
    this.serpaProductId = serpaProductId;
  }

  public Integer getProductQuantity() {
    return productQuantity;
  }

  public void setProductQuantity(Integer productQuantity) {
    this.productQuantity = productQuantity;
  }

  public Integer getDirection() {
    return direction;
  }

  public void setDirection(Integer direction) {
    this.direction = direction;
  }

  public Integer getRequesterEmployeeId() {
    return requesterEmployeeId;
  }

  public void setRequesterEmployeeId(Integer requesterEmployeeId) {
    this.requesterEmployeeId = requesterEmployeeId;
  }

  public Integer getSupervisorId() {
    return supervisorId;
  }

  public void setSupervisorId(Integer supervisorId) {
    this.supervisorId = supervisorId;
  }

  public Integer getSerpaSequenceId() {
    return serpaSequenceId;
  }

  public void setSerpaSequenceId(Integer serpaSequenceId) {
    this.serpaSequenceId = serpaSequenceId;
  }

  public Timestamp getCreatedAt() {
    return createdAt;
  }

  public void setCreatedAt(Timestamp createdAt) {
    this.createdAt = createdAt;
  }

  public String getSessionId() {
    return sessionId;
  }

  public void setSessionId(String sessionId) {
    this.sessionId = sessionId;
  }
}

我不知道,希望有人能给我一些建议。我尝试了大量转换等操作。

deliverynote entity
类中,您可以按如下方式定义时间戳并尝试:

@JsonFormat(pattern="yyyy-MM-dd HH:mm:ss.SSS")
private Timestamp createdAt;
我解决了这个问题。 问题是通过改装.builder解决的

 Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSSZ").create(); //this line was missing
    return new Retrofit.Builder()
        .baseUrl(baseUrl)
        .addConverterFactory(GsonConverterFactory.create(gson))
        .build();

因为我使用了默认的GsonConverter,所以它将格式化的json时间戳创建为“无用”的时间格式。现在我设置了它,它工作得非常完美。

ISO格式应该是“yyyy-MM-dd'T'HH:MM:ss.SSS”吗?对于一个显然很简单的问题,它需要大量的代码。是的,大量的代码,但我不知道是什么导致了问题。我认为,如果我不分享相关内容,那么更多的代码比他们要求更多的代码要好。我明白你的意思。你真的应该训练创造MCVE。很好,你已经解决了。顺便说一句,请通过接受其中一个答案(你可以在一段时间后接受自己的答案),而不是通过更改标题,将问题标记为已回答。这就是我们其他人在这里所做的。谢谢。
package com.irm.api.automata.response;

import com.fasterxml.jackson.annotation.JsonFormat;

import java.sql.Timestamp;

public class AutomataDeliveryNoteModel {
  private Integer id;
  private Integer serpaCostCenterId;
  private Integer serpaProductId;
  private Integer productQuantity;
  private Integer direction;
  private Integer requesterEmployeeId;
  private Integer supervisorId;
  private Integer serpaSequenceId;
  @JsonFormat(shape = JsonFormat.Shape.NUMBER_FLOAT)
  private Timestamp createdAt;
  private String sessionId;

  public Integer getId() {
    return id;
  }

  public void setId(Integer id) {
    this.id = id;
  }

  public Integer getSerpaCostCenterId() {
    return serpaCostCenterId;
  }

  public void setSerpaCostCenterId(Integer serpaCostCenterId) {
    this.serpaCostCenterId = serpaCostCenterId;
  }

  public Integer getSerpaProductId() {
    return serpaProductId;
  }

  public void setSerpaProductId(Integer serpaProductId) {
    this.serpaProductId = serpaProductId;
  }

  public Integer getProductQuantity() {
    return productQuantity;
  }

  public void setProductQuantity(Integer productQuantity) {
    this.productQuantity = productQuantity;
  }

  public Integer getDirection() {
    return direction;
  }

  public void setDirection(Integer direction) {
    this.direction = direction;
  }

  public Integer getRequesterEmployeeId() {
    return requesterEmployeeId;
  }

  public void setRequesterEmployeeId(Integer requesterEmployeeId) {
    this.requesterEmployeeId = requesterEmployeeId;
  }

  public Integer getSupervisorId() {
    return supervisorId;
  }

  public void setSupervisorId(Integer supervisorId) {
    this.supervisorId = supervisorId;
  }

  public Integer getSerpaSequenceId() {
    return serpaSequenceId;
  }

  public void setSerpaSequenceId(Integer serpaSequenceId) {
    this.serpaSequenceId = serpaSequenceId;
  }

  public Timestamp getCreatedAt() {
    return createdAt;
  }

  public void setCreatedAt(Timestamp createdAt) {
    this.createdAt = createdAt;
  }

  public String getSessionId() {
    return sessionId;
  }

  public void setSessionId(String sessionId) {
    this.sessionId = sessionId;
  }
}
@JsonFormat(pattern="yyyy-MM-dd HH:mm:ss.SSS")
private Timestamp createdAt;
 Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSSZ").create(); //this line was missing
    return new Retrofit.Builder()
        .baseUrl(baseUrl)
        .addConverterFactory(GsonConverterFactory.create(gson))
        .build();