@Id注释无法在Hibernate中使用Oracle

时间:2017-06-05 19:08:49

标签: java database oracle hibernate

我正在从this book学习休眠,我正在尝试保存实体Book。

import javax.persistence.Entity;



import javax.persistence.Id;


@Entity
public class Book {

@Id

private int id;

private String name;

public String getName() {
    return name;
}

public void setName(String name) {
    this.name = name;
}
}



    Book book1 = new Book();

    book1.setName("Sample");
    session.save(book1);

但是,当Books表中没有数据时,此代码只能运行一次,因为每次生成' 0'作为主键id.Below是异常跟踪。

ERROR: HHH000346: Error during managed flush 

[org.hibernate.exception.ConstraintViolationException: could not execute statement]
Exception in thread "main" javax.persistence.PersistenceException: org.hibernate.exception.ConstraintViolationException: could not execute statement
    at org.hibernate.internal.ExceptionConverterImpl.convert(ExceptionConverterImpl.java:147)
    at org.hibernate.internal.ExceptionConverterImpl.convert(ExceptionConverterImpl.java:155)
    at org.hibernate.internal.ExceptionConverterImpl.convert(ExceptionConverterImpl.java:162)
    at org.hibernate.internal.SessionImpl.flush(SessionImpl.java:1403)
    at org.hibernate.internal.SessionImpl.managedFlush(SessionImpl.java:473)
    at org.hibernate.internal.SessionImpl.flushBeforeTransactionCompletion(SessionImpl.java:3133)
    at org.hibernate.internal.SessionImpl.beforeTransactionCompletion(SessionImpl.java:2370)
    at org.hibernate.engine.jdbc.internal.JdbcCoordinatorImpl.beforeTransactionCompletion(JdbcCoordinatorImpl.java:467)
    at org.hibernate.resource.transaction.backend.jdbc.internal.JdbcResourceLocalTransactionCoordinatorImpl.beforeCompletionCallback(JdbcResourceLocalTransactionCoordinatorImpl.java:146)
    at org.hibernate.resource.transaction.backend.jdbc.internal.JdbcResourceLocalTransactionCoordinatorImpl.access$100(JdbcResourceLocalTransactionCoordinatorImpl.java:38)
    at org.hibernate.resource.transaction.backend.jdbc.internal.JdbcResourceLocalTransactionCoordinatorImpl$TransactionDriverControlImpl.commit(JdbcResourceLocalTransactionCoordinatorImpl.java:220)

Caused by: java.sql.SQLIntegrityConstraintViolationException: ORA-00001: unique constraint (SPRING.SYS_C0015610) violated

    at oracle.jdbc.driver.T4CTTIoer.processError(T4CTTIoer.java:450)
    at oracle.jdbc.driver.T4CTTIoer.processError(T4CTTIoer.java:399)
    at oracle.jdbc.driver.T4C8Oall.processError(T4C8Oall.java:1059)
    at oracle.jdbc.driver.T4CTTIfun.receive(T4CTTIfun.java:522)
    at oracle.jdbc.driver.T4CTTIfun.doRPC(T4CTTIfun.java:257)
    at oracle.jdbc.driver.T4C8Oall.doOALL(T4C8Oall.java:587)
    at oracle.jdbc.driver.T4CPreparedStatement.doOall8(T4CPreparedStatement.java:225)
    at oracle.jdbc.driver.T4CPreparedStatement.doOall8(T4CPreparedStatement.java:53)
    at oracle.jdbc.driver.T4CPreparedStatement.executeForRows(T4CPreparedStatement.java:943)
    at oracle.jdbc.driver.OracleStatement.doExecuteWithTimeout(OracleStatement.java:1150)
    at oracle.jdbc.driver.OraclePreparedStatement.executeInternal(OraclePreparedStatement.java:4798)
    at oracle.jdbc.driver.OraclePreparedStatement.executeUpdate(OraclePreparedStatement.java:4875)
    at oracle.jdbc.driver.OraclePreparedStatementWrapper.executeUpdate(OraclePreparedStatementWrapper.java:1361)
    at org.hibernate.engine.jdbc.internal.ResultSetReturnImpl.executeUpdate(ResultSetReturnImpl.java:204)
    ... 19 more

书上写道:

  

默认情况下,@ Id注释会自动确定最合适的主要注释   要使用的密钥生成策略 - 您可以通过应用@GeneratedValue来覆盖它   注释

但是,如果我将@GeneratedValue注释与@ID一起使用,则代码可以正常工作,并且每次生成新的主键ID时。这种情况对我没有意义。我错过了什么或者是否有任何特定于数据库的问题?

CREATE TABLE BOOK(
ID INTEGER,
NAME VARCHAR2(50)
);

ALTER TABLE BOOK ADD PRIMARY KEY(ID);

1 个答案:

答案 0 :(得分:1)

如果没有元素,Hibernate使用分配作为默认生成器策略。在这种情况下,您的应用程序会分配实体的ID。 如果你想hibernate将负责自动生成id,那么你应该使用GeneratedValue或任何其他id生成策略

@Id
@GeneratedValue(strategy = GenerationType.AUTO)

here是一些例子

你的id类型是int

private int id;

当你第一次插入值时,jvm将分配id默认值0,所以hibernate很容易插入id为0的值, 现在当你再次尝试插入值因为没有id生成器策略然后再次jvm设置id默认值0并且当hibernate尝试插入id为0的值然后它抛出 ConstraintViolationException 异常,因为id为0值已存在于数据库中。 因此,如果您希望hibernate自动为您的实体分配Id,您可以使用jpa特定的@GeneratedValue策略(AUTO / IDENTITY / SEQUENCE / TABLE) 或另一个hibernate策略,它将负责为实体分配id

      increment
      sequence
      hilo
      native
      identity
      seqhilo
      uuid
      guid
      select
      foreign
      sequence-identity