Настройка связи Один-ко-Многим в Hibernate
Last updated: 11 мая 2025 г.Теперь настроим в нашем приложении связь 1-ко-Многим.
Создадим еще одну таблицу "Книги авторов"
, которая будет связана с таблицей author
. В одной таблице хранятся авторы, а в другой их книги.
У каждого автора много книг, но у каждой книги только один автор. То есть связь – один автор ко многим книгам.
При удалении автора должны удаляться и его книги из другой таблицы. При удалении книги его автор не должен удаляться. Сделаем это.
Создадим теперь с помощью sql запроса таблицу author_books
, в которой будут храниться книги авторов и которая будет связана с таблицей author
с помощью внешнего ключа author_id
.

Теперь создадим класс созданной только что таблицы author_books
. И настроим теперь связь между этим классом и классом Author
Теперь в классе таблицы author
настраиваем обратную связь с новым классом.
1package HibernateApps;
2
3import java.util.List;
4
5@Entity
6//это класс с таблицы author
7@Table (name = "author")
8public class Author {
9 @Id
10 @GeneratedValue(
11 strategy=GenerationType.IDENTITY
12 )
13 @Column(name="id")
14 private int id;
15 @Column(name="name")
16 private String authorName;
17 @OneToOne(cascade={CascadeType.ALL})
18 @JoinColumn(name="author_info_id")
19 private AuthorInfo authorInfo;
20 @OneToMany(fetch=FetchType.EAGER,
21 //О том что такое EAGER
22 //в следующем уроке.
23 mappedBy="author",
24 //Пускай будут включены
25 //все типы каскадных
26 //операций – CascadeType.ALL.
27 //При удалении
28 //автора пусть удаляются
29 //из БД и все его книги.
30 cascade = CascadeType.ALL)
31 //как видим многие книжки автора
32 //будут записываться в список.
33 private List<AuthorBooks> authorbooks;
34
35 public Author() {
36 }
37
38 public Author(String authorName) {
39 this.authorName = authorName;
40 }
41
42 public int getId() {
43 return id;
44 }
45
46 public void setId(int id) {
47 this.id = id;
48 }
49
50 public String getAuthorName() {
51 return authorName;
52 }
53
54 public void setAuthorName(
55 String authorName) {
56 this.authorName = authorName;
57 }
58
59 public AuthorInfo getAuthorInfo() {
60 return authorInfo;
61 }
62
63 public void setAuthorInfo(
64 AuthorInfo authorInfo) {
65 this.authorInfo = authorInfo;
66 }
67
68 //добавляем геттер сеттер для списка
69 public List<AuthorBooks> getAuthorBooks(){
70 return authorbooks;
71 }
72
73 public void setAuthorBooks(
74 List<AuthorBooks> authorbooks){
75 this.authorbooks = authorbooks;
76 }
77
78 @Override
79 public String toString() {
80 return "Author [id=" + id
81 + ", authorName="
82 + authorName
83 + ", authorInfo="
84 + authorInfo
85 + ", authorbooks="
86 + authorbooks + "]";
87 }
88}
В программе же создадим объект автора и три объекта книг, свяжем эти книги с объектом автора, и добавим эти все объекты в БД.
Потом извлечем из БД автора в объект автора. Вместе с автором также должны извлечься и связанные с ним книги, которые сохраняться в объекте автора.
Далее удалим одну книгу из БД через объект книги, который храниться в объекте автора. При этом связанный с этой книгой автор не должен удалиться из БД.
1package HibernateApps;
2
3import org.hibernate.Session;
4import org.hibernate.SessionFactory;
5import org.hibernate.cfg.Configuration;
6
7public class HibernateApp {
8
9 public static void main(String[] args) {
10 //Добавим AuthorBooks в sessionFactory.
11 SessionFactory sessionFactory =
12 new Configuration()
13 .configure("hibernate.cfg.xml")
14 .addAnnotatedClass(Author.class)
15 .addAnnotatedClass(AuthorInfo.class)
16 .addAnnotatedClass(AuthorBooks.class)
17 .buildSessionFactory();
18
19 Session session =
20 sessionFactory.getCurrentSession();
21
22 try {
23 session.beginTransaction();
24 //создадим объект Author
25 Author author = new Author("JJ Rouling");
26 //и добавим его в таблицу author
27 session.save(author);
28 //Теперь создадим три объекта книги.
29 //Это книги автора, которого мы только
30 //что добавили в БД.
31 AuthorBooks authorbook =
32 new AuthorBooks("Harry Potter 1");;
33 AuthorBooks authorbook1 =
34 new AuthorBooks("Harry Potter 2");
35 AuthorBooks authorbook2 =
36 new AuthorBooks("Harry Potter 3");
37 //поэтому связываем автора с книгами
38 authorbook.setAuthor(author);
39 authorbook1.setAuthor(author);
40 authorbook2.setAuthor(author);
41 //сохраняем книги в базу
42 session.save(authorbook);
43 session.save(authorbook1);
44 session.save(authorbook2);
45 //Закоммитим и начнем
46 //новую сессию и транзакцию.
47 session.getTransaction().commit();
48 session=sessionFactory.getCurrentSession();
49 session.beginTransaction();
50 //Извлечем только что добавленного в БД
51 //автора из БД. Вместе с ним извлекуться
52 //связанные с ним книги и будут храниться
53 //в объекте автора author1.
54
55 Author author1 = session.get(Author.class, 1);
56 //Можем их увидеть в консоли.
57 System.out.println(author1);
58
59 //Удалим первую книгу автора из БД.
60 //При удалении книги из БД автор
61 //этой книги из БД не удаляется
62 //как и было задумано.
63 session.delete(
64 author1.getAuthorBooks().get(0));
65 //Также удалить нужно первую книгу
66 //и из списка книг в объекте author1.
67 author1.getAuthorBooks().remove(0);
68
69 //Извлечем автора из БД уже с двумя
70 //книгами.
71 Author author2 =
72 session.get(Author.class, 1);
73 //Удалим теперь автора из БД.
74 //При удалении автора из БД
75 //удаляються и его книги из БД
76 //как и было задумано.
77 session.delete(author2);
78 //Извлечем автора из БД еще раз
79 //Не должно получиться так как мы
80 //его только что удалили из БД.
81 Author author3 =
82 session.get(Author.class, 1);
83 session.getTransaction().commit();
84 //Объект author2 должен содержать
85 //две книги после удаления одной из БД.
86 //Проверим это.
87 System.out.println(author2);
88 //Объект author3 должен быть пуст
89 //после удаления его из БД.
90 //Проверим это.
91 System.out.println(author3);
92
93 } catch (Exception e) {
94 session.getTransaction().rollback();
95 e.printStackTrace();
96 } finally {
97 session.close();
98 }
99 }
100}
И потом удалим автора из БД через объект автора. При этом связанные с этим автором книги тоже должны удалиться из БД.
Давайте запустим нашу программу.

Как видим, произошла вставка в БД четырех объектов, то есть автора и его книг.
После извлечения автора из БД можно увидеть в консоли, что он содержит в себе все книги, которые связаны с ним в БД.
После этого происходит запрос на удаление одной книги из БД через объект книги, который хранился в author1
.
Далее можно увидеть, что происходят запросы на удаление из БД остальных книг вместе с автором через объект author2
.
После этого можно увидеть содержимое объекта author2
. Можно увидеть, что в нем нет одной книги, она была удалена из БД. То есть удаление одной книги автора из БД через объект author1
прошло успешно.
После этого можно увидеть содержимое объекта author3
. В нем null поскольку все книги вместе с автором уже были удалены из БД через объект author2
.
Следующие уроки
Типы извлечения данных в Hibernate (fetch types)
19
мин.
Настройка связи Многие-ко-Многим в Hibernate приложении
20
мин.
Сборщик проектов Maven
17
мин.