2017-09-17 48 views
1

我有以下HBM實體類:Hibernate的一對一的映射問題 - 級聯功能不能正常工作

  1. Train.java,Ticket.java,Booking.java,Passenger.java

我有預訂和門票之間的關係。 請找休眠POJO類如下:

@Entity 
@Table(name = "TICKET_MASTER") 
@Cache(usage = CacheConcurrencyStrategy.READ_WRITE) 
public class Ticket implements Serializable { 

@Transient 
private static final long serialVersionUID = 1L; 

@Id 
@GeneratedValue(strategy = GenerationType.AUTO, generator = "TICKET_SEQ") 
@SequenceGenerator(name = "TICKET_SEQ", sequenceName = "TICKET_SEQ", allocationSize = 1) 
@Column(name = "TICKET_ID", nullable = false) 
private Long ticketId; 

@Column(name = "TICKET_NO", nullable = false) 
private String ticketNo; 

@OneToOne(mappedBy = "ticket",cascade=CascadeType.ALL) 
private Booking booking; 

@OneToMany(fetch = FetchType.LAZY, mappedBy = "ticket") 
private Set<Passenger> passengers; 

@ManyToOne(cascade = CascadeType.ALL) 
@JoinColumn(name = "TRAIN_ID", nullable = false) 
private Train train; 

//getters & setters 
} 

@Entity 
@Table(name = "BOOKING_MASTER") 
@Cache(usage = CacheConcurrencyStrategy.READ_WRITE) 
public class Booking extends RMSEntity { 
    private static final long serialVersionUID = 1L; 

    @Id 
    @GeneratedValue(strategy = GenerationType.AUTO, generator = "BOOKING_SEQ") 
    @SequenceGenerator(name = "BOOKING_SEQ", sequenceName = "BOOKING_SEQ", allocationSize = 1) 
    @Column(name = "BOOKING_ID", nullable = false) 
    private Long bookingId; 

    @Column(name = "BOOKING_NO", nullable = false) 
    private String bookingNo; 

    @OneToOne 
    @JoinColumn(name = "TICKET_ID", referencedColumnName = "TICKET_ID") 
    private Ticket ticket; 

    //gettres & setters 
} 

我ommitting的POJO類乘客和列車,因爲上面的兩個類之間發生的問題。

請在下面找到我的業務層代碼:

@Transactional(readOnly = false, propagation = Propagation.REQUIRED, rollbackFor = { Throwable.class }) 
@Override 
public void saveBookingDetails(PassengerDTO passengerDTO) { 
    BeanUtils.copyProperties(passengerDTO, passenger);*/ 
    Train train = getDaoProvider().getTrainDao().find(passengerDTO.getTrainId()); 
    Ticket ticket = new Ticket(); 
    ticket.setTicketId((long) (Math.random() * 100)); 
    String ticketNo = UUID.randomUUID().toString().split("-")[0]; 
    ticket.setTicketNo(ticketNo); 
    Booking booking = new Booking(); 
    String bookingNo = UUID.randomUUID().toString().split("-")[0]; 
    booking.setBookingId((long)(Math.random() * 100)); 
    booking.setBookingNo(bookingNo); 
    ticket.setBooking(booking); 
    ticket.setTrain(train); 
    getDaoProvider().getTicketDao().saveOrUpdate(ticket); 
    } 

我得到以下異常:

Caused By: org.hibernate.exception.ConstraintViolationException: could not execute batch 
at org.hibernate.exception.internal.SQLStateConversionDelegate.convert(SQLStateConversionDelegate.java:112) 
at org.hibernate.exception.internal.StandardSQLExceptionConverter.convert(StandardSQLExceptionConverter.java:42) 
at org.hibernate.engine.jdbc.spi.SqlExceptionHelper.convert(SqlExceptionHelper.java:111) 
at org.hibernate.engine.jdbc.batch.internal.BatchingBatch.performExecution(BatchingBatch.java:119) 
at org.hibernate.engine.jdbc.batch.internal.BatchingBatch.doExecuteBatch(BatchingBatch.java:97) 
Truncated. see log file for complete stacktrace 
Caused By: java.sql.BatchUpdateException: ORA-01400: cannot insert NULL into ("SYSTEM"."TICKET_MASTER"."BOOKING_ID") 

at oracle.jdbc.driver.OraclePreparedStatement.executeBatch(OraclePreparedStatement.java:12296) 
at oracle.jdbc.driver.OracleStatementWrapper.executeBatch(OracleStatementWrapper.java:246) 
at weblogic.jdbc.wrapper.PreparedStatement.executeBatch(PreparedStatement.java:197) 
at org.hibernate.engine.jdbc.batch.internal.BatchingBatch.performExecution(BatchingBatch.java:110) 
at org.hibernate.engine.jdbc.batch.internal.BatchingBatch.doExecuteBatch(BatchingBatch.java:97) 
Truncated. see log file for complete stacktrace 

我使用Spring的ORM休眠功能。

回答

0

在雙向關係中,您應該從各方到另一方有一個參考,您錯過了在預訂中注入票證,與列車相同。

Booking booking = new Booking(); 
booking.setTicket(ticket); 
train.setTicket(ticket); 
String bookingNo = UUID.randomUUID().toString().split("-")[0]; 

另一件事,因爲你在預訂ID是自動生成的,你不應該設置id,Hibernate會採取持久性分配的ID給它的照顧

String bookingNo = UUID.randomUUID().toString().split("-")[0];// this line should be removed 
booking.setBookingId((long)(Math.random() * 100));//this line should be removed 
ticket.setTicketId((long) (Math.random() * 100));//this line should be removed 

同時刪除線設置ID爲門票也是如此。

此外,由於您使用序列生成你需要指定類型爲順序不會自動

@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "BOOKING_SEQ") 
+0

no.It不是解決方案,它沒有工作。 –

+0

@SumitGhosh現在檢查 –

+0

不,我認爲級聯存在一些問題。 我已經做出了你所提出的所有更改,但仍然有相同的錯誤 –

0

mappedBy意味着,因爲這是關係這邊還沒有接觸到級聯(處理數據)關係對象而不是所有者實體。 如果您想要級聯該實體,則應該擁有該實體,因此您可以刪除mappedBy參數並在@OneToOne(cascade = CascadeType.All下添加@JoinColumn