Spring JPA объединяет родительский объект из нового дочернего объекта

java spring hibernate spring-data-jpa

847 просмотра

1 ответ

700 Репутация автора

Я искал SO и не нашел подходящего решения для этого. Скажем, у меня есть родительский объект:

@Entity
public class Parent {
    @Id
    @GeneratedValue
    private int id;

    @OneToMany(mappedBy = "parent", cascade = CascadeType.REMOVE)
    private List<Child> childList;
}

И дочерний объект, внешний ключ которого связан с родительским объектом:

@Entity
public class Child {
    @Id
    @GeneratedValue
    private int id;

    @JoinColumn(name = "parentId")
    @ManyToOne(cascade = {CascadeType.PERSIST, CascadeType.MERGE})
    private Parent parent;

}

Мой сценарий немного особенный. Дочерняя сущность генерируется в огромном количестве каждый час, и мне нужно было бы сохранить их в базе данных. Эти дочерние объекты могут иметь одинаковых родителей, и связанный родительский объект может уже существовать в базе данных. Мое требование - сохранить все эти дочерние объекты без запроса управляемой родительской сущности из entityManager, и, если родительская сущность существует, просто объедините / обновите существующую. Такие как:

Child c = new Child();
// set some properties of child
Parent p = new Parent();
// set some properties from my data into the parent. The parent may already exists
child.setParent(p);
JpaRepo.saveAndFlush(child);// If parent already exists, merge with the existed parent object, otherwise, create new parent object.

Видимо, это не работает. Когда родительский объект не существует, он будет правильно создавать родительский объект и связываться с ним. Но если родительский объект уже существует, он выдаст исключение о дубликате ключа, и если я установлю Id родителя (используйте фиктивное значение, чтобы заставить его пройти через слияние), он выдаст исключение обособленного объекта сущности.

Из-за ограничений производительности я не могу загрузить родительский объект из базы данных, так как их слишком много. Так есть ли способ для JPA или базы данных автоматически объединить объект при нарушении первичного ключа?

Я использую MySQL, возможно ли использовать ON DUPLICATE KEY UPDATE?

Автор: LynxZh Источник Размещён: 18.07.2016 05:22

Ответы (1)


0 плюса

4217 Репутация автора

Это немного сложный персонал, который вы хотели бы получить. Если ленивая загрузка и т. Д. Не является вариантом (который я предпочитаю), я рекомендую Вам создать другую сущность:

@Entity
@Table(name = "sameAsTheOriginal")
public class ChildSaveObject {
    @Id
    @GeneratedValue
    private int id; //I think int will run out fast if there are a lot of objects but it is your choice. (Int max value: 2 147 483 647 is not that mutch) I prefer Long az id

    @Column(name = "parentId")
    private int parent; //note that You need to have the id of the parent object

    //Other properties...
}

В этом потоке вы должны проверить, существует ли родительский объект, и использовать ChildSaveObject, чтобы сохранить в нем вашего дополнительного потомка.

В большинстве случаев мне не очень нравятся сопоставления один ко многим, я думаю, что они являются просто корнями многих проблем. Тем не менее, если вы предпочитаете этот способ, я рекомендую использовать fetch = FetchType.LAZY и получить родительский объект (таким образом, он не будет загружать все дочерние элементы, которые вам не нужны).

Автор: Hash Размещён: 18.07.2016 08:50
Вопросы из категории :
32x32