Модель Django с несколькими внешними ключами
Я хочу создать список продуктов, которые классифицируются по области, потребности и категории продукта. Я создал 3 отдельные модели, которые отвечают друг на друга, чтобы пользователи могли легко добавлять категории и выбирать из выпадающего списка область и потребность.
На данный момент у меня есть 3 области и под каждой областью у меня есть потребности. Я хочу вывести список элементов из модели Area
, под каждым элементом из модели Area
все элементы из модели Need
и под каждым элементом из модели Need
все элементы из модели Product
(только названия).
ProductCategory
модель не используется здесь, но она нужна мне в другом месте и является соединителем между продуктами и областями/потребностями. Гораздо проще определить категории и просто выбирать их из выпадающего списка при добавлении нового продукта.
Мне нужно создать цикл, который покажет мне что-то вроде приведенного выше. Я знаю, что это не будет работать, но я хотел показать логику.
Мой вопрос в том, какой лучший подход для рендеринга чего-то подобного?
Как я могу получить category_area
и category_need
в моем классе и в моем html?
models.py
class Area(models.Model):
title = models.CharField(max_length=75, blank=False)
body = models.CharField(max_length=150, default='-', blank=False)
publish = models.DateTimeField('publish', default=timezone.now)
class Need(models.Model):
title = models.CharField(max_length=75, blank=False, null=False, help_text='max 75 characters')
body = models.CharField(max_length=150, default='-', blank=False)
publish = models.DateTimeField(default=timezone.now)
need_area = models.ForeignKey(Area, on_delete=models.CASCADE, related_name='need_area')
class ProductCategory(models.Model):
title = models.CharField(max_length=400, blank=False, null=False, help_text='max 400 characters')
body = models.TextField(default='-')
publish = models.DateTimeField('publish', default=timezone.now)
category_area = models.ForeignKey(Area, on_delete=models.CASCADE, related_name='category_area', null=True)
category_need = models.ForeignKey(Need, on_delete=models.CASCADE, related_name='category_need', null=True)
class Product(models.Model):
id = models.AutoField(primary_key=True)
title = models.CharField(max_length=400, blank=False)
category = models.ForeignKey(ProductCategory, on_delete = models.CASCADE, blank=True, related_name='products')
def get_absolute_url(self):
return reverse("product", kwargs={'slug': self.slug})
views.py
class SearchProducts(LoginRequiredMixin, ListView):
login_url = 'login'
redirect_field_name = 'login'
template_name = 'hubble/search/manual_search.html'
model = Product
queryset = Product.objects.all()
def get_context_data(self, **kwargs):
context = super(SearchProducts, self).get_context_data(**kwargs)
product_results = ProductCategory.objects.prefetch_related("products").all()
context['product_results'] = product_results
return context
product_search.html
<div>
{% for area in product_results %}
<h6>{{area.title}}</h6>
{% endfor %}
</div>
Вы можете prefetch_related
все обратные отношения и сделать итерацию, подобную этой:
areas = Area.objects.prefetch_related('need_area__category_need__products')
for area in areas:
# iterate through each instance of Area
for need in area.need_area.all():
# iterate through each instance of Need for the given area
for product_category in need.category_need.all():
# iterate through each instance of ProductCategory for the given need
for product in product_category.products.all():
# iterate through each instance of product for the given product category