Deprecate django fields and make migrations without breaking existing code.
Project description
django-deprecation
Deprecate django fields and make migrations without breaking existing code.
Install
pip install django-deprecation
Usage
TL;DR
# Before:
class Album(models.Model):
name = models.CharField(max_length=50)
# After:
class Album(models.Model):
name = DeprecatedField('title')
title = models.CharField(max_length=50)
assert album.name == album.title
assert list(Album.objects.filter(name='foo')) == list(Album.objects.filter(title='foo'))
Long explanation
Let's suppose we have the following models:
from django.db import models
class Musician(models.Model):
name = models.CharField(max_length=50)
class Album(models.Model):
musician = models.ForeignKey(Musician, on_delete=models.CASCADE)
name = models.CharField(max_length=100)
Now, for some reason, let's suppose we want to rename the field Album#musician
to Album#artist
.
So we make the migration using the RenameField operation. The problem is that any existing code that used the old field would break.
We could create a property as an alias:
class Album(models.Model):
artist = models.ForeignKey(Musician, on_delete=models.CASCADE)
name = models.CharField(max_length=100)
@property
def musician(self):
return self.artist
@musician.setter
def musician(self, value):
self.artist = value
But any code using
QuerySet#filter
would break if it uses the musician
field.
This is where django-deprecation
comes handy.
We set the musician
field as a DeprecatedField
and point it to the artist
field:
from django_deprecation import DeprecatedField
class Album(models.Model):
artist = models.ForeignKey(Musician, on_delete=models.CASCADE)
musician = DeprecatedField('artist')
name = models.CharField(max_length=100)
Now, the following code snippet will work:
from .models import Album, Musician
album = Album.objects.first()
assert album.musician == album.artist
new_musician = Musician.objects.create(
first_name='John',
last_name='Doe',
instrument='Guitar',
)
album.musician = new_musician
assert album.artist == new_musician
new_musician_album = Album.objects.filter(
musician=new_musician,
).first()
new_artist_album = Album.objects.filter(
artist=new_musician,
).first()
assert new_musician_album == new_artist_album
If you want to control how to report the error,
replace the DeprecatedField.warn
function with a custom one:
from django_deprecation import DeprecatedField
def warn_function(message):
# do stuff
import warnings
warnings.warn(message, DeprecationWarning)
DeprecatedField.warn = warn_function
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Hashes for django_deprecation-0.1.1-py2.py3-none-any.whl
Algorithm | Hash digest | |
---|---|---|
SHA256 | 9be8f772c0e7b7acbf1646bea6fc2242ba36404a42bd46b29e812ff3dfd8acc4 |
|
MD5 | ae38c6228747738d6490d2bf45b91bb8 |
|
BLAKE2b-256 | bfa942c43bc1ceecdeccb0954a245b26bf987e2bd91c110b34557b89dcdc495f |