我使用JPA时遇到了一个奇怪的问题。
在PostgreSQL数据库中,视图(ConsoView)是使用LEFT OUTER JOIN创建的,因此此视图中的某些行在一列或两列中具有空值。
通过Java端的查询请求数据(使用标准Builder,EntityManager和方法getResultList()),我获得了一个具有正确记录数的列表,但是有完整的空实体而不是实体一个或两个空属性。
更新:添加一些代码
实体ConsoView:
/**
* ConsoView generated by hbm2java
*/
@Entity
@Table(name = "conso_view")
public class ConsoView implements java.io.Serializable {
private ConsoViewId id;
public ConsoView() {
}
public ConsoView(ConsoViewId id) {
this.id = id;
}
@EmbeddedId
@AttributeOverrides({
@AttributeOverride(name = "nomSite", column = @Column(name = "nom_site", length = 20)),
@AttributeOverride(name = "day", column = @Column(name = "day", length = 13)),
@AttributeOverride(name = "dayOfWeek", column = @Column(name = "day_of_week", precision = 131089, scale = 0)),
@AttributeOverride(name = "valeurConso", column = @Column(name = "valeur_conso", precision = 131089, scale = 0)),
@AttributeOverride(name = "vacance", column = @Column(name = "vacance")),
@AttributeOverride(name = "ferie", column = @Column(name = "ferie")) })
public ConsoViewId getId() {
return this.id;
}
public void setId(ConsoViewId id) {
this.id = id;
}
}
Id:
**
* ConsoViewId generated by hbm2java
*/
@Embeddable
public class ConsoViewId implements java.io.Serializable {
private String nomSite;
private Date day;
private BigDecimal dayOfWeek;
private BigDecimal valeurConso;
private String vacance;
private String ferie;
public ConsoViewId() {
}
public ConsoViewId(String nomSite, Date day, BigDecimal dayOfWeek,
BigDecimal valeurConso, String vacance, String ferie) {
this.nomSite = nomSite;
this.day = day;
this.dayOfWeek = dayOfWeek;
this.valeurConso = valeurConso;
this.vacance = vacance;
this.ferie = ferie;
}
@Column(name = "nom_site", length = 20)
public String getNomSite() {
return this.nomSite;
}
public void setNomSite(String nomSite) {
this.nomSite = nomSite;
}
@Column(name = "day", length = 13)
public Date getDay() {
return this.day;
}
public void setDay(Date day) {
this.day = day;
}
@Column(name = "day_of_week", precision = 131089, scale = 0)
public BigDecimal getDayOfWeek() {
return this.dayOfWeek;
}
public void setDayOfWeek(BigDecimal dayOfWeek) {
this.dayOfWeek = dayOfWeek;
}
@Column(name = "valeur_conso", precision = 131089, scale = 0)
public BigDecimal getValeurConso() {
return this.valeurConso;
}
public void setValeurConso(BigDecimal valeurConso) {
this.valeurConso = valeurConso;
}
@Column(name = "vacance")
public String getVacance() {
return this.vacance;
}
public void setVacance(String vacance) {
this.vacance = vacance;
}
@Column(name = "ferie")
public String getFerie() {
return this.ferie;
}
public void setFerie(String ferie) {
this.ferie = ferie;
}
public boolean equals(Object other) {
if ((this == other))
return true;
if ((other == null))
return false;
if (!(other instanceof ConsoViewId))
return false;
ConsoViewId castOther = (ConsoViewId) other;
return ((this.getNomSite() == castOther.getNomSite()) || (this
.getNomSite() != null && castOther.getNomSite() != null && this
.getNomSite().equals(castOther.getNomSite())))
&& ((this.getDay() == castOther.getDay()) || (this.getDay() != null
&& castOther.getDay() != null && this.getDay().equals(
castOther.getDay())))
&& ((this.getDayOfWeek() == castOther.getDayOfWeek()) || (this
.getDayOfWeek() != null
&& castOther.getDayOfWeek() != null && this
.getDayOfWeek().equals(castOther.getDayOfWeek())))
&& ((this.getValeurConso() == castOther.getValeurConso()) || (this
.getValeurConso() != null
&& castOther.getValeurConso() != null && this
.getValeurConso().equals(castOther.getValeurConso())))
&& ((this.getVacance() == castOther.getVacance()) || (this
.getVacance() != null && castOther.getVacance() != null && this
.getVacance().equals(castOther.getVacance())))
&& ((this.getFerie() == castOther.getFerie()) || (this
.getFerie() != null && castOther.getFerie() != null && this
.getFerie().equals(castOther.getFerie())));
}
public int hashCode() {
int result = 17;
result = 37 * result
+ (getNomSite() == null ? 0 : this.getNomSite().hashCode());
result = 37 * result
+ (getDay() == null ? 0 : this.getDay().hashCode());
result = 37 * result
+ (getDayOfWeek() == null ? 0 : this.getDayOfWeek().hashCode());
result = 37
* result
+ (getValeurConso() == null ? 0 : this.getValeurConso()
.hashCode());
result = 37 * result
+ (getVacance() == null ? 0 : this.getVacance().hashCode());
result = 37 * result
+ (getFerie() == null ? 0 : this.getFerie().hashCode());
return result;
}
}
DAO中使用的方法:
public List<ConsoView> findAll() {
CriteriaBuilder cb = em.getCriteriaBuilder();
CriteriaQuery<ConsoView> criteria = cb.createQuery(ConsoView.class);
Root<ConsoView> consoView = criteria.from(ConsoView.class);
criteria.select(consoView);
return em.createQuery(criteria).getResultList();
}
可以为null的列是:'vacance'和'ferie'。
你知道这个问题的解决方案吗?
谢谢!
修改
我找到了一个有助于解决问题的新信息:
注释@EmbeddedId
用于指定主键,因此如果此键的某个字段为null,则返回null实体。
新问题是实体是使用Hibernate自动生成的,即使View没有主键,也会创建@EmbeddedId
的部分。
那你怎么认为问题可以解决呢?