410013796724260
• Webmoney
R335386147728
Z369087728698
Чтение объектов в HibernateИзвлечение информации из базы данных в виде коллекции объектов Hibernate может выполнять с использованием :
В данной статье будут рассмотрены различные способы чтения данных без фильтрации и с фильтрацией на основе примера, представленного на странице связанных сущностей, где описаны структуры таблиц базы данных и связанные сущности. Т.е. на этой странице будет продолжено повествование о связанных сущностях с точки зрения их извлечения из БД. Чтение данных с использованием HQLHibernate может использовать свой мощный язык запросов Hibernate Query Language, который очень похож на родной SQL. В сравнении с SQL, HQL полностью объектно-ориентирован и использует понятия наследования, полиформизма и связывания. Подробное описание языка HQL будет представлено в ближайшие дни. Следующий метод демонстрирует чтение набора данных пользователей User. HQL запрос формируется с использованием наименования класса. После этого создается запрос Query методом createQuery(sql) объекта сессии и извлекаются данные методом list ().
private void readUsers_HQL()
{
System.out.println("\n\nЧтение записей : HQL");
// HQL (Hibernate Query Language)
String sql = "From " + User.class.getSimpleName();
System.out.println("sql = " + sql);
List<User> users = session.createQuery(sql).list();
System.out.println("users.size = " + users.size());
for (Iterator<User> it = users.iterator(); it.hasNext();) {
User user = (User) it.next();
System.out.println(user.toString());
}
}
Запросы Hibernate и данные выводятся в консоль (см. ниже). Обратите внимание, что при создании запроса Query методом createQuery(sql) Hibernate формирует соответствующий запрос чтения списка пользователей. Второй запрос по чтению связанных записей Auto формируется и выполняется уже при распечатке пользователя, т.е. при обращении к связанной сущности (lazy загрузка).
Чтение записей : HQL
sql = From User
Hibernate: select user0_.id as id1_0_, user0_.login as login2_0_,
user0_.name as name3_0_
from USERS user0_
users.size = 2
Hibernate: select autos0_.user_id as user_id3_0_0_,
autos0_.aid as aid1_1_0_,
autos0_.aid as aid1_1_1_,
autos0_.name as name2_1_1_,
autos0_.user_id as user_id3_1_1_
from autos autos0_ where autos0_.user_id=?
User {id = 50, login = 'ivan, name = 'Иван',
autos =[
Auto {id = 55, name = 'Volvo, user_id = 50},
Auto {id = 56, name = 'Skoda, user_id = 50}]}
User {id = 51, login = 'serg, name = 'Сергей', autos =[]}
Чтение данных с использованием native SQL-запросаHibernate позволяет выполнять native SQL-запросы с использованием org.hibernate.SQLQuery, который создается методом createSQLQuery(String) объекта сессии. Но необходимо учитывать, что в этом случае можно потерять все преимущества HQL (ассоциации, кэширование). Следующий код демонстрирует использование нативного запроса для получения коллекции пользователей.
private void readUsers_SQL()
{
System.out.println("\n\nЧтение записей : SQL");
// Использование native SQL query
String sql = "select ID, LOGIN, NAME from USERS";
Query query = session.createSQLQuery(sql).addEntity(User.class);
List<User> users = query.list();
System.out.println("users.size = " + users.size());
for (Iterator<User> it = users.iterator(); it.hasNext();) {
User user = (User) it.next();
System.out.println(user.toString());
}
}
При формировании объекта Query был добавлен класс User.class методом addEntity, в результате чего метод list объекта Query вернул коллекцию пользователей List<User>. Объект org.hibernate.SQLQuery расширяет возможности двух классов org.hibernate.Query, org.hibernate.SynchronizeableQuery и является потокобезопасным. Набор прочитанных данных выводится в консоль, представленную ниже. Обратите внимание, что также, как и для HQL, при использовании native SQL второй запрос чтения связанных сущностей формируется по мере необходимости, т.е. при обращении.
Чтение записей : SQL
Hibernate: select ID, LOGIN, NAME from USERS
users.size = 2
Hibernate: select autos0_.user_id as user_id3_0_0_, \
autos0_.aid as aid1_1_0_, \
autos0_.aid as aid1_1_1_, \
autos0_.name as name2_1_1_, \
autos0_.user_id as user_id3_1_1_ \
from autos autos0_
where autos0_.user_id=?
User {id = 50, login = 'ivan, name = 'Иван',
autos =[
Auto {id = 55, name = 'Volvo, user_id = 50},
Auto {id = 56, name = 'Skoda, user_id = 50}]}
User {id = 51, login = 'serg, name = 'Сергей', autos =[]}
Чтение набора объектов, List<Object[]>При выполнении сложных нативных SQL-запросов для извлечения определенной информации можно сущности к объекту org.hibernate.Query не подключать. В этом случае метод list() объекта Query вернет коллекцию объектов List<Object[]>, как это показано в следующем коде. После этого список объектов можно парсить и использовать по назначению.
private void readObjects()
{
System.out.println("\n\nЧтение объектов");
String sql = "select ID, LOGIN, NAME from USERS";
Query query = session.createSQLQuery(sql);
List<Object[]> rows = query.list();
for(Object[] row : rows) {
User user = new User();
user.setId (Integer.valueOf(row[0].toString()));
user.setLogin (row[1].toString());
user.setName (row[2].toString());
System.out.println(user.toString());
}
}
В результате выполнения метода readObjects() в консоль будет выведена информация без подгрузки связанных сущностей Auto :
Чтение объектов
Hibernate: select ID, LOGIN, NAME from USERS
User {id = 50, login = 'ivan, name = 'Иван', autos =[]}
User {id = 51, login = 'serg, name = 'Сергей', autos =[]}
Использование org.hibernate.CriteriaИнтерфейс org.hibernate.Criteria представляет собой объектно-ориентированный запрос на выборку в отношении конкретной сущности и позволяет выполнять запросы без написания SQL кода. Для создания экземпляров Criteria используется класс Session, который выступает в качестве фабрики. Следующий метод выполняет чтение списка пользователей с именем "Иван". При создании Criteria используется метод createCriteria объекта сессии Session, которому в качестве параметра передается класс объекта. Объект criteria имеет метод add, позволяющий выполнить фильтрацию данных. Для этого методу add необходимо передать параметр ограничения Restrictions с определенными условиями.
private void readUsers_criteria()
{
System.out.println("\n\nCriteria API");
Criteria criteria;
criteria = session.createCriteria(User.class)
.add(Restrictions.eq("name", "Иван"));
List<User> users = criteria.list();
for (Iterator<User> it = users.iterator(); it.hasNext();) {
User user = (User) it.next();
System.out.println(user.toString());
}
}
Результат выполнения метода readUsers_criteria выведен в консоль :
Criteria API
Hibernate: select this_.id as id1_0_0_, \
this_.login as login2_0_0_, \
this_.name as name3_0_0_ \
from USERS this_ \
where this_.name=?
Hibernate: select autos0_.user_id as user_id3_0_0_, \
autos0_.aid as aid1_1_0_, \
autos0_.aid as aid1_1_1_, \
autos0_.name as name2_1_1_, \
autos0_.user_id as user_id3_1_1_
from autos autos0_
where autos0_.user_id=?
User {id = 50, login = 'ivan, name = 'Иван',
autos =[
Auto {id = 55, name = 'Volvo, user_id = 50},
Auto {id = 56, name = 'Skoda, user_id = 50}]}
Подробное описание org.hibernate.Criteria с примерами представлено здесь. Фильтрация данных в HibernateДля чтения данных с фильтрацией можно использовать как org.hibernate.Criteria, представленный выше, так и native SQL. Метод readUsers демонстрирует извлечение отдельной записи пользователя, у которой логин соответствует значению параметра метода "filter" :
private void readUsers(final String filter)
{
String sql;
// Использование native SQL query с условием
sql = "select ID, LOGIN, NAME from USERS where login like :log";
Query query = session.createSQLQuery (sql) // SQL
.addEntity (User.class) // Class
.setParameter ("log", filter); // Condition
List<User> users = query.list();
System.out.println("users.size = " + users.size());
for (Iterator<User> it = users.iterator(); it.hasNext();){
User user = (User) it.next();
System.out.println(user.toString());
}
}
При создании объекта SQLQuery (native SQL) была добавлена сущность (addEntity) и определен параметр "log" (setParameter). В консоли увидим следующую информацию :
Hibernate: select ID, LOGIN, NAME from USERS where login like ?
users.size = 1
User {id = 50, login = 'ivan, name = 'Иван',
autos =[
Auto {id = 55, name = 'Volvo, user_id = 50},
Auto {id = 56, name = 'Skoda, user_id = 50}]}
Чтение отдельной записиЕсли известен идентификатор сущности Id, то объект сессии Session позволяет прочитать запись. Для этого можно использовать метод get или load. Отличия методов get и load представлено на странице Hibernate в вопросах и ответах. Следующий код демонстрирует чтение записи пользователя с идентификатором Id=51 :
User user = (User) session.load(User.class, 51);
if (user != null)
System.out.println("\n\n" + user.toString());
Скачать примерИсходный код рассмотренного на странице примера использования различных способов Hibernate для чтения данных в виде проекта Eclipse, включающий все необходимые библиотеки hibernate, можно скачать здесь (8.02 Mб). |
