1: M отношения в Hibernate и каскадных операциях - PullRequest
2 голосов
/ 08 апреля 2010

Таблица SUBCOURSE, ссылки COURSE КУРС (идентификатор, имя) SUBCOURSE (id, идентификатор_курса, имя)

Итак, 1: М.

Hibernate генерирует для курса:

    @OneToMany(fetch = FetchType.LAZY, mappedBy = "course", cascade = CascadeType.ALL)
    public Set getSubCourses() {
        return this.subCourses;
    }

для Subcourse генерирует

    @ManyToOne(fetch = FetchType.LAZY)
    @JoinColumn(name = "course_id", nullable = false)
    public Course getCourse() {
        return this.course;
    }

Теперь проблема в том, что каскадирование работает не так, как ожидалось. Я хочу создать коллекцию объектов SubCourse (Set), заполнить ее, а затем привязать его к setSubCourses () объекта Course. Затем просто сохраните объект курса.

Хотя, имея вещь ManyToOne в таблице Subcourses, мне нужно вручную setCourse () перед добавлением в коллекцию по каждому объекту. Если я этого не сделаю, Возникает исключительная ситуация при сохранении объекта Course с его коллекцией.

Что вы можете мне порекомендовать?

P.S. а может это часть игры? установить родительский объект каждого ребенка вручную?

Ответы [ 2 ]

5 голосов
/ 09 апреля 2010

Похоже, это часть игры. Цитата из книги Hibernate (имеется в виду пример, где Item - родитель, а Bid - дочерний):

Если вы звоните только по номеру anItem.getBids().add(bid), изменения не вносятся постоянно! Вы получаете то, что хотите, только если другая сторона, aBid.setItem(anItem), установлена ​​правильно. Это согласуется с поведением в Java без Hibernate: если связь является двунаправленным, вы должны создать ссылку с указателями на двух сторонах, а не только один. Это основная причина, почему мы рекомендуем удобные методы, такие как addBid() - они заботятся о двунаправленных ссылках в системе без контейнера. управляемые отношения.

Класс, указанный выше,

public class Item {
  ...
  private Set bids = new HashSet();
  public void setBids(Set bids) {
    this.bids = bids;
  }
  public Set getBids() {
    return bids;
  }
  public void addBid(Bid bid) {
    bid.setItem(this);
    bids.add(bid);
  }
  ...
}
0 голосов
/ 09 апреля 2010

При работе с двунаправленной ассоциацией необходимо правильно установить обе стороны ссылки (как описано в 1.2.6. Рабочие двунаправленные ссылки ). Я часто использую защитный подход, предложенный в документации:

Многие разработчики программы защищаются и создать методы управления ссылками для правильно установить обе стороны (например, в Person):

protected Set getEvents() {
    return events;
}

protected void setEvents(Set events) {
    this.events = events;
}

public void addToEvent(Event event) {
    this.getEvents().add(event);
    event.getParticipants().add(this);
}

public void removeFromEvent(Event event) {
    this.getEvents().remove(event);
    event.getParticipants().remove(this);
}

Методы get и set для Коллекция теперь защищена. это позволяет занятия в одном пакете и подклассы для доступа к методы, но мешает всем остальным от изменения коллекций непосредственно. Повторите шаги для Коллекция на другой стороне.

...