Django

Code

root/django/trunk/tests/modeltests/field_subclassing/models.py

Revision 8616, 3.2 kB (checked in by gwilson, 2 weeks ago)

Removed oldforms, validators, and related code:

  • Removed Manipulator, AutomaticManipulator, and related classes.
  • Removed oldforms specific bits from model fields:
    • Removed validator_list and core arguments from constructors.
    • Removed the methods:
      • get_manipulator_field_names
      • get_manipulator_field_objs
      • get_manipulator_fields
      • get_manipulator_new_data
      • prepare_field_objs_and_params
      • get_follow
    • Renamed flatten_data method to value_to_string for better alignment with its use by the serialization framework, which was the only remaining code using flatten_data.
  • Removed oldforms methods from django.db.models.Options class: get_followed_related_objects, get_data_holders, get_follow, and has_field_type.
  • Removed oldforms-admin specific options from django.db.models.fields.related classes: num_in_admin, min_num_in_admin, max_num_in_admin, num_extra_on_change, and edit_inline.
  • Serialization framework
    • Serializer.get_string_value now calls the model fields' renamed value_to_string methods.
    • Removed a special-casing of models.DateTimeField in core.serializers.base.Serializer.get_string_value that's handled by django.db.models.fields.DateTimeField.value_to_string.
  • Removed django.core.validators:
    • Moved ValidationError exception to django.core.exceptions.
    • For the couple places that were using validators, brought over the necessary code to maintain the same functionality.
  • Introduced a SlugField? form field for validation and to compliment the SlugField? model field (refs #8040).
  • Removed an oldforms-style model creation hack (refs #2160).
  • Property svn:eol-style set to native
Line 
1 """
2 Tests for field subclassing.
3 """
4
5 from django.db import models
6 from django.utils.encoding import force_unicode
7 from django.core import serializers
8 from django.core.exceptions import FieldError
9
10 class Small(object):
11     """
12     A simple class to show that non-trivial Python objects can be used as
13     attributes.
14     """
15     def __init__(self, first, second):
16         self.first, self.second = first, second
17
18     def __unicode__(self):
19         return u'%s%s' % (force_unicode(self.first), force_unicode(self.second))
20
21     def __str__(self):
22         return unicode(self).encode('utf-8')
23
24 class SmallField(models.Field):
25     """
26     Turns the "Small" class into a Django field. Because of the similarities
27     with normal character fields and the fact that Small.__unicode__ does
28     something sensible, we don't need to implement a lot here.
29     """
30     __metaclass__ = models.SubfieldBase
31
32     def __init__(self, *args, **kwargs):
33         kwargs['max_length'] = 2
34         super(SmallField, self).__init__(*args, **kwargs)
35
36     def get_internal_type(self):
37         return 'CharField'
38
39     def to_python(self, value):
40         if isinstance(value, Small):
41             return value
42         return Small(value[0], value[1])
43
44     def get_db_prep_save(self, value):
45         return unicode(value)
46
47     def get_db_prep_lookup(self, lookup_type, value):
48         if lookup_type == 'exact':
49             return force_unicode(value)
50         if lookup_type == 'in':
51             return [force_unicode(v) for v in value]
52         if lookup_type == 'isnull':
53             return []
54         raise FieldError('Invalid lookup type: %r' % lookup_type)
55
56 class MyModel(models.Model):
57     name = models.CharField(max_length=10)
58     data = SmallField('small field')
59
60     def __unicode__(self):
61         return force_unicode(self.name)
62
63 __test__ = {'API_TESTS': ur"""
64 # Creating a model with custom fields is done as per normal.
65 >>> s = Small(1, 2)
66 >>> print s
67 12
68 >>> m = MyModel(name='m', data=s)
69 >>> m.save()
70
71 # Custom fields still have normal field's attributes.
72 >>> m._meta.get_field('data').verbose_name
73 'small field'
74
75 # The m.data attribute has been initialised correctly. It's a Small object.
76 >>> m.data.first, m.data.second
77 (1, 2)
78
79 # The data loads back from the database correctly and 'data' has the right type.
80 >>> m1 = MyModel.objects.get(pk=m.pk)
81 >>> isinstance(m1.data, Small)
82 True
83 >>> print m1.data
84 12
85
86 # We can do normal filtering on the custom field (and will get an error when we
87 # use a lookup type that does not make sense).
88 >>> s1 = Small(1, 3)
89 >>> s2 = Small('a', 'b')
90 >>> MyModel.objects.filter(data__in=[s, s1, s2])
91 [<MyModel: m>]
92 >>> MyModel.objects.filter(data__lt=s)
93 Traceback (most recent call last):
94 ...
95 FieldError: Invalid lookup type: 'lt'
96
97 # Serialization works, too.
98 >>> stream = serializers.serialize("json", MyModel.objects.all())
99 >>> stream
100 '[{"pk": 1, "model": "field_subclassing.mymodel", "fields": {"data": "12", "name": "m"}}]'
101 >>> obj = list(serializers.deserialize("json", stream))[0]
102 >>> obj.object == m
103 True
104
105 # Test retrieving custom field data
106 >>> m.delete()
107 >>> m1 = MyModel(name="1", data=Small(1, 2))
108 >>> m1.save()
109 >>> m2 = MyModel(name="2", data=Small(2, 3))
110 >>> m2.save()
111 >>> for m in MyModel.objects.all(): print unicode(m.data)
112 12
113 23
114 """}
Note: See TracBrowser for help on using the browser.