Мне любопытно, можно ли добавить сущность и ее связь с другой, просто получив прокси методом getReference
.
Мои сущности выглядят следующим образом
@Entity
@Table(name = "BOOK")
@NamedQuery(name="Book.findAll", query = "SELECT b from Book as b LEFT JOIN b.discountList as d where d.endingDate is null")
public class Book {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "ID")
private Long bookId;
@Column(name = "TITLE")
private String title;
@Column(name = "ISBN")
private String isbn;
@Column(name = "DESCRIPTION")
@Type(type="text")
private String description;
@Column(name = "PUBLISHING_DATE")
private Date publishingDate;
@Column(name = "BASE_PRICE")
private BigDecimal basePrice;
@ManyToMany(fetch = FetchType.LAZY, cascade = {
CascadeType.MERGE,
CascadeType.PERSIST
})
@JoinTable(name = "BOOK_TO_DISCOUNT",
joinColumns = {@JoinColumn(name = "book_id")},
inverseJoinColumns = {@JoinColumn(name = "discount_id")})
private Set<Discount> discountList;
}
@Entity
@Table(name = "DISCOUNT")
public class Discount {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "ID")
private Long discountId;
@Column(name = "NAME")
private String name;
@Column(name = "RATE")
private Integer rate;
@Column(name = "START_DATE")
private Timestamp startingDate;
@Column(name = "END_DATE")
private Timestamp endingDate;
@ManyToMany(fetch = FetchType.LAZY,
mappedBy = "discountList")
private Set<Book> bookList;
}
Моя цель - добавить скидку, относящуюся к некоторым книгам, поэтому мне нужно вставить новую рекламу в таблицу DISCOUNT
и добавить отношение в таблицу BOOK_TO_DISCOUNT
.
Прямо сейчас я делаю это действие следующим образом:
Set<Book> listOfLinkedBooks = discountData.getIdsOfBooksCoveredByThisDiscount().stream()
.map(idOfBook -> entityManager.find(Book.class, idOfBook)).collect(Collectors.toSet());
Discount discount = new Discount(discountData.getDiscountId(),
discountData.getName(),
discountData.getRate(),
discountData.getStartingDate(),
discountData.getEndingDate(),
listOfLinkedBooks);
listOfLinkedBooks.forEach(a -> {
Optional.ofNullable(a.getDiscountList()).orElseGet(Collections::emptySet)
.add(discount);
});
entityManager.merge(discount);
Недостаток этого решения заключается в использовании метода find, потому что hibernate извлекает все данные объекта, когда объект нужен только для отображения связи, связанной с ним. С точки зрения БД, для этой операции достаточно идентификатора. Есть ли шанс сделать это с использованием метода getRelation?
Другим решением для оптимизации этой операции является добавление нового отношения вручную, поэтому я должен создать сущность для таблицы BOOK_TO_DISCOUNT
и просто вставить новое отношение вручную. Я воспринимаю эту идею как грязную, и реализация предполагает создание большего количества сущностей. Вот почему я спрашиваю об использовании getRelation в этом случае.