[Fixed]-How to display a list of objects containing many-to-many relations in Django template?


There is no need to turn the entries QuerySet into a list. Additionally, you can let the DB do the sorting using order_by.

entries = Entry.objects.filter(user_id=user_id).order_by('id')

Add .all to get all the values from a relationship (just like Entry.objects.all()).


You can try this in the shell as well (I use ipython so your output may look different):

$ ./manage.py shell
# ...
In [1]: from yourproject.models import Entry, Tags
In [2]: entry = Entry.objects.all()[0]
In [3]: entry.tags
Out[3]: <django.db.models.fields.related.ManyRelatedManager object at 0x...>
In [4]: entry.tags.all()  # for an entry with no tags.
Out[4]: []
In [5]: # add a few tags
In [6]: for n in ('bodywork', 'happy', 'muscles'):
   ...:     t, created = Tag.objects.get_or_create(name=n)
   ...:     entry.tags.add(t)
In [7]: entry.tags.all()
Out[7]: [<Tag: ...>, <Tag: ...>, <Tag: ...>]

And if you want to call out the entries with zero tags use for..empty.

{% for tag in entry.tags.all %}
    {{ tag.name }}
{% empty %}
    No tags!
{% endfor %}


Here is the solution of your query,

Verifying your solution by giving an example

Suppose a book have number of tags, so in order to display all the tags of a book on template can be like this

{% for tag in book.tags.all %}
  {{ tag.name }}
{% endfor %}

where the model of Tag is like,

class Tag(models.Model):
    name = models.CharField(max_length=100)

    def __unicode__(self):
    return "%s" % unicode(self.name)


OK. I found the problem. I had some incorrect code which was commented out. But Django processed that code. So html comments didn’t work here. I fixed this and it all worked like a charm.

So if you didn’t know – the html comments don’t prevent template processing.

This is because the template is being processed by Django first then HTML is rendered by browser.



The above from istruble is correct but if your question contains all of your code you need to specify a property in your template:

   {% for entry in entries %}
     {{ entry.title }}
     {{ entry.date }}
     {% for tag in entry.tags.all %} {{ tag.name }} {% endfor %}
   {% endfor %}

or a default unicode function to your model:

class Tag(models.Model):
  name = models.CharField(max_length=20)
  def __unicode__(self):
      return self.name

Leave a comment