Search code examples
djangodjango-formsdjango-filterdjango-filters

Add some parameters to FilterSet (django-filter) + some parameters


i have 3 models:

class Category(models.Model):
    name = models.CharField(max_length=200)
    slug = models.SlugField(max_length=70, null=True, blank=True)

class SubCategory(models.Model):
    category= models.ForeignKey(Category, on_delete=models.CASCADE)
    name = models.CharField(max_length=200, )

class Products(models.Model):
    user= models.ForeignKey(User, on_delete=models.CASCADE)
    category= models.ForeignKey(Category, on_delete=models.CASCADE)
    subcategory = models.CharField(max_length=200, null=True, blank=True)

and i have a view which receive request and category.slug

def category_list(request, slug):
    category = Category.objects.get(slug=slug)
    products = ProductFilter(request.GET, queryset=Products.objects.filter(category=category)

    return render(request, 'products/category_list.html', {"products":products, 'category': category})

when rendering i receive a QuerySet filtered to Category

I want to send category.id to ProductsFilter and recive a dynamic Choices from database

class ProductsFilter(django_filters.FilterSet):
    subcategory= django_filters.ChoiceFilter(lookup_expr='iexact', choices=TEST, required=False)       

    class Meta:
        model = Products
        fields = {
            "subcategory",
        }

Want to change choices=TEST to choices=list(SubCategory.objects.filter(category_id=category.id)

Is this possible?


Solution

  • You can handle this in the FilterSet.__init__ method. Something like the below (Note that I haven't tested it, may require some fiddling):

    class ProductsFilter(django_filters.FilterSet):
        subcategory= django_filters.ChoiceFilter(lookup_expr='iexact', choices=[], required=False)
    
        def __init__(self, category, *args, **kwargs):
            super(ProductsFilter, self).__init__(*args, **kwargs)
    
            choices = self.fields['subcategory'].extra['choices']
            choices += [
                (subcat.name, subcat.name) for subcat 
                in SubCategory.objects.filter(category=category)
            ]
    
        class Meta:
            model = Products