Вам нужно понять две вещи.
Во-первых: когда вы говорите Select p from Profesor
, JPA выбирает только столбцы из таблицы Profesor и возвращает экземпляр Profesor, содержащий коллекцию студентов, которая еще не загружена. Он загружается лениво, когда вы впервые получаете доступ к коллекции. И когда он загружает коллекцию, он забывает, какой запрос вы использовали для загрузки профессора. То, что он загружает, является коллекцией студентов профессора. А поскольку у профессора много студентов, это все равно. Начальный запрос похож на
select p.* from Profesor inner join ...
Выполните его в SQL, и вы увидите, что он не загружает профессора и его ученика. Он загружает только профессора.
Второе: объект должен представлять данные в базе данных. Он не должен представлять результат запроса. Таким образом, собрание студентов в лице профессора - это всегда собрание всех студентов профессора.
Чтобы сделать то, что вы хотите, у вас есть несколько вариантов:
select p, s from Profesor inner join p.students s...
: это вернет массив, содержащий найденного профессора и найденного ученика.
- если ассоциация двунаправленная:
select s from Profesor p inner join p.students s ...
: это загрузит студента и отсылает его к профессору
- при использовании Hibernate, который нарушает спецификацию JPA в этой области:
select p from Profesor inner join fetch p.students...
: выборка заставляет hibernate загружать профессора и его учеников в одном запросе. Но поскольку вы добавили предложение where для студента, он загружает только подходящих студентов профессора.
Обратите внимание, что третье решение очень опасно, и я бы не советовал его использовать. Во-первых, потому что это не действительно JPQL. И что еще более важно, потому что код, загружающий сущность Professor, загруженную таким запросом, ожидает, что Professor.getStudents () вернет всех студентов профессора, а не только одного из них. Таким образом, он может отображать ложные результаты или изменять коллекцию и вызывать несогласованность в базе данных.