mirror of
https://github.com/encode/django-rest-framework.git
synced 2025-01-23 15:54:16 +03:00
Fix #285
This commit is contained in:
parent
4fd8ab17a3
commit
52ba2e3333
|
@ -77,16 +77,15 @@ class UpdateModelMixin(object):
|
|||
self.object = None
|
||||
|
||||
serializer = self.get_serializer(data=request.DATA, instance=self.object)
|
||||
|
||||
if serializer.is_valid():
|
||||
if self.object is None:
|
||||
obj = serializer.object
|
||||
# TODO: Make ModelSerializers return regular instances,
|
||||
# not DeserializedObject
|
||||
if hasattr(obj, 'object'):
|
||||
obj = obj.object
|
||||
self.update_urlconf_attributes(serializer.object.object)
|
||||
# If PUT occurs to a non existant object, we need to set any
|
||||
# attributes on the object that are implicit in the URL.
|
||||
self.update_urlconf_attributes(serializer.object)
|
||||
self.object = serializer.save()
|
||||
return Response(serializer.data)
|
||||
|
||||
return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)
|
||||
|
||||
def update_urlconf_attributes(self, obj):
|
||||
|
|
|
@ -2,7 +2,6 @@ import copy
|
|||
import datetime
|
||||
import types
|
||||
from decimal import Decimal
|
||||
from django.core.serializers.base import DeserializedObject
|
||||
from django.db import models
|
||||
from django.utils.datastructures import SortedDict
|
||||
from rest_framework.compat import get_concrete_model
|
||||
|
@ -224,9 +223,6 @@ class BaseSerializer(Field):
|
|||
"""
|
||||
Serialize objects -> primatives.
|
||||
"""
|
||||
if isinstance(obj, DeserializedObject):
|
||||
obj = obj.object
|
||||
|
||||
if isinstance(obj, dict):
|
||||
return dict([(key, self.to_native(val))
|
||||
for (key, val) in obj.items()])
|
||||
|
@ -383,23 +379,30 @@ class ModelSerializer(Serializer):
|
|||
"""
|
||||
Restore the model instance.
|
||||
"""
|
||||
self.m2m_data = {}
|
||||
|
||||
if instance:
|
||||
for key, val in attrs.items():
|
||||
setattr(instance, key, val)
|
||||
return DeserializedObject(instance)
|
||||
return instance
|
||||
|
||||
m2m_data = {}
|
||||
for field in self.opts.model._meta.many_to_many:
|
||||
if field.name in attrs:
|
||||
m2m_data[field.name] = attrs.pop(field.name)
|
||||
return DeserializedObject(self.opts.model(**attrs), m2m_data)
|
||||
self.m2m_data[field.name] = attrs.pop(field.name)
|
||||
return self.opts.model(**attrs)
|
||||
|
||||
def save(self):
|
||||
def save(self, save_m2m=True):
|
||||
"""
|
||||
Save the deserialized object and return it.
|
||||
"""
|
||||
self.object.save()
|
||||
return self.object.object
|
||||
|
||||
if self.m2m_data and save_m2m:
|
||||
for accessor_name, object_list in self.m2m_data.items():
|
||||
setattr(self.object, accessor_name, object_list)
|
||||
self.m2m_data = {}
|
||||
|
||||
return self.object
|
||||
|
||||
|
||||
class HyperlinkedModelSerializerOptions(ModelSerializerOptions):
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
from django.test import TestCase
|
||||
from django.test.client import RequestFactory
|
||||
from django.utils import simplejson as json
|
||||
from rest_framework import generics, status
|
||||
from rest_framework.tests.models import BasicModel
|
||||
from rest_framework import generics, serializers, status
|
||||
from rest_framework.tests.models import BasicModel, Comment
|
||||
|
||||
|
||||
factory = RequestFactory()
|
||||
|
@ -223,3 +223,36 @@ class TestInstanceView(TestCase):
|
|||
self.assertEquals(response.data, {'id': 1, 'text': 'foobar'})
|
||||
updated = self.objects.get(id=1)
|
||||
self.assertEquals(updated.text, 'foobar')
|
||||
|
||||
|
||||
# Regression test for #285
|
||||
|
||||
class CommentSerializer(serializers.ModelSerializer):
|
||||
class Meta:
|
||||
model = Comment
|
||||
exclude = ('created',)
|
||||
|
||||
|
||||
class CommentView(generics.ListCreateAPIView):
|
||||
serializer_class = CommentSerializer
|
||||
model = Comment
|
||||
|
||||
|
||||
class TestCreateModelWithAutoNowAddField(TestCase):
|
||||
def setUp(self):
|
||||
self.objects = Comment.objects
|
||||
self.view = CommentView.as_view()
|
||||
|
||||
def test_create_model_with_auto_now_add_field(self):
|
||||
"""
|
||||
Regression test for #285
|
||||
|
||||
https://github.com/tomchristie/django-rest-framework/issues/285
|
||||
"""
|
||||
content = {'email': 'foobar@example.com', 'content': 'foobar'}
|
||||
request = factory.post('/', json.dumps(content),
|
||||
content_type='application/json')
|
||||
response = self.view(request).render()
|
||||
self.assertEquals(response.status_code, status.HTTP_201_CREATED)
|
||||
created = self.objects.get(id=1)
|
||||
self.assertEquals(created.content, 'foobar')
|
||||
|
|
|
@ -83,3 +83,11 @@ class TaggedItem(RESTFrameworkModel):
|
|||
class Bookmark(RESTFrameworkModel):
|
||||
url = models.URLField()
|
||||
tags = GenericRelation(TaggedItem)
|
||||
|
||||
|
||||
# Model for regression test for #285
|
||||
|
||||
class Comment(RESTFrameworkModel):
|
||||
email = models.EmailField()
|
||||
content = models.CharField(max_length=200)
|
||||
created = models.DateTimeField(auto_now_add=True)
|
||||
|
|
Loading…
Reference in New Issue
Block a user