45

I'm using ListView in my Class Based Views and I was wondering if there was a way to display the model object set on the template by sorting it. This is what I have so far:

My views:

class Reviews(ListView):
    model = ProductReview
    paginate_by = 50
    template_name = 'review_system/reviews.html'

The model ProductReview has a date_created field. I'd like to sort the date in descending order. How can I achieve this?

1
  • 1
    It may be possible that you may want the same ordering in multiple views. In that case, you may also look into Meta order which is set on the model itself. Commented Sep 28, 2018 at 13:58

2 Answers 2

96

Set the ordering attribute for the view.

class Reviews(ListView):
    model = ProductReview
    paginate_by = 50
    template_name = 'review_system/reviews.html'

    ordering = ['-date_created']

If you need to change the ordering dynamically, you can use get_ordering instead.

class Reviews(ListView):
    ...
    def get_ordering(self):
        ordering = self.request.GET.get('ordering', '-date_created')
        # validate ordering here
        return ordering

If you are always sorting a fixed date field, you may be interested in the ArchiveIndexView.

from django.views.generic.dates import ArchiveIndexView

class Reviews(ArchiveIndexView):
    model = ProductReview
    paginate_by = 50
    template_name = 'review_system/reviews.html'
    date_field = "date_created"

Note that ArchiveIndexView won't show objects with a date in the future unless you set allow_future to True.

Sign up to request clarification or add additional context in comments.

3 Comments

I like the ArchiveIndexView, it does the trick, but the template has a table that allows sorting columns by clicking on headers. When I do that, this doesn't work, do you know how I could make it work there as well?
If you're sorting by other fields, it sounds like the archive index view is not suitable.
@user3118363 please ask a new question, I’m not on Stack Overflow much any more so can’t help in the comments
9

Why don't you override the get_queryset method like this:

class Reviews(ListView):
    model = ProductReview
    paginate_by = 50
    template_name = 'review_system/reviews.html'

    def get_queryset(self):
        return YourModel.objects.order_by('model_field_here')

4 Comments

I'll try this, but your method is missing a def
This did not have any errors rendering or executing, but the order_by did not work.
@DeA Overriding get_queryset and using order_by should work, although with ListView you might prefer to override ordering or get_ordering instead.
This works perfectly well. I had to do a custom order using Case, When, Then, Value clause which I could not do with get_ordering.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.