Jinja2: how to evaluate Python variable in an if-statement? [duplicate] - python

I have a Jinja2 Template I'm working on for a database editing app, and I'm trying to make it 'extendible' - rather than hard-coding the editing page, I'm passing a list of attributes that I want in the table, and using a for loop to iterate over them. It works aside from one thing - in the hardcoded version, I use an attribute of an object that's being passed to see if that value has been set (they are all boolean), but I can't see how to get jinja2 to take the 'capability' and use that as an attribute of the 'pupil' object; i would have used 'eval' in Python, but can't see how to get this to work. Here's an idea of the code:
{% for capability in capability_list %}
<tr>
<td>{{ capability }}</td>
<td>
{% if pupil.capability %}
<img src="{{request.static_url('gdpr_permissions:static/tick.png')}}" width="25">
{% else %}
<img src="{{request.static_url('gdpr_permissions:static/cross.png')}}" width="25">
{% endif %}
</td>
<td>
<div class="onoffswitch">
<input type="checkbox" name="{{ capability }}" class="onoffswitch-checkbox" value ='No' id="{{ capability }}" checked>
<label class="onoffswitch-label" for="{{ capability }}">
<span class="onoffswitch-inner"></span>
<span class="onoffswitch-switch"></span>
</label>
</div>
</td>
</tr>
{% endfor %}
It's the {% if pupil.capability %} part that doesn't work - I want this to become (say) pupil.web_access and pupil.database_access etc., following the capability list which is being iterated over.
Any ideas on how to get this working with jinja2, or how else it can be approached? The other idea I had was to iterate over the current settings in the python backend and then pass a list of booleans separately, but this seems to be adding an extra level of complexity.

This is because you are passing in a string instead of an attribute. Use getattr() instead. Do something like getattr(pupil, capability)

Related

How can I bundle up the input data by users and the numbers generated by my sudoku generator, and pass them to Django?

I've made the sudoku generator and the templates, but now I stuck in posting the whole array(9x9) to Django (i.e. sudoku_checker) for checking the duplicates and determine whether the user can go next game.
Here is my template looks like in Django, and you'll see I've indexed/positioned every single table cell, thought it might help with later checking:
<table>
<caption>Sudoku of the day</caption>
{% for row in numbers %}
<tr>
{% for col in row %}
{% if col is 0 %}
<td>
<input class="d0" size="1" autocomplete="off" maxlength="1" name="{{ forloop.parentloop.counter0 }}{{ forloop.counter0 }}">
</td>
{% else %}
<td id="{{ forloop.parentloop.counter0 }}{{ forloop.counter0 }}">{{ col }}</td>
{% endif %}
{% endfor %}
</tr>
{% endfor %}
</table>
<button class="btn btn-primary" type="submit">Submit</button>
but then what should I do next? Am I correct to use Form method to Post the data to Django? But how can i make sure all the data have been bundled up when passing through for checking, in terms of both the known numbers and unknown numbers(input by users)? any hints please?
This is the code of the views, but i only completed the numbers_fill_table one, i dont know what to write in second part of views and forms properly to post the exact data i want. Please help!
from .sudoku_generator import sudoku_generator
def board_fill(request):
context = {'numbers': sudoku_generator.final_board()}
template = 'sudoku_board.html'
return render(request, template, context)
When you have the view (you must map it to the url that is used as the form target) it gets the request object. From there you can read the user input:
request.POST.get('44', 0) # Will return 0 if 44 is not found
More hint about writing a view: https://docs.djangoproject.com/en/2.1/topics/http/views/ and mapping the view to the url: https://docs.djangoproject.com/en/2.1/topics/http/urls/

Updating Jinja2 Variables every X seconds - Python Flask

I am trying to update variables inside of my index.html file. I am going to be running a thread with a loop in python but I want a way to update my jinja2 table listed below to update every x seconds just like if you were using php and ajax.
Here is my Jinja2 Code:
<table border=1 id="allTable" class="display">
<tbody id="eliteTable">
<tr><td colspan=9 class=queueheader>Elite (Current SLA: {{ eliteSLA | safe}}%)</td></tr>
<tr><th>Skill</th><th>SLA</th><th>Calls Waiting</th><th>Hold Time</th><th>Staffed</th><th>Avail</th><th>ACW</th><th>Aux</th><th>ACD Calls</th></tr>
{% for row in eliteList %}
{% if row[2]|int > 30 %}
<tr class=longwait>
{% elif row[2]|int > 0 %}
<tr class=waiting>
{% else %}
<tr>
{% endif %}
{% for i in row %}
<td> {{ i | safe }} </td>
{% endfor %}
</tr>
{% endfor %}
</tbody>
</table>
You'll need some javascript in there.
Either ajax requests, or websockets, though ajax might be simpler.
Simply use javascript setInterval() with an ajax request.
I'd recommend using a library, maybe jquery as it is very simple.
$.get( "/auto_refresh", function( data ) {
alert( "Data Loaded: " + data );
});
Note that jinja2 is just for the templating, meaning that at some point the jinja templates get translated into html/css.
So you can play with ajax like you did when you were using PHP.
Jinja variables are generated at template render-time. There's no way to programmatically update them without using javascript of some sort.
From the docs (emphasis mine):
A [Jinja] template contains variables and/or expressions, which get replaced with values when a template is rendered; and tags, which control the logic of the template. The template syntax is heavily inspired by Django and Python.

How to index elements of a tuple in Django template using a variable?

I have week_infos tuple and pass it to template
{{ week_infos.4.0 }}
This works. However the following does not:
{% for j in 7|get_range %}
<td row={{j}} col={{i|add:6}}>
{{ week_infos.j }}
How can I access a specific item item in a tuple?
You seem to be using the range in order to number your rows, however, you can do the same thing using a for loop's counter if you loop over the week_infos tuple:
{% for week_info in week_infos %}
<td row="{{ forloop.counter0 }}" col="{{ i|add:6 }}">
{{ week_info }}
(Also, you should always wrap HTML attributes in quotes since they can contain spaces)

python, create dynamic html name values..

i need a small help.. i am looping over objects which are in db and rendering all objects to template, so far so good. but what i want is that every rendered html name field should have different name so that i can refer to all of them latter. my code is this:
{% for p in products %}
<input type="number" name="name1" value="{{p.arg1}}" size="12"/>
<input type="number" name="name2" value="{{p-arg2}}" size="12"/>
{% endfor %}
but if i have 4 objects in DB, then i will have 8 rendered input fields in template, but all of them will have the "name" value as name1 and name2, is it possible to create 8 different names dynamically so that i can refer to all of them in my view again...
thanks
Use the forloop.counter variable
{% for p in products %}
<input type="number" name="name-{{forloop.counter}}-arg1" value="{{p.arg1}}" size="12"/>
<input type="number" name="name-{{forloop.counter}}-arg2" value="{{p.arg2}}" size="12"/>
{% endfor %}
The forloop.counter is 1-indexed. There is also the forloop.counter0 for indices
starting with 0.
Are you sure though that django formsets isn't what you need?

increment a variable in django templates

All,
How Can we increment a value like the following in django templates,
{{ flag =0 }}
{% for op in options %}
{{op.choices}}<input type="radio" name="template" id="template" value="template{{flag++}}"/>
{% endfor %}
thanks..
I don't think it's intended you should alter data in your templates. For in your specific case, you could instead use the forloop.counter variable.
For example:
{% for op in options %}
{{op.choices}}<input type="radio" name="template" id="template{{forloop.counter}}" value="template{{forloop.counter}}"/>
{% endfor %}
Also note that I added that number to the id attributes of the <input /> tag. Otherwise you'll have multiple inputs with the same id.
EDIT: I didn't note that it was a radio input. You could of course have the same name for each <input type="radio" />.
You explicitly can't do that in a template. Variable assignment is not allowed.
However if all you want is a counter in your loop, you just need to use {{ forloop.counter }}.
You might also want to look into having Django forms produce these values

Categories

Resources