2014-04-28 5 views
1

je la structure de base de données suivante:optimize django admin sql

class Book(models.Model): 
    id = models.AutoField(primary_key=True, db_column='id') 
    name = models.CharField(max_length=255, db_column='name') 
    author = models.ForeignKey('Author', to_field='id', db_column='author_id') 


class Author(models.Model): 
    id = models.AutoField(primary_key=True, db_column='id') 
    fio = models.CharField(max_length=255, db_column='fio') 

    def __unicode__(self): 
     return self.name 

Et cette classe Admin pour livre:

class BookAdmin(admin.ModelAdmin): 
    list_display = ('id', 'name',) 
    fields = ('id', 'name', 'author',) 
    readonly_fields = ('id',) 
    raw_id_fields = ('author',) 

Tout fonctionne très bien quand il est 500-1000 records du livre, mais sur 1 2 millions de pages de livres geler pendant quelques minutes avant de montrer quelque chose. Profiler montre moi que Django joindre des livres avec des auteurs et ensuite couper les 100 derniers enregistrements. Comment puis-je optimiser django pour joindre des auteurs après avoir sélectionné des livres de la base de données? Ou utiliser quelque chose comme ça

select * from (SELECT * FROM books ORDER BY books.id DESC LIMIT 100) t, authors a where t.author_id = a.id 

Répondre

1

Vous rencontrez un problème connu: Slow INNER JOIN in MySQL can be fixed in Django ORM, but should it?

Il y a un projet appelé django-mysql-fix qui a été lancé sur PyCon 2014 sprints qui ont introduit un backend de base de données MySQL personnalisée pour la fixation INNER JOIN questions spécifiquement:

Ce projet contient des optimisations (hacks) pour MySQL pour Django ORM.

Il y a deux façons très simples pour cacth INNER JOIN bug:

  • Une fois que vous spécifiez champ de la table étrangère list_display dans votre modèle Django Administrateur;

  • Une fois que vous essayez de trier (ordonner) par champ de table étrangère.

Pour autant que je comprends, sous le capot, il remplace tous les INNER JOIN s avec STRAIGHT_JOIN s, citation de mysql docs:

STRAIGHT_JOIN est similaire à JOIN, sauf que la table gauche est toujours lire avant la bonne table. Cela peut être utilisé pour les (rares) cas pour lesquels l'optimiseur de jointure place les tables dans le mauvais ordre.

voir aussi:

+0

Cela affecte-t postgresql aussi? –

+0

@BurhanKhalid Je suis sûr que c'est mysql-spécifique. Merci. – alecxe