__(Двойное подчеркивание) что это?

В Django __(Двойное подчеркивание) используется для написания запросов к базе данных через реляционные поля между моделями. Проще говоря, это используется для доступа к полям, связанным с другой таблицей, или для фильтрации данных с определенными условиями.

Например, если две или более модели связаны с помощью ForeignKey или OneToOneField, можно получить доступ к нужному полю через эту связь. Здесь __ выступает в роли "связующего звена", позволяя соединять поля разных моделей в цепочку для доступа.

Пример: использование __ в отношениях между моделями

Давайте рассмотрим простой пример. Допустим, модель Profile связана с моделью User, и в этой модели пользователя есть поле username. Мы можем фильтровать определенные профили на основе username модели User.

Определение модели:

from django.db import models
from django.contrib.auth.models import AbstractUser

class CustomUser(AbstractUser):
    pass

class Profile(models.Model):
    user = models.OneToOneField(CustomUser, on_delete=models.CASCADE)
    bio = models.TextField()

В приведенном примере модель Profile имеет 1:1 связь с CustomUser. Теперь давайте посмотрим, как использовать __ для доступа к полям CustomUser из Profile.

Запрос с использованием __:

# Фильтруем объекты Profile на основе username CustomUser
profiles = Profile.objects.filter(user__username='jesse')

Здесь user__username является ключевым моментом. user — это поле, связанное с моделью CustomUser, и для доступа к полю username необходимо соединить их с помощью __. Это позволяет нам извлекать данные на основе поля username модели CustomUser из Profile.

Разнообразие использования __

__ используется не только для доступа к полям, но и для установки условий. Django предлагает множество фильтров для настройки различных условий в queryset, и большинство из них реализуется через __. Часто используемые условия включают:

  • exact: находит точное совпадение значения. (по умолчанию, поэтому можно опустить)
  • icontains: находит значения без учета регистра.
  • gt, lt, gte, lte: условия для поиска значений больше или меньше (больше чем, меньше чем).
  • startswith, endswith: находит значения, начинающиеся или заканчивающиеся определенной строкой.

Пример: различные условия фильтрации

# Получаем все профили, чьи email содержат 'gmail.com'
profiles_with_gmail = Profile.objects.filter(user__email__icontains='gmail.com')

# Получаем профили с ID больше 10
profiles_with_id_gt_10 = Profile.objects.filter(user__id__gt=10)

# Получаем профили, чьи username начинаются с 'jesse'
profiles_starting_with_jesse = Profile.objects.filter(user__username__startswith='jesse')

Доступ к нескольким полям отношений через __

Одна из самых мощных функций Django заключается в том, что можно использовать __ для получения данных, следуя через несколько моделей. Например, представим, что модель Order связана с Profile, а затем Profile связана с CustomUser.

Пример многосвязной модели:

class Order(models.Model):
    profile = models.ForeignKey(Profile, on_delete=models.CASCADE)
    order_date = models.DateTimeField()
    amount = models.DecimalField(max_digits=10, decimal_places=2)

Теперь мы хотим получить данные из Order на основе username CustomUser.

Фильтрация многосвязной модели:

# Получаем заказы, где username CustomUser равен 'jesse'
orders_for_user = Order.objects.filter(profile__user__username='jesse')

Здесь мы можем получить доступ к полю username CustomUser через несколько уровней отношений с помощью profile__user__username. Мы реализовали фильтрацию, связывая отношения OrderProfileCustomUser через __.

Резюме

  • __ используется для ссылки на поля, следуя отношениям между моделями.
  • Можно устанавливать различные условия запроса для фильтрации данных.
  • Можно соединять поля многосвязной модели для выполнения сложных запросов.

Теперь, когда вы понимаете роль и использование __, вы сможете создавать более эффективные запросы в Django ORM. Если вы будете правильно использовать этот символ, учитывая реляционную структуру базы данных, вы сможете эффективно обрабатывать данные и легко работать со сложными отношениями.