2009-04-16 8 views
1

so habe ich dieses Modell:Filter für viele zu viele Feld

class Message(models.Model): 
    creator = models.ForeignKey(User, unique=True) 
    note = models.CharField(max_length=200, blank=True) 
    recipients = models.ManyToManyField(User, related_name="shared_to") 
    read = models.ManyToManyField(User, related_name="read", blank=True) 

Ich möchte auf die Menschen filtern, die in beiden Empfänger sind und lesen, zur Zeit ich das tue.

Ich bin sicher, es gibt eine Möglichkeit, dies zu filtern, aber ich kann nicht herausfinden, wie.

Antwort

0

Ich denke, dass ich ursprünglich deine Frage falsch gelesen habe. Versuchen Sie die folgende Abfrage.

for message in user.shared_to.exclude(read__id__in=[user.id]): 
    do_something() 
1

Wenn Sie die Entwicklerversion von Django verwenden, oder warten, bis die Version 1.1 freigegeben wird, dann Filter können reference other fields in the model. So würde Ihre Frage wie folgt aussehen:

>>> Message.objects.filter(recipients=F('read')) 

(Anmerkung: Ich reciepients das gleiche geschrieben, wie Sie in Ihrem Modell hatte, obwohl die korrekte Schreibweise „Empfänger“ wäre)

bearbeiten:

Ok, Ihre Frage ist verwirrend. Als ich die obige Antwort gab, las ich Ihre Aussage, dass Sie alle Benutzer wollten, die sowohl "Empfänger" als auch "gelesen" hatten. Nach dem Lesen des Code-Snippets möchten Sie jedoch eine Liste der Benutzer anzeigen, die zwar Empfänger sind, aber noch nicht in der Liste "Lesen" aufgeführt sind.

Dies ist wahrscheinlich, was Sie wollen, aber ich bin mir nicht ganz sicher wegen der vagen Anforderungen und ich kann es nicht schnell prüfen:

# Get list of recipients 
shared_to = Message.shared_to.all().values('id') 

# Now list of recipients who are not in the read field 
unread = Message.objects.exclude(recipients__in=shared_to) 

Dies wird eine einzelne Abfrage machen, aber wenn Wenn Sie MySQL verwenden, könnte es immer noch more efficient to do two queries sein (lesen Sie die Warnung zu den Leistungsmerkmalen).