Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/jpa/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Hibernate自定义类型和JPA2标准查询_Hibernate_Jpa_Jboss7.x - Fatal编程技术网

Hibernate自定义类型和JPA2标准查询

Hibernate自定义类型和JPA2标准查询,hibernate,jpa,jboss7.x,Hibernate,Jpa,Jboss7.x,我们在尝试将CriteriaBuilder用于自定义类型字段时遇到了一个问题 下面的示例显示了用自定义@Type注释的生日字段 @Entity @Table(name = "People") public class People { @Id @NotNull @Column(name = "id") private Integer id; @NotNull @Size(min = 1, max = 20) @Column(name = "Name") priv

我们在尝试将CriteriaBuilder用于自定义类型字段时遇到了一个问题

下面的示例显示了用自定义@Type注释的生日字段

@Entity
@Table(name = "People")
public class People {
  @Id
  @NotNull
  @Column(name = "id")
  private Integer id;

  @NotNull
  @Size(min = 1, max = 20)
  @Column(name = "Name")
  private String name;

  @NotNull
  @Column(name = "Birthdate")
  @Type(type = "test.MyDateType")
  @Temporal(TemporalType.TIMESTAMP)
  private MyDate birthdate;

  ...

}
MyDateType实现hibernate的EnhancedUserType

package test;

import java.io.Serializable;
import java.sql.*;
import java.text.*;
import java.util.*;
import java.util.Date;

import org.hibernate.HibernateException;
import org.hibernate.usertype.EnhancedUserType;

import org.hibernate.engine.spi.SessionImplementor;

public class MyDateType implements EnhancedUserType {

  static final ThreadLocal<Calendar> utcCalendar = new ThreadLocal<Calendar>() {
    @Override
    protected Calendar initialValue() {
      return Calendar.getInstance(TimeZone.getTimeZone("GMT"));
    }
  };

  static final ThreadLocal<SimpleDateFormat> utcSimpleDateFormat = new ThreadLocal<SimpleDateFormat>() {
    @Override
    protected SimpleDateFormat initialValue() {
      SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss.SSS");
      df.setTimeZone(TimeZone.getTimeZone("GMT"));
      return df;
    }
  };

  private static final int[] SQL_TYPES = {Types.TIMESTAMP};

  @Override
  public int[] sqlTypes() {
    return SQL_TYPES;
  }

  @Override
  public boolean equals(Object o1, Object o2) {
    if(o1 == o2) {
      return true;
    }
    if((o1 == null) || (o2 == null)) {
      return false;
    }
    return o1.equals(o2);
  }

  @Override
  public boolean isMutable() {
    return true;
  }

  @Override
  public Class<?> returnedClass() {
    return objectClass;
  }

  protected Class<?> objectClass = MyDate.class;

  @Override
  public Object deepCopy(Object value) {
    return (value == null) ? null : new MyDate(((Date)value).getTime());
  }

  @Override
  public Object nullSafeGet(ResultSet rs, String[] columns, SessionImplementor si, Object owner) throws HibernateException, SQLException {
    Timestamp ts = rs.getTimestamp(columns[0], utcCalendar.get());
    if(ts != null) {
      return new Date(ts.getTime());
    }
    return null;
  }

  @Override
  public void nullSafeSet(PreparedStatement statement, Object value, int index, SessionImplementor si) throws HibernateException,
    SQLException {
    Object val = value;
    if(!(val instanceof java.sql.Timestamp)) {
      val = (val == null) ? null : new java.sql.Timestamp(((Date)val).getTime());
    }
    statement.setTimestamp(index, (java.sql.Timestamp)val, utcCalendar.get());
  }

  @Override
  public Object assemble(Serializable cached, Object owner) throws HibernateException {
    return deepCopy(cached);
  }

  @Override
  public Serializable disassemble(Object value) throws HibernateException {
    return (Serializable)deepCopy(value);
  }

  @Override
  public int hashCode(Object x) throws HibernateException {
    return x.hashCode();
  }

  @Override
  public Object replace(Object original, Object target, Object owner) throws HibernateException {
    return deepCopy(original);
  }

  @Override
  public Object fromXMLString(String xmlValue) {
    try {
      return new Date(utcSimpleDateFormat.get().parse(xmlValue).getTime());
    } catch(ParseException e) {
      System.out.println(e);
    }
    return xmlValue;
  }

  @Override
  public String objectToSQLString(Object value) {
    return null;
  }

  @Override
  public String toXMLString(Object value) {
    return value.toString();
  }
}
我们知道注释是有效的,因为当我们查询Id时,我们会为birthdate字段返回正确的数据。 当我们构建以下查询时,它也可以正常工作

MyDate start = new MyDate(...);
MyDate end = new MyDate(...):

TypedQuery<People> q = entityManager.createQuery("select p from people where birthdate >= :start and birthdate <= :end", People.class);
q.setParameter("start", start);
q.setParameter("end", end);

List<People> results = q.getResultList();
MyDate start=newmydate(…);
MyDate end=新的MyDate(…):

TypedQuery q=entityManager.createQuery(“从出生日期>=:开始和出生日期的人中选择p,请添加
test.MyDateType
我已经在上面包含了MyDataType
22:03:44,733 WARN  [org.hibernate.engine.jdbc.spi.SqlExceptionHelper] (http-/0.0.0.0:8080-1) SQL Error: 210, SQLState: S0001
22:03:44,734 ERROR [org.hibernate.engine.jdbc.spi.SqlExceptionHelper] (http-/0.0.0.0:8080-1) Conversion failed when converting datetime from binary/varbinary string.
MyDate start = new MyDate(...);
MyDate end = new MyDate(...):

TypedQuery<People> q = entityManager.createQuery("select p from people where birthdate >= :start and birthdate <= :end", People.class);
q.setParameter("start", start);
q.setParameter("end", end);

List<People> results = q.getResultList();