Django - QuerySetManager - Bonnes pratiques

Publié le 23 novembre 2011 par Samuel Martin

J'ai déjà parlé de l'intérêt des querySetManager et de leur mise en place dans un projet Django. Désormais avec un peu de recul et l'intervention d'Olivier Meunier (l'homme aux milles pseudonymes), il semble plus pertinent d'externaliser la création du manager et du queryset. C'est à dire, pour l'exemple ci-dessous, définir tout ce joyeux code en dehors de la classe "Project".

Voici les 3 étapes importantes pour pouvoir utiliser un Querysetmanager

  • Création de la classe
  • Création du manager
  • Création du queryset + définition des méthodes

La classe appelle le manager qui appelle le queryset ce qui nous donne Classe > Manager > Queryset

Création de la classe

from django.db.models.query import QuerySet
from django.db.models import Model, Manager

class Project(Model, ...):
    name = CharField(max_length = 100)
    description = TextField(blank = True, null = True)
    url = URLField(verify_exists = settings.SERVER_WEB_ACCESS)
    ...
    objects = ProjectManager() # Appel du manager

Création du Manager

class ProjectManager(Manager):
    def get_query_set(self):
        return ProjectQuerySet(self.model) # Appel du queryset

Création du Queryset

class ProjectQuerySet(QuerySet):
    def get_coworkers(self):
        coworkers = []
        for project in self:
           for coworker in project.get_coworkers():
               coworkers.append(coworker.id)
        return User.objects.filter(pk__in = coworkers)
    def get_toto(self):
        return ...

En pratique

On peut désormais utiliser les méthodes get_coworkers() et get_toto() sur un queryset Project.

Project.objects.filter(name__contains=".net").get_coworkers() --> Récupère l'ensemble des collaborateurs des projets dont le nom contient ".net"