JPA: Ссылочный столбец в дочерней сущности равен нулю при использовании однонаправленного @OneToMany - PullRequest
0 голосов
/ 04 февраля 2019

У меня есть два класса сущностей.

Order.java

@Entity
@Table(name = "order_table")
public class Order implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name = "id")
    private Long id;

    @Column(name = "name")
    private String name;

    @OneToMany(fetch = FetchType.EAGER, cascade = CascadeType.ALL, orphanRemoval = true)
    @JoinColumn(name = "order_id", referencedColumnName = "id", nullable = false, insertable=false, updatable=false)
    private Set<Item> items;

    // getters & setters & toString

Item.java

@Entity
@Table(name = "item")
public class Item implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name = "id")
    private Long id;

    @Column(name = "name")
    private String name;

    @Column(name = "order_id", nullable = false)
    private Long orderId;

    // getters & setters && toString

Я создал тестовый класс, подобный этому:

@Test
public void createOrderWithItems() {

    Item item = new Item();
    item.setName("Iron Man");

    Order order = new Order();
    order.setName("Toy");
    order.getItems().add(item);

    Order created = service.createOrder(order);

    Order orderById = service.getOrderById(order.getId());
    System.out.println("Created Order: " + orderById);

    Item itemById = service.getItemById(item.getId());
    System.out.println("Created item: " + itemById);


    Assert.notNull(created.getId(), "Order ID is Null");
}

Тест зеленыйно если вы проверите выходные данные, вы увидите, что поле orderId в классе Item равно нулю.

Created Order: Order{id=1, name='Toy', items=[Item{id=2, name='Iron Man', orderId=null}]}
Created item: Item{id=2, name='Iron Man', orderId=null}

Не JPA не обновляет этот столбец в БД автоматически?Является ли этот столбец избыточным?Если да, как я могу получить эту информацию из тестового кода?

1 Ответ

0 голосов
/ 04 февраля 2019

Вам необходимо явно указать orderId.

item.setOrderId(order.getId());
order.getItems().add(item);

Вы можете создать метод addItem(Item item) в своем классе Order и скрыть в нем эту логику.

Каскадное создание создастзапись в БД, но она не будет инициализировать поле.JPA-аннотации просто указывают провайдеру JPA, как выполнить сопоставление между сущностью и таблицей.

Кроме того, проверьте свои аннотации.@JoinColumn следует использовать в сущности, которой принадлежит отношение (соответствующая таблица имеет столбец в качестве внешнего ключа).Для получения подробных объяснений просмотрите верхний ответ на этот вопрос: В чем разница между @JoinColumn и mappedBy при использовании ассоциации JPA @OneToMany

...