Запрашивать элементы по атрибуту Foreignkey Relation, а также наиболее эффективно запрашивать иностранные атрибуты
Существует три модели
Product
: Наличие идентификатора, имени
Storage
: Имеет идентификатор, имя, цвет и ветку
ProductStorage
: Сопоставляет каждый продукт со складом и имеет некоторые дополнительные атрибуты.
Я хочу перечислить все ProductStorages
с определенным Storage.branch
значением, сгруппированные по хранилищу, отображая также имя хранилища и цвет.
Возможно ли сделать это в одном запросе? Я новичок в Django и не знаю, как сделать это наиболее эффективным способом.
Я знаю, что могу запросить все ProductStorages и отфильтровать по веткам. Затем отсортировать их по хранилищам и запросить атрибуты хранилищ вторым запросом. Но я полагаю, что это не лучший способ сделать это.
Я бы инвертировал запрос: вместо запроса ProductStorage
можно запросить Storage
и использовать prefetch_related для получения связанных товаров, также я бы определил отношение между Storage
и Product
с помощью "through"
Тогда ваш запрос будет выглядеть примерно так:
Storage.objects.all().prefetch_related("products")
Или с .filter(branch=..).
, если вы хотите отфильтровать ветку
Простой запрос со связанными Storage
и ProductStorage
s:
from django.db.models import Prefetch
products = Product.objects.prefetch_related(
Prefetch(
'productstorage_set', ProductStorage.objects.select_related('storage')
)
)
тогда мы можем сгруппировать элементы по соответствующим name
и color
:
from collections import defaultdict
for product in products:
product.items = defaultdict(list)
for item in product.productstorage_set.all():
product.items[item.storage.name, item.storage.color].append(item)
и передайте products
шаблону:
{% for product in products %}
<h1>{{ product.name }}</h1>
<ul>
{% for key, val in product.items %}
<li><b>{{ key.0 }} - {{ key.1 }}</b>
{% for item in val %}
<li>{{ item.name }} - {{ item.extra_attr }}</li>
{% endfor %}
</li>
{% endfor %}
</ul>
{% endfor %}