diff --git a/django/db/backends/__init__.py b/django/db/backends/__init__.py index 3f012eadff..e6776a19b7 100644 --- a/django/db/backends/__init__.py +++ b/django/db/backends/__init__.py @@ -109,3 +109,13 @@ class BaseDatabaseOperations(object): column. """ return cursor.lastrowid + + def limit_offset_sql(self, limit, offset=None): + """ + Returns a LIMIT/OFFSET SQL clause, given a limit and optional offset. + """ + # 'LIMIT 40 OFFSET 20' + sql = "LIMIT %s" % limit + if offset and offset != 0: + sql += " OFFSET %s" % offset + return sql diff --git a/django/db/backends/ado_mssql/base.py b/django/db/backends/ado_mssql/base.py index 02795fd0c1..19dd7278d2 100644 --- a/django/db/backends/ado_mssql/base.py +++ b/django/db/backends/ado_mssql/base.py @@ -100,13 +100,6 @@ dictfetchone = util.dictfetchone dictfetchmany = util.dictfetchmany dictfetchall = util.dictfetchall -def get_limit_offset_sql(limit, offset=None): - # TODO: This is a guess. Make sure this is correct. - sql = "LIMIT %s" % limit - if offset and offset != 0: - sql += " OFFSET %s" % offset - return sql - def get_random_function_sql(): return "RAND()" diff --git a/django/db/backends/dummy/base.py b/django/db/backends/dummy/base.py index e6547fa765..334e5146b7 100644 --- a/django/db/backends/dummy/base.py +++ b/django/db/backends/dummy/base.py @@ -43,7 +43,6 @@ quote_name = complain dictfetchone = complain dictfetchmany = complain dictfetchall = complain -get_limit_offset_sql = complain get_random_function_sql = complain get_pk_default_value = complain get_max_name_length = ignore diff --git a/django/db/backends/mysql/base.py b/django/db/backends/mysql/base.py index a9ca8e046a..259034b4bb 100644 --- a/django/db/backends/mysql/base.py +++ b/django/db/backends/mysql/base.py @@ -77,6 +77,13 @@ class DatabaseOperations(BaseDatabaseOperations): def fulltext_search_sql(self, field_name): return 'MATCH (%s) AGAINST (%%s IN BOOLEAN MODE)' % field_name + def limit_offset_sql(self, limit, offset=None): + # 'LIMIT 20,40' + sql = "LIMIT " + if offset and offset != 0: + sql += "%s," % offset + return sql + str(limit) + class DatabaseWrapper(BaseDatabaseWrapper): ops = DatabaseOperations() @@ -155,12 +162,6 @@ dictfetchone = util.dictfetchone dictfetchmany = util.dictfetchmany dictfetchall = util.dictfetchall -def get_limit_offset_sql(limit, offset=None): - sql = "LIMIT " - if offset and offset != 0: - sql += "%s," % offset - return sql + str(limit) - def get_random_function_sql(): return "RAND()" diff --git a/django/db/backends/mysql_old/base.py b/django/db/backends/mysql_old/base.py index 8497cc5983..5de2cbfda8 100644 --- a/django/db/backends/mysql_old/base.py +++ b/django/db/backends/mysql_old/base.py @@ -87,6 +87,13 @@ class DatabaseOperations(BaseDatabaseOperations): def fulltext_search_sql(self, field_name): return 'MATCH (%s) AGAINST (%%s IN BOOLEAN MODE)' % field_name + def limit_offset_sql(self, limit, offset=None): + # 'LIMIT 20,40' + sql = "LIMIT " + if offset and offset != 0: + sql += "%s," % offset + return sql + str(limit) + class DatabaseWrapper(BaseDatabaseWrapper): ops = DatabaseOperations() @@ -174,12 +181,6 @@ dictfetchone = util.dictfetchone dictfetchmany = util.dictfetchmany dictfetchall = util.dictfetchall -def get_limit_offset_sql(limit, offset=None): - sql = "LIMIT " - if offset and offset != 0: - sql += "%s," % offset - return sql + str(limit) - def get_random_function_sql(): return "RAND()" diff --git a/django/db/backends/oracle/base.py b/django/db/backends/oracle/base.py index f35586cbbc..df153378f0 100644 --- a/django/db/backends/oracle/base.py +++ b/django/db/backends/oracle/base.py @@ -62,6 +62,11 @@ class DatabaseOperations(BaseDatabaseOperations): cursor.execute('SELECT %s_sq.currval FROM dual' % sq_name) return cursor.fetchone()[0] + def limit_offset_sql(self, limit, offset=None): + # Limits and offset are too complicated to be handled here. + # Instead, they are handled in django/db/backends/oracle/query.py. + return "" + class DatabaseWrapper(BaseDatabaseWrapper): ops = DatabaseOperations() @@ -178,11 +183,6 @@ def get_field_cast_sql(db_type): else: return "%s%s" -def get_limit_offset_sql(limit, offset=None): - # Limits and offset are too complicated to be handled here. - # Instead, they are handled in django/db/backends/oracle/query.py. - return "" - def get_random_function_sql(): return "DBMS_RANDOM.RANDOM" diff --git a/django/db/backends/postgresql/base.py b/django/db/backends/postgresql/base.py index 1642a51d7e..4926ddf8d1 100644 --- a/django/db/backends/postgresql/base.py +++ b/django/db/backends/postgresql/base.py @@ -131,12 +131,6 @@ def dictfetchall(cursor): "Returns all rows from a cursor as a dict" return cursor.dictfetchall() -def get_limit_offset_sql(limit, offset=None): - sql = "LIMIT %s" % limit - if offset and offset != 0: - sql += " OFFSET %s" % offset - return sql - def get_random_function_sql(): return "RANDOM()" diff --git a/django/db/backends/postgresql_psycopg2/base.py b/django/db/backends/postgresql_psycopg2/base.py index 9ba5c8a170..f8d8765e92 100644 --- a/django/db/backends/postgresql_psycopg2/base.py +++ b/django/db/backends/postgresql_psycopg2/base.py @@ -85,12 +85,6 @@ dictfetchone = util.dictfetchone dictfetchmany = util.dictfetchmany dictfetchall = util.dictfetchall -def get_limit_offset_sql(limit, offset=None): - sql = "LIMIT %s" % limit - if offset and offset != 0: - sql += " OFFSET %s" % offset - return sql - def get_random_function_sql(): return "RANDOM()" diff --git a/django/db/backends/sqlite3/base.py b/django/db/backends/sqlite3/base.py index b1d7dc8db1..75c753ef22 100644 --- a/django/db/backends/sqlite3/base.py +++ b/django/db/backends/sqlite3/base.py @@ -115,12 +115,6 @@ def _sqlite_extract(lookup_type, dt): return None return str(getattr(dt, lookup_type)) -def get_limit_offset_sql(limit, offset=None): - sql = "LIMIT %s" % limit - if offset and offset != 0: - sql += " OFFSET %s" % offset - return sql - def get_random_function_sql(): return "RANDOM()" diff --git a/django/db/models/query.py b/django/db/models/query.py index faf469f1bf..df3be74632 100644 --- a/django/db/models/query.py +++ b/django/db/models/query.py @@ -555,7 +555,7 @@ class _QuerySet(object): # LIMIT and OFFSET clauses if self._limit is not None: - sql.append("%s " % backend.get_limit_offset_sql(self._limit, self._offset)) + sql.append("%s " % connection.ops.limit_offset_sql(self._limit, self._offset)) else: assert self._offset is None, "'offset' is not allowed without 'limit'"