From 53a1205dd03703e6f93bbf7bcb2686c617638242 Mon Sep 17 00:00:00 2001 From: Vadim Date: Fri, 24 Jun 2016 15:04:18 +0300 Subject: [PATCH 1/3] Fix partial update for the ListSerializer. --- rest_framework/serializers.py | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/rest_framework/serializers.py b/rest_framework/serializers.py index 3fcc85c3b7..9f06f5a4f4 100644 --- a/rest_framework/serializers.py +++ b/rest_framework/serializers.py @@ -533,6 +533,10 @@ def __init__(self, *args, **kwargs): super(ListSerializer, self).__init__(*args, **kwargs) self.child.bind(field_name='', parent=self) + def bind(self, field_name, parent): + super(ListSerializer, self).bind(field_name, parent) + self.partial = self.parent.partial + def get_initial(self): if hasattr(self, 'initial_data'): return self.to_representation(self.initial_data) @@ -584,6 +588,9 @@ def to_internal_value(self, data): }) if not self.allow_empty and len(data) == 0: + if self.partial: + raise SkipField() + message = self.error_messages['empty'] raise ValidationError({ api_settings.NON_FIELD_ERRORS_KEY: [message] From c0f4dfd8f33819dab001b5b23da148cc7830b1ba Mon Sep 17 00:00:00 2001 From: Vadim Date: Wed, 29 Jun 2016 09:48:31 +0300 Subject: [PATCH 2/3] Add tests for the ListSerializer for the TestSerializerPartialUsage. Additional fix partial update for the ListSerializer. --- rest_framework/serializers.py | 2 +- tests/test_serializer_lists.py | 214 +++++++++++++++++++++++++++++++++ 2 files changed, 215 insertions(+), 1 deletion(-) diff --git a/rest_framework/serializers.py b/rest_framework/serializers.py index 9f06f5a4f4..c4057dc46f 100644 --- a/rest_framework/serializers.py +++ b/rest_framework/serializers.py @@ -588,7 +588,7 @@ def to_internal_value(self, data): }) if not self.allow_empty and len(data) == 0: - if self.partial: + if self.parent and self.partial: raise SkipField() message = self.error_messages['empty'] diff --git a/tests/test_serializer_lists.py b/tests/test_serializer_lists.py index 607ddba04a..740197c280 100644 --- a/tests/test_serializer_lists.py +++ b/tests/test_serializer_lists.py @@ -318,3 +318,217 @@ class MultipleChoiceSerializer(serializers.Serializer): assert serializer.is_valid() assert serializer.validated_data == {} assert serializer.errors == {} + + def test_allow_empty_true(self): + class ListSerializer(serializers.Serializer): + update_field = serializers.IntegerField() + store_field = serializers.IntegerField() + + instance = [ + {'update_field': 11, 'store_field': 12}, + {'update_field': 21, 'store_field': 22}, + ] + + serializer = ListSerializer(instance, data=[], partial=True, many=True) + assert serializer.is_valid() + assert serializer.validated_data == [] + assert serializer.errors == [] + + def test_update_allow_empty_true(self): + class ListSerializer(serializers.Serializer): + update_field = serializers.IntegerField() + store_field = serializers.IntegerField() + + instance = [ + {'update_field': 11, 'store_field': 12}, + {'update_field': 21, 'store_field': 22}, + ] + input_data = [{'update_field': 31}, {'update_field': 41}] + updated_data_list = [ + {'update_field': 31, 'store_field': 12}, + {'update_field': 41, 'store_field': 22}, + ] + + serializer = ListSerializer( + instance, data=input_data, partial=True, many=True) + assert serializer.is_valid() + + for index, data in enumerate(serializer.validated_data): + for key, value in data.items(): + assert value == updated_data_list[index][key] + + assert serializer.errors == [] + + def test_allow_empty_false(self): + class ListSerializer(serializers.Serializer): + update_field = serializers.IntegerField() + store_field = serializers.IntegerField() + + instance = [ + {'update_field': 11, 'store_field': 12}, + {'update_field': 21, 'store_field': 22}, + ] + + serializer = ListSerializer( + instance, data=[], allow_empty=False, partial=True, many=True) + assert not serializer.is_valid() + assert serializer.validated_data == [] + assert len(serializer.errors) == 1 + assert serializer.errors['non_field_errors'] == [u'This list may not be empty.'] + + def test_update_allow_empty_false(self): + class ListSerializer(serializers.Serializer): + update_field = serializers.IntegerField() + store_field = serializers.IntegerField() + + instance = [ + {'update_field': 11, 'store_field': 12}, + {'update_field': 21, 'store_field': 22}, + ] + input_data = [{'update_field': 31}, {'update_field': 41}] + updated_data_list = [ + {'update_field': 31, 'store_field': 12}, + {'update_field': 41, 'store_field': 22}, + ] + + serializer = ListSerializer( + instance, data=input_data, allow_empty=False, partial=True, many=True) + assert serializer.is_valid() + + for index, data in enumerate(serializer.validated_data): + for key, value in data.items(): + assert value == updated_data_list[index][key] + + assert serializer.errors == [] + + def test_as_field_allow_empty_true(self): + class ListSerializer(serializers.Serializer): + update_field = serializers.IntegerField() + store_field = serializers.IntegerField() + + class Serializer(serializers.Serializer): + extra_field = serializers.IntegerField() + list_field = ListSerializer(many=True) + + instance = { + 'extra_field': 1, + 'list_field': [ + {'update_field': 11, 'store_field': 12}, + {'update_field': 21, 'store_field': 22}, + ] + } + + serializer = Serializer(instance, data={}, partial=True) + assert serializer.is_valid() + assert serializer.validated_data == {} + assert serializer.errors == {} + + def test_udate_as_field_allow_empty_true(self): + class ListSerializer(serializers.Serializer): + update_field = serializers.IntegerField() + store_field = serializers.IntegerField() + + class Serializer(serializers.Serializer): + extra_field = serializers.IntegerField() + list_field = ListSerializer(many=True) + + instance = { + 'extra_field': 1, + 'list_field': [ + {'update_field': 11, 'store_field': 12}, + {'update_field': 21, 'store_field': 22}, + ] + } + input_data_1 = {'extra_field': 2} + input_data_2 = { + 'list_field': [ + {'update_field': 31}, + {'update_field': 41}, + ] + } + + # data_1 + serializer = Serializer(instance, data=input_data_1, partial=True) + assert serializer.is_valid() + assert len(serializer.validated_data) == 1 + assert serializer.validated_data['extra_field'] == 2 + assert serializer.errors == {} + + # data_2 + serializer = Serializer(instance, data=input_data_2, partial=True) + assert serializer.is_valid() + + updated_data_list = [ + {'update_field': 31, 'store_field': 12}, + {'update_field': 41, 'store_field': 22}, + ] + for index, data in enumerate(serializer.validated_data['list_field']): + for key, value in data.items(): + assert value == updated_data_list[index][key] + + assert serializer.errors == {} + + def test_as_field_allow_empty_false(self): + class ListSerializer(serializers.Serializer): + update_field = serializers.IntegerField() + store_field = serializers.IntegerField() + + class Serializer(serializers.Serializer): + extra_field = serializers.IntegerField() + list_field = ListSerializer(many=True, allow_empty=False) + + instance = { + 'extra_field': 1, + 'list_field': [ + {'update_field': 11, 'store_field': 12}, + {'update_field': 21, 'store_field': 22}, + ] + } + + serializer = Serializer(instance, data={}, partial=True) + assert serializer.is_valid() + assert serializer.validated_data == {} + assert serializer.errors == {} + + def test_update_as_field_allow_empty_false(self): + class ListSerializer(serializers.Serializer): + update_field = serializers.IntegerField() + store_field = serializers.IntegerField() + + class Serializer(serializers.Serializer): + extra_field = serializers.IntegerField() + list_field = ListSerializer(many=True, allow_empty=False) + + instance = { + 'extra_field': 1, + 'list_field': [ + {'update_field': 11, 'store_field': 12}, + {'update_field': 21, 'store_field': 22}, + ] + } + input_data_1 = {'extra_field': 2} + input_data_2 = { + 'list_field': [ + {'update_field': 31}, + {'update_field': 41}, + ] + } + updated_data_list = [ + {'update_field': 31, 'store_field': 12}, + {'update_field': 41, 'store_field': 22}, + ] + + # data_1 + serializer = Serializer(instance, data=input_data_1, partial=True) + assert serializer.is_valid() + assert serializer.errors == {} + + # data_2 + serializer = Serializer(instance, data=input_data_2, partial=True) + assert serializer.is_valid() + + for index, data in enumerate(serializer.validated_data['list_field']): + for key, value in data.items(): + assert value == updated_data_list[index][key] + + assert serializer.errors == {} From c752e9618fedc6eb3e103cf8740742ff3e731899 Mon Sep 17 00:00:00 2001 From: Vadim Date: Wed, 29 Jun 2016 10:21:28 +0300 Subject: [PATCH 3/3] Fix test for py32-django18. --- tests/test_serializer_lists.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/test_serializer_lists.py b/tests/test_serializer_lists.py index 740197c280..a7955d83c7 100644 --- a/tests/test_serializer_lists.py +++ b/tests/test_serializer_lists.py @@ -374,7 +374,7 @@ class ListSerializer(serializers.Serializer): assert not serializer.is_valid() assert serializer.validated_data == [] assert len(serializer.errors) == 1 - assert serializer.errors['non_field_errors'] == [u'This list may not be empty.'] + assert serializer.errors['non_field_errors'][0] == 'This list may not be empty.' def test_update_allow_empty_false(self): class ListSerializer(serializers.Serializer): pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy