For if Loop ManyToMany Field Django - python

How can I query a manytomanyfield in a Django template? For example,
this if statement doesn't work, but this shows what I'd like to do:
Model:
class Product(models.Model):
Category = models.ManyToManyField(Category)
Template:
{% for p in Product %}
{% if p.Category_id == 6 %}
{{p.id}}
{% endif %}
{% endfor %}

I think it's better to filter your queryset in views.py as
products = Product.objects.filter(Category__id=6)
then loop through that queryset in template
{% for p in products %}
{{p.id}}
{% endfor %}

I don't know the actual use case. You haven't posted the view. Assuming in django template products is the queryset. e.g products= Product.objects.all(). This is how you will detect the Category instance with id=6 for all the products in django template.
{% for p in products %}
{% for category in p.Category.all %}
{% if category.id == 6 %}
{{p.id}}
{% endif %}
{% endfor %}
{% endfor %}

Related

Django filter and count in template tag

I'm trying to filter and count a specific QuerySet in the template with Django template engine. Cant get it to work. The film_list is the context and film is the table and language is a field. Any tips on how to use filter and count at the same time in the template engine? Or should I solve it in another way?
{% if filmlist.film.language == "danish" %}
{{ film_list.all.count }}
{% endif %}
View
class FilmListView(LoginRequiredMixin, ListView):
paginate_by = 150
model = Film
context_object_name = 'film_list'
template_name = 'movies/movie_list.html'
You have to iterate over your context to get each object like this
{% for item in filmlist %}
{% if item.language == "danish" %}
{{ film_list.count }}
{% endif %}
{% endfor %}

Get n items in django model using releverse relationship

Is possible to get the last n items in the Django model, using the reverse relationship.
{% for brand in brands %}
{% for product in brand.product_set.all %}
{% endfor %}
{% endfor %}
I am tried in this way, But it prints all things. But want only last 3 items
You can make use of the |slice template tag [Django-doc] to slice the collection with:
{% for brand in brands %}
{% for product in brand.product_set.reverse|slice:":3" %}
…
{% endfor %}
{% endfor %}

how to get a list of questions posted by followed users

Friends, I am trying to implement a question answer site in which a logged in user gets a list of questions and answers asked by the users he follows.
I am using django-friendship to implement user follows. I want to know how we can fetch all the questions posted by the users whom the current user follows.
I have tried the following but doesn't work.
views.py
def index(request):
if request.session.get('current_user'):
questions = []
users = Follow.objects.following(request.user)
i = 0
while i < len(users):
posts = Question.objects.filter(user=users[i])
questions.append(posts)
i = i + 1
return render(request, "welcome/index.html",locals())
Here's my template
welcome/index.html
{% extends "layout.html" %}
{% block content %}
{% for q in questions %}
{{ q.title }}
{% endfor %}
{% endblock %}
You can fetch all questions without looping
views.py
def index(request):
if request.session.get('current_user'):
users = Follow.objects.following(request.user)
questions = Question.objects.filter(user__in=users)
return render(request, "welcome/index.html",locals())
template
{% extends "layout.html" %}
{% block content %}
{% for q in questions %}
{{ q.title }}
{% endfor %}
{% endblock %}
posts is a queryset. Thus, questions is a list of querysets and, in your template, you are not iterating over Question instances, but querysets that do NOT have a title attribute. You can try in your view:
questions.extend(posts) # not: append
in order to obtain an actual list of Question instances. Or, you can change your template:
{% for qs in questions %}
{% for q in qs %}
{{ q.title }}
{% endfor %}
{% endfor %}

Django Get Primary + Foreign Attributes

I have two models: Site and Metric.
I want to display the Metric values alongside each Site.
My views.py is as follows:
from django.shortcuts import render
from .models import Site, Metric
def site_graph(request):
sites = Site.objects.order_by('name')
metrics = [s.metric_set.all() for s in sites]
return render(request, 'da/site_graph.html', {'sites': sites, 'metrics': metrics})
And my template content looks like this:
{% block content %}
{% for metric in metrics %}
[
{% for query in metric %}
{{ query.domain_authority }}
{{ query.date_queried }}
{% endfor %}
]
{% endfor %}
{% endblock content %}
I am not sure how I would go about getting the data I need in Django.
This data is going to be eventually passed onto d3.js for visualization which is why I need the data from the matching the primary key for each Site to be together.
You can use a list of dictionaries:
def site_graph(request):
metrics=[]
sites = Site.objects.order_by('name')
for site in sites:
metrics_site={}
metrics_site["site"] = site
metrics_site["metrics"] = site.metric_set.all()
metrics.append(metrics_site)
return render(request, 'da/site_graph.html', {'metrics': metrics})
And then in the template:
{% block content %}
{% for metric in metrics %}
{{ metric.site.name }}
{% for query in metric.metrics %}
{{ query.domain_authority }}
{{ query.date_queried }}
{% endfor %}
{% endfor %}
{% endblock content %}
metric.site.name is just an example if your model "site" contains a field "name" that you want to show.

'for' loop through form fields and excluding one of the fields with 'if'

The problem I'm struggling with is as follows:
I have:
{% for field in form %}
{{ field }}
{% end for %}
What I want is to put an 'if' statement to exclude a field which .label or whatever is provided. Like:
{% for field in form%}
{% if field == title %}
{% else %}
{{ field }}
{% endif %}
{% endfor %}
Is it possible? I have to many fields to write them one by one and only one or two to exclude.
Thank you for any tips.
BR,
Czlowiekwidmo.
Yes, this should be possible:
{% for field in form %}
{% ifnotequal field.label title %}
{{ field }}
{% endifnotequal %}
{% endfor %}
Django's template tags offer ifequal and ifnotequal variants, and you can test the field.label against either a context variable, or a string.
You might be a lot happier creating a subclass of the form, excluding the offending field.
See http://docs.djangoproject.com/en/dev/topics/forms/modelforms/#form-inheritance
class SmallerForm( MyForm ):
class Meta(MyForm.Meta):
exclude = [ title ]
{% for field in form %}
{% if field.name != 'field_name' %}
{{ field }}
{% endif %}
{% endfor %}

Categories