Java 使用JPA和Oracle管理具有增量id的复合主键
使用JPA,我尝试修改多语言内容的持久化对象,这意味着我需要一个具有id和语言的复合键。id还需要使用序列递增(我使用的是Oracle)。怎样才能做到呢 目前,我有一个Contenu课程:Java 使用JPA和Oracle管理具有增量id的复合主键,java,oracle,jpa,sequence,composite-key,Java,Oracle,Jpa,Sequence,Composite Key,使用JPA,我尝试修改多语言内容的持久化对象,这意味着我需要一个具有id和语言的复合键。id还需要使用序列递增(我使用的是Oracle)。怎样才能做到呢 目前,我有一个Contenu课程: @Entity @Table(name = "CONTENUS") public class Contenus implements java.io.Serializable { private ContenusId id; ... } 和ContenusId类: @Embeddable
@Entity
@Table(name = "CONTENUS")
public class Contenus implements java.io.Serializable {
private ContenusId id;
...
}
和ContenusId类:
@Embeddable
public class ContenusId implements java.io.Serializable {
private Long id;
private String langue;
...
}
但这并不处理增量id。有什么想法吗?首先,您需要为JPA实体管理器创建和id类,以了解如何检查两个对象是否相等。这个ID类应该重写
equals()
和hashcode()
方法
/**
* ContenusPK.java
*
* $Source$
*/
import java.io.Serializable;
public class ContenusPK implements Serializable
{
public static final long serialVersionUID = 1L;
private Long id;
private String langue;
/*
* (non-Javadoc)
* @see java.lang.Object#hashCode()
*/
@Override
public int hashCode()
{
final int prime = 31;
int result = 1;
result = prime * result + ((id == null) ? 0 : id.hashCode());
result = prime * result + ((langue == null) ? 0 : langue.hashCode());
return result;
}
/*
* (non-Javadoc)
* @see java.lang.Object#equals(java.lang.Object)
*/
@Override
public boolean equals(Object obj)
{
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
ContenusPK other = (ContenusPK) obj;
if (id == null)
{
if (other.id != null)
return false;
}
else if (!id.equals(other.id))
return false;
if (langue == null)
{
if (other.langue != null)
return false;
}
else if (!langue.equals(other.langue))
return false;
return true;
}
/**
* @return the serialversionuid
*/
public static long getSerialversionuid()
{
return serialVersionUID;
}
/**
* @return the id
*/
public Long getId()
{
return id;
}
/**
* @return the langue
*/
public String getLangue()
{
return langue;
}
/**
* @param id the id to set
*/
protected void setId(Long id)
{
this.id = id;
}
/**
* @param langue the langue to set
*/
protected void setLangue(String langue)
{
this.langue = langue;
}
}
然后,您需要声明实体的复合主键属性,将ID类与实体关联,并定义ID生成策略,如下所示:
@IdClass(ContenusPK.class)
@Entity
@TableName(name="")
public class Contenus {
@Id
@GeneratedValue(
strategy = GenerationType.SEQUENCE,
generator = "GENERATOR_NAME")
@SequenceGenerator(
name = "GENERATOR_NAME",
sequenceName = "SEQUENCE NAME IN DB")
@Column(name = "CONTENUS_ID")
private Long id;
@Id
@Column(name = "LANGUE")
private String langue;
...
}
因此,如果我创建3个Contenus对象,它们的语言值为“en”、“fr”和“de”,我调用
myEntityManager.persist()代码>,这3个对象会用相同的id值保存吗?不会,序列会为每个记录生成不同的id。我想这是Alexis试图避免的。因为它是一个复合键,所以应该有一种只在需要时使用下一个序列值的方法。应该可以手动使用下一个序列号,这样就可以决定何时必须增加id。