diff options
| author | Ian Kelly <ian.g.kelly@gmail.com> | 2010-09-16 19:53:41 +0000 |
|---|---|---|
| committer | Ian Kelly <ian.g.kelly@gmail.com> | 2010-09-16 19:53:41 +0000 |
| commit | 320c46999c44efdc31be9cc80d3a2d1bf5186f18 (patch) | |
| tree | 77c242a2be11e589678485456c60a7657e12f599 /django/db/models/sql | |
| parent | 763bcf8472e61ba09cc739086bb181822501efa4 (diff) | |
Fixed #14244: Allow lists of more than 1000 items to be used with the 'in' lookup in Oracle, by breaking them up into groups of 1000 items and ORing them together. Thanks to rlynch for the report and initial patch.
git-svn-id: http://code.djangoproject.com/svn/django/trunk@13859 bcc190cf-cafb-0310-a4f2-bffc1f526a37
Diffstat (limited to 'django/db/models/sql')
| -rw-r--r-- | django/db/models/sql/where.py | 21 |
1 files changed, 19 insertions, 2 deletions
diff --git a/django/db/models/sql/where.py b/django/db/models/sql/where.py index 72b2d4cc82..2427a528fb 100644 --- a/django/db/models/sql/where.py +++ b/django/db/models/sql/where.py @@ -2,6 +2,7 @@ Code to manage the creation and SQL rendering of 'where' constraints. """ import datetime +from itertools import repeat from django.utils import tree from django.db.models.fields import Field @@ -178,8 +179,24 @@ class WhereNode(tree.Node): raise EmptyResultSet if extra: return ('%s IN %s' % (field_sql, extra), params) - return ('%s IN (%s)' % (field_sql, ', '.join(['%s'] * len(params))), - params) + max_in_list_size = connection.ops.max_in_list_size() + if max_in_list_size and len(params) > max_in_list_size: + # Break up the params list into an OR of manageable chunks. + in_clause_elements = ['('] + for offset in xrange(0, len(params), max_in_list_size): + if offset > 0: + in_clause_elements.append(' OR ') + in_clause_elements.append('%s IN (' % field_sql) + group_size = min(len(params) - offset, max_in_list_size) + param_group = ', '.join(repeat('%s', group_size)) + in_clause_elements.append(param_group) + in_clause_elements.append(')') + in_clause_elements.append(')') + return ''.join(in_clause_elements), params + else: + return ('%s IN (%s)' % (field_sql, + ', '.join(repeat('%s', len(params)))), + params) elif lookup_type in ('range', 'year'): return ('%s BETWEEN %%s and %%s' % field_sql, params) elif lookup_type in ('month', 'day', 'week_day'): |
