0

I have a problem with Spring Data and a Timestamp during a simple findOne request on my entity with a composite primary key. I have a SQL Server Database.

My entity class :

@Entity
@Table(name = "transition_log")
public class TransitionLog implements Serializable {

    private static final long serialVersionUID = 1L;

    @EmbeddedId
    private TransitionLogPK primaryKey;

    @ManyToOne
    @JoinColumn(name = "step", referencedColumnName = "step_name")
    private UpdateEventStep updateEventStep;

    @ManyToOne
    @JoinColumn(name = "step_status", referencedColumnName = "step_status_name")
    private StepStatus stepStatus;

    public Timestamp getTransitionTs() {
        return this.primaryKey.getTransitionTs();
    }

    public void setTransitionTs(Timestamp ts) {
        if(this.primaryKey == null){
            this.primaryKey = new TransitionLogPK();
        }
        this.primaryKey.setTransitionTs(ts);
    }

    public Long getEventId() {
        return this.primaryKey.getEventId();
    }

    public void setEventId(Long eventId) {
        if(this.primaryKey == null) {
            this.primaryKey = new TransitionLogPK();
        }
        this.primaryKey.setEventId(eventId);
    }

    public UpdateEventStep getUpdateEventStep() {
        return updateEventStep;
    }

    public void setUpdateEventStep(UpdateEventStep updateEventStep) {
        this.updateEventStep = updateEventStep;
    }

    public StepStatus getStepStatus() {
        return stepStatus;
    }

    public void setStepStatus(StepStatus stepStatus) {
        this.stepStatus = stepStatus;
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;

        TransitionLog that = (TransitionLog) o;

        if (primaryKey != null ? !primaryKey.equals(that.primaryKey) : that.primaryKey != null) return false;
        if (getUpdateEventStep() != null ? !getUpdateEventStep().equals(that.getUpdateEventStep()) : that.getUpdateEventStep() != null) return false;
        return getStepStatus() != null ? getStepStatus().equals(that.getStepStatus()) : that.getStepStatus() == null;

    }

    @Override
    public int hashCode() {
        int result = primaryKey != null ? primaryKey.hashCode() : 0;
        result = 31 * result + (getUpdateEventStep() != null ? getUpdateEventStep().hashCode() : 0);
        result = 31 * result + (getStepStatus() != null ? getStepStatus().hashCode() : 0);
        return result;
    }

    @Override
    public String toString() {
        return "TransitionLog{" +
                "primaryKey=" + primaryKey +
                ", updateEventStep=" + updateEventStep +
                ", stepStatus=" + stepStatus +
                '}';
    }
}

My Primary key class :

@Embeddable
public class TransitionLogPK implements Serializable {

    @Column(name = "event_id")
    private Long eventId;

    @Column(name = "transition_ts")
    private Timestamp transitionTs;

    public Long getEventId() {
        return eventId;
    }

    public void setEventId(Long eventId) {
        this.eventId = eventId;
    }

    public Timestamp getTransitionTs() {
        return transitionTs;
    }

    public void setTransitionTs(Timestamp transitionTs) {
        this.transitionTs = transitionTs;
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;

        TransitionLogPK that = (TransitionLogPK) o;

        if (getEventId() != null ? !getEventId().equals(that.getEventId()) : that.getEventId() != null) return false;
        return getTransitionTs() != null ? getTransitionTs().equals(that.getTransitionTs()) : that.getTransitionTs() == null;

    }

    @Override
    public int hashCode() {
        int result = getEventId() != null ? getEventId().hashCode() : 0;
        result = 31 * result + (getTransitionTs() != null ? getTransitionTs().hashCode() : 0);
        return result;
    }

    @Override
    public String toString() {
        return "TransitionLogPK{" +
                "eventId=" + eventId +
                ", transitionTs=" + transitionTs +
                '}';
    }
}

My JPA Repository :

public interface TransitionLogRepository extends JpaRepository<TransitionLog,TransitionLogPK> {

    @Query("select e from TransitionLog e where e.primaryKey.eventId = ?1 and e.primaryKey.transitionTs = ?2")
    TransitionLog namedQuery(Long eventId, Timestamp transitionTs);

    @Query(value = "select * from transition_log where event_id = ?1 and transition_ts = ?2", nativeQuery = true)
    TransitionLog nativeQuery(Long eventId, String transitionTs);
}

My executed code :

//Work
TransitionLog test = TransitionLogRepository.nativeQuery(2L, correctTimestamp.toString());    

//Doesn't work 
TransitionLog test2 = TransitionLogRepository.namedQuery(2L, correctTimestamp);

//Doesn't work 
TransitionLogPK pk = new TransitionLogPK();
pk.setEventId(2L);
pk.setTransitionTs(correctTimestamp);
TransitionLog test3 = TransitionLogRepository.findOne(pk);

It's probably due to timestamp, but I can't see with Hibernate the real SQL Query who is executed. For your informations, this SQL request work fine :

select *
from transition_log as e
where e.event_id=2 and e.transition_ts='2016-11-16 10:08:03.633'       

Thanks for your help ;)

Rtrompier
  • 113
  • 1
  • 6
  • why can't you see what SQL is executed with your JPA provider? All JPA providers put it in their log – Neil Stockton Nov 16 '16 at 15:05
  • I can see the request with param but not the real param value like this : where e.event_id=2 and e.transition_ts='2016-11-16 10:08:03.633' – Rtrompier Nov 16 '16 at 15:52
  • Could you try [this answer](http://stackoverflow.com/questions/40613171/spring-data-jpa-custom-query-with-param-date-doesnt-work/40615029#40615029) and see what happened ? (Add @Temporal, and make sure the timestamp value is have exactly correct value) – xsalefter Nov 16 '16 at 21:51
  • Please post the exception. Did you find a solution? – chrisinmtown Aug 05 '17 at 10:05

0 Answers0