如何在Django中将过滤元素分组到类别中?

bttbmeg0  于 2023-04-22  发布在  Go
关注(0)|答案(1)|浏览(80)

我需要实现动态产品过滤。我面临着如何按类别对过滤选项进行分组的问题。例如,我有3个过滤选项-8 GB,16 GB和32 GB。我需要将这些值分组到RAM类别中。
模型

class CategoryCharacteristic(models.Model):
    category = models.ForeignKey("mainapp.Category", verbose_name='category', on_delete=models.CASCADE)
    feature_filter_name = models.CharField(verbose_name='name_of_filter', max_length=50)
    unit = models.CharField(max_length=50, verbose_name='unit_of_measurement', null=True, blank=True)

    class Meta:
        unique_together = ('category', 'feature_filter_name')
        ordering = ('id',)

    def __str__(self):
        return f"{self.category.title}-{self.feature_filter_name}-{self.unit}"

class ProductCharacteristic(models.Model):
    product = models.ForeignKey(Product, on_delete=models.CASCADE, related_name='characteristics')
    feature = models.ForeignKey(CategoryCharacteristic,verbose_name='name_of_filter', on_delete=models.CASCADE)
    value = models.CharField(max_length=100)

    def __str__(self):
        return f'{self.feature.feature_filter_name} {self.value}'

表格

class ProductFilterForm(forms.Form):
min_price = forms.DecimalField(required=False)
max_price = forms.DecimalField(required=False)
characteristics = forms.ModelMultipleChoiceField(
    queryset=ProductCharacteristic.objects.all(),
    widget=forms.CheckboxSelectMultiple,
    required=False
)

def filter_queryset(self, queryset):
    min_price = self.cleaned_data.get('min_price')
    max_price = self.cleaned_data.get('max_price')
    characteristics = self.cleaned_data.get('characteristics')
    if min_price:
        queryset = queryset.filter(price__gte=min_price)
    if max_price:
        queryset = queryset.filter(price__lte=max_price)
    if characteristics:
        characteristic_query = Q()
        for characteristic in characteristics:
            characteristic_query |= Q(characteristics=characteristic)
        queryset = queryset.filter(characteristic_query)
    return queryset

观点

class ProductListView(ListView):
    model = Product
    template_name = 'mainapp/product_list.html'

    def get_queryset(self):
        self.category = get_object_or_404(Category, slug=self.kwargs['category_slug'])
        queryset = super().get_queryset().filter(category=self.category)
        filter_form = ProductFilterForm(self.request.GET)
        if filter_form.is_valid():
            queryset = filter_form.filter_queryset(queryset)
        return queryset

    def get_context_data(self, **kwargs):
        context = super().get_context_data(**kwargs)
        context['filter_form'] = ProductFilterForm(self.request.GET)
        context['product'] = self.get_queryset()
        return context

最后,我想得到这样的东西。enter image description here

p4rjhz4m

p4rjhz4m1#

from django.db.models import Count

Product.objects.values('category').annotate(cnt=Count('category')).values('category__name','cnt').order_by('-cnt')

相关问题