我在我的网站上到处都使用Django Paginator,甚至编写了一个特殊的模板标签,以使其更加方便。但是现在我进入一种状态,需要进行一个复杂的自定义原始SQL查询,如果没有LIMIT
,它将返回大约10万条记录。
如何在自定义查询中使用Django Pagintor?
我的问题的简化示例:
我的模特:
class PersonManager(models.Manager):
def complicated_list(self):
from django.db import connection
#Real query is much more complex
cursor.execute("""SELECT * FROM `myapp_person`""");
result_list = []
for row in cursor.fetchall():
result_list.append(row[0]);
return result_list
class Person(models.Model):
name = models.CharField(max_length=255);
surname = models.CharField(max_length=255);
age = models.IntegerField();
objects = PersonManager();
我在Django ORM中使用分页的方式:
all_objects = Person.objects.all();
paginator = Paginator(all_objects, 10);
try:
page = int(request.GET.get('page', '1'))
except ValueError:
page = 1
try:
persons = paginator.page(page)
except (EmptyPage, InvalidPage):
persons = paginator.page(paginator.num_pages)
这样,Django变得非常聪明,并在执行查询时将
LIMIT
添加到查询中。但是当我使用自定义管理器时:all_objects = Person.objects.complicated_list();
所有数据都被选中,然后才对python list进行切片,这非常慢。如何使自定义管理器的行为类似于内置管理器?
最佳答案
查看Paginator的源代码,尤其是page() function,我认为这只是在您这一边实现slicing并将其转换为SQL查询中的相关LIMIT子句的问题。您可能还需要添加一些缓存,但是开始看起来像QuerySet,所以也许您可以做其他事情:
(供您引用-我已经使用这种方法很长时间了,即使与VIEWs的复杂多对多关系伪造了m2m中间表。)