1

For a Django project, I have a dictionary which contains the model name and the columns where to look for. So what I want to achieve is to build the query from the variables coming from my dictionary.

        sq = []
        for x in columns:
            print(x)
            sq.append(f'Q({x}__icontains=val)')
        print(sq)
        query = (' | '.join(sq))
        print(query)

        lookups = Q(name__icontains=val) | Q(code__icontains=val)
       # lookups = query

When I do the above, it correctly builds the "string" representing the query, but I'm unable to use it.

The error is as follows:

Traceback (most recent call last):   File "/home/user/price_engine/env/lib/python3.9/site-packages/django/core/handlers/exception.py", line 55, in inner
    response = get_response(request)   File "/home/user/price_engine/env/lib/python3.9/site-packages/django/core/handlers/base.py", line 197, in _get_response
    response = wrapped_callback(request, *callback_args, **callback_kwargs)   File "/home/user/price_engine/masterdata/views.py", line 50, in search_form
    results = Plant.objects.filter(query).distinct()   File "/home/user/price_engine/env/lib/python3.9/site-packages/django/db/models/manager.py", line 87, in manager_method
    return getattr(self.get_queryset(), name)(*args, **kwargs)   File "/home/user/price_engine/env/lib/python3.9/site-packages/django/db/models/query.py", line 1436, in filter
    return self._filter_or_exclude(False, args, kwargs)   File "/home/user/price_engine/env/lib/python3.9/site-packages/django/db/models/query.py", line 1454, in _filter_or_exclude
    clone._filter_or_exclude_inplace(negate, args, kwargs)   File "/home/user/price_engine/env/lib/python3.9/site-packages/django/db/models/query.py", line 1461, in _filter_or_exclude_inplace
    self._query.add_q(Q(*args, **kwargs))   File "/home/user/price_engine/env/lib/python3.9/site-packages/django/db/models/sql/query.py", line 1534, in add_q
    clause, _ = self._add_q(q_object, self.used_aliases)   File "/home/user/price_engine/env/lib/python3.9/site-packages/django/db/models/sql/query.py", line 1565, in _add_q
    child_clause, needed_inner = self.build_filter(   File "/home/user/price_engine/env/lib/python3.9/site-packages/django/db/models/sql/query.py", line 1412, in build_filter
    arg, value = filter_expr ValueError: too many values to unpack (expected 2) [05/Jul/2023 04:27:27] "POST /master/search/plant HTTP/1.1" 500 97494

What am I overlooking? Or am I trying to achieve something in a stupid way?

Basically I want to build the query from a a set of variables, derived from a dictionary based on a single string value (representing the key).

Edit: I think it should be rather as follows, but still the same issue (overlooked the {val}:

sq.append(f"Q({x}__icontains='{val}')")

2 Answers 2

4

you can pass unpacked dictionary to Q object.

so, create dictionary then pass Q object. like this.

filter_q = Q()
for x in columns:
    filter_q |= Q(**{f'{x}__icontains': val}  # '|' means as you know 'OR'

then using q.

somequeryset.filter(filter_q)

additional

Q object can choose connector ('OR' or 'AND')

like this.

Q(foo__icontains='bar', zoo__icontains='bar', _connector=Q.OR)

which means (default _connector is 'AND', see this -https://stackoverflow.com/a/58145006/19176724)

Q(foo_icontains='bar') | Q(foo__icontains='bar')

good luck!

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

4 Comments

Awesome. Thank you for you response. Would this also allow for a method to change the Model based of a variable?
Getting the model also solved: stackoverflow.com/questions/4881607/…
Sorry for the late reply. I saw the link, That's exactly what I know. Glad it helped anyway :)
, _connector=Q.OR Awesome. Thank you for you response. this code exactly what i want.
1

Before passing it into filter, you need to convert it into correct Q objects, try evaluating the query:

query = eval(query)
results = Plant.objects.filter(query).distinct()

1 Comment

Thank you very much for this. It indeed works as intended! I only understood using eval() is not allways recommended due to a security risk?

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.