Hibernate provides a support for inter-system paging mechanism, so that the bottom no matter what kind of database are able to interface with a unified operation of pagination. Such as the following code is to start from the first 500 out 100 records:
Query q = session.createQuery ( "from FooBar as f");
q.setFirstResult (500);
q.setMaxResults (100);
List l = q.list ();
Well, the bottom of how Hibernate pagination implementation of it? Hibernate under the SQL statement Query assembled at the place are org.hibernate.loader.Loader category prepareQueryStatement methods, pagination support for the code in this section can be found:
if (useLimit)
(
sql = dialect.getLimitString (
sql.trim (), / / use of trim () here is ugly?
useOffset? getFirstRow (selection): 0,
getMaxOrLimit (selection, dialect)
);
)
Dialect of the calls here getLimitString Ways to get the pagination statement on different platforms.
At MySQLDialect in implementation are as follows getLimitString methods:
public String getLimitString (String sql, boolean hasOffset)
(
return new StringBuffer (sql.length () +20)
. append (sql)
. append (hasOffset? "limit?,?": "limit?")
. toString ();
)
This is a dedicated MySQL pagination statement, let's look at Oracle9Dialect:
public String getLimitString (String sql, boolean hasOffset) (
sql = sql.trim ();
boolean isForUpdate = false;
if (sql.toLowerCase (). endsWith ( "for update")) (
sql = sql.substring (0, sql.length () -11);
isForUpdate = true;
)
StringBuffer pagingSelect = new StringBuffer (sql.length () +100);
if (hasOffset) (
pagingSelect.append ( "select * from (select row_ .*, rownum rownum_ from (");
)
else (
pagingSelect.append ( "select * from (");
)
pagingSelect.append (sql);
if (hasOffset) (
pagingSelect.append ( ") row_ where rownum <=?) where rownum_>?");
)
else (
pagingSelect.append ( ") where rownum <=?");
)
if (isForUpdate) (
pagingSelect.append ( "for update");
)
return pagingSelect.toString ();
)
Oracle using nested query layer 3 combines RowNum to achieve pagination, which at Oracle are on the best way, because if only one or two-tier query RowNum should not support the order by.
In addition Interbase, PostgreSQL, HSQL, etc. also support pagination on grammar level, the specific implementation can view the corresponding Dialect implementation. If the database does not support pagination of the SQL statement, then if the database support scrollable cursors, then Hibernate will adopt the use of the absolute method of ResultSet inquiries directly to the starting point; otherwise use the loop through step by step to move to one rs.next to query Data Service:
final int firstRow = getFirstRow (selection);
if (firstRow! = 0)
(
if (getFactory (). getSettings (). isScrollableResultSetsEnabled ())
(
/ / We can go straight to the first required row
rs.absolute (firstRow);
)
else
(
/ / We need to step through the rows one row at a time (slow)
for (int m = 0; m <firstRow; m + +) rs.next ();
)
)
Shows that the use of Hibernate, conducting inquiries on the operation of pagination, is a very large flexibility, Hibernate will first try to use a specific database pagination sql, if useless, to try Scrollable, if we do not support the use of Scrollable again rset.next () Mobile solution. In this way, that takes care of pagination query performance, while at the same time to ensure that the code in different database portability between.








Responses to “hibernate pagination”