2013-05-16 21 views
7

私はannotateを使用してオブジェクトにプロパティを追加し、order_byに使用します。しかし、私は関係上の関係のフィールドに注釈を付ける必要があります。私はフィールドに何とか二重のアンダースコア表記を使って得ることができるはずだが、私はそれの周りに頭を包むように見えない。ここでDjango:関連フィールドの関連フィールドでorder_byを作成する方法

はモデルです:だから

class Group(Taggable, Uploadable): 
    name   = models.CharField(max_length=250, db_index=True) 
    description  = models.TextField(max_length=5000, null=True, 
         blank=True, db_index=True) 
    private   = models.BooleanField(default=False) 
    members   = models.ManyToManyField(User, null=True, 
         related_name='members', through='GroupToUser') 
    pending_members = models.ManyToManyField(User, null=True, 
         related_name='pending_members') 
    admin   = models.ForeignKey(User, null=True) 
    timestamp  = models.DateTimeField(auto_now_add=True) 
    author   = models.ForeignKey(User, related_name='author') 

class Discussion(Taggable, Uploadable): 
    author  = models.ForeignKey(User) 
    title  = models.CharField(max_length=250, db_index=True) 
    description = models.TextField(max_length=5000, null=True, 
        blank=True, db_index=True) 
    group  = models.ForeignKey(Group, null=True) 
    timestamp = models.DateTimeField(auto_now_add=True) 

class DiscussionResponse(Uploadable): 
    author  = models.ForeignKey(User) 
    discussion = models.ForeignKey(Discussion) 
    message = models.TextField(max_length=5000) 
    timestamp = models.DateTimeField(auto_now_add=True) 

、ディスカッションは、必要に応じてグループに関連付けることができ、かつDiscussionResponsesは議論に関連しています。私がしたいのは、グループに結びついているディスカッションのディスカッション・リスポンスがあればそれを見つけ、それがあればそれを並べ替えることです。私は、この限りで得ている

Group.objects.filter(some_filtering).distinct().annotate(
    last_response=Max('some__reverse__relationship__timestamp').order_by(
     '-last_response') 

私はこのケースでDiscussionResponseのタイムスタンプを取得するための正しい方法を見つけ出すように見えることはできません。

更新: 実際に注釈付きの値で注文することができます。ここで関連する議論のタイムスタンプにorder_byとの一例である。この場合

>>> groups = Group.objects.all().annotate(
     last_response=Max('discussion__timestamp')).order_by('-last_response') 
>>> for group in groups: 
...  print(group.id, group.last_response) 
...  
... 
(2L, datetime.datetime(2013, 5, 8, 15, 32, 31)) 
(1L, None) 
(3L, None) 
(4L, None) 
(6L, None) 
(7L, None) 
(8L, None) 
(9L, None) 

は、それが上部に移動したので、唯一のグループ#2が議論に関連しています。残りの部分は自然順序を保持します。しかし、私が本当にやりたいことは、最近のレスポンスを持っているムーブグループがリストの先頭に移動したことです。だから私は'discussion__discussionresponse__timestamp'がうまくいくと思ったのですが、そうではありません。

+0

、のどれも働いていません'discussion set__discussionresponse__timestamp' – foresmac

+0

私はあなたが達成しようとしていることを理解していません。たとえば、タイムスタンプを与える 'last_response = Max(...) 'を宣言してから、この値をorder_byにすると、値ではなく列で注文する必要があります。あなたが望むのはタイムスタンプ列による注文ですか? –

+0

注釈付きの値に対して 'order_by'を実行できます。私は以前にそのトリックを使いました。問題は、私はグループに関するディスカッションに関連するDiscussionResponsesのタイムスタンプに到達することができないということです。 – foresmac

答えて

1

Ok、明らかにそれです。'discussion__discussionresponse__timestamp'です。私は、Djangoのシェルでそれを試してみましたが、それは新しいDiscussionResponseを保存した後動作しませんでしたが、私は再びそれをしようとしたときには、数分後に働いた:

>>> groups = Group.objects.all().annotate(last_response=Max(
     'discussion__discussionresponse__timestamp')).order_by('-last_response') 
>>> for group in groups: 
...  print(group.id, group.last_response) 
...  
... 
(2L, datetime.datetime(2013, 5, 16, 14, 56, 22)) 
(1L, None) 
(3L, None) 
(4L, None) 
(6L, None) 
(7L, None) 
(8L, None) 
(9L, None) 
>>> 

、誰もがそれを保存した後、右に動作しなかった理由を知っているなら新しいオブジェクトをデータベースに追加しましたが、後で作業しました。これはおそらく有益な情報になります。ここで

追加したばかりの検証のために別のグループに追加議論/レスポンスを使用してクエリで別の実行です: `discussion__discussionresponse__timestamp`、` discussion_set__discussionresponse__timestamp`、および:私は次のことを試してみた

>>> groups = Group.objects.all().annotate(last_response=Max('discussion__discussionresponse__timestamp')).order_by('-last_response') 
>>> for group in groups: 
...  print(group.id, group.last_response) 
...  
... 
(4L, datetime.datetime(2013, 5, 16, 15, 25, 40)) 
(2L, datetime.datetime(2013, 5, 16, 15, 16, 46)) 
(1L, None) 
(3L, None) 
(6L, None) 
(7L, None) 
(8L, None) 
(9L, None) 
>>> 
+0

お気軽に回答してください。 – stellarchariot

関連する問題