chiranjeevi
chiranjeevi

Reputation: 73

unable to update objects of one to one relation in hibernate

I have relation as shown bellow:

    @Entity
@Table(name = "ORDER_", catalog = "smartorder")
public class Order implements Serializable {

    /**
     * serial version id
     */
    private static final long serialVersionUID = 13875615L;

    @Id
    @Column(name = "ORDER_ID", unique = true, nullable = false)
    @SequenceGenerator(name = "ORDER_ID_GEN", sequenceName = "ORDER_ID_SEQ")
    @GeneratedValue(generator = "ORDER_ID_GEN")
    private long orderId;

    @OneToOne(cascade = CascadeType.ALL, fetch = FetchType.LAZY)
    @JoinColumn(name = "INVOICE_ID", referencedColumnName = "INVOICE_ID")
    private Invoice invoice;

    // setters and getters
}





@Entity
@Table(name = "INVOICE_")
public class Invoice implements Serializable {
    /**
     * serial version id
     */
    private static final long serialVersionUID = 13875612L;

    @Id
    @Column(name = "INVOICE_ID", unique = true, nullable = false)
    @SequenceGenerator(name = "INVOICE_ID_GEN", sequenceName = "INVOICE_ID_SEQ")
    @GeneratedValue(generator = "INVOICE_ID_GEN")
    private int invoiceId;

    @OneToOne(cascade = CascadeType.ALL, fetch = FetchType.LAZY)
    @JoinColumn(name = "ORDER_ID", referencedColumnName = "ORDER_ID")
    private Order order;

    @Column(name = "SUB_TOTAL", precision = 6, nullable = false)
    private double subTotal;

    @Column(name = "SERVICE_TAX", precision = 6, nullable = false)
    private double serviceTax;

    @Column(name = "VAT", precision = 6, nullable = false)
    private double vat;

    @Column(name = "SURCHAARGE", precision = 6, nullable = false)
    private double surChaarge;

    @Column(name = "GRAND_TOTAL", precision = 6, nullable = false)
    private double grandTotal;


    //setters and getters
}

I am able to save the records properly. But when i am trying to update orders objects by setting invoice object to order object then the order object is nor persisting only invoice object is persisting.

Order o = getSession().load(Order.class,1L);
o.setInvoice(new Invoice(.........));
getSession().update(o);

in console I am able to see one SQL statement only, insert into INVOICE_ (DISCOUNT, GRAND_TOTAL, ORDER_ID, ROUNDING, SERVICE_TAX, SUB_TOTAL, SURCHAARGE, VAT) values (?, ?, ?, ?, ?, ?, ?, ?)

Invoice Id is not getting update in Order table :(

Can anyone suggest whats the issue is.

Thanks in advance.....

Upvotes: 1

Views: 3144

Answers (2)

Volker Seibt
Volker Seibt

Reputation: 1536

This may depend on your unusual design.

With INVOICE_ID in ORDR_ and ORDER_ID in INVOICE_ you have both tables at the same time as parent and child of each other.

If your database uses foreign keys deleting and inserting will be hard.

You should use one type/table as parent, (e. g. Order, because it's normaly first) and the other as child (order_id will be in invoice_ table).

In your object model you can have both directions (see first example of http://docs.oracle.com/javaee/6/api/javax/persistence/OneToOne.html)

Upvotes: 2

Radim Köhler
Radim Köhler

Reputation: 123861

The issue is incorrect scenario in which you used your Entities/Tables and the one-to-one mapping style. The concept of One-To-One does not corresponed with your current design of both tables and entities.

Please, try to read more about one-to-one here: The concept for one-to-one mapping. Explain the mapping

And mostly take a deep look here: Hibernate – One-to-One example (Annotation), where you can find examples of the one-to-one mapping.

If you really would like to continue with one-to-one mapping you have to:

  1. Remove the "INVOICE_ID" column from the "INVOICE_" table (surprising but a fact)
  2. make the "ORDER_ID" column in the "INVOICE_" table as a primary key (another fact)
  3. change the mapping of the Invoice entity to be more submissive (driven by Order entity)

Example of changes of the Invoice mapping:

// just a draft, to give you idea about the 
// "submissive" side mapping.
// All the ID stuff of the Invoice is driven by its 
// "Master" - Order
@GenericGenerator(name = "generator", strategy = "foreign", 
parameters = @Parameter(name = "property", value = "order"))
@Id
@GeneratedValue(generator = "generator")
@Column(name = "ORDER_ID", unique = true, nullable = false)
public Integer getOrderId() {
    return this.orderId;
}

public void setOrderId(Integer orderId) {
    this.orderId = orderId;
}

@OneToOne(fetch = FetchType.LAZY)
@PrimaryKeyJoinColumn
public Order getOrder() {
    return this.order;
}

Please, take it as a draft, to show how different the one-to-one concept is.

Upvotes: 1

Related Questions