Django how to call a choice field in template - django

I have a model field with choices. Like this:
CHAIN_CHOICES = (
('P','Public'),
('N','Private')
)
chain = models.CharField(max_length=1, choices=CHAIN_CHOICES, verbose_name=u"Chain")
In my template I would like to call it simillary to this:
<li><i class="glyphicon glyphicon-tags"></i> <span>{{mymodel.chain}}</span></li>
Problem is .... this is calling 'N' or 'P' and I would like to call the 'Public' - 'Private' values.
Any hint would be wellcome.
Regards,
J.M.

Guess I have found my answer:
{{ mymodel.get_chain_display }}
Unless there is a different way ??

#JanMejor I want to call from templates to "choices" too but without duplicates. Here is a different way you did:
...
{% for i in mymodel %}
{{ i.chain }}
{% endfor %}
...
Still, it will show duplicates if you have couple posts with the same "choice value"

Related

Was wondering why iterating through a dictionary using .keys in django would not work?

I know that .items would be useful to grab the value, but wanted to see why this would not work?
Data:
...
city_data = {
'city': json_data['name'],
'country': json_data['sys']['country'],
'temp': json_data['main']['temp'],
'feels_like': json_data['main']['feels_like'],
'temp_max': json_data['main']['temp_max'],
'temp_min': json_data['main']['temp_min']
}
return render(request, ..., context={'city_data':city_data})
template:
...
{% for key in city_data.keys %}
<li>{{city_data.key}}</li>
{% endfor %}
...
I think that the reason that it doesn't work that way is because django will look at test.key and try to look up a string "key" as an actual key to the dictionary. There are a couple ways that you could do this. One way is you could define a custom template filter that would allow you to do it. I don't know much about custom filters so I can't say how specifically to do it. Another way though is to use city_data.items in your template instead like this:
{% for key,value in city_data.items %}
<li>{{ value }}</li>
{% endfor %}

Django custom template filter feeding cookie or default value

I'm designing a custom django filter, just to make sure it works I have something like this
{{ "Sleeps:"|translate:"fr" }}
and it works.
Now in the final implementation, I want it to get a cookie or else use a default value
{{ pg.title|translate:request.COOKIES.lang|default:"en" }}
I'm getting this error
VariableDoesNotExist at /chalet/belle-chery
Failed lookup for key [lang] in {'_ga': 'GA1.1.1026479868.1547798010', 'cookie-policy': 'true', 'csrftoken': 'VrVrvgZUfFrWhFDFjLIvZgOus9NrmjDx1JwNP2lzvz2FRAGmC1lLrKwiH4g31X5F', 'sessionid': 'ptp6smvt9w95qtqlkc7klx736u5k7uu5'}
so it doesn't implement the default part.
So I figure there's either a way to fix this or use middleware to set the cookie if it's not set.
Would be nice if it doesn't need middleware.
so it doesn't implement the default part.
It does, it applies the |default:"en" filter to the result of {{ pg.title|translate:request.COOKIES.lang }}, not to the request.COOKIES.lang expression.
The easiest way to solve this is probably defining a local variable, for example with the {% with ... %} template tag:
{% with lang=request.COOKIES.lang|default:"en" %}
{{ pg.title|translate:lang }}
{% endwith %}

Django ManyToMany two for loops

I have two for loops from which the first one (for i in var) is for getting the posts and the other is for getting the tags (ManyToManyField in the Post model) for that post:
{% for i in var %}
{% for j in i.tags.all %}
{{ j.name }}
{% endfor %}
{% endfor %}
Why won't this work?
EDIT:
Here is what the variables contain:
var:
[<SearchResult: myapp.post (pk='1')>, <SearchResult: myapp.post (pk='2')>]
and here is {{ i.tags }}:
<django.db.models.fields.related.ManyRelatedManager object at 0x1620dd0>
If I try to iterate it with .all it returns nothing.
EDIT 2:
This might be the problem - var is a variable from a SearchQuerySet (django haystack):
var = SearchQuerySet().all()
Inside the template, the j is something like <SearchResult: myapp.post (pk='1')>, which does not have .tags attributes. Try for j in i.object.tags.all, the .object refers the actual Model instance.
Note that Django normally does not complain about trying of accessing non-existing attributes (i.tags here) during template rendering. Hence rendering nothing may also mean incorrect attributes referring.
Solved it by adding the tag field into the haystack searchindex. Now it outputs the list of tags. Thank you all for your help!

Django: How do I get the number of elements returned in a database call?

This seems to me like a very simple question, but I can't seem to find the answer.
All I need to do is determine the number of objects returned by a database query.
The specific circumstance is this: I have a model named Student. This model has a ManyToManyField member named courses_current, which relates to a table of Course models. When I pass my Student instance to a template, I want to be able to do something like the following (the syntax may not be exact, but you'll get the basic idea):
<div id="classes">
{% if student.classes_current.all.size == 0 %}
<h1> HEY! YOU AREN'T TAKING ANY CLASSES! REGISTER NOW!
{% else %}
Here are your courses:
<!-- ... -->
{% endif %}
</div>
Now, I'm fairly certain that X_set.all.size is not a real thing. In the manage.py shell I can just use len(student.classes_current.all()), but I don't know of any way to use built-in functions, and "dictionary-like objects" don't have .size() functions, so I'm at a loss. I'm sure there's a very simple solution (or at least I hope there is), but I can't seem to find it.
{{ student.classes_current.all.count }} but be warned that it doesn't fetch the objects so you will need to do a separate query if you want to loop over them.
If you need loop over the classes for tag has way to get what you need.
{% for cl in student.current_classes.all %}
{{ cl }}
{% empty %}
<h1>Hey! ...</h1>
{% endfor %}
Documentation https://docs.djangoproject.com/en/dev/ref/templates/builtins/?from=olddocs#for-empty

Django: Add number of results

I'm displaying the number of search results, however, i do more than one search.
So to display the number of results i'd have to add them up.
So i've tried this:
<p>Found {{ products|length + categories|length + companies|length }} results.</p>
But i get an error.
How do i do this?
Django templates do not support arithmetic operators. However you can use the add filter. I think you need something like this:
<p>Found {{ products|length|add:categories|length|add:companies|length }} results.</p>
Alternatively you should calculate the total in the view and pass it pre-calculated to the template.
EDIT: Further to the comments, this version should work:
{% with categories|length as catlen %}
{% with companies|length as complen %}
<p>Found {{ products|length|add:catlen|add:complen }} results.</p>
{% endwith %}
{% endwith %}
However, this feels very hacky and it would be preferable to calculate the figure in the view.
I would do this in your view when you are creating your context dictionary:
'result_count': len(products) + len(categories) + len(companies)
Then, in your template, just use:
<p>Found {{ result_count }} results.</p>
I'd like to point that Van Gale's answer is not optimal.
From the QuerySet API documentation, you should use query.count() rather than len(query)
A count() call performs a SELECT COUNT(*) behind the scenes, so you
should always use count() rather than loading all of the record into
Python objects and calling len() on the result (unless you need to
load the objects into memory anyway, in which case len() will be
faster).
So the answer should be:
In the view:
'result_count': products.count() + categories.count() + companies.count()
The template remains unchanged