diff options
| author | Tom Christie | 2012-12-15 20:40:41 +0000 |
|---|---|---|
| committer | Tom Christie | 2012-12-15 20:40:41 +0000 |
| commit | 35f72cecb199e1790a42fadd6037da43cdd5a05a (patch) | |
| tree | 2cc58cb4f1b03de86eca022fccb59b5174b0b716 | |
| parent | 1d24d1fc5928d32372e700907aa71cf887b16ba9 (diff) | |
| download | django-rest-framework-35f72cecb199e1790a42fadd6037da43cdd5a05a.tar.bz2 | |
Fix model validation exclusions. Fixes #500. Fixes #506.
| -rw-r--r-- | docs/topics/release-notes.md | 1 | ||||
| -rw-r--r-- | rest_framework/fields.py | 1 | ||||
| -rw-r--r-- | rest_framework/serializers.py | 25 | ||||
| -rw-r--r-- | rest_framework/tests/models.py | 2 |
4 files changed, 16 insertions, 13 deletions
diff --git a/docs/topics/release-notes.md b/docs/topics/release-notes.md index 4ea393af..6d7dc348 100644 --- a/docs/topics/release-notes.md +++ b/docs/topics/release-notes.md @@ -8,6 +8,7 @@ ### Master +* Bugfix: Ensure read-only fields don't have model validation applied. * Bugfix: Fix hyperlinked fields in paginated results. ### 2.1.9 diff --git a/rest_framework/fields.py b/rest_framework/fields.py index da588082..d3ef8f77 100644 --- a/rest_framework/fields.py +++ b/rest_framework/fields.py @@ -32,6 +32,7 @@ def is_simple_callable(obj): class Field(object): + read_only = True creation_counter = 0 empty = '' type_name = None diff --git a/rest_framework/serializers.py b/rest_framework/serializers.py index 8026205e..1d93f777 100644 --- a/rest_framework/serializers.py +++ b/rest_framework/serializers.py @@ -128,17 +128,6 @@ class BaseSerializer(Field): """ return {} - def get_excluded_fieldnames(self): - """ - Returns the fieldnames that should not be validated. - """ - excluded_fields = list(self.opts.exclude) - if self.opts.fields: - for field in self.fields.keys() + self.get_default_fields().keys(): - if field not in list(self.opts.fields) + excluded_fields: - excluded_fields.append(field) - return excluded_fields - def get_fields(self): """ Returns the complete set of fields for the object as a dict. @@ -491,6 +480,18 @@ class ModelSerializer(Serializer): except KeyError: return ModelField(model_field=model_field, **kwargs) + def get_validation_exclusions(self): + """ + Return a list of field names to exclude from model validation. + """ + cls = self.opts.model + opts = get_concrete_model(cls)._meta + exclusions = [field.name for field in opts.fields + opts.many_to_many] + for field_name, field in self.fields.items(): + if field_name in exclusions and not field.read_only: + exclusions.remove(field_name) + return exclusions + def restore_object(self, attrs, instance=None): """ Restore the model instance. @@ -515,7 +516,7 @@ class ModelSerializer(Serializer): instance = self.opts.model(**attrs) try: - instance.full_clean(exclude=list(self.get_excluded_fieldnames())) + instance.full_clean(exclude=self.get_validation_exclusions()) except ValidationError, err: self._errors = err.message_dict return None diff --git a/rest_framework/tests/models.py b/rest_framework/tests/models.py index 428bf130..e2b287d0 100644 --- a/rest_framework/tests/models.py +++ b/rest_framework/tests/models.py @@ -61,7 +61,7 @@ class BasicModel(RESTFrameworkModel): class SlugBasedModel(RESTFrameworkModel): text = models.CharField(max_length=100) - slug = models.SlugField(max_length=32, blank=True) + slug = models.SlugField(max_length=32) class DefaultValueModel(RESTFrameworkModel): |
