Browse Source

Fixed #27148 -- Fixed ModelMultipleChoiceField crash with invalid UUID.

Tim Graham 8 years ago
parent
commit
2f9861d823

+ 3 - 6
django/db/models/fields/__init__.py

@@ -2371,20 +2371,17 @@ class UUIDField(Field):
         if value is None:
             return None
         if not isinstance(value, uuid.UUID):
-            try:
-                value = uuid.UUID(value)
-            except AttributeError:
-                raise TypeError(self.error_messages['invalid'] % {'value': value})
+            value = self.to_python(value)
 
         if connection.features.has_native_uuid_field:
             return value
         return value.hex
 
     def to_python(self, value):
-        if value and not isinstance(value, uuid.UUID):
+        if not isinstance(value, uuid.UUID):
             try:
                 return uuid.UUID(value)
-            except ValueError:
+            except (AttributeError, ValueError):
                 raise exceptions.ValidationError(
                     self.error_messages['invalid'],
                     code='invalid',

+ 4 - 4
tests/model_fields/test_uuid.py

@@ -40,17 +40,17 @@ class TestSaveLoad(TestCase):
         self.assertIsNone(loaded.field)
 
     def test_pk_validated(self):
-        with self.assertRaisesMessage(TypeError, 'is not a valid UUID'):
+        with self.assertRaisesMessage(exceptions.ValidationError, 'is not a valid UUID'):
             PrimaryKeyUUIDModel.objects.get(pk={})
 
-        with self.assertRaisesMessage(TypeError, 'is not a valid UUID'):
+        with self.assertRaisesMessage(exceptions.ValidationError, 'is not a valid UUID'):
             PrimaryKeyUUIDModel.objects.get(pk=[])
 
     def test_wrong_value(self):
-        with self.assertRaisesMessage(ValueError, 'badly formed hexadecimal UUID string'):
+        with self.assertRaisesMessage(exceptions.ValidationError, 'is not a valid UUID'):
             UUIDModel.objects.get(field='not-a-uuid')
 
-        with self.assertRaisesMessage(ValueError, 'badly formed hexadecimal UUID string'):
+        with self.assertRaisesMessage(exceptions.ValidationError, 'is not a valid UUID'):
             UUIDModel.objects.create(field='not-a-uuid')
 
 

+ 6 - 0
tests/model_forms/test_uuid.py

@@ -1,6 +1,7 @@
 from __future__ import unicode_literals
 
 from django import forms
+from django.core.exceptions import ValidationError
 from django.test import TestCase
 
 from .models import UUIDPK
@@ -27,3 +28,8 @@ class ModelFormBaseTest(TestCase):
         msg = "The UUIDPK could not be changed because the data didn't validate."
         with self.assertRaisesMessage(ValueError, msg):
             form.save()
+
+    def test_model_multiple_choice_field_uuid_pk(self):
+        f = forms.ModelMultipleChoiceField(UUIDPK.objects.all())
+        with self.assertRaisesMessage(ValidationError, "'invalid_uuid' is not a valid UUID."):
+            f.clean(['invalid_uuid'])