我正在尝试将对象持久化到数据库。继续获取'列ID不能接受空值错误'。我的对象看起来像这样:
@Entity
public class TestTable {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Integer id = 0;
@Column(nullable=false, length=256)
private String data = "";
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getData() {
return data;
}
public void setData(String data) {
this.data = data;
}
}
我的坚持功能:
public static synchronized boolean persistObject(Object obj){
boolean success = true;
EntityManager em = null;
EntityTransaction tx = null;
try{
em = getEmf().createEntityManager();
tx = em.getTransaction();
tx.begin();
em.persist(obj);
tx.commit();
} catch (Exception e){
success = false;
} finally{
try{
em.close();
} catch(Exception e){
//nothing
}
}
return success;
}
答案 0 :(得分:21)
您可以使用GenerationType.TABLE。 这样,jpa使用序列表进行id分配,您可能永远不需要生成序列或自动递增值或触发器,从而降低可移植性。
另请注意,在java int类型中,默认启动为0,因此您也可以将其删除。
答案 1 :(得分:4)
就我而言,这是关于糟糕的方言:
hibernate.dialect=org.hibernate.dialect.H2Dialect
而不是:
hibernate.dialect=org.hibernate.dialect.PostgreSQL9Dialect
当我切换到生产数据库时。 Hibernate试图使用为不同的db引擎准备的策略。
答案 2 :(得分:2)
我遇到了类似表现的问题。我最终发现我的数据库连接的配置是错误的:我正在连接到具有不正确架构的旧数据库。新架构将主键列声明为
"ID" BIGINT NOT NULL GENERATED ALWAYS AS IDENTITY (START WITH 1, INCREMENT BY 1)
所以the database itself automatically generated the primary key而旧架构将其声明为
"ID" INTEGER NOT NULL
Hibernate为新架构执行了正确的代码,该架构在旧架构上失败,因为旧架构要求SQL INSERT
为ID
列提供值。
答案 3 :(得分:1)
当ID列是Int时,Hibernate以静默和神秘的方式失败。尝试在代码中将其更改为Long,并在数据库中将其更改为无符号的64位整数。这解决了我的问题。
答案 4 :(得分:1)
以防万一有人遇到与我相同的问题而到达此线程。我已经为此奋斗了几个小时,只想发布我的解决方案。似乎ID始终设置为0,这引发了错误。
模型中的id属性必须是“ Long”或“ Integer”类型,而不是“ long”或“ integer”(请注意大写)。我输入了“ long”,这是一个原始类型,不能为null。因此默认值为0,而Hibernate并未意识到这是一个新实体,并尝试将其保存为ID = 0,这显然是行不通的。
将其更改为引用类型“ Long”(可以为null)即可解决该问题。
答案 5 :(得分:0)
或尝试使用@GeneratedValue(strategy = GenerationType.AUTO)
而不是@GeneratedValue(strategy = GenerationType.SEQUENCE)
。
答案 6 :(得分:0)
我一直在同一个问题上挣扎,而不是LONG类型:)我需要长时间工作。作为工作环境,我将数据库中的id列转换为SERIEL。我正在使用postgres db。