代码之家  ›  专栏  ›  技术社区  ›  amarynets

更改get\ context\ data中的queryset后,分页不起作用

  •  0
  • amarynets  · 技术社区  · 7 年前

    分页工作正常,直到我添加 reverse arg到QS,用于在反向模式下对queryset进行排序。在它分页被打破之后。 get() 函数并在那里分页,但我认为对于这个问题应该有更好的解决方案。谢谢

    型号.py:

    class Log(models.Model):
        user = models.ForeignKey('auth.User')
        comment = models.CharField()
        date_add = models.DateTimeField()
        class Meta:
            ordering = ['-date_add']
    

    视图.py:

    class LogView(ListView):
        model = UserLog
        template_name = 'log.html'
        context_object_name = 'log_list'
        paginate_by = 13
    
        def get_queryset(self):
            return Log.objects.filter(user=self.request.user).all()
    
        def get_context_data(self, *, object_list=None, **kwargs):
            context = super(LogView, self).get_context_data(**kwargs)
            if 'reverse' in self.request.GET:
                context['log_list'] = Log.objects.filter(user=self.request.user).all().order_by('date_add')
            return context
    
    2 回复  |  直到 7 年前
        1
  •  4
  •   Alasdair    7 年前

    get_queryset ,以便在查询集分页之前运行。

    def get_queryset(self):
        queryset = Log.objects.filter(user=self.request.user).all()
        if 'reverse' in self.request.GET:
            queryset = queryset.order_by('date_add')
        return queryset
    
        2
  •  1
  •   willeM_ Van Onsem    7 年前

    get_context_data of the MultipleObjectMixin [GitHub] :

    def get_context_data(self, *, object_list=None, **kwargs):
        """Get the context for this view."""
        queryset = object_list if object_list is not None else self.object_list
        page_size = self.get_paginate_by(queryset)
        context_object_name = self.get_context_object_name(queryset)
        if page_size:
            paginator, page, queryset, is_paginated = self.paginate_queryset(queryset, page_size)
            context = {
                'paginator': paginator,
                'page_obj': page,
                'is_paginated': is_paginated,
                'object_list': queryset
            }
        else:
            context = {
                'paginator': None,
                'page_obj': None,
                'is_paginated': False,
                'object_list': queryset
            }
        if context_object_name is not None:
            context[context_object_name] = queryset
        context.update(kwargs)
        return super().get_context_data(**context)
    

    此分页。

    我认为在这个用例中,将逻辑转移到 get_queryset 方法,在这种情况下,你甚至 必须覆盖 获取上下文数据 :

    class LogView(ListView):
        model = UserLog
        template_name = 'log.html'
        context_object_name = 'log_list'
        paginate_by = 13
    
        def get_queryset(self):
            if 'reverse' in self.request.GET:
                return Log.objects.filter(user=self.request.user).all().order_by('date_add')
            else:
                return Log.objects.filter(user=self.request.user).all()

    1. 'reverse' self.request.GET ,这意味着-除非您在模型中排序-没有顺序,因此分页可能会在多个页面上出错;
    2. page 输入 request.GET ,这可能会导致更改GET参数的链接出现一些问题,因为如果使用 ?page=3 ,的 reverse