Django循环返回多个帖子

时间:2017-06-01 07:53:46

标签: python django django-templates django-views jinja2

我试图让django在该类别的页面上显示来自单个目录的帖子,而是显示模板中每个类别下的所有类别和帖子。

这是我的模特(我把它们剪掉了):

class Category(models.Model):
    ...
    title = models.CharField(max_length=255, verbose_name="Title", null=True, blank=True)
    slug = models.SlugField(max_length=200, unique=True)


class Petition(models.Model):
    ...
    category = models.ManyToManyField(Category, verbose_name="Category", related_name='petitions')
    ...

views.py

class CategoryMixin(object):
    def get_context_data(self, **kwargs):
        context = super(CategoryMixin, self).get_context_data(**kwargs)
        context['categories'] = Category.objects.all()
        return context


class CategoryView(CategoryMixin, generic.ListView):
    model = Category
    categories = Category.objects.all() # this will get all categories, you can do some filtering if you need (e.g. excluding categories without posts in it)
    queryset = Category.objects.all()
    template_name = 'petition/category_list.html'


class CategoryIndexView(generic.ListView):
    model = Category
    template_name = 'petition/category.html'
    context_object_name = 'category_list'

    def get_queryset(self): 
        return Category.objects.prefetch_related('petitions').order_by('-created_on')[:10]



class PetitionIndexView(generic.ListView):
    template_name = 'petition/home.html'
    context_object_name = 'petition_list'
    queryset = Petition.objects.order_by('-created_on')

    def get_queryset(self):
        queryset_list = Petition.objects.order_by('-created_on')

        #SEARCH QUERY LOGIC
        query = self.request.GET.get("q")
        if query:
            queryset_list = queryset_list.filter(
                Q(title__icontains = query) |
                Q(petition__icontains = query) |
                Q(created_by__first_name__icontains = query) | #icontains = only text fields. Use text field within foreign key field
                Q(created_by__last_name__icontains = query) 
                ).distinct()

        paginator = Paginator(queryset_list, 10) # Show 10 posts per page
        page = self.request.GET.get('page')

        try:
            queryset = paginator.page(page)
        except PageNotAnInteger:
            # If page is not an integer, deliver first page.
            queryset = paginator.page(1)
        except EmptyPage:
            # If page is out of range (e.g. 9999), deliver last page of results.
            queryset = paginator.page(paginator.num_pages)

        return queryset

        context = {
        'object_list' : queryset,
        'title' : 'List'
        }

urls.py

url(r'^$',views.PetitionIndexView.as_view(), name="homepage"),
url(r'^petition/(?P<slug>[\w-]+)/$',views.DetailView.as_view(), name="detail"),
url(r'^categories/$', views.CategoryView.as_view(), name='category_list'),
url(r'^category/(?P<slug>[\w-]+)/$',views.CategoryIndexView.as_view(), name="category_detail"),

我的模板(CategoryIndexView的category.html)采用这种格式,

category.html

{% for category in category_list %}
    {% for petition in category.petitions.all %}
        ...
        {{ petition.title }}
        ...
    {% end for %}
{% end for %}

这显示了同一模板中A,B和C类的帖子。

根据我设定的观点,如何在点击类别A时仅显示类别A的帖子?

此外,订购无法正常工作。它没有遵守我在视图中给出的顺序

2 个答案:

答案 0 :(得分:1)

您正在使用错误的视图类。 ListView用于显示类的实例列表;所以CategoryIndexView将显示类别列表。但是你不想要一个类别列表;你想要一个类别,以及它的请愿列表。所以,你应该使用DetailView。

class CategoryDetailView(generic.DetailView):
    model = Category
    template_name = 'petition/category.html'
    context_object_name = 'category'

    def get_queryset(self): 
        return Category.objects.prefetch_related('petitions')

模板只是:

{% for petition in category.petitions.all %}
    ...
    {{ petition.title }}
    ...
{% end for %}

编辑:我更改了&#39; category_list&#39;中的context_object_name到&#39;类别&#39;并且模板现在返回正确的帖子。

答案 1 :(得分:0)

我猜每次更改类别时,整个循环会再次执行,而不会更改category_list的内容(最初是[“A”,“B”,“C”])。在这种情况下,即使您单击按钮更改类别,循环也会再次显示“A”,“B”和“C”类别的内容。

您是否尝试过添加if语句来检查您目前所属的类别并仅显示该类别中的帖子?

{% for category in category_list %}
  {% if category.name == ACTUAL_CATEGORY_TO_DISPLAY %}
    {% for petition in category.petitions.all %}
      ...
      {{ petition.title }}
      ...
     {% end for %}
  {% end if %}
{% end for %}

编辑:

@Daniel Roseman在评论中指出,这是一个效率很低的解决方案。我刚发布它是因为我猜这是不是真的发生在你身上。

如果是这种情况,你不应该这样做。其中一个正确的解决方案是创建一个新请求,每次更改时都会检索该给定类别的所有帖子。

无论如何,我只是在这里猜测。为了让您更好地了解,您应该发布进行类别更改的模板代码。