Added south field triple to SortableForeignKey field

This commit is contained in:
Brandon Taylor
2012-03-07 21:52:57 -06:00
19 changed files with 154 additions and 256 deletions
+2 -2
View File
@@ -1,4 +1,4 @@
VERSION = (1, 2, 0, "f", 0) # following PEP 386
VERSION = (1, 3, "f", 0) # following PEP 386
DEV_N = None
@@ -7,7 +7,7 @@ def get_version():
if VERSION[2]:
version = "%s.%s" % (version, VERSION[2])
if VERSION[3] != "f":
version = "%s%s%s" % (version, VERSION[3], VERSION[4])
version = "%s%s" % (version, VERSION[3])
if DEV_N:
version = "%s.dev%s" % (version, DEV_N)
return version
Executable → Regular
+31 -7
View File
@@ -9,6 +9,7 @@ from django.shortcuts import render
from django.template.defaultfilters import capfirst
from django.views.decorators.csrf import csrf_exempt
from adminsortable.fields import SortableForeignKey
from adminsortable.models import Sortable
STATIC_URL = settings.STATIC_URL
@@ -20,8 +21,17 @@ class SortableAdmin(ModelAdmin):
class Meta:
abstract = True
def _get_sortable_foreign_key(self):
sortable_foreign_key = None
for field in self.model._meta.fields:
if isinstance(field, SortableForeignKey):
sortable_foreign_key = field
break
return sortable_foreign_key
def __init__(self, *args, **kwargs):
super(SortableAdmin, self).__init__(*args, **kwargs)
self.has_sortable_tabular_inlines = False
self.has_sortable_stacked_inlines = False
for klass in self.inlines:
@@ -55,11 +65,16 @@ class SortableAdmin(ModelAdmin):
#Determine if we need to regroup objects relative to a foreign key specified on the
# model class that is extending Sortable.
sortable_by = getattr(self.model, 'sortable_by', None)
if sortable_by:
#Legacy support for 'sortable_by' defined as a model property
sortable_by_property = getattr(self.model, 'sortable_by', None)
#`sortable_by` defined as a SortableForeignKey
sortable_by_fk = self._get_sortable_foreign_key()
if sortable_by_property:
#backwards compatibility for < 1.1.1, where sortable_by was a classmethod instead of a property
try:
sortable_by_class, sortable_by_expression = sortable_by()
sortable_by_class, sortable_by_expression = sortable_by_property()
except TypeError, ValueError:
sortable_by_class = self.model.sortable_by
sortable_by_expression = sortable_by_class.__name__.lower()
@@ -67,15 +82,24 @@ class SortableAdmin(ModelAdmin):
sortable_by_class_display_name = sortable_by_class._meta.verbose_name_plural
sortable_by_class_is_sortable = sortable_by_class.is_sortable()
elif sortable_by_fk:
#get sortable by properties from the SortableForeignKey field - supported in 1.3+
sortable_by_class_display_name = sortable_by_fk.rel.to._meta.verbose_name_plural
sortable_by_class = sortable_by_fk.rel.to
sortable_by_expression = sortable_by_fk.name.lower()
sortable_by_class_is_sortable = sortable_by_class.is_sortable()
else:
#model is not sortable by another model
sortable_by_class = sortable_by_expression = sortable_by_class_display_name =\
sortable_by_class_is_sortable = None
if sortable_by_property or sortable_by_fk:
# Order the objects by the property they are sortable by, then by the order, otherwise the regroup
# template tag will not show the objects correctly as
# shown in https://docs.djangoproject.com/en/1.3/ref/templates/builtins/#regroup
objects = objects.order_by(sortable_by_expression, 'order')
else:
sortable_by_class = sortable_by_expression = sortable_by_class_display_name =\
sortable_by_class_is_sortable = None
try:
verbose_name_plural = opts.verbose_name_plural.__unicode__()
except AttributeError:
+18
View File
@@ -0,0 +1,18 @@
from django.db.models.fields.related import ForeignKey
class SortableForeignKey(ForeignKey):
"""
Field simply acts as a flag to determine the class to sort by.
This field replaces previous functionality where `sortable_by` was definied as a model property
that specified another model class.
"""
def south_field_triple(self):
try:
from south.modelsinspector import introspector
cls_name = '%s.%s' % (self.__class__.__module__ , self.__class__.__name__)
args, kwargs = introspector(self)
return cls_name, args, kwargs
except ImportError:
pass
Executable → Regular
+24
View File
@@ -1,6 +1,16 @@
from django.contrib.contenttypes.models import ContentType
from django.db import models
from adminsortable.fields import SortableForeignKey
class MultipleSortableForeignKeyException(Exception):
def __init__(self, value):
self.value = value
def __str__(self):
return repr(self.value)
class Sortable(models.Model):
"""
@@ -18,7 +28,10 @@ class Sortable(models.Model):
Override `sortable_by` method to make your model be sortable by a foreign key field.
Set `sortable_by` to the class specified in the foreign key relationship.
"""
order = models.PositiveIntegerField(editable=False, default=1, db_index=True)
#legacy support
sortable_by = None
class Meta:
@@ -37,6 +50,17 @@ class Sortable(models.Model):
def model_type_id(cls):
return ContentType.objects.get_for_model(cls).id
def __init__(self, *args, **kwargs):
super(Sortable, self).__init__(*args, **kwargs)
#Validate that model only contains at most one SortableForeignKey
sortable_foreign_keys = []
for field in self._meta.fields:
if isinstance(field, SortableForeignKey):
sortable_foreign_keys.append(field)
if len(sortable_foreign_keys) > 1:
raise MultipleSortableForeignKeyException(u'%s may only have one SortableForeignKey' % self)
def save(self, *args, **kwargs):
if not self.id:
try:
View File
View File
View File
View File