Despite the temptation of buying new servers and adding CPU and RAM – you need to do what you can with the code first. I am exploring and cataloguing these methods to speed up Django QuerySets before server scaling.
The general idea is simple – use more QuerySet methods instead of Python methods to avoid evaluation.
1. Use exists()
Add .exists to your QuerySet if you need to find if the QuerySet is empty or not. Most likely, if you are interested in this kind of article – you already have enough database records for this advice to be notable. If your DB is small, it won’t change much. But it would be a good practice to start using
.exists() as well as
.count() (say, instead of
2. Use .filter() and .exclude() more
There QuerySet methods don’t access the QuerySet itself before the iteration – they are executed in the DB, therefore they are faster.
Basically, instead of:
for profile in Profile.objects.all(): if not profile.is_blocked.filter(user__name='Katerina'): return profile
profiles = Profile.objects.exclude(is_blocked__user__name='Katerina') return profiles.first() # returns None if pool is empty # you can also do this if profiles.exists(): # do what you need
3. Do not use list()
Say, instead of
QuerySet.last(). You hardly ever need to do
list() – find a way to do it with
QuerySet methods. In most cased you may need a for cycle or a generator to further do something with the data, but that’s about that.