Значение обратного поиска ForeignKey (от дочернего к родительскому)

Мне нужно получить доступ к значению обратным способом, используя ForeignKey. Я хочу перейти от дочерней модели Category к родительской модели Post и получить значение title в свой шаблон

Я пробовал category.posts.title, но это не показывает никакого успеха для меня.

Основная цель этого — создать <div> для каждой категории и перечислить сообщения в блоге с этой категорией внизу.

Модели:

class Category(models.Model):
    name = models.CharField(max_length=30)

class Post(models.Model):
    slug = models.SlugField(max_length = 250, null = True, blank = True)
    title = models.CharField(max_length = 250, default = "Blog Post")
    body = models.TextField()
    created_on = models.DateTimeField(null=True)
    last_modified = models.DateTimeField(null=True)
    categories = models.ForeignKey('Category', related_name='posts', default = "2", unique=False, on_delete=models.CASCADE)

Вид:

def blog_index(request):
    posts = Post.objects.all().order_by('-created_on')
    categories = Category.objects.all()
    context = {
        "posts": posts,
        "categories": categories,
    }
    return render(request, "blog_index.html", context)

Шаблон

<div class = "row">
<div style = "padding: 0px;" class = "col l12">
    {% for category in categories %}

<div class = "col l3">
    <div style = "background-color: white; box-shadow: 0 1px 15px 1px rgba(62,57,107,.07); border-radius: .6rem;" class = "card ">
        <div class = "card-body text-center">
            <div class = "mb-4 pb-3"><i class = "ti-briefcase text-muted font-40"></i></div>

            <h5 class = "mb-3"> <a href = "{% url 'blog_category' category %}">{{ category.name }}</a></h5>

            <div><a class = "d-inline-flex align-items-center text-danger" ><a href = "{% url 'blog_detail' category.name category.posts.slug category.posts.pk %}">{{ category.posts.title }}</a><i class = "material-icons">
                keyboard_arrow_right
                </i></a></div>

        </div>
    </div>
</div>
{% endfor %}

Почему в Python есть оператор "pass"?
Почему в Python есть оператор "pass"?
Оператор pass в Python - это простая концепция, которую могут быстро освоить даже новички без опыта программирования.
Некоторые методы, о которых вы не знали, что они существуют в Python
Некоторые методы, о которых вы не знали, что они существуют в Python
Python - самый известный и самый простой в изучении язык в наши дни. Имея широкий спектр применения в области машинного обучения, Data Science,...
Основы Python Часть I
Основы Python Часть I
Вы когда-нибудь задумывались, почему в программах на Python вы видите приведенный ниже код?
LeetCode - 1579. Удаление максимального числа ребер для сохранения полной проходимости графа
LeetCode - 1579. Удаление максимального числа ребер для сохранения полной проходимости графа
Алиса и Боб имеют неориентированный граф из n узлов и трех типов ребер:
Оптимизация кода с помощью тернарного оператора Python
Оптимизация кода с помощью тернарного оператора Python
И последнее, что мы хотели бы показать вам, прежде чем двигаться дальше, это
Советы по эффективной веб-разработке с помощью Python
Советы по эффективной веб-разработке с помощью Python
Как веб-разработчик, Python может стать мощным инструментом для создания эффективных и масштабируемых веб-приложений.
0
0
62
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Ответ принят как подходящий

Вам нужно перебрать сообщения в каждой категории

{% for post in category.posts.all %}
    <a href = "{% url 'blog_detail' category.name post.slug post.pk %}">{{ post.title }}</a>
{% endfor %}

Вам также следует использовать prefetch_related в наборе запросов категорий, чтобы уменьшить количество запросов к БД, которые вы делаете при доступе к category.posts.all, поскольку вам больше не нужен набор запросов сообщений.

def blog_index(request):
    categories = Category.objects.annotate(
        post_count=Count('posts')
    ).prefetch_related('posts')
    context = {
        "categories": categories,
    }
    return render(request, "blog_index.html", context)

Добавлен аннотация для получения количества сообщений для каждой категории.

{% category.post_count %}

Абсолютно в точку! Спасибо за помощь и дополнительную информацию по оптимизации вызовов базы данных!

Lesnie Sncheider 27.05.2019 21:54

Как я могу подсчитать общее количество сообщений в данной категории? Я пробовал {{category.posts.title.count}}, но это не работает.

Lesnie Sncheider 27.05.2019 22:35

Вы можете использовать category.posts.count, но это будет выполнять запрос БД для каждой категории. Лучше использовать annotate, я обновлю свой ответ

Iain Shelvington 27.05.2019 22:37

Спасибо за обновление ответа! Я получаю эту ошибку в представлениях name 'Count' is not defined

Lesnie Sncheider 27.05.2019 22:44

Вам нужно импортировать Count: from django.db.models import Count

Iain Shelvington 27.05.2019 22:46

Поскольку у одного Category может быть несколько сообщений, вам нужно будет перебрать их:

category.posts.all()

В шаблоне:

{% for category in categories %}
    {{ category.name }}
    { % for post in category.posts.all %}
        {{ post.title }}
    {% endfor %}
{% endfor%}

Также правильный ответ, но он решил отметить ответ Лэйна как правильный, так как он добавил в свой ответ некоторую оптимизацию БД. Спасибо!

Lesnie Sncheider 27.05.2019 21:55

Другие вопросы по теме