Búsquedas inversas de claves externas en Django

Vaibhav Vaibhav 10 agosto 2021
Búsquedas inversas de claves externas en Django

Django es un marco de desarrollo web eficiente que simplifica la creación de aplicaciones web. Django facilita la tarea de autenticar y autorizar, crear plantillas HTML, manejar archivos estáticos, interactuar con bases de datos y realizar operaciones CRUD sobre ellos.

Hablando de bases de datos, Django simplifica la mayoría de las consultas que puede realizar mientras trabaja con bases de datos. Una de esas consultas es la vista inversa; un ejemplo es cuando tenemos que obtener todos los objetos de una tabla que hacen referencia a un registro particular de la misma tabla o de un modelo diferente.

Este artículo mostrará lo simple que es realizar búsquedas inversas de claves externas en Django.

Búsquedas inversas en modelos Django

Antes de pasar al paso real, necesitamos algunos modelos o tablas para la demostración. Consideraremos dos entidades: profesor y alumno. El alumno tiene dos tipos de profesores; un maestro de clase y un maestro favorito. El modelo Student hace referencia al modelo Teacher.

from django.db import models


class Teacher(models.Model):
    name = models.CharField(max_length=200)
    subject = models.CharField(max_length=200)


class Student(models.Model):
    name = models.CharField(max_length=200)
    classTeacher = models.ForeignKey(
        Teacher, on_delete=models.SET_NULL, null=True, related_name="classTeacherOf"
    )
    favouriteTeacher = models.ForeignKey(
        Teacher, on_delete=models.SET_NULL, null=True, related_name="favouriteTeacherOf"
    )

Dos campos del modelo Student hacen referencia al modelo Teacher. En Django, cuando se hace referencia al mismo modelo más de una vez, tenemos que proporcionar un related_name para todos los campos porque el related_name predeterminado de Django para un solo campo de referencia choca con otros campos de referencia. De lo contrario, Django lanzará una excepción.

El related_name es lo que usamos para la búsqueda inversa. En general, es una buena práctica proporcionar un related_name para todas las claves externas en lugar de usar el nombre relacionado por defecto de Django.

Ejemplo 1

Tenemos un profesor cuyo id es 1. Si tenemos que conseguir a todos los alumnos que tienen a este individuo como profesor de clase, haremos lo siguiente:

teacher = Teacher.objects.get(id=1)
students = teacher.classTeacherOf.all()
print(students)  # A QuerySet of Student objects

Observe cómo estamos usando el related_name. El teacher.classTeacherOf es un objeto administrador, lo que significa que llamamos a métodos como all(), filter(), exclude() en él.

Ejemplo 2

Tenemos un profesor cuyo id es 6. Si tenemos que conseguir a todos los alumnos que consideran a este profesor como su profesor favorito, haremos algo como esto:

teacher = Teacher.objects.get(id=6)
students = teacher.favouriteTeacherOf.all()
print(students)  # A QuerySet of Student objects

Ejemplo 3

Tenemos un profesor cuyo id es 25. Si tenemos que comprobar si este profesor es el profesor de clase de un alumno cuyo id es 5, haremos algo de la siguiente manera:

teacher = Teacher.objects.get(id=25)
student = teacher.classTeacherOf.filter(id=5)
print(student)  # A QuerySet of either 1 or 0 Student

Tenga en cuenta que si no se encuentran objetos en la búsqueda inversa, se devuelve un QuerySet vacío.

Vaibhav Vaibhav avatar Vaibhav Vaibhav avatar

Vaibhav is an artificial intelligence and cloud computing stan. He likes to build end-to-end full-stack web and mobile applications. Besides computer science and technology, he loves playing cricket and badminton, going on bike rides, and doodling.

Artículo relacionado - Django Object