| 1 | Index: django/db/models/base.py
|
|---|
| 2 | ===================================================================
|
|---|
| 3 | --- django/db/models/base.py (revision 15796)
|
|---|
| 4 | +++ django/db/models/base.py (working copy)
|
|---|
| 5 | @@ -677,23 +677,25 @@
|
|---|
| 6 | # Gather a list of checks for fields declared as unique and add them to
|
|---|
| 7 | # the list of checks.
|
|---|
| 8 |
|
|---|
| 9 | - fields_with_class = [(self.__class__, self._meta.local_fields)]
|
|---|
| 10 | - for parent_class in self._meta.parents.keys():
|
|---|
| 11 | - fields_with_class.append((parent_class, parent_class._meta.local_fields))
|
|---|
| 12 | + fields_with_class = []
|
|---|
| 13 | + for field in self._meta.fields:
|
|---|
| 14 | + name, model_class, junk, junk = self._meta.get_field_by_name(field.name)
|
|---|
| 15 | + if model_class == None:
|
|---|
| 16 | + model_class = self.__class__
|
|---|
| 17 | + fields_with_class.append((model_class, field))
|
|---|
| 18 |
|
|---|
| 19 | - for model_class, fields in fields_with_class:
|
|---|
| 20 | - for f in fields:
|
|---|
| 21 | - name = f.name
|
|---|
| 22 | - if name in exclude:
|
|---|
| 23 | - continue
|
|---|
| 24 | - if f.unique:
|
|---|
| 25 | - unique_checks.append((model_class, (name,)))
|
|---|
| 26 | - if f.unique_for_date and f.unique_for_date not in exclude:
|
|---|
| 27 | - date_checks.append((model_class, 'date', name, f.unique_for_date))
|
|---|
| 28 | - if f.unique_for_year and f.unique_for_year not in exclude:
|
|---|
| 29 | - date_checks.append((model_class, 'year', name, f.unique_for_year))
|
|---|
| 30 | - if f.unique_for_month and f.unique_for_month not in exclude:
|
|---|
| 31 | - date_checks.append((model_class, 'month', name, f.unique_for_month))
|
|---|
| 32 | + for model_class, f in fields_with_class:
|
|---|
| 33 | + name = f.name
|
|---|
| 34 | + if name in exclude:
|
|---|
| 35 | + continue
|
|---|
| 36 | + if f.unique:
|
|---|
| 37 | + unique_checks.append((model_class, (name,)))
|
|---|
| 38 | + if f.unique_for_date and f.unique_for_date not in exclude:
|
|---|
| 39 | + date_checks.append((model_class, 'date', name, f.unique_for_date))
|
|---|
| 40 | + if f.unique_for_year and f.unique_for_year not in exclude:
|
|---|
| 41 | + date_checks.append((model_class, 'year', name, f.unique_for_year))
|
|---|
| 42 | + if f.unique_for_month and f.unique_for_month not in exclude:
|
|---|
| 43 | + date_checks.append((model_class, 'month', name, f.unique_for_month))
|
|---|
| 44 | return unique_checks, date_checks
|
|---|
| 45 |
|
|---|
| 46 | def _perform_unique_checks(self, unique_checks):
|
|---|
| 47 | Index: tests/modeltests/validation/models.py
|
|---|
| 48 | ===================================================================
|
|---|
| 49 | --- tests/modeltests/validation/models.py (revision 15796)
|
|---|
| 50 | +++ tests/modeltests/validation/models.py (working copy)
|
|---|
| 51 | @@ -27,6 +27,12 @@
|
|---|
| 52 | unique_integerfield = models.IntegerField(unique=True)
|
|---|
| 53 | non_unique_field = models.IntegerField()
|
|---|
| 54 |
|
|---|
| 55 | +class SubUniqueFieldsModel(UniqueFieldsModel):
|
|---|
| 56 | + pass
|
|---|
| 57 | +
|
|---|
| 58 | +class SubSubUniqueFieldsModel(SubUniqueFieldsModel):
|
|---|
| 59 | + pass
|
|---|
| 60 | +
|
|---|
| 61 | class CustomPKModel(models.Model):
|
|---|
| 62 | my_pk_field = models.CharField(max_length=100, primary_key=True)
|
|---|
| 63 |
|
|---|
| 64 | Index: tests/modeltests/validation/test_unique.py
|
|---|
| 65 | ===================================================================
|
|---|
| 66 | --- tests/modeltests/validation/test_unique.py (revision 15796)
|
|---|
| 67 | +++ tests/modeltests/validation/test_unique.py (working copy)
|
|---|
| 68 | @@ -7,7 +7,8 @@
|
|---|
| 69 | from django.utils import unittest
|
|---|
| 70 |
|
|---|
| 71 | from models import (CustomPKModel, UniqueTogetherModel, UniqueFieldsModel,
|
|---|
| 72 | - UniqueForDateModel, ModelToValidate, Post, FlexibleDatePost)
|
|---|
| 73 | + UniqueForDateModel, ModelToValidate, Post, FlexibleDatePost,
|
|---|
| 74 | + SubSubUniqueFieldsModel)
|
|---|
| 75 |
|
|---|
| 76 |
|
|---|
| 77 | class GetUniqueCheckTests(unittest.TestCase):
|
|---|
| 78 | @@ -149,3 +150,9 @@
|
|---|
| 79 | self.fail("unique_for_month checks shouldn't trigger when the associated DateField is None.")
|
|---|
| 80 | except:
|
|---|
| 81 | self.fail("unique_for_month checks shouldn't explode when the associated DateField is None.")
|
|---|
| 82 | +
|
|---|
| 83 | + def test_sub_sub_unique_check(self):
|
|---|
| 84 | + unique_sub_sub = SubSubUniqueFieldsModel.objects.create(unique_charfield="unique_charfield", unique_integerfield=1, non_unique_field=2)
|
|---|
| 85 | + unique_sub_sub2 = SubSubUniqueFieldsModel(unique_charfield="unique_charfield", unique_integerfield=1, non_unique_field=2)
|
|---|
| 86 | + self.assertRaises(ValidationError, unique_sub_sub2.full_clean)
|
|---|
| 87 | +
|
|---|