#26807 closed Cleanup/optimization (fixed)
Document how to replicate SubfieldBase behavior of calling to_python on assignment
| Reported by: | Aarni Koskela | Owned by: | nobody |
|---|---|---|---|
| Component: | Documentation | Version: | 1.8 |
| Severity: | Normal | Keywords: | |
| Cc: | Triage Stage: | Accepted | |
| Has patch: | yes | Needs documentation: | no |
| Needs tests: | no | Patch needs improvement: | no |
| Easy pickings: | no | UI/UX: | no |
Description
With the deprecation of SubfieldBase, custom fields no longer automatically have the Creator class behavior that calls to_python() on every assignment (see https://github.com/django/django/blob/4fd264b6f1737b0317fdd95b3d7ff3bba15ae6c3/django/db/models/fields/subclassing.py#L44), incl. construction.
This causes the problem described here – https://github.com/hzdg/django-enumfields/issues/60 – i.e. enumfields.EnumField doesn't coerce values to the actual Enum value types anymore.
The fix is naturally to reimplement a descriptor like Creator (and that does indeed fix this particular issue), but I feel like I'm missing something doing that.
(The deprecation warning for SubfieldBase says that one should use from_db_value(), but it doesn't get called on instance construction either, it seems.)
Here's a trivial py.test style test case (the assertions fail):
from django.db import models
class CoolCharField(models.CharField):
def to_python(self, value):
return str(value).upper() + "!!!"
def from_db_value(self, value):
return self.to_python(value)
class CoolModel(models.Model):
yay = CoolCharField()
def test_cool_char_field_1():
m = CoolModel(yay="ponies")
assert m.yay == "PONIES!!!"
def test_cool_char_field_2():
m = CoolModel()
m.yay = "ponies"
assert m.yay == "PONIES!!!"
Change History (5)
comment:1 by , 9 years ago
| Component: | Database layer (models, ORM) → Documentation |
|---|---|
| Summary: | Custom fields do not call to_python on assignment → Document how to replicate SubfieldBase behavior of calling to_python on assignment |
| Triage Stage: | Unreviewed → Accepted |
| Type: | Uncategorized → Cleanup/optimization |
| Version: | 1.9 → 1.8 |
The django-developers thread that proposed the removal of
SubfieldBasesays:The deprecation note in the the 1.8 release notes says, "the new approach does not call the
to_python()method on assignment as was the case withSubfieldBase." We could say that custom fields can copy theCreatorimplementation if they require this behavior.