2009-09-07 14 views
8

Tengo un problema inusual. Vamos a considerar este tipo de modelos (tomado de documentos django):Pedido predeterminado para elementos m2m por campo modelo intermedio en Django

class Person(models.Model): 
    name = models.CharField(max_length=128) 

    def __unicode__(self): 
     return self.name 

class Group(models.Model): 
    name = models.CharField(max_length=128) 
    members = models.ManyToManyField(Person, through='Membership') 

    def __unicode__(self): 
     return self.name 

class Membership(models.Model): 
    person = models.ForeignKey(Person) 
    group = models.ForeignKey(Group) 
    date_joined = models.DateField() 
    invite_reason = models.CharField(max_length=64) 

Ahora, supongamos que tenemos 2 miembros de los Beatles en fuera de banda de los Beatles (siguiendo el ejemplo de la documentación de Django para modelos intermedios):

>>> beatles.members.all() 
[<Person: Ringo Starr>, <Person: Paul McCartney>] 

El código anterior devolverá los miembros ordenados por pedidos predeterminados para el modelo de persona. Si especifico:

>>> beatles.members.all().order_by('membership__date_joined') 

los miembros, se ordenan a través de la fecha unida. ¿Puedo de alguna manera establecer esto como comportamiento predeterminado para este campo ManyToMany? ¿Es para establecer el orden predeterminado de los elementos relacionados por campo en el modelo intermedio? El ManyRelatedManager parece tener un argumento init core_filters, pero no tengo una idea vaga de cómo acceder a él subclassing todo el campo m2m en django. ¿Alguna idea creativa? :)

Gracias de antemano :)

He abierto un ticket in django trac.

Respuesta

4

Aquí es un método sucio truco para conseguir esto (ver modelo del Grupo):

class Person(models.Model): 
    name = models.CharField(max_length=128) 

    def __unicode__(self): 
     return self.name 

class Group(models.Model): 
    name = models.CharField(max_length=128) 
    _members = models.ManyToManyField(Person, through='Membership') 
    @property 
    def members(self): 
     return self._members.order_by('membership__date_joined') 

    def __unicode__(self): 
     return self.name 

class Membership(models.Model): 
    person = models.ForeignKey(Person) 
    group = models.ForeignKey(Group) 
    date_joined = models.DateField() 
    invite_reason = models.CharField(max_length=64) 

no se molestó en crear un conjunto decorador de propiedades, pero debería ser bastante fácil imitar la configuración del campo original. Una solución fea, pero parece hacer el truco.

+0

este método devuelve más registros de los que esperaba para mí. termina creando una UNIÓN EXTERIOR IZQUIERDA y duplicando datos – MrE

0

creo que esto debería funcionar:

class Membership(models.Model): 
    ... 

    class Meta: 
     ordering = ['date_joined'] 
+0

Desafortunadamente no aparece, ManyRelatedManager parece copiar el orden del modelo de destino :( – pielgrzym

+0

Eso parece tonto, no es así. Sugiero abrir un ticket y traerlo al grupo de google de django-dev – SmileyChris

+0

Buena idea , Lo haré y publicaré aquí lo que surgió de la discusión :) – pielgrzym

Cuestiones relacionadas