Django template for loop is empty in another block - python

I have a function in my view.py:
#login_required(login_url='login')
def gpd(request,pk):
# get gpd by id
current_gpd = get_gpd(pk)
# get current campaign year #TODO check types
current_campaign = get_campaign(current_gpd.gpd_year)
# get all corporate goals for current campaign
corp_goals = CorporateGoal.objects.filter(gpd_year=current_campaign.year)
compl_weight = []
for goal in corp_goals:
compl_weight.append(goal.corp_factor_weight*current_gpd.bonus.corporate_component//100)
corporate_goals = zip(corp_goals, compl_weight)
if is_manager(request)!=None:
team = get_team(request)
context = {'gpd':current_gpd,
'corporate_goals':corporate_goals,
}
return render(request, 'app/gpd_forms/form_gpd.html', context)
else:
context = {'gpd':current_gpd,
'corporate_goals':corporate_goals,
}
return render(request, 'app/gpd_forms/form_gpd.html', context)
As you can see, in context I have corporate_goal.
My form_gpd.html:
{% extends 'app/navbar/main.html' %}
{% load static %}
{% block content %}
{% include 'app/slidebar/gpd_form_slidebar.html' %}
<div class="container" style="background-color:white">
<div class="row">
<div id="section2" class="container-fluid">
{% include 'app/gpd_blocks/corporate_goal.html' %}
</div>
</div>
<hr />
</div>
<div class="container" style="background-color:white">
<div class="row">
<div id="section5" class="container-fluid">
{% include 'app/gpd_blocks/summary.html' %}
</div>
</div>
<hr />
</div>
</div>
{% endblock %}
for example in corporate block I am executing next:
{% load static %}
{% block content %}
<div class="row" id="super">
<p>&nbsp</p>
</div>
<div class="row" id="super">
<div class="col-11" style="color: ivory; font-weight: bold; font-size: 1.3em;">
CORPORATE GOALS BLOCK
</div>
</div>
<div class="row" id="super">
<p>&nbsp</p>
</div>
{% for goal, compl_weight in corporate_goals %}
<hr style="height:2px;border:none;color:rgb(87, 124, 161);background-color:rgb(87, 124, 161);" />
<!-- Corporate goal section-->
<div class="row">
<div class="col">
Corp. Goal: {{ goal.corp_goal_title }}
</div>
</div>
<div class="row">
<div class="col-8">
<div>
{% if goal.corp_factor_rate %}
<p style="color:mediumspringgreen">rated</p>
{% else %}
<p style="color:indianred">unrated</p>
{% endif %}
</div>
</div>
<div class="col-3">
<div style="margin-inline-start:auto">
{{compl_weight}} % of total score
</div>
</div>
</div>
<!-- Tabs for details-->
<ul class="nav nav-tabs">
<li class="nav-item">
<a class="nav-link active" data-toggle="tab" href="#det1{{ goal.id }}">Goal Details</a></li>
<li class="nav-item">
<a class="nav-link" data-toggle="tab" href="#det2{{ goal.id }}">Other Details</a></li>
</ul>
<!-- Tabs content for details-->
<div class="tab-content" >
<!--First tab-->
<div id="det1{{ goal.id }}" class="tab-pane fade show active">
<div class="row">
<!--Column 1-->
<div class="col">
<table class="table-bordless" style="margin-top:20px;">
<tbody>
<tr>
<th>Start Date</th>
<td width="50"></td>
<td>{{ goal.start_date }}</td>
</tr>
<tr>
<th>Weight</th>
<td width="20"></td>
<td>{{ goal.corp_factor_weight }} %</td>
</tr>
<tr>
<th><p>&nbsp</p></th>
</tr>
<tr>
<th style="color:dimgray">Goal description</th>
<td width="18"></td>
<td></td>
</tr>
</tbody>
</table>
<div class="row">
<textarea class="form-control" readonly title="Description" style="background-color:aliceblue !important;">{{goal.corp_goal_description}}</textarea>
</div>
</div>
<!--Column 2-->
<div class="col">
<table class="table-bordless" style="margin-top:20px;">
<tbody>
<tr>
<th>Due Date</th>
<td width="50"></td>
<td>{{ goal.end_date }}</td>
</tr>
<tr>
<th>Factor Rate</th>
<td width="50"></td>
<td>
{% if goal.corp_factor_rate %}
{{ goal.corp_factor_rate }}
{% else %}
<div style="color:mediumspringgreen; font-weight: bold;">ongoing...</div>
{% endif %}
</td>
</tr>
<tr>
<th><p>&nbsp</p></th>
</tr>
<tr>
<th style="color:dimgray">Goal comment</th>
<td width="18"></td>
<td></td>
</tr>
</tbody>
</table>
<div class="row">
<textarea class="form-control" readonly title="Comment" style="background-color:aliceblue !important;">{{goal.corp_goal_comment}}</textarea>
</div>
</div>
</div>
</div>
<!--Second tab-->
<div id="det2{{ goal.id }}" class="tab-pane fade" style="margin-top:20px;">
<p>Factor for Goal Achievement:</p>
<table class="table">
<tbody>
<tr>
<th>Factor</th>
<td>0</td>
<th>Description</th>
<td>{{ goal.corp_factor_0 }}</td>
</tr>
<tr>
<th>Factor</th>
<td>1</td>
<th>Description</th>
<td>{{ goal.corp_factor_1 }}</td>
</tr>
<tr>
<th>Factor</th>
<td>2</td>
<th>Description</th>
<td>{{ goal.corp_factor_2 }}</td>
</tr>
<tr>
<th>Factor</th>
<td>3</td>
<th>Description</th>
<td>{{ goal.corp_factor_3 }}</td>
</tr>
</tbody>
</table>
</div>
</div>
<br />
<br />
<br />
{% endfor %}
{% endblock %}
And it works perfectly. But when in last block summary I want to use corporate_goals one more time - I have nothing on my page, looks like corporate_goals is not exist.
my summary.html
{% load static %}
{% block content %}
<div class="row">
<p>123</p>
</div>
<div class="row">
{% for goal, compl_weight in corporate_goals %}
{{ goal.corp_goal_title }}
{% endfor %}
</div>
<div class="row">
<p>123</p>
</div>
{% endblock %}
Even If I copy all my code from corporate_goal.html into summary - I will have nothing. Why ?

I think that the problem is that your html structure has no sense. You have three {% block content %}. Please, delete the content blocks of your include files (corporate_goal.html and summary.html) and check if this is the problem. I think that one of your content block is overriding the other one.
Just to clarify, when you use the "include tag" is like you were pasting the code from other file. So imagine the result. You have a block content that contains two other block contents inside it.

My problem was in zip objects. When we are iterating through a zip object it is exhausted and you cannot iterate through it again. So, solution is corporate_goals = list(zip(corp_goals, compl_weight)). Anyway, thank you, #LaCharcaSoftware, for the advice, I've changed my structure to avoid duplication with block content.

Related

Displaying details of api results using id

I am working with the omdb api (https://www.omdbapi.com/) and I was able to get the search results to display, but now I am trying to get the movie details when I click on each search result.
Right now I am getting a response of 'Not Found' which I think has something to do with retrieving the movie id, but I haven't been able to figure it out. I appreciate any tips/advice you may have.
app.py:
#app.route('/movies/search_results', methods=['GET'])
def show_search_results():
"""Logic for sending an API request and displaying the JSON response as an HTML. Expects a GET request."""
movies = []
s = request.args.get("s")
results = requests.get(f"{API_BASE_URL}search/movies/",params={"s": s}).json()
results = results['Search']
for movie in results:
movies.append(movie)
return render_template('movies/search_results.html', movies=movies, s=s, id=movie['imdbID'])
#app.route('/movies/<int:id>', methods=['GET'])
def show_movie_details(id):
"""For displaying information about the individual movie. Not a list. GET request only."""
movie = requests.get(f'{API_BASE_URL}movie/{id}')
print(movie)
return render_template('movies/detail.html', movie=movie, id=id)
search_results.html:
{% extends 'base.html' %}
{% block title %} {% endblock %}
{% block nav1 %} active {% endblock %}
{% block content %}
<div class="container-fluid" id="movie-list">
<div class="row row-cols-2 justify-content-center mt-2" style="--bs-gutter-x:0; ">
<p> Search Results for "{{s}}"</p>
<table class="movie-table">
<thead>
<tr>
<th>IMDB ID</th>
<th>Movie Title</th>
<th>Year Released</th>
</tr>
</thead>
<tbody>
{% for movie in movies %}
<tr>
<td>
<a href="/movies/{{id}}" id="id">
{{ id }}
</a>
</td>
<td>
{{ movie['Title'] }}
</td>
<td>
{{ movie['Year'] }}
</td>
</tr>
{% endfor %}
</tbody>
</table>
</div>
</div>
{% endblock %}
{% block footer %} {% endblock %}
movies/details.html:
{% extends 'movies/search_results.html' %}
{% block content %}
<div class="card text-center" style="width: 18rem;">
<div class="card-body">
<!-- <div class="d-flex justify-content-between align-items-center mb-3 "> -->
<h5 class="card-title text-center"> Title: {{ movie['Title'] }} </h5>
<form method="POST" action="/movie/add_like/{{ movie['imdbID'] }}" id="messages-form">
<button class="btn btn-sm float-left">
<i class="fa fa-thumbs-up"></i>
</button>
</form>
<p class="card-text">With supporting text below as a natural lead-in to additional content.</p>
</div>
</div>
{% endblock %}
I tried not using int:id in the route and just redirecting to movies/detail.html, but I was still not receiving any results and just viewing the template without any API information on it.

JInja2 Template Syntax Error Encountered Unknown tag 'endif'

I am building a basic api based website as I was going to display some info om page and was checking for a condition i encountered --
jinja2.exceptions.TemplateSyntaxError: Encountered unknown tag 'endif'. Jinja was looking for the following tags: 'endblock'. The innermost block that needs to be closed is 'block'.
Below is the palatte I copied form Bootstrap and was modifying and then the error happened -- And Yeah This is my first time posting question here as you can tell!
{% include "header.html" %}
{% block contnet %}
<div class="container-fluid">
<div class="row row-dark">
<div class="col px-2 py-5">
<h6 class="px-2 py-3">Click to Know Upcoming Events</h6>
<a href="{{ url_for('upcoming_events') }}"
><button type="button" class="btn btn-dark mx-2 my-3">Events</button></a
>
</div>
</div>
<div class="row">
<div class="col col-lg-4 col-md-6">
<table class="table table-borderless py-5 table-light">
<thead>
<tr class="table-light">
<th scope="col">Batting</th>
<th scope="col">Bowling</th>
<th scope="col">Wickets</th>
<th scope="col">Over</th>
</tr>
</thead>
<tbody>
{% if error %} # <========
<p>{{ error }}</p>
{% endif %} <======= Here is the error traceback
<tr>
<th scope="row"></th>
<td>Mark</td>
<td>Otto</td>
<td>#mdo</td>
</tr>
<tr>
<th scope="row">2</th>
<td>Jacob</td>
<td>Thornton</td>
<td>#fat</td>
</tr>
<tr>
<th scope="row">3</th>
<td colspan="2">Larry the Bird</td>
<td>#twitter</td>
</tr>
{% endif %}
</tbody>
</table>
</div>
</div>
</div>
{% endblock %}
You close the "if" twice ({% endif %}) but only open one...
Try this:
Click to Know Upcoming Events Events Batting Bowling Wickets Over
{% if error: %}
{{ error }}
{% endif %}
Mark Otto #mdo 2 Jacob Thornton #fat 3 Larry the Bird #twitter
{% endblock %}
You can move the {% endif %} where you want

Showing JSON data from DB to django template using Bootstrap tabs

Sorry I'm a programming newb....
But I am trying to use Bootstrap's tabs navigation to view JSON data from a DB. I'm transforming the JSON data to a 2d array and storing my data as the following dictionary:
tables = {u'table1': [[u'CS6140', u'Machine Learning', u'Sara
Arunagiri'], [u'CS5100', u'Foundations of
Artificial Intelligence ', u'Chris Amato'],
[u'CS6220', u'Data Mining', u'Pablo Esteves']],
u'table2': [[u'Paris, France', u'06/01/2019 - 06/15/2019',
u'James Fraser'], [u'Edinborough, Scotland',
u'10/14/2019 - 10/20/2019', u'Claire Beauchamp'],
[u'Rome, Italy', u'12/14/2019-12/24/2019',
u'Timothy Dalton']],
u'table3': [[32423, u'iced coffee', 3.67], [34241, u'bagel',
2.99], [3109247, u'sanwich', 5.99]]}
Thus each table dict entry corresponds to one table.So I'm trying to loop through the dictionary and 2d array to create different tables.
I'm currently trying to loop through the dictionary as follows but I am getting the 2d arrays replicated 3 times for each of the tables when instead I want each table in my dictionary to only be shown once for each tab.
{% for table in tables %}
<div class="tab-content">
<div id="{{ table }}" class="tab-pane active">
{% for table in tables.values %}
<table class="table">
<tbody>
{% for row in table %}
<tr>
{% for item in row %}
<td>{{ item }}</td>
{% endfor %}
</tr>
{% endfor %}
</tbody>
</table>
{% endfor %}
</div>
</div>
{% endfor %}
I'm hoping for some insight on to how else store or pass the data to my context to get what I want i.e.
<div class="tab-content">
<div id="table1" class="tab-pane active">
<table class="table">...</table>
</div>
<div id="table2" class="tab-pane active">
<table class="table">...</table>
</div>
<div id="table3" class="tab-pane active">
<table class="table">...</table>
</div>
</div>
...
vs. what I'm currently getting:
<div class="tab-content">
<div id="table1" class="tab-pane active">
<table class="table">...</table>
<table class="table">...</table>
<table class="table">...</table>
</div>
<div id="table2" class="tab-pane active">
<table class="table">...</table>
<table class="table">...</table>
<table class="table">...</table>
</div>
<div id="table3" class="tab-pane active">
<table class="table">...</table>
<table class="table">...</table>
<table class="table">...</table>
</div>
</div>
...
This should work:
<div class="tab-content">
{% for table_name, table in tables.items %}
<div id="{{ table_name }}" class="tab-pane {% if forloop.first %} active {% endif %}">
<table class="table">
<tbody>
{% for row in table %}
<tr>
{% for item in row %}
<td>{{ item }}</td>
{% endfor %}
</tr>
{% endfor %}
</tbody>
</table>
</div>
{% endfor %}
</div>
It's better to use your keys and values of your dictionary using .items at the beginning of your loop, rather than getting your values further down your loop logic. It avoids confusion in your loop logic.
EDIT:
The active class should only be for the first tab. Thus, you need to use the forloop.first template tag to add the class thr first time you run through the loop.

How to create collapsible cards in bootstrap in django template?

I have a table of these collapsible cards with dynamic content in them. The code I have taken from bootstrap looks like this:
<p>
<a class="btn btn-primary" data-toggle="collapse" href="#multiCollapseExample1" role="button" aria-expanded="false" aria-controls="multiCollapseExample1">Toggle first element</a>
<button class="btn btn-primary" type="button" data-toggle="collapse" data-target="#multiCollapseExample2" aria-expanded="false" aria-controls="multiCollapseExample2">Toggle second element</button>
<button class="btn btn-primary" type="button" data-toggle="collapse" data-target=".multi-collapse" aria-expanded="false" aria-controls="multiCollapseExample1 multiCollapseExample2">Toggle both elements</button>
</p>
<div class="row">
<div class="col">
<div class="collapse multi-collapse" id="multiCollapseExample1">
<div class="card card-body">
Anim pariatur cliche reprehenderit, enim eiusmod high life accusamus terry richardson ad squid. Nihil anim keffiyeh helvetica, craft beer labore wes anderson cred nesciunt sapiente ea proident.
</div>
</div>
</div>
<div class="col">
<div class="collapse multi-collapse" id="multiCollapseExample2">
<div class="card card-body">
Anim pariatur cliche reprehenderit, enim eiusmod high life accusamus terry richardson ad squid. Nihil anim keffiyeh helvetica, craft beer labore wes anderson cred nesciunt sapiente ea proident.
</div>
</div>
</div>
</div>
Problem
But as you can see, each collapse is controlled by this attribute multiCollapseExample1. In my django template, when I use this, on clicking any of the close button, only the first card collases because it has a static value of 1. How can I give it a dynamic value so every card opens and closes correctly? Reason I am asking is because my code is pretty complicated and is return about 10+ parameters from the views.py function, and I am iterating a dictionary of dictionaries to print all the values in the format I want. For that reason, I have about 4-5 nested for loops, and also an if statement which checks if the if looper counter is same as the parent's loop counter. I am not able to undertand how I can simple solve this problem.
This is my actual full code:
<table class="table mb-0 table-striped loadingplan">
<thead>
<tr>
<th>ID</th>
<th>Vehicles</th>
<th>Gross Weight</th>
<th>Route</th>
<th>Route Distance</th>
<th>Route TAT</th>
<th>ETD</th>
<th>ETA</th>
<th></th>
<th>Action</th>
</tr>
</thead>
<tbody>
{% for d,t,r,y,w,f in open_route_info %}
{% for k,v in open_trucks.items %}
{% if forloop.counter == forloop.parentloop.counter %}
<td class="align-middle">YNT1151<br>
<small class="align-right">{{ f }}% Filled</small>
</td>
<td>
{% for x in v %}
{% for y,z in x.items %}
{{ y.display_name }}
{% endfor %}
{% endfor %}
</td>
{% for truck,value in v.items %}
<td class="align-middle">{{ truck }} {{ value }}<br>o
<a href="#">
<small>Download Loading Plan {{ value.pk }}</small>
</a>
</td>
{% endfor %}
<td class="align-middle">{{ w }}KG</td>
<td class="align-middle">{{ k }}</td>
<td class="align-middle">{{ d }} KM</td>
<td class="align-middle">{{ t }}</td>
<td class="align-middle">{{ y }}</td>
<td class="align-middle">{{ scheduled_date }}</td>
<td class="align-middle">
<button class="btn" type="button" data-toggle="collapse"
data-target="#multiCollapseExample2" aria-expanded="false"
aria-controls="multiCollapseExample2"><img
src="{% static 'img/cardopen.svg' %}" alt="card open"></button>
</td>
<td class="align-middle">Raise RFQ
</td>
<tr class="collapse multi-collapse" id="multiCollapseExample2">
<td colspan="5">
<table class="table table-bordered">
<thead>
<tr>
<th>SKU ID</th>
<th>SKU Name</th>
<th>Quantity</th>
</tr>
</thead>
<tbody>
{% for x in v %}
{% for y,z in x.items %}
{% for w in z %}
<tr>
<td>{{ w.name }}</td>
<td>{{ w.pid }}</td>
<td>{{ w.quantity }}</td>
</tr>
{% endfor %}
{% endfor %}
{% endfor %}
</tbody>
</table>
</td>
<td colspan="5" class="align-middle">
<div class="card card-body iframecard">
<iframe src="{{ r }}"></iframe>
</div>
</td>
</tr>
{% endif %}
{% endfor %}
{% endfor %}
</tbody>
</table>
What I want
All I want to do is, replace multiCollapseExample2 with a dynamic variable which is the same length as the number of items. I tried using a simple loop on a list which has the length as the number of items, but it did not work probably because of the if statement {% if forloop.counter == forloop.parentloop.counter %}.
Looks like you can use the 2 for-loops and their variables to create an unique id for your cards.
Something like
data-target="#multiCollapse{{d}}{{t}}{{k}}{{v}}"
Where d,t is from outer for-loop and k,v is from the inner loop.

Second loop is not executing in django template

HI I have very strange problem .
Here is my template
<table class="table table-striped table-condensed tablesorter" id="myTable">
<thead>
<tr>
<th>Store</th>
<th>Image</th>
<th>Price(USD)</th>
<th>Manufacturer</th>
<th>Model</th>
<th>Shipping</th>
<th>Replacement</th>
<th>Details</th>
</tr>
</thead>
<tbody>
{% for x in result_amazon|slice:"1" %}
{% if forloop.first %} <tr>
<td>
<a href="" target="_blank">
<img height="85" width="110" src={% static "images/Amazon-Logo.jpg" %} alt="">
</a>
</td>
<td><img src={{x.medium_image_url}} alt=""></td>
<td><strong><span class="WebRupee"></span>
{% for y in x.list_price %}
{% if y.price != 'None'%}
{{y}}
{% endif %}
{% endfor %}</strong>
</td>
<td>{{x.manufacturer}}</td>
<td>{{x.model}}</td>
<td>Rs. 99</td>
<td>Out of Stock</td>
<td>
<a href="{{x.detail_page_url}}" class="btn btn-mini btn-primary trackinfo" rel="7###17205" title="Visit Store" target="_blank">
Visit Store
</a>
</td>
</tr>
{% endif %}
{% endfor %}
{% for x in result_bestbuy.products %}
{% if forloop.first %}
<tr>
<td>
<a href="">
<img height="85" width="110" src={% static "images/bestbuy.gif" %} alt="">
</a>
</td>
<td><img style="height: 168px;" src={{x.image}} alt=""></td>
<td><strong><span class="WebRupee"></span>{{x.regularPrice}}</strong></td>
<td>{{x.manufacturer}}</td>
<td>{{x.modelNumber}}</td>
<td>{% if x.freeShipping %}Free Shipping {% else %}{{x.shippingCost }}{% endif %}</td>
<td>14 Days</td>
<td>
<a href="{{x.url}}" class="btn btn-mini btn-primary trackinfo" rel="27###17205" title="Visit Store" target="_blank">
Visit Store
</a>
</td>
</tr>
{% endif %}
{% endfor %}
{% for x in result_amazon %}
{% if not forloop.first %}
<tr>
<td>
<img height="85" width="110" src={% static "images/Amazon-Logo.jpg" %} alt="">
</a>
</td>
<td><img src={{x.medium_image_url}} alt=""></td>
<td><strong><span class="WebRupee"></span>
{% for y in x.list_price %}
{% if y.price != 'None'%}
{{y}}
{% endif %}
{% endfor %}
</strong>
</td>
<td>{{x.manufacturer}}</td>
<td>{{x.model}}</td>
<td>Rs. 99</td>
<td>Out of Stock</td>
<td>
<a href="{{x.detail_page_url}}" class="btn btn-mini btn-primary trackinfo" rel="7###17205" title="Visit Store" target="_blank">
Visit Store
</a>
</td>
</tr>
{% endif %}
{% endfor %}
{% for x in result_bestbuy.products %}
{% if not forloop.first %}
<tr>
<td>
</td>
<td><img style="height: 168px;" src={{x.image}} alt=""></td>
<td><strong><span class="WebRupee"></span>{{x.regularPrice}}</strong></td>
<td>{{x.manufacturer}}</td>
<td>{{x.modelNumber}}</td>
<td>{% if x.freeShipping %}Free Shipping {% else %}{{x.shippingCost }}{% endif %}</td>
<td>14 Days</td>
<td>
<a href="{{x.url}}" class="btn btn-mini btn-primary trackinfo" rel="27###17205" title="Visit Store" target="_blank">
Visit Store
</a>
</td>
</tr>
{% endif %}
{% endfor %}
</tbody>
</table>
I am trying to limit the first loop to execute only once initially then rest all has to be executed hence I have applied the forloop.first condition .
My simple question is "Why the third loop(result_amazon) is not printing any data" (There are lot many data present in the result_amazon).
Please help me out what might I am doing wrong here .
Check the console of your browser and look for any errors in your html code.

Categories

Resources