mirror of
https://github.com/encode/django-rest-framework.git
synced 2024-12-01 22:14:06 +03:00
2182 lines
78 KiB
Python
2182 lines
78 KiB
Python
from rest_framework import serializers
|
|
import pytest
|
|
|
|
|
|
# Tests for core functionality.
|
|
# -----------------------------
|
|
|
|
class TestSerializer:
|
|
def setup(self):
|
|
class ExampleSerializer(serializers.Serializer):
|
|
char = serializers.CharField()
|
|
integer = serializers.IntegerField()
|
|
self.Serializer = ExampleSerializer
|
|
|
|
def test_valid_serializer(self):
|
|
serializer = self.Serializer(data={'char': 'abc', 'integer': 123})
|
|
assert serializer.is_valid()
|
|
assert serializer.validated_data == {'char': 'abc', 'integer': 123}
|
|
assert serializer.errors == {}
|
|
|
|
def test_invalid_serializer(self):
|
|
serializer = self.Serializer(data={'char': 'abc'})
|
|
assert not serializer.is_valid()
|
|
assert serializer.validated_data == {}
|
|
assert serializer.errors == {'integer': ['This field is required.']}
|
|
|
|
def test_partial_validation(self):
|
|
serializer = self.Serializer(data={'char': 'abc'}, partial=True)
|
|
assert serializer.is_valid()
|
|
assert serializer.validated_data == {'char': 'abc'}
|
|
assert serializer.errors == {}
|
|
|
|
def test_empty_serializer(self):
|
|
serializer = self.Serializer()
|
|
assert serializer.data == {'char': '', 'integer': None}
|
|
|
|
def test_missing_attribute_during_serialization(self):
|
|
class MissingAttributes:
|
|
pass
|
|
instance = MissingAttributes()
|
|
serializer = self.Serializer(instance)
|
|
with pytest.raises(AttributeError):
|
|
serializer.data
|
|
|
|
|
|
class TestValidateMethod:
|
|
def test_non_field_error_validate_method(self):
|
|
class ExampleSerializer(serializers.Serializer):
|
|
char = serializers.CharField()
|
|
integer = serializers.IntegerField()
|
|
|
|
def validate(self, attrs):
|
|
raise serializers.ValidationError('Non field error')
|
|
|
|
serializer = ExampleSerializer(data={'char': 'abc', 'integer': 123})
|
|
assert not serializer.is_valid()
|
|
assert serializer.errors == {'non_field_errors': ['Non field error']}
|
|
|
|
def test_field_error_validate_method(self):
|
|
class ExampleSerializer(serializers.Serializer):
|
|
char = serializers.CharField()
|
|
integer = serializers.IntegerField()
|
|
|
|
def validate(self, attrs):
|
|
raise serializers.ValidationError({'char': 'Field error'})
|
|
|
|
serializer = ExampleSerializer(data={'char': 'abc', 'integer': 123})
|
|
assert not serializer.is_valid()
|
|
assert serializer.errors == {'char': ['Field error']}
|
|
|
|
|
|
class TestBaseSerializer:
|
|
def setup(self):
|
|
class ExampleSerializer(serializers.BaseSerializer):
|
|
def to_representation(self, obj):
|
|
return {
|
|
'id': obj['id'],
|
|
'email': obj['name'] + '@' + obj['domain']
|
|
}
|
|
|
|
def to_internal_value(self, data):
|
|
name, domain = str(data['email']).split('@')
|
|
return {
|
|
'id': int(data['id']),
|
|
'name': name,
|
|
'domain': domain,
|
|
}
|
|
|
|
self.Serializer = ExampleSerializer
|
|
|
|
def test_serialize_instance(self):
|
|
instance = {'id': 1, 'name': 'tom', 'domain': 'example.com'}
|
|
serializer = self.Serializer(instance)
|
|
assert serializer.data == {'id': 1, 'email': 'tom@example.com'}
|
|
|
|
def test_serialize_list(self):
|
|
instances = [
|
|
{'id': 1, 'name': 'tom', 'domain': 'example.com'},
|
|
{'id': 2, 'name': 'ann', 'domain': 'example.com'},
|
|
]
|
|
serializer = self.Serializer(instances, many=True)
|
|
assert serializer.data == [
|
|
{'id': 1, 'email': 'tom@example.com'},
|
|
{'id': 2, 'email': 'ann@example.com'}
|
|
]
|
|
|
|
def test_validate_data(self):
|
|
data = {'id': 1, 'email': 'tom@example.com'}
|
|
serializer = self.Serializer(data=data)
|
|
assert serializer.is_valid()
|
|
assert serializer.validated_data == {
|
|
'id': 1,
|
|
'name': 'tom',
|
|
'domain': 'example.com'
|
|
}
|
|
|
|
def test_validate_list(self):
|
|
data = [
|
|
{'id': 1, 'email': 'tom@example.com'},
|
|
{'id': 2, 'email': 'ann@example.com'},
|
|
]
|
|
serializer = self.Serializer(data=data, many=True)
|
|
assert serializer.is_valid()
|
|
assert serializer.validated_data == [
|
|
{'id': 1, 'name': 'tom', 'domain': 'example.com'},
|
|
{'id': 2, 'name': 'ann', 'domain': 'example.com'}
|
|
]
|
|
|
|
|
|
class TestStarredSource:
|
|
"""
|
|
Tests for `source='*'` argument, which is used for nested representations.
|
|
|
|
For example:
|
|
|
|
nested_field = NestedField(source='*')
|
|
"""
|
|
data = {
|
|
'nested1': {'a': 1, 'b': 2},
|
|
'nested2': {'c': 3, 'd': 4}
|
|
}
|
|
|
|
def setup(self):
|
|
class NestedSerializer1(serializers.Serializer):
|
|
a = serializers.IntegerField()
|
|
b = serializers.IntegerField()
|
|
|
|
class NestedSerializer2(serializers.Serializer):
|
|
c = serializers.IntegerField()
|
|
d = serializers.IntegerField()
|
|
|
|
class TestSerializer(serializers.Serializer):
|
|
nested1 = NestedSerializer1(source='*')
|
|
nested2 = NestedSerializer2(source='*')
|
|
|
|
self.Serializer = TestSerializer
|
|
|
|
def test_nested_validate(self):
|
|
"""
|
|
A nested representation is validated into a flat internal object.
|
|
"""
|
|
serializer = self.Serializer(data=self.data)
|
|
assert serializer.is_valid()
|
|
assert serializer.validated_data == {
|
|
'a': 1,
|
|
'b': 2,
|
|
'c': 3,
|
|
'd': 4
|
|
}
|
|
|
|
def test_nested_serialize(self):
|
|
"""
|
|
An object can be serialized into a nested representation.
|
|
"""
|
|
instance = {'a': 1, 'b': 2, 'c': 3, 'd': 4}
|
|
serializer = self.Serializer(instance)
|
|
assert serializer.data == self.data
|
|
|
|
# # -*- coding: utf-8 -*-
|
|
# from __future__ import unicode_literals
|
|
# from django.db import models
|
|
# from django.db.models.fields import BLANK_CHOICE_DASH
|
|
# from django.test import TestCase
|
|
# from django.utils import unittest
|
|
# from django.utils.datastructures import MultiValueDict
|
|
# from django.utils.translation import ugettext_lazy as _
|
|
# from rest_framework import serializers, fields, relations
|
|
# from tests.models import (
|
|
# HasPositiveIntegerAsChoice, Album, ActionItem, Anchor, BasicModel,
|
|
# BlankFieldModel, BlogPost, BlogPostComment, Book, CallableDefaultValueModel,
|
|
# DefaultValueModel, ManyToManyModel, Person, ReadOnlyManyToManyModel, Photo,
|
|
# RESTFrameworkModel, ForeignKeySource
|
|
# )
|
|
# from tests.models import BasicModelSerializer
|
|
# import datetime
|
|
# import pickle
|
|
# try:
|
|
# import PIL
|
|
# except:
|
|
# PIL = None
|
|
|
|
|
|
# if PIL is not None:
|
|
# class AMOAFModel(RESTFrameworkModel):
|
|
# char_field = models.CharField(max_length=1024, blank=True)
|
|
# comma_separated_integer_field = models.CommaSeparatedIntegerField(max_length=1024, blank=True)
|
|
# decimal_field = models.DecimalField(max_digits=64, decimal_places=32, blank=True)
|
|
# email_field = models.EmailField(max_length=1024, blank=True)
|
|
# file_field = models.FileField(upload_to='test', max_length=1024, blank=True)
|
|
# image_field = models.ImageField(upload_to='test', max_length=1024, blank=True)
|
|
# slug_field = models.SlugField(max_length=1024, blank=True)
|
|
# url_field = models.URLField(max_length=1024, blank=True)
|
|
# nullable_char_field = models.CharField(max_length=1024, blank=True, null=True)
|
|
|
|
# class DVOAFModel(RESTFrameworkModel):
|
|
# positive_integer_field = models.PositiveIntegerField(blank=True)
|
|
# positive_small_integer_field = models.PositiveSmallIntegerField(blank=True)
|
|
# email_field = models.EmailField(blank=True)
|
|
# file_field = models.FileField(upload_to='test', blank=True)
|
|
# image_field = models.ImageField(upload_to='test', blank=True)
|
|
# slug_field = models.SlugField(blank=True)
|
|
# url_field = models.URLField(blank=True)
|
|
|
|
|
|
# class SubComment(object):
|
|
# def __init__(self, sub_comment):
|
|
# self.sub_comment = sub_comment
|
|
|
|
|
|
# class Comment(object):
|
|
# def __init__(self, email, content, created):
|
|
# self.email = email
|
|
# self.content = content
|
|
# self.created = created or datetime.datetime.now()
|
|
|
|
# def __eq__(self, other):
|
|
# return all([getattr(self, attr) == getattr(other, attr)
|
|
# for attr in ('email', 'content', 'created')])
|
|
|
|
# def get_sub_comment(self):
|
|
# sub_comment = SubComment('And Merry Christmas!')
|
|
# return sub_comment
|
|
|
|
|
|
# class CommentSerializer(serializers.Serializer):
|
|
# email = serializers.EmailField()
|
|
# content = serializers.CharField(max_length=1000)
|
|
# created = serializers.DateTimeField()
|
|
# sub_comment = serializers.Field(source='get_sub_comment.sub_comment')
|
|
|
|
# def restore_object(self, data, instance=None):
|
|
# if instance is None:
|
|
# return Comment(**data)
|
|
# for key, val in data.items():
|
|
# setattr(instance, key, val)
|
|
# return instance
|
|
|
|
|
|
# class NamesSerializer(serializers.Serializer):
|
|
# first = serializers.CharField()
|
|
# last = serializers.CharField(required=False, default='')
|
|
# initials = serializers.CharField(required=False, default='')
|
|
|
|
|
|
# class PersonIdentifierSerializer(serializers.Serializer):
|
|
# ssn = serializers.CharField()
|
|
# names = NamesSerializer(source='names', required=False)
|
|
|
|
|
|
# class BookSerializer(serializers.ModelSerializer):
|
|
# isbn = serializers.RegexField(regex=r'^[0-9]{13}$', error_messages={'invalid': 'isbn has to be exact 13 numbers'})
|
|
|
|
# class Meta:
|
|
# model = Book
|
|
|
|
|
|
# class ActionItemSerializer(serializers.ModelSerializer):
|
|
|
|
# class Meta:
|
|
# model = ActionItem
|
|
|
|
|
|
# class ActionItemSerializerOptionalFields(serializers.ModelSerializer):
|
|
# """
|
|
# Intended to test that fields with `required=False` are excluded from validation.
|
|
# """
|
|
# title = serializers.CharField(required=False)
|
|
|
|
# class Meta:
|
|
# model = ActionItem
|
|
# fields = ('title',)
|
|
|
|
|
|
# class ActionItemSerializerCustomRestore(serializers.ModelSerializer):
|
|
|
|
# class Meta:
|
|
# model = ActionItem
|
|
|
|
# def restore_object(self, data, instance=None):
|
|
# if instance is None:
|
|
# return ActionItem(**data)
|
|
# for key, val in data.items():
|
|
# setattr(instance, key, val)
|
|
# return instance
|
|
|
|
|
|
# class PersonSerializer(serializers.ModelSerializer):
|
|
# info = serializers.Field(source='info')
|
|
|
|
# class Meta:
|
|
# model = Person
|
|
# fields = ('name', 'age', 'info')
|
|
# read_only_fields = ('age',)
|
|
|
|
|
|
# class NestedSerializer(serializers.Serializer):
|
|
# info = serializers.Field()
|
|
|
|
|
|
# class ModelSerializerWithNestedSerializer(serializers.ModelSerializer):
|
|
# nested = NestedSerializer(source='*')
|
|
|
|
# class Meta:
|
|
# model = Person
|
|
|
|
|
|
# class NestedSerializerWithRenamedField(serializers.Serializer):
|
|
# renamed_info = serializers.Field(source='info')
|
|
|
|
|
|
# class ModelSerializerWithNestedSerializerWithRenamedField(serializers.ModelSerializer):
|
|
# nested = NestedSerializerWithRenamedField(source='*')
|
|
|
|
# class Meta:
|
|
# model = Person
|
|
|
|
|
|
# class PersonSerializerInvalidReadOnly(serializers.ModelSerializer):
|
|
# """
|
|
# Testing for #652.
|
|
# """
|
|
# info = serializers.Field(source='info')
|
|
|
|
# class Meta:
|
|
# model = Person
|
|
# fields = ('name', 'age', 'info')
|
|
# read_only_fields = ('age', 'info')
|
|
|
|
|
|
# class AlbumsSerializer(serializers.ModelSerializer):
|
|
|
|
# class Meta:
|
|
# model = Album
|
|
# fields = ['title', 'ref'] # lists are also valid options
|
|
|
|
|
|
# class PositiveIntegerAsChoiceSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = HasPositiveIntegerAsChoice
|
|
# fields = ['some_integer']
|
|
|
|
|
|
# class ForeignKeySourceSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = ForeignKeySource
|
|
|
|
|
|
# class HyperlinkedForeignKeySourceSerializer(serializers.HyperlinkedModelSerializer):
|
|
# class Meta:
|
|
# model = ForeignKeySource
|
|
|
|
|
|
# class BasicTests(TestCase):
|
|
# def setUp(self):
|
|
# self.comment = Comment(
|
|
# 'tom@example.com',
|
|
# 'Happy new year!',
|
|
# datetime.datetime(2012, 1, 1)
|
|
# )
|
|
# self.actionitem = ActionItem(title='Some to do item',)
|
|
# self.data = {
|
|
# 'email': 'tom@example.com',
|
|
# 'content': 'Happy new year!',
|
|
# 'created': datetime.datetime(2012, 1, 1),
|
|
# 'sub_comment': 'This wont change'
|
|
# }
|
|
# self.expected = {
|
|
# 'email': 'tom@example.com',
|
|
# 'content': 'Happy new year!',
|
|
# 'created': datetime.datetime(2012, 1, 1),
|
|
# 'sub_comment': 'And Merry Christmas!'
|
|
# }
|
|
# self.person_data = {'name': 'dwight', 'age': 35}
|
|
# self.person = Person(**self.person_data)
|
|
# self.person.save()
|
|
|
|
# def test_empty(self):
|
|
# serializer = CommentSerializer()
|
|
# expected = {
|
|
# 'email': '',
|
|
# 'content': '',
|
|
# 'created': None
|
|
# }
|
|
# self.assertEqual(serializer.data, expected)
|
|
|
|
# def test_retrieve(self):
|
|
# serializer = CommentSerializer(self.comment)
|
|
# self.assertEqual(serializer.data, self.expected)
|
|
|
|
# def test_create(self):
|
|
# serializer = CommentSerializer(data=self.data)
|
|
# expected = self.comment
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# self.assertEqual(serializer.object, expected)
|
|
# self.assertFalse(serializer.object is expected)
|
|
# self.assertEqual(serializer.data['sub_comment'], 'And Merry Christmas!')
|
|
|
|
# def test_create_nested(self):
|
|
# """Test a serializer with nested data."""
|
|
# names = {'first': 'John', 'last': 'Doe', 'initials': 'jd'}
|
|
# data = {'ssn': '1234567890', 'names': names}
|
|
# serializer = PersonIdentifierSerializer(data=data)
|
|
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# self.assertEqual(serializer.object, data)
|
|
# self.assertFalse(serializer.object is data)
|
|
# self.assertEqual(serializer.data['names'], names)
|
|
|
|
# def test_create_partial_nested(self):
|
|
# """Test a serializer with nested data which has missing fields."""
|
|
# names = {'first': 'John'}
|
|
# data = {'ssn': '1234567890', 'names': names}
|
|
# serializer = PersonIdentifierSerializer(data=data)
|
|
|
|
# expected_names = {'first': 'John', 'last': '', 'initials': ''}
|
|
# data['names'] = expected_names
|
|
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# self.assertEqual(serializer.object, data)
|
|
# self.assertFalse(serializer.object is expected_names)
|
|
# self.assertEqual(serializer.data['names'], expected_names)
|
|
|
|
# def test_null_nested(self):
|
|
# """Test a serializer with a nonexistent nested field"""
|
|
# data = {'ssn': '1234567890'}
|
|
# serializer = PersonIdentifierSerializer(data=data)
|
|
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# self.assertEqual(serializer.object, data)
|
|
# self.assertFalse(serializer.object is data)
|
|
# expected = {'ssn': '1234567890', 'names': None}
|
|
# self.assertEqual(serializer.data, expected)
|
|
|
|
# def test_update(self):
|
|
# serializer = CommentSerializer(self.comment, data=self.data)
|
|
# expected = self.comment
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# self.assertEqual(serializer.object, expected)
|
|
# self.assertTrue(serializer.object is expected)
|
|
# self.assertEqual(serializer.data['sub_comment'], 'And Merry Christmas!')
|
|
|
|
# def test_partial_update(self):
|
|
# msg = 'Merry New Year!'
|
|
# partial_data = {'content': msg}
|
|
# serializer = CommentSerializer(self.comment, data=partial_data)
|
|
# self.assertEqual(serializer.is_valid(), False)
|
|
# serializer = CommentSerializer(self.comment, data=partial_data, partial=True)
|
|
# expected = self.comment
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# self.assertEqual(serializer.object, expected)
|
|
# self.assertTrue(serializer.object is expected)
|
|
# self.assertEqual(serializer.data['content'], msg)
|
|
|
|
# def test_model_fields_as_expected(self):
|
|
# """
|
|
# Make sure that the fields returned are the same as defined
|
|
# in the Meta data
|
|
# """
|
|
# serializer = PersonSerializer(self.person)
|
|
# self.assertEqual(
|
|
# set(serializer.data.keys()),
|
|
# set(['name', 'age', 'info'])
|
|
# )
|
|
|
|
# def test_field_with_dictionary(self):
|
|
# """
|
|
# Make sure that dictionaries from fields are left intact
|
|
# """
|
|
# serializer = PersonSerializer(self.person)
|
|
# expected = self.person_data
|
|
# self.assertEqual(serializer.data['info'], expected)
|
|
|
|
# def test_read_only_fields(self):
|
|
# """
|
|
# Attempting to update fields set as read_only should have no effect.
|
|
# """
|
|
# serializer = PersonSerializer(self.person, data={'name': 'dwight', 'age': 99})
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
# self.assertEqual(serializer.errors, {})
|
|
# # Assert age is unchanged (35)
|
|
# self.assertEqual(instance.age, self.person_data['age'])
|
|
|
|
# def test_invalid_read_only_fields(self):
|
|
# """
|
|
# Regression test for #652.
|
|
# """
|
|
# self.assertRaises(AssertionError, PersonSerializerInvalidReadOnly, [])
|
|
|
|
# def test_serializer_data_is_cleared_on_save(self):
|
|
# """
|
|
# Check _data attribute is cleared on `save()`
|
|
|
|
# Regression test for #1116
|
|
# """
|
|
# serializer = ActionItemSerializer(self.actionitem)
|
|
# self.assertIsNone(serializer.data.get('id', None), 'New instance. `id` should not be set.')
|
|
# serializer.save()
|
|
# self.assertIsNotNone(serializer.data.get('id', None), 'Model is saved. `id` should be set.')
|
|
|
|
# def test_fields_marked_as_not_required_are_excluded_from_validation(self):
|
|
# """
|
|
# Check that fields with `required=False` are included in list of exclusions.
|
|
# """
|
|
# serializer = ActionItemSerializerOptionalFields(self.actionitem)
|
|
# exclusions = serializer.get_validation_exclusions()
|
|
# self.assertTrue('title' in exclusions, '`title` field was marked `required=False` and should be excluded')
|
|
|
|
|
|
# class DictStyleSerializer(serializers.Serializer):
|
|
# """
|
|
# Note that we don't have any `restore_object` method, so the default
|
|
# case of simply returning a dict will apply.
|
|
# """
|
|
# email = serializers.EmailField()
|
|
|
|
|
|
# class DictStyleSerializerTests(TestCase):
|
|
# def test_dict_style_deserialize(self):
|
|
# """
|
|
# Ensure serializers can deserialize into a dict.
|
|
# """
|
|
# data = {'email': 'foo@example.com'}
|
|
# serializer = DictStyleSerializer(data=data)
|
|
# self.assertTrue(serializer.is_valid())
|
|
# self.assertEqual(serializer.data, data)
|
|
|
|
# def test_dict_style_serialize(self):
|
|
# """
|
|
# Ensure serializers can serialize dict objects.
|
|
# """
|
|
# data = {'email': 'foo@example.com'}
|
|
# serializer = DictStyleSerializer(data)
|
|
# self.assertEqual(serializer.data, data)
|
|
|
|
|
|
# class ValidationTests(TestCase):
|
|
# def setUp(self):
|
|
# self.comment = Comment(
|
|
# 'tom@example.com',
|
|
# 'Happy new year!',
|
|
# datetime.datetime(2012, 1, 1)
|
|
# )
|
|
# self.data = {
|
|
# 'email': 'tom@example.com',
|
|
# 'content': 'x' * 1001,
|
|
# 'created': datetime.datetime(2012, 1, 1)
|
|
# }
|
|
# self.actionitem = ActionItem(title='Some to do item',)
|
|
|
|
# def test_create(self):
|
|
# serializer = CommentSerializer(data=self.data)
|
|
# self.assertEqual(serializer.is_valid(), False)
|
|
# self.assertEqual(serializer.errors, {'content': ['Ensure this value has at most 1000 characters (it has 1001).']})
|
|
|
|
# def test_update(self):
|
|
# serializer = CommentSerializer(self.comment, data=self.data)
|
|
# self.assertEqual(serializer.is_valid(), False)
|
|
# self.assertEqual(serializer.errors, {'content': ['Ensure this value has at most 1000 characters (it has 1001).']})
|
|
|
|
# def test_update_missing_field(self):
|
|
# data = {
|
|
# 'content': 'xxx',
|
|
# 'created': datetime.datetime(2012, 1, 1)
|
|
# }
|
|
# serializer = CommentSerializer(self.comment, data=data)
|
|
# self.assertEqual(serializer.is_valid(), False)
|
|
# self.assertEqual(serializer.errors, {'email': ['This field is required.']})
|
|
|
|
# def test_missing_bool_with_default(self):
|
|
# """Make sure that a boolean value with a 'False' value is not
|
|
# mistaken for not having a default."""
|
|
# data = {
|
|
# 'title': 'Some action item',
|
|
# # No 'done' value.
|
|
# }
|
|
# serializer = ActionItemSerializer(self.actionitem, data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# self.assertEqual(serializer.errors, {})
|
|
|
|
# def test_cross_field_validation(self):
|
|
|
|
# class CommentSerializerWithCrossFieldValidator(CommentSerializer):
|
|
|
|
# def validate(self, attrs):
|
|
# if attrs["email"] not in attrs["content"]:
|
|
# raise serializers.ValidationError("Email address not in content")
|
|
# return attrs
|
|
|
|
# data = {
|
|
# 'email': 'tom@example.com',
|
|
# 'content': 'A comment from tom@example.com',
|
|
# 'created': datetime.datetime(2012, 1, 1)
|
|
# }
|
|
|
|
# serializer = CommentSerializerWithCrossFieldValidator(data=data)
|
|
# self.assertTrue(serializer.is_valid())
|
|
|
|
# data['content'] = 'A comment from foo@bar.com'
|
|
|
|
# serializer = CommentSerializerWithCrossFieldValidator(data=data)
|
|
# self.assertFalse(serializer.is_valid())
|
|
# self.assertEqual(serializer.errors, {'non_field_errors': ['Email address not in content']})
|
|
|
|
# def test_null_is_true_fields(self):
|
|
# """
|
|
# Omitting a value for null-field should validate.
|
|
# """
|
|
# serializer = PersonSerializer(data={'name': 'marko'})
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# self.assertEqual(serializer.errors, {})
|
|
|
|
# def test_modelserializer_max_length_exceeded(self):
|
|
# data = {
|
|
# 'title': 'x' * 201,
|
|
# }
|
|
# serializer = ActionItemSerializer(data=data)
|
|
# self.assertEqual(serializer.is_valid(), False)
|
|
# self.assertEqual(serializer.errors, {'title': ['Ensure this value has at most 200 characters (it has 201).']})
|
|
|
|
# def test_modelserializer_max_length_exceeded_with_custom_restore(self):
|
|
# """
|
|
# When overriding ModelSerializer.restore_object, validation tests should still apply.
|
|
# Regression test for #623.
|
|
|
|
# https://github.com/tomchristie/django-rest-framework/pull/623
|
|
# """
|
|
# data = {
|
|
# 'title': 'x' * 201,
|
|
# }
|
|
# serializer = ActionItemSerializerCustomRestore(data=data)
|
|
# self.assertEqual(serializer.is_valid(), False)
|
|
# self.assertEqual(serializer.errors, {'title': ['Ensure this value has at most 200 characters (it has 201).']})
|
|
|
|
# def test_default_modelfield_max_length_exceeded(self):
|
|
# data = {
|
|
# 'title': 'Testing "info" field...',
|
|
# 'info': 'x' * 13,
|
|
# }
|
|
# serializer = ActionItemSerializer(data=data)
|
|
# self.assertEqual(serializer.is_valid(), False)
|
|
# self.assertEqual(serializer.errors, {'info': ['Ensure this value has at most 12 characters (it has 13).']})
|
|
|
|
# def test_datetime_validation_failure(self):
|
|
# """
|
|
# Test DateTimeField validation errors on non-str values.
|
|
# Regression test for #669.
|
|
|
|
# https://github.com/tomchristie/django-rest-framework/issues/669
|
|
# """
|
|
# data = self.data
|
|
# data['created'] = 0
|
|
|
|
# serializer = CommentSerializer(data=data)
|
|
# self.assertEqual(serializer.is_valid(), False)
|
|
|
|
# self.assertIn('created', serializer.errors)
|
|
|
|
# def test_missing_model_field_exception_msg(self):
|
|
# """
|
|
# Assert that a meaningful exception message is outputted when the model
|
|
# field is missing (e.g. when mistyping ``model``).
|
|
# """
|
|
# class BrokenModelSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# fields = ['some_field']
|
|
|
|
# try:
|
|
# BrokenModelSerializer()
|
|
# except AssertionError as e:
|
|
# self.assertEqual(e.args[0], "Serializer class 'BrokenModelSerializer' is missing 'model' Meta option")
|
|
# except:
|
|
# self.fail('Wrong exception type thrown.')
|
|
|
|
# def test_writable_star_source_on_nested_serializer(self):
|
|
# """
|
|
# Assert that a nested serializer instantiated with source='*' correctly
|
|
# expands the data into the outer serializer.
|
|
# """
|
|
# serializer = ModelSerializerWithNestedSerializer(data={
|
|
# 'name': 'marko',
|
|
# 'nested': {'info': 'hi'}},
|
|
# )
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
|
|
# def test_writable_star_source_on_nested_serializer_with_parent_object(self):
|
|
# class TitleSerializer(serializers.Serializer):
|
|
# title = serializers.WritableField(source='title')
|
|
|
|
# class AlbumSerializer(serializers.ModelSerializer):
|
|
# nested = TitleSerializer(source='*')
|
|
|
|
# class Meta:
|
|
# model = Album
|
|
# fields = ('nested',)
|
|
|
|
# class PhotoSerializer(serializers.ModelSerializer):
|
|
# album = AlbumSerializer(source='album')
|
|
|
|
# class Meta:
|
|
# model = Photo
|
|
# fields = ('album', )
|
|
|
|
# photo = Photo(album=Album())
|
|
|
|
# data = {'album': {'nested': {'title': 'test'}}}
|
|
|
|
# serializer = PhotoSerializer(photo, data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# self.assertEqual(serializer.data, data)
|
|
|
|
# def test_writable_star_source_with_inner_source_fields(self):
|
|
# """
|
|
# Tests that a serializer with source="*" correctly expands the
|
|
# it's fields into the outer serializer even if they have their
|
|
# own 'source' parameters.
|
|
# """
|
|
|
|
# serializer = ModelSerializerWithNestedSerializerWithRenamedField(data={
|
|
# 'name': 'marko',
|
|
# 'nested': {'renamed_info': 'hi'}},
|
|
# )
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# self.assertEqual(serializer.errors, {})
|
|
|
|
|
|
# class CustomValidationTests(TestCase):
|
|
# class CommentSerializerWithFieldValidator(CommentSerializer):
|
|
|
|
# def validate_email(self, attrs, source):
|
|
# attrs[source]
|
|
# return attrs
|
|
|
|
# def validate_content(self, attrs, source):
|
|
# value = attrs[source]
|
|
# if "test" not in value:
|
|
# raise serializers.ValidationError("Test not in value")
|
|
# return attrs
|
|
|
|
# def test_field_validation(self):
|
|
# data = {
|
|
# 'email': 'tom@example.com',
|
|
# 'content': 'A test comment',
|
|
# 'created': datetime.datetime(2012, 1, 1)
|
|
# }
|
|
|
|
# serializer = self.CommentSerializerWithFieldValidator(data=data)
|
|
# self.assertTrue(serializer.is_valid())
|
|
|
|
# data['content'] = 'This should not validate'
|
|
|
|
# serializer = self.CommentSerializerWithFieldValidator(data=data)
|
|
# self.assertFalse(serializer.is_valid())
|
|
# self.assertEqual(serializer.errors, {'content': ['Test not in value']})
|
|
|
|
# def test_missing_data(self):
|
|
# """
|
|
# Make sure that validate_content isn't called if the field is missing
|
|
# """
|
|
# incomplete_data = {
|
|
# 'email': 'tom@example.com',
|
|
# 'created': datetime.datetime(2012, 1, 1)
|
|
# }
|
|
# serializer = self.CommentSerializerWithFieldValidator(data=incomplete_data)
|
|
# self.assertFalse(serializer.is_valid())
|
|
# self.assertEqual(serializer.errors, {'content': ['This field is required.']})
|
|
|
|
# def test_wrong_data(self):
|
|
# """
|
|
# Make sure that validate_content isn't called if the field input is wrong
|
|
# """
|
|
# wrong_data = {
|
|
# 'email': 'not an email',
|
|
# 'content': 'A test comment',
|
|
# 'created': datetime.datetime(2012, 1, 1)
|
|
# }
|
|
# serializer = self.CommentSerializerWithFieldValidator(data=wrong_data)
|
|
# self.assertFalse(serializer.is_valid())
|
|
# self.assertEqual(serializer.errors, {'email': ['Enter a valid email address.']})
|
|
|
|
# def test_partial_update(self):
|
|
# """
|
|
# Make sure that validate_email isn't called when partial=True and email
|
|
# isn't found in data.
|
|
# """
|
|
# initial_data = {
|
|
# 'email': 'tom@example.com',
|
|
# 'content': 'A test comment',
|
|
# 'created': datetime.datetime(2012, 1, 1)
|
|
# }
|
|
|
|
# serializer = self.CommentSerializerWithFieldValidator(data=initial_data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.object
|
|
|
|
# new_content = 'An *updated* test comment'
|
|
# partial_data = {
|
|
# 'content': new_content
|
|
# }
|
|
|
|
# serializer = self.CommentSerializerWithFieldValidator(instance=instance,
|
|
# data=partial_data,
|
|
# partial=True)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.object
|
|
# self.assertEqual(instance.content, new_content)
|
|
|
|
|
|
# class PositiveIntegerAsChoiceTests(TestCase):
|
|
# def test_positive_integer_in_json_is_correctly_parsed(self):
|
|
# data = {'some_integer': 1}
|
|
# serializer = PositiveIntegerAsChoiceSerializer(data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
|
|
|
|
# class ModelValidationTests(TestCase):
|
|
# def test_validate_unique(self):
|
|
# """
|
|
# Just check if serializers.ModelSerializer handles unique checks via .full_clean()
|
|
# """
|
|
# serializer = AlbumsSerializer(data={'title': 'a', 'ref': '1'})
|
|
# serializer.is_valid()
|
|
# serializer.save()
|
|
# second_serializer = AlbumsSerializer(data={'title': 'a'})
|
|
# self.assertFalse(second_serializer.is_valid())
|
|
# self.assertEqual(second_serializer.errors, {'title': ['Album with this Title already exists.']})
|
|
# third_serializer = AlbumsSerializer(data=[{'title': 'b', 'ref': '1'}, {'title': 'c'}], many=True)
|
|
# self.assertFalse(third_serializer.is_valid())
|
|
# self.assertEqual(third_serializer.errors, [{'ref': ['Album with this Ref already exists.']}, {}])
|
|
|
|
# def test_foreign_key_is_null_with_partial(self):
|
|
# """
|
|
# Test ModelSerializer validation with partial=True
|
|
|
|
# Specifically test that a null foreign key does not pass validation
|
|
# """
|
|
# album = Album(title='test')
|
|
# album.save()
|
|
|
|
# class PhotoSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = Photo
|
|
|
|
# photo_serializer = PhotoSerializer(data={'description': 'test', 'album': album.pk})
|
|
# self.assertTrue(photo_serializer.is_valid())
|
|
# photo = photo_serializer.save()
|
|
|
|
# # Updating only the album (foreign key)
|
|
# photo_serializer = PhotoSerializer(instance=photo, data={'album': ''}, partial=True)
|
|
# self.assertFalse(photo_serializer.is_valid())
|
|
# self.assertTrue('album' in photo_serializer.errors)
|
|
# self.assertEqual(photo_serializer.errors['album'], [photo_serializer.error_messages['required']])
|
|
|
|
# def test_foreign_key_with_partial(self):
|
|
# """
|
|
# Test ModelSerializer validation with partial=True
|
|
|
|
# Specifically test foreign key validation.
|
|
# """
|
|
|
|
# album = Album(title='test')
|
|
# album.save()
|
|
|
|
# class PhotoSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = Photo
|
|
|
|
# photo_serializer = PhotoSerializer(data={'description': 'test', 'album': album.pk})
|
|
# self.assertTrue(photo_serializer.is_valid())
|
|
# photo = photo_serializer.save()
|
|
|
|
# # Updating only the album (foreign key)
|
|
# photo_serializer = PhotoSerializer(instance=photo, data={'album': album.pk}, partial=True)
|
|
# self.assertTrue(photo_serializer.is_valid())
|
|
# self.assertTrue(photo_serializer.save())
|
|
|
|
# # Updating only the description
|
|
# photo_serializer = PhotoSerializer(instance=photo,
|
|
# data={'description': 'new'},
|
|
# partial=True)
|
|
|
|
# self.assertTrue(photo_serializer.is_valid())
|
|
# self.assertTrue(photo_serializer.save())
|
|
|
|
|
|
# class RegexValidationTest(TestCase):
|
|
# def test_create_failed(self):
|
|
# serializer = BookSerializer(data={'isbn': '1234567890'})
|
|
# self.assertFalse(serializer.is_valid())
|
|
# self.assertEqual(serializer.errors, {'isbn': ['isbn has to be exact 13 numbers']})
|
|
|
|
# serializer = BookSerializer(data={'isbn': '12345678901234'})
|
|
# self.assertFalse(serializer.is_valid())
|
|
# self.assertEqual(serializer.errors, {'isbn': ['isbn has to be exact 13 numbers']})
|
|
|
|
# serializer = BookSerializer(data={'isbn': 'abcdefghijklm'})
|
|
# self.assertFalse(serializer.is_valid())
|
|
# self.assertEqual(serializer.errors, {'isbn': ['isbn has to be exact 13 numbers']})
|
|
|
|
# def test_create_success(self):
|
|
# serializer = BookSerializer(data={'isbn': '1234567890123'})
|
|
# self.assertTrue(serializer.is_valid())
|
|
|
|
|
|
# class MetadataTests(TestCase):
|
|
# def test_empty(self):
|
|
# serializer = CommentSerializer()
|
|
# expected = {
|
|
# 'email': serializers.CharField,
|
|
# 'content': serializers.CharField,
|
|
# 'created': serializers.DateTimeField
|
|
# }
|
|
# for field_name, field in expected.items():
|
|
# self.assertTrue(isinstance(serializer.data.fields[field_name], field))
|
|
|
|
|
|
# class ManyToManyTests(TestCase):
|
|
# def setUp(self):
|
|
# class ManyToManySerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = ManyToManyModel
|
|
|
|
# self.serializer_class = ManyToManySerializer
|
|
|
|
# # An anchor instance to use for the relationship
|
|
# self.anchor = Anchor()
|
|
# self.anchor.save()
|
|
|
|
# # A model instance with a many to many relationship to the anchor
|
|
# self.instance = ManyToManyModel()
|
|
# self.instance.save()
|
|
# self.instance.rel.add(self.anchor)
|
|
|
|
# # A serialized representation of the model instance
|
|
# self.data = {'id': 1, 'rel': [self.anchor.id]}
|
|
|
|
# def test_retrieve(self):
|
|
# """
|
|
# Serialize an instance of a model with a ManyToMany relationship.
|
|
# """
|
|
# serializer = self.serializer_class(instance=self.instance)
|
|
# expected = self.data
|
|
# self.assertEqual(serializer.data, expected)
|
|
|
|
# def test_create(self):
|
|
# """
|
|
# Create an instance of a model with a ManyToMany relationship.
|
|
# """
|
|
# data = {'rel': [self.anchor.id]}
|
|
# serializer = self.serializer_class(data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
# self.assertEqual(len(ManyToManyModel.objects.all()), 2)
|
|
# self.assertEqual(instance.pk, 2)
|
|
# self.assertEqual(list(instance.rel.all()), [self.anchor])
|
|
|
|
# def test_update(self):
|
|
# """
|
|
# Update an instance of a model with a ManyToMany relationship.
|
|
# """
|
|
# new_anchor = Anchor()
|
|
# new_anchor.save()
|
|
# data = {'rel': [self.anchor.id, new_anchor.id]}
|
|
# serializer = self.serializer_class(self.instance, data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
# self.assertEqual(len(ManyToManyModel.objects.all()), 1)
|
|
# self.assertEqual(instance.pk, 1)
|
|
# self.assertEqual(list(instance.rel.all()), [self.anchor, new_anchor])
|
|
|
|
# def test_create_empty_relationship(self):
|
|
# """
|
|
# Create an instance of a model with a ManyToMany relationship,
|
|
# containing no items.
|
|
# """
|
|
# data = {'rel': []}
|
|
# serializer = self.serializer_class(data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
# self.assertEqual(len(ManyToManyModel.objects.all()), 2)
|
|
# self.assertEqual(instance.pk, 2)
|
|
# self.assertEqual(list(instance.rel.all()), [])
|
|
|
|
# def test_update_empty_relationship(self):
|
|
# """
|
|
# Update an instance of a model with a ManyToMany relationship,
|
|
# containing no items.
|
|
# """
|
|
# new_anchor = Anchor()
|
|
# new_anchor.save()
|
|
# data = {'rel': []}
|
|
# serializer = self.serializer_class(self.instance, data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
# self.assertEqual(len(ManyToManyModel.objects.all()), 1)
|
|
# self.assertEqual(instance.pk, 1)
|
|
# self.assertEqual(list(instance.rel.all()), [])
|
|
|
|
# def test_create_empty_relationship_flat_data(self):
|
|
# """
|
|
# Create an instance of a model with a ManyToMany relationship,
|
|
# containing no items, using a representation that does not support
|
|
# lists (eg form data).
|
|
# """
|
|
# data = MultiValueDict()
|
|
# data.setlist('rel', [''])
|
|
# serializer = self.serializer_class(data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
# self.assertEqual(len(ManyToManyModel.objects.all()), 2)
|
|
# self.assertEqual(instance.pk, 2)
|
|
# self.assertEqual(list(instance.rel.all()), [])
|
|
|
|
|
|
# class ReadOnlyManyToManyTests(TestCase):
|
|
# def setUp(self):
|
|
# class ReadOnlyManyToManySerializer(serializers.ModelSerializer):
|
|
# rel = serializers.RelatedField(many=True, read_only=True)
|
|
|
|
# class Meta:
|
|
# model = ReadOnlyManyToManyModel
|
|
|
|
# self.serializer_class = ReadOnlyManyToManySerializer
|
|
|
|
# # An anchor instance to use for the relationship
|
|
# self.anchor = Anchor()
|
|
# self.anchor.save()
|
|
|
|
# # A model instance with a many to many relationship to the anchor
|
|
# self.instance = ReadOnlyManyToManyModel()
|
|
# self.instance.save()
|
|
# self.instance.rel.add(self.anchor)
|
|
|
|
# # A serialized representation of the model instance
|
|
# self.data = {'rel': [self.anchor.id], 'id': 1, 'text': 'anchor'}
|
|
|
|
# def test_update(self):
|
|
# """
|
|
# Attempt to update an instance of a model with a ManyToMany
|
|
# relationship. Not updated due to read_only=True
|
|
# """
|
|
# new_anchor = Anchor()
|
|
# new_anchor.save()
|
|
# data = {'rel': [self.anchor.id, new_anchor.id]}
|
|
# serializer = self.serializer_class(self.instance, data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
# self.assertEqual(len(ReadOnlyManyToManyModel.objects.all()), 1)
|
|
# self.assertEqual(instance.pk, 1)
|
|
# # rel is still as original (1 entry)
|
|
# self.assertEqual(list(instance.rel.all()), [self.anchor])
|
|
|
|
# def test_update_without_relationship(self):
|
|
# """
|
|
# Attempt to update an instance of a model where many to ManyToMany
|
|
# relationship is not supplied. Not updated due to read_only=True
|
|
# """
|
|
# new_anchor = Anchor()
|
|
# new_anchor.save()
|
|
# data = {}
|
|
# serializer = self.serializer_class(self.instance, data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
# self.assertEqual(len(ReadOnlyManyToManyModel.objects.all()), 1)
|
|
# self.assertEqual(instance.pk, 1)
|
|
# # rel is still as original (1 entry)
|
|
# self.assertEqual(list(instance.rel.all()), [self.anchor])
|
|
|
|
|
|
# class DefaultValueTests(TestCase):
|
|
# def setUp(self):
|
|
# class DefaultValueSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = DefaultValueModel
|
|
|
|
# self.serializer_class = DefaultValueSerializer
|
|
# self.objects = DefaultValueModel.objects
|
|
|
|
# def test_create_using_default(self):
|
|
# data = {}
|
|
# serializer = self.serializer_class(data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
# self.assertEqual(len(self.objects.all()), 1)
|
|
# self.assertEqual(instance.pk, 1)
|
|
# self.assertEqual(instance.text, 'foobar')
|
|
|
|
# def test_create_overriding_default(self):
|
|
# data = {'text': 'overridden'}
|
|
# serializer = self.serializer_class(data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
# self.assertEqual(len(self.objects.all()), 1)
|
|
# self.assertEqual(instance.pk, 1)
|
|
# self.assertEqual(instance.text, 'overridden')
|
|
|
|
# def test_partial_update_default(self):
|
|
# """ Regression test for issue #532 """
|
|
# data = {'text': 'overridden'}
|
|
# serializer = self.serializer_class(data=data, partial=True)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
|
|
# data = {'extra': 'extra_value'}
|
|
# serializer = self.serializer_class(instance=instance, data=data, partial=True)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
|
|
# self.assertEqual(instance.extra, 'extra_value')
|
|
# self.assertEqual(instance.text, 'overridden')
|
|
|
|
|
|
# class WritableFieldDefaultValueTests(TestCase):
|
|
|
|
# def setUp(self):
|
|
# self.expected = {'default': 'value'}
|
|
# self.create_field = fields.WritableField
|
|
|
|
# def test_get_default_value_with_noncallable(self):
|
|
# field = self.create_field(default=self.expected)
|
|
# got = field.get_default_value()
|
|
# self.assertEqual(got, self.expected)
|
|
|
|
# def test_get_default_value_with_callable(self):
|
|
# field = self.create_field(default=lambda: self.expected)
|
|
# got = field.get_default_value()
|
|
# self.assertEqual(got, self.expected)
|
|
|
|
# def test_get_default_value_when_not_required(self):
|
|
# field = self.create_field(default=self.expected, required=False)
|
|
# got = field.get_default_value()
|
|
# self.assertEqual(got, self.expected)
|
|
|
|
# def test_get_default_value_returns_None(self):
|
|
# field = self.create_field()
|
|
# got = field.get_default_value()
|
|
# self.assertIsNone(got)
|
|
|
|
# def test_get_default_value_returns_non_True_values(self):
|
|
# values = [None, '', False, 0, [], (), {}] # values that assumed as 'False' in the 'if' clause
|
|
# for expected in values:
|
|
# field = self.create_field(default=expected)
|
|
# got = field.get_default_value()
|
|
# self.assertEqual(got, expected)
|
|
|
|
|
|
# class RelatedFieldDefaultValueTests(WritableFieldDefaultValueTests):
|
|
|
|
# def setUp(self):
|
|
# self.expected = {'foo': 'bar'}
|
|
# self.create_field = relations.RelatedField
|
|
|
|
# def test_get_default_value_returns_empty_list(self):
|
|
# field = self.create_field(many=True)
|
|
# got = field.get_default_value()
|
|
# self.assertListEqual(got, [])
|
|
|
|
# def test_get_default_value_returns_expected(self):
|
|
# expected = [1, 2, 3]
|
|
# field = self.create_field(many=True, default=expected)
|
|
# got = field.get_default_value()
|
|
# self.assertListEqual(got, expected)
|
|
|
|
|
|
# class CallableDefaultValueTests(TestCase):
|
|
# def setUp(self):
|
|
# class CallableDefaultValueSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = CallableDefaultValueModel
|
|
|
|
# self.serializer_class = CallableDefaultValueSerializer
|
|
# self.objects = CallableDefaultValueModel.objects
|
|
|
|
# def test_create_using_default(self):
|
|
# data = {}
|
|
# serializer = self.serializer_class(data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
# self.assertEqual(len(self.objects.all()), 1)
|
|
# self.assertEqual(instance.pk, 1)
|
|
# self.assertEqual(instance.text, 'foobar')
|
|
|
|
# def test_create_overriding_default(self):
|
|
# data = {'text': 'overridden'}
|
|
# serializer = self.serializer_class(data=data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# instance = serializer.save()
|
|
# self.assertEqual(len(self.objects.all()), 1)
|
|
# self.assertEqual(instance.pk, 1)
|
|
# self.assertEqual(instance.text, 'overridden')
|
|
|
|
|
|
# class ManyRelatedTests(TestCase):
|
|
# def test_reverse_relations(self):
|
|
# post = BlogPost.objects.create(title="Test blog post")
|
|
# post.blogpostcomment_set.create(text="I hate this blog post")
|
|
# post.blogpostcomment_set.create(text="I love this blog post")
|
|
|
|
# class BlogPostCommentSerializer(serializers.Serializer):
|
|
# text = serializers.CharField()
|
|
|
|
# class BlogPostSerializer(serializers.Serializer):
|
|
# title = serializers.CharField()
|
|
# comments = BlogPostCommentSerializer(source='blogpostcomment_set')
|
|
|
|
# serializer = BlogPostSerializer(instance=post)
|
|
# expected = {
|
|
# 'title': 'Test blog post',
|
|
# 'comments': [
|
|
# {'text': 'I hate this blog post'},
|
|
# {'text': 'I love this blog post'}
|
|
# ]
|
|
# }
|
|
|
|
# self.assertEqual(serializer.data, expected)
|
|
|
|
# def test_include_reverse_relations(self):
|
|
# post = BlogPost.objects.create(title="Test blog post")
|
|
# post.blogpostcomment_set.create(text="I hate this blog post")
|
|
# post.blogpostcomment_set.create(text="I love this blog post")
|
|
|
|
# class BlogPostSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = BlogPost
|
|
# fields = ('id', 'title', 'blogpostcomment_set')
|
|
|
|
# serializer = BlogPostSerializer(instance=post)
|
|
# expected = {
|
|
# 'id': 1, 'title': 'Test blog post', 'blogpostcomment_set': [1, 2]
|
|
# }
|
|
# self.assertEqual(serializer.data, expected)
|
|
|
|
# def test_depth_include_reverse_relations(self):
|
|
# post = BlogPost.objects.create(title="Test blog post")
|
|
# post.blogpostcomment_set.create(text="I hate this blog post")
|
|
# post.blogpostcomment_set.create(text="I love this blog post")
|
|
|
|
# class BlogPostSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = BlogPost
|
|
# fields = ('id', 'title', 'blogpostcomment_set')
|
|
# depth = 1
|
|
|
|
# serializer = BlogPostSerializer(instance=post)
|
|
# expected = {
|
|
# 'id': 1, 'title': 'Test blog post',
|
|
# 'blogpostcomment_set': [
|
|
# {'id': 1, 'text': 'I hate this blog post', 'blog_post': 1},
|
|
# {'id': 2, 'text': 'I love this blog post', 'blog_post': 1}
|
|
# ]
|
|
# }
|
|
# self.assertEqual(serializer.data, expected)
|
|
|
|
# def test_callable_source(self):
|
|
# post = BlogPost.objects.create(title="Test blog post")
|
|
# post.blogpostcomment_set.create(text="I love this blog post")
|
|
|
|
# class BlogPostCommentSerializer(serializers.Serializer):
|
|
# text = serializers.CharField()
|
|
|
|
# class BlogPostSerializer(serializers.Serializer):
|
|
# title = serializers.CharField()
|
|
# first_comment = BlogPostCommentSerializer(source='get_first_comment')
|
|
|
|
# serializer = BlogPostSerializer(post)
|
|
|
|
# expected = {
|
|
# 'title': 'Test blog post',
|
|
# 'first_comment': {'text': 'I love this blog post'}
|
|
# }
|
|
# self.assertEqual(serializer.data, expected)
|
|
|
|
|
|
# class RelatedTraversalTest(TestCase):
|
|
# def test_nested_traversal(self):
|
|
# """
|
|
# Source argument should support dotted.source notation.
|
|
# """
|
|
# user = Person.objects.create(name="django")
|
|
# post = BlogPost.objects.create(title="Test blog post", writer=user)
|
|
# post.blogpostcomment_set.create(text="I love this blog post")
|
|
|
|
# class PersonSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = Person
|
|
# fields = ("name", "age")
|
|
|
|
# class BlogPostCommentSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = BlogPostComment
|
|
# fields = ("text", "post_owner")
|
|
|
|
# text = serializers.CharField()
|
|
# post_owner = PersonSerializer(source='blog_post.writer')
|
|
|
|
# class BlogPostSerializer(serializers.Serializer):
|
|
# title = serializers.CharField()
|
|
# comments = BlogPostCommentSerializer(source='blogpostcomment_set')
|
|
|
|
# serializer = BlogPostSerializer(instance=post)
|
|
|
|
# expected = {
|
|
# 'title': 'Test blog post',
|
|
# 'comments': [{
|
|
# 'text': 'I love this blog post',
|
|
# 'post_owner': {
|
|
# "name": "django",
|
|
# "age": None
|
|
# }
|
|
# }]
|
|
# }
|
|
|
|
# self.assertEqual(serializer.data, expected)
|
|
|
|
# def test_nested_traversal_with_none(self):
|
|
# """
|
|
# If a component of the dotted.source is None, return None for the field.
|
|
# """
|
|
# from tests.models import NullableForeignKeySource
|
|
# instance = NullableForeignKeySource.objects.create(name='Source with null FK')
|
|
|
|
# class NullableSourceSerializer(serializers.Serializer):
|
|
# target_name = serializers.Field(source='target.name')
|
|
|
|
# serializer = NullableSourceSerializer(instance=instance)
|
|
|
|
# expected = {
|
|
# 'target_name': None,
|
|
# }
|
|
|
|
# self.assertEqual(serializer.data, expected)
|
|
|
|
|
|
# class SerializerMethodFieldTests(TestCase):
|
|
# def setUp(self):
|
|
|
|
# class BoopSerializer(serializers.Serializer):
|
|
# beep = serializers.SerializerMethodField('get_beep')
|
|
# boop = serializers.Field()
|
|
# boop_count = serializers.SerializerMethodField('get_boop_count')
|
|
|
|
# def get_beep(self, obj):
|
|
# return 'hello!'
|
|
|
|
# def get_boop_count(self, obj):
|
|
# return len(obj.boop)
|
|
|
|
# self.serializer_class = BoopSerializer
|
|
|
|
# def test_serializer_method_field(self):
|
|
|
|
# class MyModel(object):
|
|
# boop = ['a', 'b', 'c']
|
|
|
|
# source_data = MyModel()
|
|
|
|
# serializer = self.serializer_class(source_data)
|
|
|
|
# expected = {
|
|
# 'beep': 'hello!',
|
|
# 'boop': ['a', 'b', 'c'],
|
|
# 'boop_count': 3,
|
|
# }
|
|
|
|
# self.assertEqual(serializer.data, expected)
|
|
|
|
|
|
# # Test for issue #324
|
|
# class BlankFieldTests(TestCase):
|
|
# def setUp(self):
|
|
|
|
# class BlankFieldModelSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = BlankFieldModel
|
|
|
|
# class BlankFieldSerializer(serializers.Serializer):
|
|
# title = serializers.CharField(required=False)
|
|
|
|
# class NotBlankFieldModelSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = BasicModel
|
|
|
|
# class NotBlankFieldSerializer(serializers.Serializer):
|
|
# title = serializers.CharField()
|
|
|
|
# self.model_serializer_class = BlankFieldModelSerializer
|
|
# self.serializer_class = BlankFieldSerializer
|
|
# self.not_blank_model_serializer_class = NotBlankFieldModelSerializer
|
|
# self.not_blank_serializer_class = NotBlankFieldSerializer
|
|
# self.data = {'title': ''}
|
|
|
|
# def test_create_blank_field(self):
|
|
# serializer = self.serializer_class(data=self.data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
|
|
# def test_create_model_blank_field(self):
|
|
# serializer = self.model_serializer_class(data=self.data)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
|
|
# def test_create_model_null_field(self):
|
|
# serializer = self.model_serializer_class(data={'title': None})
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# serializer.save()
|
|
# self.assertIsNot(serializer.object.pk, None)
|
|
# self.assertEqual(serializer.object.title, '')
|
|
|
|
# def test_create_not_blank_field(self):
|
|
# """
|
|
# Test to ensure blank data in a field not marked as blank=True
|
|
# is considered invalid in a non-model serializer
|
|
# """
|
|
# serializer = self.not_blank_serializer_class(data=self.data)
|
|
# self.assertEqual(serializer.is_valid(), False)
|
|
|
|
# def test_create_model_not_blank_field(self):
|
|
# """
|
|
# Test to ensure blank data in a field not marked as blank=True
|
|
# is considered invalid in a model serializer
|
|
# """
|
|
# serializer = self.not_blank_model_serializer_class(data=self.data)
|
|
# self.assertEqual(serializer.is_valid(), False)
|
|
|
|
# def test_create_model_empty_field(self):
|
|
# serializer = self.model_serializer_class(data={})
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
|
|
# def test_create_model_null_field_save(self):
|
|
# """
|
|
# Regression test for #1330.
|
|
|
|
# https://github.com/tomchristie/django-rest-framework/pull/1330
|
|
# """
|
|
# serializer = self.model_serializer_class(data={'title': None})
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
|
|
# try:
|
|
# serializer.save()
|
|
# except Exception:
|
|
# self.fail('Exception raised on save() after validation passes')
|
|
|
|
|
|
# # Test for issue #460
|
|
# class SerializerPickleTests(TestCase):
|
|
# """
|
|
# Test pickleability of the output of Serializers
|
|
# """
|
|
# def test_pickle_simple_model_serializer_data(self):
|
|
# """
|
|
# Test simple serializer
|
|
# """
|
|
# pickle.dumps(PersonSerializer(Person(name="Methusela", age=969)).data)
|
|
|
|
# def test_pickle_inner_serializer(self):
|
|
# """
|
|
# Test pickling a serializer whose resulting .data (a SortedDictWithMetadata) will
|
|
# have unpickleable meta data--in order to make sure metadata doesn't get pulled into the pickle.
|
|
# See DictWithMetadata.__getstate__
|
|
# """
|
|
# class InnerPersonSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = Person
|
|
# fields = ('name', 'age')
|
|
# pickle.dumps(InnerPersonSerializer(Person(name="Noah", age=950)).data, 0)
|
|
|
|
# def test_getstate_method_should_not_return_none(self):
|
|
# """
|
|
# Regression test for #645.
|
|
# """
|
|
# data = serializers.DictWithMetadata({1: 1})
|
|
# self.assertEqual(data.__getstate__(), serializers.SortedDict({1: 1}))
|
|
|
|
# def test_serializer_data_is_pickleable(self):
|
|
# """
|
|
# Another regression test for #645.
|
|
# """
|
|
# data = serializers.SortedDictWithMetadata({1: 1})
|
|
# repr(pickle.loads(pickle.dumps(data, 0)))
|
|
|
|
|
|
# # test for issue #725
|
|
# class SeveralChoicesModel(models.Model):
|
|
# color = models.CharField(
|
|
# max_length=10,
|
|
# choices=[('red', 'Red'), ('green', 'Green'), ('blue', 'Blue')],
|
|
# blank=False
|
|
# )
|
|
# drink = models.CharField(
|
|
# max_length=10,
|
|
# choices=[('beer', 'Beer'), ('wine', 'Wine'), ('cider', 'Cider')],
|
|
# blank=False,
|
|
# default='beer'
|
|
# )
|
|
# os = models.CharField(
|
|
# max_length=10,
|
|
# choices=[('linux', 'Linux'), ('osx', 'OSX'), ('windows', 'Windows')],
|
|
# blank=True
|
|
# )
|
|
# music_genre = models.CharField(
|
|
# max_length=10,
|
|
# choices=[('rock', 'Rock'), ('metal', 'Metal'), ('grunge', 'Grunge')],
|
|
# blank=True,
|
|
# default='metal'
|
|
# )
|
|
|
|
|
|
# class SerializerChoiceFields(TestCase):
|
|
|
|
# def setUp(self):
|
|
# super(SerializerChoiceFields, self).setUp()
|
|
|
|
# class SeveralChoicesSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = SeveralChoicesModel
|
|
# fields = ('color', 'drink', 'os', 'music_genre')
|
|
|
|
# self.several_choices_serializer = SeveralChoicesSerializer
|
|
|
|
# def test_choices_blank_false_not_default(self):
|
|
# serializer = self.several_choices_serializer()
|
|
# self.assertEqual(
|
|
# serializer.fields['color'].choices,
|
|
# [('red', 'Red'), ('green', 'Green'), ('blue', 'Blue')]
|
|
# )
|
|
|
|
# def test_choices_blank_false_with_default(self):
|
|
# serializer = self.several_choices_serializer()
|
|
# self.assertEqual(
|
|
# serializer.fields['drink'].choices,
|
|
# [('beer', 'Beer'), ('wine', 'Wine'), ('cider', 'Cider')]
|
|
# )
|
|
|
|
# def test_choices_blank_true_not_default(self):
|
|
# serializer = self.several_choices_serializer()
|
|
# self.assertEqual(
|
|
# serializer.fields['os'].choices,
|
|
# BLANK_CHOICE_DASH + [('linux', 'Linux'), ('osx', 'OSX'), ('windows', 'Windows')]
|
|
# )
|
|
|
|
# def test_choices_blank_true_with_default(self):
|
|
# serializer = self.several_choices_serializer()
|
|
# self.assertEqual(
|
|
# serializer.fields['music_genre'].choices,
|
|
# BLANK_CHOICE_DASH + [('rock', 'Rock'), ('metal', 'Metal'), ('grunge', 'Grunge')]
|
|
# )
|
|
|
|
|
|
# # Regression tests for #675
|
|
# class Ticket(models.Model):
|
|
# assigned = models.ForeignKey(
|
|
# Person, related_name='assigned_tickets')
|
|
# reviewer = models.ForeignKey(
|
|
# Person, blank=True, null=True, related_name='reviewed_tickets')
|
|
|
|
|
|
# class SerializerRelatedChoicesTest(TestCase):
|
|
|
|
# def setUp(self):
|
|
# super(SerializerRelatedChoicesTest, self).setUp()
|
|
|
|
# class RelatedChoicesSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = Ticket
|
|
# fields = ('assigned', 'reviewer')
|
|
|
|
# self.related_fields_serializer = RelatedChoicesSerializer
|
|
|
|
# def test_empty_queryset_required(self):
|
|
# serializer = self.related_fields_serializer()
|
|
# self.assertEqual(serializer.fields['assigned'].queryset.count(), 0)
|
|
# self.assertEqual(
|
|
# [x for x in serializer.fields['assigned'].widget.choices],
|
|
# []
|
|
# )
|
|
|
|
# def test_empty_queryset_not_required(self):
|
|
# serializer = self.related_fields_serializer()
|
|
# self.assertEqual(serializer.fields['reviewer'].queryset.count(), 0)
|
|
# self.assertEqual(
|
|
# [x for x in serializer.fields['reviewer'].widget.choices],
|
|
# [('', '---------')]
|
|
# )
|
|
|
|
# def test_with_some_persons_required(self):
|
|
# Person.objects.create(name="Lionel Messi")
|
|
# Person.objects.create(name="Xavi Hernandez")
|
|
# serializer = self.related_fields_serializer()
|
|
# self.assertEqual(serializer.fields['assigned'].queryset.count(), 2)
|
|
# self.assertEqual(
|
|
# [x for x in serializer.fields['assigned'].widget.choices],
|
|
# [(1, 'Person object - 1'), (2, 'Person object - 2')]
|
|
# )
|
|
|
|
# def test_with_some_persons_not_required(self):
|
|
# Person.objects.create(name="Lionel Messi")
|
|
# Person.objects.create(name="Xavi Hernandez")
|
|
# serializer = self.related_fields_serializer()
|
|
# self.assertEqual(serializer.fields['reviewer'].queryset.count(), 2)
|
|
# self.assertEqual(
|
|
# [x for x in serializer.fields['reviewer'].widget.choices],
|
|
# [('', '---------'), (1, 'Person object - 1'), (2, 'Person object - 2')]
|
|
# )
|
|
|
|
|
|
# class DepthTest(TestCase):
|
|
# def test_implicit_nesting(self):
|
|
|
|
# writer = Person.objects.create(name="django", age=1)
|
|
# post = BlogPost.objects.create(title="Test blog post", writer=writer)
|
|
# comment = BlogPostComment.objects.create(text="Test blog post comment", blog_post=post)
|
|
|
|
# class BlogPostCommentSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = BlogPostComment
|
|
# depth = 2
|
|
|
|
# serializer = BlogPostCommentSerializer(instance=comment)
|
|
# expected = {'id': 1, 'text': 'Test blog post comment', 'blog_post': {'id': 1, 'title': 'Test blog post',
|
|
# 'writer': {'id': 1, 'name': 'django', 'age': 1}}}
|
|
|
|
# self.assertEqual(serializer.data, expected)
|
|
|
|
# def test_explicit_nesting(self):
|
|
# writer = Person.objects.create(name="django", age=1)
|
|
# post = BlogPost.objects.create(title="Test blog post", writer=writer)
|
|
# comment = BlogPostComment.objects.create(text="Test blog post comment", blog_post=post)
|
|
|
|
# class PersonSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = Person
|
|
|
|
# class BlogPostSerializer(serializers.ModelSerializer):
|
|
# writer = PersonSerializer()
|
|
|
|
# class Meta:
|
|
# model = BlogPost
|
|
|
|
# class BlogPostCommentSerializer(serializers.ModelSerializer):
|
|
# blog_post = BlogPostSerializer()
|
|
|
|
# class Meta:
|
|
# model = BlogPostComment
|
|
|
|
# serializer = BlogPostCommentSerializer(instance=comment)
|
|
# expected = {'id': 1, 'text': 'Test blog post comment', 'blog_post': {'id': 1, 'title': 'Test blog post',
|
|
# 'writer': {'id': 1, 'name': 'django', 'age': 1}}}
|
|
|
|
# self.assertEqual(serializer.data, expected)
|
|
|
|
|
|
# class NestedSerializerContextTests(TestCase):
|
|
|
|
# def test_nested_serializer_context(self):
|
|
# """
|
|
# Regression for #497
|
|
|
|
# https://github.com/tomchristie/django-rest-framework/issues/497
|
|
# """
|
|
# class PhotoSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = Photo
|
|
# fields = ("description", "callable")
|
|
|
|
# callable = serializers.SerializerMethodField('_callable')
|
|
|
|
# def _callable(self, instance):
|
|
# if 'context_item' not in self.context:
|
|
# raise RuntimeError("context isn't getting passed into 2nd level nested serializer")
|
|
# return "success"
|
|
|
|
# class AlbumSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = Album
|
|
# fields = ("photo_set", "callable")
|
|
|
|
# photo_set = PhotoSerializer(source="photo_set", many=True)
|
|
# callable = serializers.SerializerMethodField("_callable")
|
|
|
|
# def _callable(self, instance):
|
|
# if 'context_item' not in self.context:
|
|
# raise RuntimeError("context isn't getting passed into 1st level nested serializer")
|
|
# return "success"
|
|
|
|
# class AlbumCollection(object):
|
|
# albums = None
|
|
|
|
# class AlbumCollectionSerializer(serializers.Serializer):
|
|
# albums = AlbumSerializer(source="albums", many=True)
|
|
|
|
# album1 = Album.objects.create(title="album 1")
|
|
# album2 = Album.objects.create(title="album 2")
|
|
# Photo.objects.create(description="Bigfoot", album=album1)
|
|
# Photo.objects.create(description="Unicorn", album=album1)
|
|
# Photo.objects.create(description="Yeti", album=album2)
|
|
# Photo.objects.create(description="Sasquatch", album=album2)
|
|
# album_collection = AlbumCollection()
|
|
# album_collection.albums = [album1, album2]
|
|
|
|
# # This will raise RuntimeError if context doesn't get passed correctly to the nested Serializers
|
|
# AlbumCollectionSerializer(album_collection, context={'context_item': 'album context'}).data
|
|
|
|
|
|
# class DeserializeListTestCase(TestCase):
|
|
|
|
# def setUp(self):
|
|
# self.data = {
|
|
# 'email': 'nobody@nowhere.com',
|
|
# 'content': 'This is some test content',
|
|
# 'created': datetime.datetime(2013, 3, 7),
|
|
# }
|
|
|
|
# def test_no_errors(self):
|
|
# data = [self.data.copy() for x in range(0, 3)]
|
|
# serializer = CommentSerializer(data=data, many=True)
|
|
# self.assertTrue(serializer.is_valid())
|
|
# self.assertTrue(isinstance(serializer.object, list))
|
|
# self.assertTrue(
|
|
# all((isinstance(item, Comment) for item in serializer.object))
|
|
# )
|
|
|
|
# def test_errors_return_as_list(self):
|
|
# invalid_item = self.data.copy()
|
|
# invalid_item['email'] = ''
|
|
# data = [self.data.copy(), invalid_item, self.data.copy()]
|
|
|
|
# serializer = CommentSerializer(data=data, many=True)
|
|
# self.assertFalse(serializer.is_valid())
|
|
# expected = [{}, {'email': ['This field is required.']}, {}]
|
|
# self.assertEqual(serializer.errors, expected)
|
|
|
|
|
|
# # Test for issue 747
|
|
|
|
# class LazyStringModel(object):
|
|
# def __init__(self, lazystring):
|
|
# self.lazystring = lazystring
|
|
|
|
|
|
# class LazyStringSerializer(serializers.Serializer):
|
|
# lazystring = serializers.Field()
|
|
|
|
# def restore_object(self, attrs, instance=None):
|
|
# if instance is not None:
|
|
# instance.lazystring = attrs.get('lazystring', instance.lazystring)
|
|
# return instance
|
|
# return LazyStringModel(**attrs)
|
|
|
|
|
|
# class LazyStringsTestCase(TestCase):
|
|
# def setUp(self):
|
|
# self.model = LazyStringModel(lazystring=_('lazystring'))
|
|
|
|
# def test_lazy_strings_are_translated(self):
|
|
# serializer = LazyStringSerializer(self.model)
|
|
# self.assertEqual(type(serializer.data['lazystring']),
|
|
# type('lazystring'))
|
|
|
|
|
|
# # Test for issue #467
|
|
|
|
# class FieldLabelTest(TestCase):
|
|
# def setUp(self):
|
|
# self.serializer_class = BasicModelSerializer
|
|
|
|
# def test_label_from_model(self):
|
|
# """
|
|
# Validates that label and help_text are correctly copied from the model class.
|
|
# """
|
|
# serializer = self.serializer_class()
|
|
# text_field = serializer.fields['text']
|
|
|
|
# self.assertEqual('Text comes here', text_field.label)
|
|
# self.assertEqual('Text description.', text_field.help_text)
|
|
|
|
# def test_field_ctor(self):
|
|
# """
|
|
# This is check that ctor supports both label and help_text.
|
|
# """
|
|
# self.assertEqual('Label', fields.Field(label='Label', help_text='Help').label)
|
|
# self.assertEqual('Help', fields.CharField(label='Label', help_text='Help').help_text)
|
|
# self.assertEqual('Label', relations.HyperlinkedRelatedField(view_name='fake', label='Label', help_text='Help', many=True).label)
|
|
|
|
|
|
# # Test for issue #961
|
|
|
|
# class ManyFieldHelpTextTest(TestCase):
|
|
# def test_help_text_no_hold_down_control_msg(self):
|
|
# """
|
|
# Validate that help_text doesn't contain the 'Hold down "Control" ...'
|
|
# message that Django appends to choice fields.
|
|
# """
|
|
# rel_field = fields.Field(help_text=ManyToManyModel._meta.get_field('rel').help_text)
|
|
# self.assertEqual('Some help text.', rel_field.help_text)
|
|
|
|
|
|
# class AttributeMappingOnAutogeneratedRelatedFields(TestCase):
|
|
|
|
# def test_primary_key_related_field(self):
|
|
# serializer = ForeignKeySourceSerializer()
|
|
# self.assertEqual(serializer.fields['target'].help_text, 'Target')
|
|
# self.assertEqual(serializer.fields['target'].label, 'Target')
|
|
|
|
# def test_hyperlinked_related_field(self):
|
|
# serializer = HyperlinkedForeignKeySourceSerializer()
|
|
# self.assertEqual(serializer.fields['target'].help_text, 'Target')
|
|
# self.assertEqual(serializer.fields['target'].label, 'Target')
|
|
|
|
|
|
# @unittest.skipUnless(PIL is not None, 'PIL is not installed')
|
|
# class AttributeMappingOnAutogeneratedFieldsTests(TestCase):
|
|
|
|
# def setUp(self):
|
|
|
|
# class AMOAFSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = AMOAFModel
|
|
|
|
# self.serializer_class = AMOAFSerializer
|
|
# self.fields_attributes = {
|
|
# 'char_field': [
|
|
# ('max_length', 1024),
|
|
# ],
|
|
# 'comma_separated_integer_field': [
|
|
# ('max_length', 1024),
|
|
# ],
|
|
# 'decimal_field': [
|
|
# ('max_digits', 64),
|
|
# ('decimal_places', 32),
|
|
# ],
|
|
# 'email_field': [
|
|
# ('max_length', 1024),
|
|
# ],
|
|
# 'file_field': [
|
|
# ('max_length', 1024),
|
|
# ],
|
|
# 'image_field': [
|
|
# ('max_length', 1024),
|
|
# ],
|
|
# 'slug_field': [
|
|
# ('max_length', 1024),
|
|
# ],
|
|
# 'url_field': [
|
|
# ('max_length', 1024),
|
|
# ],
|
|
# 'nullable_char_field': [
|
|
# ('max_length', 1024),
|
|
# ('allow_none', True),
|
|
# ],
|
|
# }
|
|
|
|
# def field_test(self, field):
|
|
# serializer = self.serializer_class(data={})
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
|
|
# for attribute in self.fields_attributes[field]:
|
|
# self.assertEqual(
|
|
# getattr(serializer.fields[field], attribute[0]),
|
|
# attribute[1]
|
|
# )
|
|
|
|
# def test_char_field(self):
|
|
# self.field_test('char_field')
|
|
|
|
# def test_comma_separated_integer_field(self):
|
|
# self.field_test('comma_separated_integer_field')
|
|
|
|
# def test_decimal_field(self):
|
|
# self.field_test('decimal_field')
|
|
|
|
# def test_email_field(self):
|
|
# self.field_test('email_field')
|
|
|
|
# def test_file_field(self):
|
|
# self.field_test('file_field')
|
|
|
|
# def test_image_field(self):
|
|
# self.field_test('image_field')
|
|
|
|
# def test_slug_field(self):
|
|
# self.field_test('slug_field')
|
|
|
|
# def test_url_field(self):
|
|
# self.field_test('url_field')
|
|
|
|
# def test_nullable_char_field(self):
|
|
# self.field_test('nullable_char_field')
|
|
|
|
|
|
# @unittest.skipUnless(PIL is not None, 'PIL is not installed')
|
|
# class DefaultValuesOnAutogeneratedFieldsTests(TestCase):
|
|
|
|
# def setUp(self):
|
|
|
|
# class DVOAFSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = DVOAFModel
|
|
|
|
# self.serializer_class = DVOAFSerializer
|
|
# self.fields_attributes = {
|
|
# 'positive_integer_field': [
|
|
# ('min_value', 0),
|
|
# ],
|
|
# 'positive_small_integer_field': [
|
|
# ('min_value', 0),
|
|
# ],
|
|
# 'email_field': [
|
|
# ('max_length', 75),
|
|
# ],
|
|
# 'file_field': [
|
|
# ('max_length', 100),
|
|
# ],
|
|
# 'image_field': [
|
|
# ('max_length', 100),
|
|
# ],
|
|
# 'slug_field': [
|
|
# ('max_length', 50),
|
|
# ],
|
|
# 'url_field': [
|
|
# ('max_length', 200),
|
|
# ],
|
|
# }
|
|
|
|
# def field_test(self, field):
|
|
# serializer = self.serializer_class(data={})
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
|
|
# for attribute in self.fields_attributes[field]:
|
|
# self.assertEqual(
|
|
# getattr(serializer.fields[field], attribute[0]),
|
|
# attribute[1]
|
|
# )
|
|
|
|
# def test_positive_integer_field(self):
|
|
# self.field_test('positive_integer_field')
|
|
|
|
# def test_positive_small_integer_field(self):
|
|
# self.field_test('positive_small_integer_field')
|
|
|
|
# def test_email_field(self):
|
|
# self.field_test('email_field')
|
|
|
|
# def test_file_field(self):
|
|
# self.field_test('file_field')
|
|
|
|
# def test_image_field(self):
|
|
# self.field_test('image_field')
|
|
|
|
# def test_slug_field(self):
|
|
# self.field_test('slug_field')
|
|
|
|
# def test_url_field(self):
|
|
# self.field_test('url_field')
|
|
|
|
|
|
# class MetadataSerializer(serializers.Serializer):
|
|
# field1 = serializers.CharField(max_length=3, required=True)
|
|
# field2 = serializers.CharField(max_length=10, required=False)
|
|
|
|
|
|
# class MetadataSerializerTestCase(TestCase):
|
|
# def setUp(self):
|
|
# self.serializer = MetadataSerializer()
|
|
|
|
# def test_serializer_metadata(self):
|
|
# metadata = self.serializer.metadata()
|
|
# expected = {
|
|
# 'field1': {
|
|
# 'required': True,
|
|
# 'max_length': 3,
|
|
# 'type': 'string',
|
|
# 'read_only': False
|
|
# },
|
|
# 'field2': {
|
|
# 'required': False,
|
|
# 'max_length': 10,
|
|
# 'type': 'string',
|
|
# 'read_only': False
|
|
# }
|
|
# }
|
|
# self.assertEqual(expected, metadata)
|
|
|
|
|
|
# # Regression test for #840
|
|
|
|
# class SimpleModel(models.Model):
|
|
# text = models.CharField(max_length=100)
|
|
|
|
|
|
# class SimpleModelSerializer(serializers.ModelSerializer):
|
|
# text = serializers.CharField()
|
|
# other = serializers.CharField()
|
|
|
|
# class Meta:
|
|
# model = SimpleModel
|
|
|
|
# def validate_other(self, attrs, source):
|
|
# del attrs['other']
|
|
# return attrs
|
|
|
|
|
|
# class FieldValidationRemovingAttr(TestCase):
|
|
# def test_removing_non_model_field_in_validation(self):
|
|
# """
|
|
# Removing an attr during field valiation should ensure that it is not
|
|
# passed through when restoring the object.
|
|
|
|
# This allows additional non-model fields to be supported.
|
|
|
|
# Regression test for #840.
|
|
# """
|
|
# serializer = SimpleModelSerializer(data={'text': 'foo', 'other': 'bar'})
|
|
# self.assertTrue(serializer.is_valid())
|
|
# serializer.save()
|
|
# self.assertEqual(serializer.object.text, 'foo')
|
|
|
|
|
|
# # Regression test for #878
|
|
|
|
# class SimpleTargetModel(models.Model):
|
|
# text = models.CharField(max_length=100)
|
|
|
|
|
|
# class SimplePKSourceModelSerializer(serializers.Serializer):
|
|
# targets = serializers.PrimaryKeyRelatedField(queryset=SimpleTargetModel.objects.all(), many=True)
|
|
# text = serializers.CharField()
|
|
|
|
|
|
# class SimpleSlugSourceModelSerializer(serializers.Serializer):
|
|
# targets = serializers.SlugRelatedField(queryset=SimpleTargetModel.objects.all(), many=True, slug_field='pk')
|
|
# text = serializers.CharField()
|
|
|
|
|
|
# class SerializerSupportsManyRelationships(TestCase):
|
|
# def setUp(self):
|
|
# SimpleTargetModel.objects.create(text='foo')
|
|
# SimpleTargetModel.objects.create(text='bar')
|
|
|
|
# def test_serializer_supports_pk_many_relationships(self):
|
|
# """
|
|
# Regression test for #878.
|
|
|
|
# Note that pk behavior has a different code path to usual cases,
|
|
# for performance reasons.
|
|
# """
|
|
# serializer = SimplePKSourceModelSerializer(data={'text': 'foo', 'targets': [1, 2]})
|
|
# self.assertTrue(serializer.is_valid())
|
|
# self.assertEqual(serializer.data, {'text': 'foo', 'targets': [1, 2]})
|
|
|
|
# def test_serializer_supports_slug_many_relationships(self):
|
|
# """
|
|
# Regression test for #878.
|
|
# """
|
|
# serializer = SimpleSlugSourceModelSerializer(data={'text': 'foo', 'targets': [1, 2]})
|
|
# self.assertTrue(serializer.is_valid())
|
|
# self.assertEqual(serializer.data, {'text': 'foo', 'targets': [1, 2]})
|
|
|
|
|
|
# class TransformMethodsSerializer(serializers.Serializer):
|
|
# a = serializers.CharField()
|
|
# b_renamed = serializers.CharField(source='b')
|
|
|
|
# def transform_a(self, obj, value):
|
|
# return value.lower()
|
|
|
|
# def transform_b_renamed(self, obj, value):
|
|
# if value is not None:
|
|
# return 'and ' + value
|
|
|
|
|
|
# class TestSerializerTransformMethods(TestCase):
|
|
# def setUp(self):
|
|
# self.s = TransformMethodsSerializer()
|
|
|
|
# def test_transform_methods(self):
|
|
# self.assertEqual(
|
|
# self.s.to_native({'a': 'GREEN EGGS', 'b': 'HAM'}),
|
|
# {
|
|
# 'a': 'green eggs',
|
|
# 'b_renamed': 'and HAM',
|
|
# }
|
|
# )
|
|
|
|
# def test_missing_fields(self):
|
|
# self.assertEqual(
|
|
# self.s.to_native({'a': 'GREEN EGGS'}),
|
|
# {
|
|
# 'a': 'green eggs',
|
|
# 'b_renamed': None,
|
|
# }
|
|
# )
|
|
|
|
|
|
# class DefaultTrueBooleanModel(models.Model):
|
|
# cat = models.BooleanField(default=True)
|
|
# dog = models.BooleanField(default=False)
|
|
|
|
|
|
# class SerializerDefaultTrueBoolean(TestCase):
|
|
|
|
# def setUp(self):
|
|
# super(SerializerDefaultTrueBoolean, self).setUp()
|
|
|
|
# class DefaultTrueBooleanSerializer(serializers.ModelSerializer):
|
|
# class Meta:
|
|
# model = DefaultTrueBooleanModel
|
|
# fields = ('cat', 'dog')
|
|
|
|
# self.default_true_boolean_serializer = DefaultTrueBooleanSerializer
|
|
|
|
# def test_enabled_as_false(self):
|
|
# serializer = self.default_true_boolean_serializer(data={'cat': False,
|
|
# 'dog': False})
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# self.assertEqual(serializer.data['cat'], False)
|
|
# self.assertEqual(serializer.data['dog'], False)
|
|
|
|
# def test_enabled_as_true(self):
|
|
# serializer = self.default_true_boolean_serializer(data={'cat': True,
|
|
# 'dog': True})
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# self.assertEqual(serializer.data['cat'], True)
|
|
# self.assertEqual(serializer.data['dog'], True)
|
|
|
|
# def test_enabled_partial(self):
|
|
# serializer = self.default_true_boolean_serializer(data={'cat': False},
|
|
# partial=True)
|
|
# self.assertEqual(serializer.is_valid(), True)
|
|
# self.assertEqual(serializer.data['cat'], False)
|
|
# self.assertEqual(serializer.data['dog'], False)
|
|
|
|
|
|
# class BoolenFieldTypeTest(TestCase):
|
|
# '''
|
|
# Ensure the various Boolean based model fields are rendered as the proper
|
|
# field type
|
|
|
|
# '''
|
|
|
|
# def setUp(self):
|
|
# '''
|
|
# Setup an ActionItemSerializer for BooleanTesting
|
|
# '''
|
|
# data = {
|
|
# 'title': 'b' * 201,
|
|
# }
|
|
# self.serializer = ActionItemSerializer(data=data)
|
|
|
|
# def test_booleanfield_type(self):
|
|
# '''
|
|
# Test that BooleanField is infered from models.BooleanField
|
|
# '''
|
|
# bfield = self.serializer.get_fields()['done']
|
|
# self.assertEqual(type(bfield), fields.BooleanField)
|
|
|
|
# def test_nullbooleanfield_type(self):
|
|
# '''
|
|
# Test that BooleanField is infered from models.NullBooleanField
|
|
|
|
# https://groups.google.com/forum/#!topic/django-rest-framework/D9mXEftpuQ8
|
|
# '''
|
|
# bfield = self.serializer.get_fields()['started']
|
|
# self.assertEqual(type(bfield), fields.BooleanField)
|