Why nullable = false causes FK to embed in the insert, but without it it does an update to install FK in JPA / Hibernate

Using JPA annotations and hibernation, we recently ran into the onetomany unidirectional display problem, which looked like this:

@Entity public class FooOrder extends AbstractEntity{ @OneToMany(cascade= CascadeType.ALL,orphanRemoval = true) @JoinColumn(name = "fooOrderId") private List<FooItem> fooItems = new ArrayList<FooItem>(); public void addFooItem(foo item properties here) { fooItems.add(fooItem); } } @Entity public class FooItem extends AbstractEntity { SomeRandomStuffButNoLinkToParent } 

Basically this test code:

 FooOrder fooOrder = new FooOrder(stuff here); fooOrder.addFooItem(foo item properties here); fooOrder = fooOrderRepository.save(fooOrder); 

When we run the tests, we get sql, which looks something like this:

 insert FooOrder(columns here) insert FooItem(columns here missing the FK to FooOrder) update FooItem set FooOrderFK to proper key. 

but if I set @JoinColumn(name = "activeOrderId", nullable = false) , then my sql looks something like this:

 insert FooOrder(columns here) insert FooItem(columns here with FK to FooOrder) 

Why does hibernate install FK through an update if it is NULL but sets it in the insert when it cannot be null?

+4
source share
1 answer

Well, if the foreign key is not zero

 insert FooOrder(columns here) insert FooItem(columns here with FK to FooOrder) 

This is the only way to actually perform inserts. So the real question is why this is not always done this way.

I believe that the way you use updates works at a time when the other will never work.

Suppose we have some kind of circular connection. A has a foreign key for B B has a foreign key for A if none of these foreign keys is NULL, it may not be possible to insert this. You cannot insert A first, because the foreign key for B cannot be null. The same goes for B.

Also note that my example may be too simple. This circular foreign key can be called by any number of tables.

So, inserting data first and then adding foreign keys is just a way that works in this more complex scenario. Your non-zero constraint forces Hibernate to take a different path. For the case of input by default, insert first, and adding keys is simply better.

0
source

Source: https://habr.com/ru/post/1483612/


All Articles