Как стать автором
Обновить

Комментарии 12

Наследование на уровне SQL красиво и ИМХО правильно реализуется примерно так же, как оно физически реализовано в объектно-ориентированных языках программирования. Класс-родитель представляется в виде первой таблицы, класс-потомок представляется в виде второй таблицы с отношением один-к-одному к первой. Унаследованные поля/свойства хранит в первой таблице, новые — во второй.
Добрый день!
В принципе, Вы правы. Об этом как раз говорится здесь:
Стратегия №4 (JOINED) подойдет в случаях, когда требуются полиморфные запросы и ассоциации, но подклассы объявляют относительно много новых полей.

Другое дело, что если их нет, то нет и особого смысла выбирать «заточенную» под них стратегию JOINED, при наличии более выигрышных в плане производительности вариантов.

Странно, почему нет смешанной стратегии JOINED и SINGLE_TABLE. Родительская таблица содержит поля первичного ключа, дискриминатор и поля нагрузки. Дочерние таблицы — поля первичного ключа и поля своей нагрузки.


Как я понимаю, основной недостаток JOINED — когда и нас десятки классов в иерархии, соединяться будут все десятки таблиц только ради того, чтобы выяснить для каждой строки, откуда брать данные.

Как я понимаю, основной недостаток JOINED — когда и нас десятки классов в иерархии

Так и есть, но модель данных обычно не имеет зверских иерархий, там как правило один (а чаще, пожалуй, вообще ноль), ну максимум два уровня наследования.

Ну количество таблиц-то зависит не только от глубины дерева наследования, но и его ширины. У вас может быть один суперкласс и десятки его прямых потомков. Мне кажется, вполне не редкая ситуация, особенно, если в этом месте система предполагает расширяемость (добавление новых классов). И при каждой выборке объектов суперкласса придется джойнить все эти таблицы. Надо надеяться, в Hibernate есть оптимизации, когда он не джойнит заведомо ненужные "братские" таблицы, если выбираем какого-то потомка.

Мне лично не понятны не стратегии, а как дальше работать с наследуемыми entity.
Например, как определить Spring'овый JPA Repository для BillingDetails в данном случае?

Или как определить класс Payment со связью к BankAccount или CreditCard?
Добрый вечер!
Например, вот так:
image

Пример не связан с исходниками статьи, но суть понятна. Используя SpEL, указываете в Query нужную реализацию User'a, которая и будет выступать в качестве T.
Добрый вечер!
Бывает, но только в качестве фич конкретных СУБД:) На мой взгляд, при реализации лучше все-таки держать в голове вероятность смены провайдера.

Как насчет самого простого варианта?
"0. Не используйте наследование реализаций для объектов, отображаемых на базу данных."

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

А не надо менять опубликованные интерфейсы, это и без базы данных слишком дорого.

Зарегистрируйтесь на Хабре, чтобы оставить комментарий

Публикации