很多外键 - Django Admin

时间:2012-09-24 22:12:01

标签: sql django query-optimization admin models

有SQL问题,添加此模型都可以正常工作,问题出在ADMIN。

当我将数据添加到每个表格时,点击TYPE& PAGE ADMIN页面加载速度很慢,安装debug_toolbar,SQL TYPE需要17秒。当我尝试PAGE它给我超时时,我的问题是我的模型出了什么问题?它构造得不好吗?

我的目标就是举例如:

http://www.example.com/audi/4doors/s4/sport/red/audi-url

基本上所有6个网址都是动态的,我会在每个表格中指定,并且在PAGE中作为下拉列表也在其他网格中。这样做或优化模型的最佳方法是什么?

以下是TYPE页面加载的屏幕截图:

屏幕截图:http://cl.ly/image/2931040E0t35

请帮助谢谢

from django.db import models

class Client(models.Model):
    title = models.CharField(max_length=100, unique=True)
    def __unicode__(self):
        return self.title

class Category(models.Model):
    client = models.ForeignKey(Client, to_field='title')
    title = models.CharField(max_length=200, unique=True)
    def __unicode__(self):
        return self.title

class Subcategory(models.Model):
    client = models.ForeignKey(Client, to_field='title')
    category = models.ForeignKey(Category, to_field='title')
    title = models.CharField(max_length=200, unique=True)
    def __unicode__(self):
        return self.title

class Project(models.Model):
    client = models.ForeignKey(Client, to_field='title')
    category = models.ForeignKey(Category, to_field='title')
    subcategory = models.ForeignKey(Subcategory, to_field='title')
    title = models.CharField(max_length=200, unique=True)
    def __unicode__(self):
        return self.title

class Type(models.Model):
    client = models.ForeignKey(Client, to_field='title')
    category = models.ForeignKey(Category, to_field='title')
    subcategory = models.ForeignKey(Subcategory, to_field='title')
    project = models.ForeignKey(Project, to_field='title')
    title = models.CharField(max_length=200, unique=True)
    def __unicode__(self):
        return self.title

class Page(models.Model):
    client = models.ForeignKey(Client, to_field='title')
    category = models.ForeignKey(Category, to_field='title')
    subcategory = models.ForeignKey(Subcategory, to_field='title')
    project = models.ForeignKey(Project, to_field='title')
    type = models.ForeignKey(Type, to_field='title')
    pageurl = models.CharField(max_length=200)

当我从admin.py list_display移除外键时,我发现它的速度非常快:

class ClientAdmin(admin.ModelAdmin):
    list_display = ('title',)
    admin.site.register(Client, ClientAdmin)

class CategoryAdmin(admin.ModelAdmin):
    list_display = ('client', 'title',)
    admin.site.register(Category, CategoryAdmin)

class SubcategoryAdmin(admin.ModelAdmin):
    list_display = ('client', 'category', 'title', )
    admin.site.register(Subcategory, SubcategoryAdmin)

class ProjectAdmin(admin.ModelAdmin):
    list_display = ('client', 'category', 'subcategory', 'title', )
    admin.site.register(Project, ProjectAdmin)

class TypeAdmin(admin.ModelAdmin):
    list_display = ('client', 'title', )
    admin.site.register(Type, TypeAdmin)

class PageAdmin(admin.ModelAdmin):
    list_display = ('client', )
    admin.site.register(Page, PageAdmin)

FOREIGN KEYS不能在list_display中?如何优化它们?

更新

class Client(models.Model):
    title = models.CharField(max_length=100, unique=True, db_index=True)
    def __unicode__(self):
        return self.title

class Category(models.Model):
    client = models.ForeignKey(Client)
    title = models.CharField(max_length=200, unique=True)
    def __unicode__(self):
        return self.title

class Subcategory(models.Model):
    client = models.ForeignKey(Client)
    category = models.ForeignKey(Category)
    title = models.CharField(max_length=200, unique=True)
    def __unicode__(self):
        return self.title

class Project(models.Model):
    client = models.ForeignKey(Client)
    category = models.ForeignKey(Category)
    subcategory = models.ForeignKey(Subcategory)
    title = models.CharField(max_length=200, unique=True)
    def __unicode__(self):
        return self.title

class Type(models.Model):
    client = models.ForeignKey(Client)
    category = models.ForeignKey(Category)
    subcategory = models.ForeignKey(Subcategory)
    project = models.ForeignKey(Project)
    title = models.CharField(max_length=200, unique=True)
    def __unicode__(self):
        return self.title

class Page(models.Model):
    client = models.ForeignKey(Client)
    category = models.ForeignKey(Category)
    subcategory = models.ForeignKey(Subcategory)
    project = models.ForeignKey(Project)
    type = models.ForeignKey(Type)
    pageurl = models.CharField(max_length=200)

更新2

from django.db import models


class Client(models.Model):
    title = models.CharField(max_length=100, primary_key=True)
    def __unicode__(self):
        return self.title

class Category(models.Model):
    client = models.ForeignKey(Client)
    title = models.CharField(max_length=200, primary_key=True)
    def __unicode__(self):
        return self.title

class Subcategory(models.Model):
    client = models.ForeignKey(Client)
    category = models.ForeignKey(Category)
    title = models.CharField(max_length=200, primary_key=True)
    def __unicode__(self):
        return self.title

class Project(models.Model):
    client = models.ForeignKey(Client)
    category = models.ForeignKey(Category)
    subcategory = models.ForeignKey(Subcategory)
    title = models.CharField(max_length=200, primary_key=True)
    def __unicode__(self):
        return self.title

class Type(models.Model):
    client = models.ForeignKey(Client)
    category = models.ForeignKey(Category)
    subcategory = models.ForeignKey(Subcategory)
    project = models.ForeignKey(Project)
    title = models.CharField(max_length=200, primary_key=True)
    def __unicode__(self):
        return self.title

class Page(models.Model):
    client = models.ForeignKey(Client)
    category = models.ForeignKey(Category)
    subcategory = models.ForeignKey(Subcategory)
    project = models.ForeignKey(Project)
    type = models.ForeignKey(Type)
    pageurl = models.CharField(max_length=200)

更新3 - ADMIN.PY

class ClientAdmin(admin.ModelAdmin):

    list_display = ('title',)

admin.site.register(Client, ClientAdmin)

class CategoryAdmin(admin.ModelAdmin):

    list_display = ('client', 'title',)

admin.site.register(Category, CategoryAdmin)

class SubcategoryAdmin(admin.ModelAdmin):

    list_display = ('client', 'category', 'title', )

admin.site.register(Subcategory, SubcategoryAdmin)

class ProjectAdmin(admin.ModelAdmin):

        list_display = ('client', 'category', 'subcategory', 'title', )

admin.site.register(Project, ProjectAdmin)

class TypeAdmin(admin.ModelAdmin):

    list_display = ('client', 'category', 'subcategory', 'project', 'title', )

admin.site.register(Type, TypeAdmin)

class PageAdmin(admin.ModelAdmin):

   list_display = ('client', 'category', 'subcategory', 'project', 'type', 'pageurl', )

admin.site.register(Page, PageAdmin)

2 个答案:

答案 0 :(得分:4)

而不是你可以使用django admin的raw_id_fields选项。

admin.site.register(Client)

class CategoryAdmin(admin.ModelAdmin):

    raw_id_fields = ('client',)

admin.site.register(Category, CategoryAdmin)

class SubcategoryAdmin(admin.ModelAdmin):

    raw_id_fields = ('client', 'category')

admin.site.register(Subcategory, SubcategoryAdmin)

class ProjectAdmin(admin.ModelAdmin):

    raw_id_fields = ('client', 'category', 'subcategory')

admin.site.register(Project, ProjectAdmin)

class TypeAdmin(admin.ModelAdmin):

    raw_id_fields = ('client', 'category', 'subcategory', 'project')

admin.site.register(Type, TypeAdmin)

class PageAdmin(admin.ModelAdmin):

    raw_id_fields = ('client', 'category', 'subcategory', 'project', 'type')

admin.site.register(Page, PageAdmin)

this is the old one this is new sql query

答案 1 :(得分:1)

嗯,我不确定这是否100%相关(因为我在list_display list_editable中使用FK)。我使用这里描述的技巧加快速度: http://blog.ionelmc.ro/2012/01/19/tweaks-for-making-django-admin-faster/

似乎为每一行评估选项(特别是在为FK使用list_editable时),因此使用formfield_for_dbfield可以按照链接中的建议缓存选项。这将保存到db,以便为foreign_keys呈现每个下拉/选择框。

如果打开mysql常规日志(如果使用MySQL),则可以看到正在视图上执行的查询。