Modulo in django queryset?

Is there a way to select objects according to id % 4 == 0 in django queryset?

The only solution I have found so far is to write a custom Transform, since Postgresql seems to support modulo, but I got errors.

Here is my code:

 from django.db.models import Lookup, Transform from django.db.models.fields import Field, IntegerField, AutoField class Modulo4(Transform): lookup_name = 'modulo4' def as_sql(self, compiler, connection): lhs, params = compiler.compile(self.lhs) return "%s %% 4" % lhs, params AutoField.register_lookup(Modulo4) foos = Foo.filter(id__modulo4=0) 

And I get an error while evaluating the request (using foos.count() or something else):

 IndexError: tuple index out of range 

referring to the django file. This seems to be related to the module, since I manage to do work with a custom conversion using the doc example .

Any idea on how to achieve this?

+5
source share
1 answer

I don't have Django 1.8 to test it, but it looks like you can do it using F with annotation , like this:

 Foo.objects.annotate(idmod4=F('id') % 4).filter(idmod4=0) 

(Django 1.7 and earlier does not support the use of F in annotate )


For Django 1.7 and earlier, you can always use .extra() , but this is not very pretty:

 Foo.objects.extra(where=["id %% %s = 0"], params=[4]) 
+7
source

All Articles