Ticket #7760: subquery_patch

File subquery_patch, 2.9 KB (added by henrybaxter, 16 years ago)

Subquery LIMIT and OFFSET

Line 
1Index: django/db/models/sql/query.py
2===================================================================
3--- django/db/models/sql/query.py (revision 7922)
4+++ django/db/models/sql/query.py (working copy)
5@@ -252,7 +252,7 @@
6
7 # This must come after 'select' and 'ordering' -- see docstring of
8 # get_from_clause() for details.
9- from_, f_params = self.get_from_clause()
10+ from_, f_params = self.get_from_clause(with_limits)
11
12 where, w_params = self.where.as_sql(qn=self.quote_name_unless_alias)
13 params = list(self.extra_select_params)
14@@ -283,7 +283,7 @@
15 if ordering:
16 result.append('ORDER BY %s' % ', '.join(ordering))
17
18- if with_limits:
19+ if self.outer_limits:
20 if self.high_mark is not None:
21 result.append('LIMIT %d' % (self.high_mark - self.low_mark))
22 if self.low_mark:
23@@ -502,7 +502,7 @@
24 return result, None
25 return result, aliases
26
27- def get_from_clause(self):
28+ def get_from_clause(self, with_limits):
29 """
30 Returns a list of strings that are joined together to go after the
31 "FROM" part of the query, as well as a list any extra parameters that
32@@ -517,6 +517,7 @@
33 qn = self.quote_name_unless_alias
34 qn2 = self.connection.ops.quote_name
35 first = True
36+ self.outer_limits = True
37 for alias in self.tables:
38 if not self.alias_refcount[alias]:
39 continue
40@@ -533,7 +534,25 @@
41 qn2(lhs_col), qn(alias), qn2(col)))
42 else:
43 connector = not first and ', ' or ''
44- result.append('%s%s%s' % (connector, qn(name), alias_str))
45+ where, w_params = self.where.as_sql(qn=self.quote_name_unless_alias)
46+ if not where and first and with_limits and (self.high_mark or self.low_mark) and len(self.tables) > 1:
47+ self.outer_limits = False
48+ result.append('(SELECT * FROM %s' % qn(name))
49+ if self.high_mark is not None:
50+ result.append('LIMIT %d' % (self.high_mark - self.low_mark))
51+ if self.low_mark:
52+ if self.high_mark is None:
53+ val = self.connection.ops.no_limit_value()
54+ if val:
55+ result.append('LIMIT %d' % val)
56+ result.append('OFFSET %d' % self.low_mark)
57+ my_alias = alias_str
58+ if not my_alias:
59+ my_alias = name
60+ result.append(') %s' % qn(my_alias))
61+ #assert False, result
62+ else:
63+ result.append('%s%s%s' % (connector, qn(name), alias_str))
64 first = False
65 for t in self.extra_tables:
66 alias, unused = self.table_alias(t)
Back to Top