Django Admin:如何根据其他模型的数据进行排序?

时间:2014-07-28 12:58:11

标签: python django orm django-admin

我在Django应用中有以下两个模型:EventEventDate。我想在事件 的管理列表视图中显示来自 EventDate 的一些计算数据,我希望能够按它排序。

我从 EventDate 中的数据计算每个事件下一个即将到来的日期。现在我希望它不仅显示在事件Django Admin列表视图中,而且还希望事件按其排序。

Django模型看起来像这样:

class EventDate(models.Model):

  date = models.DateField(db_index=True)
  start = models.TimeField(blank=True, null=True)
  end = models.TimeField(blank=True, null=True)
  event = models.ForeignKey('Event')

class Event(TimeStampedModel):

  title = models.CharField(max_length=200)
  text = models.TextField()
  published = models.BooleanField(default=False, db_index=True)

到目前为止我尝试了什么

首先,我向事件模型提供了一个属性,它返回了下一个日期,这有点有用:我可以在list_display中显示下一个日期甚至使用prefetch_related进行优化。 但是我无法在列表显示中对该字段进行排序:(

接下来,我尝试使用extra添加到模型中,以解决此限制...不是那么好,前进但是我提出了这个:

class EventAdmin(admin.ModelAdmin):

  def get_queryset(self, request):
    qs = super(EventAdmin, self).get_queryset(request)
    qs.extra(
      select={
        'n2': """SELECT MIN(events_eventdate.date) FROM events_eventdate
          WHERE events_event.id == events_eventdate.event_id AND
          events_eventdate.date >= '{}'
          """.format(now().date().isoformat())
      }
    )
    return qs

它适用于调试shell,但我无法在管理员中使用它。我不清楚如何将其包含在list_display或其他什么内容中。

1 个答案:

答案 0 :(得分:0)

好像我找到了一种方法来使用来自额外呼叫的数据......

我向EventAdmin添加了一个方法,并将该方法的admin_order_field设置为额外调用生成的字段:

class EventAdmin(admin.ModelAdmin):

  def get_queryset(self, request):
    qs = super(EventAdmin, self).get_queryset(request)
    qs = qs.prefetch_related('eventdate_set')
    qs = qs.extra(
      select={
        'next_date': """SELECT MIN(events_eventdate.date)
          FROM events_eventdate
          WHERE events_event.id == events_eventdate.event_id AND
          events_eventdate.date >= '{}'
          """.format(now().date().isoformat())
      }
    )
    return qs

  def next_date(self, obj):
      try:
        return obj.next_date
      except IndexError:
        return 'abgelaufen'

  next_date.short_description = 'Nächster Termin'
  next_date.admin_order_field = 'next_date'

不确定这是干净还是理智......似乎工作正常,因为在这里找到Django问题的答案非常困难。如果它对我不利,我会报告。