通过Meta自定义模型实例排序?

时间:2018-11-02 14:47:21

标签: wagtail

我无法为我的页面模型实例获得自定义默认顺序。它们始终按其pk升序排列。

这会导致下拉菜单,选择器(例如CheckboxSelectMultiple)不直观;尤其是当项目/实例很多时。

用例:AuthorPagePublicationPage模型:

class AuthorPage(Page):
    first_name = CharField(max_length=255)
    last_name = CharField(max_length=255)

    class Meta:
        ordering = ['last_name', 'first_name']

class ArticlePage(Page):
    authors = ParentalManyToManyField('AuthorPage',)
    content_panels = Page.content_panels + [
        FieldPanel('authors', widget=CheckboxSelectMultiple),
    ]

我喜欢我的CheckboxSelectMultiple遵守相关模型的Meta排序,这里AuthorPage并显示按字母顺序排列的作者列表。但是,相反,我按作者实例的pk排序此列表。似乎ordering类上的AuthorPage没有被评估/使用。

检查默认的AuthorPage查询集(AuthorPage.objects.all())时,作者的下拉列表和python shell中出现相同(不需要的)排序。

如何通过自定义条件(而非pk)来排序我的页面模型实例?


设置:

  • Django 2.0.8
  • wa 2.2.2

2 个答案:

答案 0 :(得分:1)

另一种可能性是扩展和更改此模型类的默认PageManager(再次:感谢@allcaps):

class ProfilePageManager(PageManager):
    def get_queryset(self):
        return super().get_queryset().order_by('last_name', 'first_name')

class ProfilePage(Page):
    objects = ProfilePageManager()

默认页面管理器返回带有order_by('path') [1]的查询集,因此我将其更改为返回按我的自定义条件order_by('last_name', 'first_name')排序的查询集。

现在的窗口小部件(例如CheckboxSelectMultiple,下拉菜单等)在整个站点中都接收此有序查询集作为选项/选择,而无需修改其现有实例。

[1] https://github.com/wagtail/wagtail/blob/master/wagtail/core/models.py#L191

答案 1 :(得分:0)

您认为Wagtail页面顺序由pk决定是错误的。 Wagtail按路径对页面进行排序(Wagtail使用django-treebeard)。这样可以实现用户定义的排序。首先单击订单符号(第一列),然后拖放页面。

Wagtail Page list ordering

这是文档所说的:

  通过使用标准Django方法(向内部Meta类添加排序属性),不能为

基于页面的模型 提供默认排序。

     

这是因为Page强制按路径对QuerySet进行排序。而是在构造QuerySet时必须显式应用排序:

news_items = NewsItemPage.objects.live().order_by('-publication_date')

文档:https://docs.wagtail.io/en/v2.3/topics/pages.html#page-queryset-ordering

您可以尝试自己定义选择-从而定义顺序吗?这样的事情可能会起作用:

FieldPanel(
    'authors', 
    widget=CheckboxSelectMultiple(
        choices=ProfilePage.objects.all().order_by('title').values_list('pk', 'title')
    )
),