Pesquisas reversas de chaves estrangeiras no Django

Pesquisas reversas de chaves estrangeiras no Django

Django é uma estrutura de desenvolvimento web eficiente que simplifica a criação de aplicativos web. Django torna fácil lidar com autenticação e autorização, criação de templates HTML, lidar com arquivos estáticos, interagir com bancos de dados e realizar operações CRUD sobre eles.

Falando em bancos de dados, o Django simplifica a maioria das consultas que você pode fazer enquanto trabalha com bancos de dados. Uma dessas perguntas é a aparência inversa; um exemplo é quando temos que obter todos os objetos de uma tabela que fazem referência a um determinado registro da mesma tabela ou de um modelo diferente.

Este artigo mostrará como é simples realizar pesquisas reversas de chaves estrangeiras no Django.

Pesquisas reversas em modelos Django

Antes de passarmos para a etapa real, precisamos de alguns modelos ou tabelas para demonstração. Vamos considerar duas entidades: professor e aluno. O aluno tem dois tipos de professores; um professor de classe e um professor favorito. O modelo Student faz referência ao 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"
    )

Dois campos do modelo Student fazem referência ao modelo Teacher. No Django, ao fazer referência ao mesmo modelo mais de uma vez, temos que fornecer um related_name para todos os campos porque o padrão related_name do Django para um único campo de referência entra em conflito com outros campos de referência. Caso contrário, o Django lançará uma exceção.

O related_name é o que usamos para a pesquisa inversa. Em geral, é uma boa prática fornecer um related_name para todas as chaves estrangeiras ao invés de usar o nome relacionado padrão do Django.

Exemplo 1

Temos um professor cujo id é 1. Se tivermos que obter todos os alunos que têm esse indivíduo como professor da turma, faremos o seguinte:

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

Observe como estamos usando o related_name. O teacher.classTeacherOf é um objeto gerenciador, o que significa que nele chamamos métodos como all(), filter(), exclude().

Exemplo 2

Temos um professor cujo id é 6. Se tivermos que conseguir todos os alunos que consideram esse professor como seu professor favorito, faremos algo assim:

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

Exemplo 3

Temos um professor cujo id é 25. Se tivermos de verificar se este professor é o professor da turma de um aluno cujo id é 5, faremos o seguinte:

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

Observe que, se nenhum objeto for encontrado na pesquisa reversa, um QuerySet vazio será retornado.

Está gostando dos nossos tutoriais? Inscreva-se no DelftStack no YouTube para nos apoiar na criação de mais vídeos tutoriais de alta qualidade. Inscrever-se
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.