summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAnssi Kääriäinen <akaariai@gmail.com>2012-07-15 14:41:05 +0300
committerAnssi Kääriäinen <akaariai@gmail.com>2012-08-12 21:52:52 +0300
commit59a655988ee95e4b4e4646cebea88b620d8fcdd2 (patch)
tree0226231d1c22d01a4059892e4a20c60cb68c0cb9
parent5513480fe1e616c236a7629072b4317e334b9b4b (diff)
Fixed #13844 -- Avoid converting unknown db values to float
This patch removes an unconditional float(value) conversion from db backend default convert_values() method. This can cause problems when aggregating over character fields for example. In addition, Oracle and SQLite already return the bare value from their convert_values(). In the long term the converting should be done by fields, and the fields should then call database backend specific converters when needed. The current setup is inflexible for 3rd party fields. Thanks to Merlijn van Deen for the original patch.
-rw-r--r--django/db/backends/__init__.py12
-rw-r--r--tests/regressiontests/aggregation_regress/tests.py12
2 files changed, 18 insertions, 6 deletions
diff --git a/django/db/backends/__init__.py b/django/db/backends/__init__.py
index 9606245162..9f64cfc5f0 100644
--- a/django/db/backends/__init__.py
+++ b/django/db/backends/__init__.py
@@ -878,19 +878,19 @@ class BaseDatabaseOperations(object):
return self.year_lookup_bounds(value)
def convert_values(self, value, field):
- """Coerce the value returned by the database backend into a consistent type that
- is compatible with the field type.
+ """
+ Coerce the value returned by the database backend into a consistent type
+ that is compatible with the field type.
"""
internal_type = field.get_internal_type()
if internal_type == 'DecimalField':
return value
- elif internal_type and internal_type.endswith('IntegerField') or internal_type == 'AutoField':
+ elif (internal_type and (internal_type.endswith('IntegerField')
+ or internal_type == 'AutoField')):
return int(value)
elif internal_type in ('DateField', 'DateTimeField', 'TimeField'):
return value
- # No field, or the field isn't known to be a decimal or integer
- # Default to a float
- return float(value)
+ return value
def check_aggregate_support(self, aggregate_func):
"""Check that the backend supports the provided aggregate
diff --git a/tests/regressiontests/aggregation_regress/tests.py b/tests/regressiontests/aggregation_regress/tests.py
index e24eb43b87..b9f3ab27eb 100644
--- a/tests/regressiontests/aggregation_regress/tests.py
+++ b/tests/regressiontests/aggregation_regress/tests.py
@@ -866,3 +866,15 @@ class AggregationTests(TestCase):
['Peter Norvig'],
lambda b: b.name
)
+
+ def test_type_conversion(self):
+ # The database backend convert_values function should not try to covert
+ # CharFields to float. Refs #13844.
+ from django.db.models import CharField
+ from django.db import connection
+ testData = 'not_a_float_value'
+ testField = CharField()
+ self.assertEqual(
+ connection.ops.convert_values(testData, testField),
+ testData
+ )