Django 3.2 как исправить ошибку AttributeError: 'itertools.chain' object has no attribute 'filter'?

У меня есть 3 набора запросов, которые мне нужно объединить и использовать метод filter, когда пользователь выбирает флажок. Ajax работает нормально, но я испытываю трудности с отображением отфильтрованных данных, потому что получаю эту ошибку:

AttributeError: 'itertools.chain' object has no attribute 'filter'

Когда я пытаюсь выполнить итерацию над 1 моделью следующим образом favourite_list=Product.objects.all() все работает нормально, но в моем случае мне нужно отфильтровать данные из 3 различных моделей

Я пытался использовать list(chain(fa, fv, fp)), но это дает мне list object has no attribute filter ошибку.

def filter_favourites(request):
    favourite_articles = request.GET.getlist('favourite_articles[]')
    favourite_video = request.GET.getlist('favourite_video[]')
    favourite_product = request.GET.getlist('favourite_product[]')

    fa = request.user.favourite_article.all().distinct() #list of favourites items from Article model
    fv = request.user.favourite_video.all().distinct() #list of favourites items from Video model
    fp = request.user.favourite_product.all().distinct() #list of favourites items from Product model
    favourite_list = chain(fa, fv, fp)

    if len(favourite_articles) > 0:
        favourite_list = favourite_list.filter(title__in=favourite_articles).distinct()
    if len(favourite_video) > 0:
        favourite_list = favourite_list.filter(title__in=favourite_video).distinct()
    if len(favourite_product) > 0:
        favourite_list = favourite_list.filter(title__in=favourite_product).distinct()

    context = {
        'combined_queryset': favourite_list,
    }
    ajax_template = render_to_string('user/user_favourites_ajax.html', context)
    
    return JsonResponse({'data': ajax_template})

Мой вопрос в том, как я могу исправить эту ошибку? Как я должен объединить fa, fv, pd, чтобы они вели себя как нормальные наборы запросов и я мог использовать метод filter на них.

<<<Метод

filter предназначен для объектов с типом QuerySet, поэтому вы не можете использовать его на списке и цепочке.
Вместо этого вы можете сгруппировать избранные объекты после фильтрации

def filter_favourites(request):
    favourite_articles = request.GET.getlist('favourite_articles[]')
    favourite_video = request.GET.getlist('favourite_video[]')
    favourite_product = request.GET.getlist('favourite_product[]')

    fa = request.user.favourite_article.all().distinct() #list of favourites items from Article model
    fv = request.user.favourite_video.all().distinct() #list of favourites items from Video model
    fp = request.user.favourite_product.all().distinct() #list of favourites items from Product model

    if len(favourite_articles) > 0:
        fa = fa.filter(title__in=favourite_articles)
    if len(favourite_video) > 0:
        fv = fv.filter(title__in=favourite_video)
    if len(favourite_product) > 0:
        fp = fp.filter(title__in=favourite_product)
    
    favourite_list = chain(fa, fv, fp)
    
    context = {
        'combined_queryset': favourite_list,
    }
    ajax_template = render_to_string('user/user_favourites_ajax.html', context)
    
    return JsonResponse({'data': ajax_template})

и нет необходимости снова использовать distinct после условий, это уже было сделано один раз

Ну, похоже, что QuerySet.union() это то, что вы ищете.

favourite_list = fa.union(fv, fp)

Что касается вашего первоначального вопроса, ни у типов list, ни у intertools.chain (который является типом, возвращаемым itertools.chain()) нет метода filter(), отсюда и ошибки.

>>> chain(["a"], ["b"])
<itertools.chain object at 0x7fd3f0a86580>
Вернуться на верх