200π
You could chain your queries as follows:
values = [1,2,3]
# Turn list of values into list of Q objects
queries = [Q(pk=value) for value in values]
# Take one Q object from the list
query = queries.pop()
# Or the Q object with the ones remaining in the list
for item in queries:
query |= item
# Query the model
Article.objects.filter(query)
95π
To build more complex queries there is also the option to use built in Q() objectβs constants Q.OR and Q.AND together with the add() method like so:
list = [1, 2, 3]
# it gets a bit more complicated if we want to dynamically build
# OR queries with dynamic/unknown db field keys, let's say with a list
# of db fields that can change like the following
# list_with_strings = ['dbfield1', 'dbfield2', 'dbfield3']
# init our q objects variable to use .add() on it
q_objects = Q(id__in=[])
# loop trough the list and create an OR condition for each item
for item in list:
q_objects.add(Q(pk=item), Q.OR)
# for our list_with_strings we can do the following
# q_objects.add(Q(**{item: 1}), Q.OR)
queryset = Article.objects.filter(q_objects)
# sometimes the following is helpful for debugging (returns the SQL statement)
# print queryset.query
- [Django]-How to check if ManyToMany field is not empty?
- [Django]-Django MultiValueDictKeyError error, how do I deal with it
- [Django]-Handle `post_save` signal in celery
48π
A shorter way of writing Dave Webbβs answer using pythonβs reduce function:
# For Python 3 only
from functools import reduce
values = [1,2,3]
# Turn list of values into one big Q objects
query = reduce(lambda q,value: q|Q(pk=value), values, Q())
# Query the model
Article.objects.filter(query)
- [Django]-Django rest framework lookup_field through OneToOneField
- [Django]-Django stops working with RuntimeError: populate() isn't reentrant
- [Django]-How to concatenate strings in django templates?
45π
from functools import reduce
from operator import or_
from django.db.models import Q
values = [1, 2, 3]
query = reduce(or_, (Q(pk=x) for x in values))
- [Django]-How to check if a user is logged in (how to properly use user.is_authenticated)?
- [Django]-RuntimeWarning: DateTimeField received a naive datetime
- [Django]-How to migrate back from initial migration in Django 1.7?
25π
Maybe itβs better to use sql IN statement.
Article.objects.filter(id__in=[1, 2, 3])
If you really need to make queries with dynamic logic, you can do something like this (ugly + not tested):
query = Q(field=1)
for cond in (2, 3):
query = query | Q(field=cond)
Article.objects.filter(query)
- [Django]-Getting Values of QuerySet in Django
- [Django]-How to resize the new uploaded images using PIL before saving?
- [Django]-How do you perform Django database migrations when using Docker-Compose?
10π
See the docs:
>>> Blog.objects.in_bulk([1])
{1: <Blog: Beatles Blog>}
>>> Blog.objects.in_bulk([1, 2])
{1: <Blog: Beatles Blog>, 2: <Blog: Cheddar Talk>}
>>> Blog.objects.in_bulk([])
{}
Note that this method only works for primary key lookups, but that seems to be what youβre trying to do.
So what you want is:
Article.objects.in_bulk([1, 2, 3])
- [Django]-Django-reversion and related model
- [Django]-Django 1.5 β How to use variables inside static tag
- [Django]-Django gives Bad Request (400) when DEBUG = False
10π
Solution which use reduce
and or_
operators to filter by multiply fields.
from functools import reduce
from operator import or_
from django.db.models import Q
filters = {'field1': [1, 2], 'field2': ['value', 'other_value']}
qs = Article.objects.filter(
reduce(or_, (Q(**{f'{k}__in': v}) for k, v in filters.items()))
)
p.s. f
is a new format strings literal. It was introduced in python 3.6
- [Django]-Is it better to use path() or url() in urls.py for django 2.0?
- [Django]-How to disable Django's CSRF validation?
- [Django]-Django Installed Apps Location
7π
In case we want to programmatically set what db field we want to query:
import operator
questions = [('question__contains', 'test'), ('question__gt', 23 )]
q_list = [Q(x) for x in questions]
Poll.objects.filter(reduce(operator.or_, q_list))
- [Django]-How to convert a Django QuerySet to a list?
- [Django]-CORS: Cannot use wildcard in Access-Control-Allow-Origin when credentials flag is true
- [Django]-Django gives Bad Request (400) when DEBUG = False
6π
For loop
values = [1, 2, 3]
q = Q(pk__in=[]) # generic "always false" value
for val in values:
q |= Q(pk=val)
Article.objects.filter(q)
Reduce
from functools import reduce
from operator import or_
values = [1, 2, 3]
q_objects = [Q(pk=val) for val in values]
q = reduce(or_, q_objects, Q(pk__in=[]))
Article.objects.filter(q)
Both of these are equivalent to Article.objects.filter(pk__in=values)
Why Q()
is dangerous
Itβs important to consider what you want when values
is empty. Many answers with Q()
as a starting value will return everything. Q(pk__in=[])
is a better starting value. Itβs an always-failing Q object thatβs handled nicely by the optimizer (even for complex equations).
Article.objects.filter(Q(pk__in=[])) # doesn't hit DB
Article.objects.filter(Q(pk=None)) # hits DB and returns nothing
Article.objects.none() # doesn't hit DB
Article.objects.filter(Q()) # returns everything
If you want to return everything when values
is empty, you should AND with ~Q(pk__in=[])
to ensure that behaviour:
values = []
q = Q()
for val in values:
q |= Q(pk=val)
Article.objects.filter(q) # everything
Article.objects.filter(q | author="Tolkien") # only Tolkien
q &= ~Q(pk__in=[])
Article.objects.filter(q) # everything
Article.objects.filter(q | author="Tolkien") # everything
Q()
is nothing, not an always-succeeding Q object. Any operation involving it will just drop it completely.
- [Django]-Pulling data to the template from an external database with django
- [Django]-How to get an ImageField URL within a template?
- [Django]-'staticfiles' is not a valid tag library: Template library staticfiles not found
- [Django]-Django.db.utils.ProgrammingError: relation "bot_trade" does not exist
- [Django]-Django 1.8 KeyError: 'manager' on relationship
- [Django]-How to manage local vs production settings in Django?
2π
This one is for dynamic pk list:
pk_list = qs.values_list('pk', flat=True) # i.e [] or [1, 2, 3]
if len(pk_list) == 0:
Article.objects.none()
else:
q = None
for pk in pk_list:
if q is None:
q = Q(pk=pk)
else:
q = q | Q(pk=pk)
Article.objects.filter(q)
- [Django]-Removing 'Sites' from Django admin page
- [Django]-Django Template Language: Using a for loop with else
- [Django]-How to get username from Django Rest Framework JWT token
1π
Another option I wasnβt aware of until recently β QuerySet
also overrides the &
, |
, ~
, etc, operators. The other answers that OR Q objects are a better solution to this question, but for the sake of interest/argument, you can do:
id_list = [1, 2, 3]
q = Article.objects.filter(pk=id_list[0])
for i in id_list[1:]:
q |= Article.objects.filter(pk=i)
str(q.query)
will return one query with all the filters in the WHERE
clause.
- [Django]-How do I remove Label text in Django generated form?
- [Django]-Saving ModelForm error(User_Message could not be created because the data didn't validate)
- [Django]-Django admin TabularInline β is there a good way of adding a custom html column?
1π
Found solution for dynamical field names:
def search_by_fields(value, queryset, search_in_fields):
if value:
value = value.strip()
if value:
query = Q()
for one_field in search_in_fields:
query |= Q(("{}__icontains".format(one_field), value))
queryset = queryset.filter(query)
return queryset
- [Django]-Django: why i can't get the tracebacks (in case of error) when i run LiveServerTestCase tests?
- [Django]-__init__() got an unexpected keyword argument 'mimetype'
- [Django]-How do I convert a Django QuerySet into list of dicts?
0π
easy..
from django.db.models import Q
import you model
args = (Q(visibility=1)|(Q(visibility=0)&Q(user=self.user))) #Tuple
parameters={} #dic
order = βcreate_atβ
limit = 10
Models.objects.filter(*args,**parameters).order_by(order)[:limit]
- [Django]-How to make two django projects share the same database
- [Django]-Django: How to check if the user left all fields blank (or to initial values)?
- [Django]-Django β how to visualize signals and save overrides?