I'm trying to add data from two models into one table. They are linked via a Foreign Key. I have searched the forum but cannot find a method that works with my data.
At the moment, I can display a single models data in the table but not the other. I'm using MySQL as my database.
My models.py file:
class location(models.Model):
loc_room = models.CharField(max_length=20, blank=True, null=True)
loc_block = models.IntegerField(blank=True, null=True)
loc_shelf = models.CharField(max_length=4, blank=True, null=True)
class box(models.Model):
box_contents = models.CharField(max_length=300, blank=True, null=True)
project_assigned_to = models.ForeignKey('project', null=True)
location_id = models.ForeignKey('location', null=True)
My views.py file:
def all_assets(request):
box_data = box.objects.all()
return render(request, 'main_app/all_assets.html', { "box_data":box_data
})
My table:
<thead>
<tr>
<th>Assets</th>
<th>Project</th>
<th>Room</th>
<th>Block</th>
<th>Shelf</th>
</tr>
</thead>
<tbody>
{% for item in box_data %}
<tr>
<td>{{ item.box_contents }}</td>
<td>{{ item.project_assigned_to }}</td>
<td>**Here I need to add data from ROOM**</td>
<td>**Here I need to add data from BLOCK**</td>
<td>**Here I need to add data from SHELF**</td>
</tr>
{% endfor %}
</tbody>
</table>
I hope somebody can help me with this. I've been trying out all the solutions on the forum but non work with my data. The closest I got was Django query to join records of two tables But again, I couldn't get it to work :(
try {{ item.location_id.loc_room }}
Related
I have a class HardBook that inherits from Book:
class Book(models.Model):
title = models.CharField('Book Title', max_length=200)
image = models.ImageField('Book Cover', upload_to='covers')
description = models.CharField('Description', max_length= 350)
class HardBook(Book):
quantity = models.IntegerField('Quantity')
views.py
class BookCreateView(CreateView):
def get_context_data(self,**kwargs):
context = super(BookCreateView, self).get_context_data(**kwargs)
context['softbooks'] = SoftBook.objects.all()
context['hardbooks'] = SoftBook.objects.all()
return context
I want to display the field data in a table, I want to show title, image and quantity. Everthing is displayed except quantity.
{% for hardbook in hardbooks %}
<tr>
<td>
<div class="cover-image" style="background-image:url({{hardbook.image.url}});"></div>
</td>
<td>{{hardbook.title}}</td>
<td>{{hardbook.quantity}}</td>
</tr>
{% endfor %}
So I am trying to create a django view where retrieval is done on the basis of past number of months for the current logged in user, as selected by him/her in the radio choices. But I am facing an error stating that one of my model fields 'timestamp' is not defined. Also, I am a bit confused as to how to print the retrieved model in the html. Given below are my files:
html:
{% if model %}
<table>
<thead>
<tr>
<th style = "padding: 20px;">Vendor ID</th>
<th style = "padding: 20px;">Employee ID</th>
<th style = "padding: 20px;">Debit</th>
<th style = "padding: 20px;">Credit</th>
<th style = "padding: 20px;">Time of transaction</th>
</tr>
</thead>
<tbody>
{% for i in model %}
<tr>
<td style="text-align: center;">{{ i.vendor_id }}</td>
<td style="text-align: center;">{{ i.emp_id }}</td>
<td style="text-align: center;">{{ i.debit }}</td>
<td style="text-align: center;">{{ i.credit }}</td>
<td style="text-align: center;">{{ i.timestamp }}</td>
</tr>
{% endfor %}
</tbody>
</table>
{% else %}
<p>There are no active transactions!</p>
{% endif %}
Views.py
if 'form2' in request.POST:
d = {}
date_id = request.POST["groupOfDefaultRadios1"]
x = employee.objects.get(name = request.user)
if date_id == 1:
d = transaction.objects.filter(emp_id = x, timestamp = datetime.date.today-timestamp(days=30))
elif date_id == 2:
d = transaction.objects.filter(emp_id = x, timestamp = datetime.date.today-timestamp(days=60))
else:
d = transaction.objects.filter(emp_id = x, timestamp = datetime.date.today-timestamp(days=180))
print(d)
return render(request, 'profiles/userLogin.html', {'model':d})
models.py:
class vendor(models.Model):
id = models.CharField(max_length=20, primary_key=True)
name = models.CharField(max_length=30)
class employee(models.Model):
name = models.OneToOneField(User, on_delete=models.CASCADE)
id = models.CharField(max_length=20, primary_key=True)
balance = models.IntegerField(default=0)
class transaction(models.Model):
vendor_id = models.ForeignKey(vendor, on_delete=models.CASCADE)
emp_id = models.ForeignKey(employee, on_delete=models.CASCADE)
debit = models.IntegerField()
credit = models.IntegerField()
timestamp = models.DateField(("Date"), default=datetime.date.today)
Any help is appreciated.
If i understand you right, you want filter transaction if their timestamp date less than 30, 60, 180 days from today
Then your filter should look like this
d = transaction.objects.filter(emp_id = x, timestamp__gte = datetime.date.today() - datetime.timedelta(days=30))
e.t.c
p.s.: Avoid naming models field with names that used in libs that you use, like timestamp
First things first, when Django raised an undefined error, are you sure that you applied migrations to this application?
python manage.py makemigrations APP_NAME
python manage.py sqlmigrate APP_NAME 0001
python manage.py migrate
Next, in your models file:
timestamp = models.DateField(("Date"), default=datetime.date.today)
When I looked up Django's model field reference, I found this:
class DateField(auto_now=False, auto_now_add=False, **options)
After reviewing your needs, will it help when you switch auto_now_add to True? I'm doubtful that default= will work in every circumstance. https://docs.djangoproject.com/en/3.0/ref/models/fields/#datefield
As a side note, when you create an object in the admin dashboard, sometimes Django will mischeck field requirements (like creating superusers), so please do watch out those objects in the management site.
I am new to django and working on a project where admin have to assign a team to manager and when ever admin assign a team to manager then it will be shown to that specific manager only.I have no idea how can i do this. Please if someone can help please help me.
here is my .html file for admin from where admin can assign team to manager.
<thead>
<tr>
<th>S No.</th>
<th>COMPANY NAME</th>
<th>TEAM MEMBER</th>
<th>EMAIL</th>
<th>ASSIGN TEAM</th>
</tr>
</thead>
<tbody>
{%for team in object%}
<tr>
<form id="form_id" method="POST" action = "{% url 'accept' %}">
{% csrf_token %}
<th scope="row"> {{ forloop.counter }}</th>
<td>{{team.company_name}}</td>
<td>{{team.team_member}}</td>
<td>{{team.email}}</td>
<td>
<select name="manager_{{manager.id}}">
{% for manager in managers %}
<option value ="{{manager.id}}">{{manager.name}}</option>
{% endfor %}
</select>
</td>
<td>
<input class="btn btn-raised btn-primary btn-round waves-effect" type="submit" value="Assign">
</td>
</tr>
{% endfor %}
here is my model for the team and manager:
class Create_Team(models.Model):
first_name = models.CharField(max_length= 50)
last_name = models.CharField(max_length= 50)
company_name = models.CharField(max_length= 100)
address = models.CharField(max_length= 1000)
state = models.CharField(max_length= 100)
city = models.CharField(max_length= 100)
status = models.CharField(max_length= 30)
class manager(models.Model):
name = models.CharField(max_length= 500)
designation = models.CharField(max_length= 500)
here is my views.py file for manager and from where the admin is accepting the request:
def accept(request):
obj= Create_Team.objects.filter(status='Accept')
managers = manager.objects.all()
if request.method == 'POST':
acc = manager()
manager_id = int(request.POST.get('manager', 1))
acc.manager = manager.objects.get(pk=manager_id)
return render(request, "admin/accept.html", {"object": obj, "managers": managers})
def superior(request):
return render(request, 'manager/index-3.html')
I want that whenever the admin will click on the assign button then that team will be displayed to that manager.Please help me.
There are several issues with your code.
There is no relation from the Create_Team to the manager model.
The name attribute on your <select> tags do not match the key you using to read from request.POST. manager_{{manager.id}} renders as manager_, so int(request.POST.get('manager', 1)) will always return 1.
The forms in your template do not contain the information which team you want to update.
You do not set the attribute selected on any <option>. As a consequence, the first choice will always be selected.
You are not updating any team in your view.
Let's address these issues.
1 - We fix the models by adding a ForeignKey from CreateTeam to Manager. Note that I've renamed the models, which is optional. If you decide to keep your names, adapt it accordingly.
# models.py
from django.db import models
class CreateTeam(models.Model):
first_name = models.CharField(max_length= 50)
last_name = models.CharField(max_length= 50)
company_name = models.CharField(max_length= 100)
address = models.CharField(max_length= 1000)
state = models.CharField(max_length= 100)
city = models.CharField(max_length= 100)
status = models.CharField(max_length= 30)
manager = models.ForeignKey('Manager', on_delete=models.SET_NULL, null=True, blank=True)
class Manager(models.Model):
name = models.CharField(max_length= 500)
designation = models.CharField(max_length= 500)
You have to pass two bits of information to the assign view: the id of the CreateTeam you want to assign and the id of the Manager you want to assign it to.
Note that the name attribute of form fields is the key in request.POST. These can be any string, just make sure it matches between form and view. It obviously makes life to give them an expressive name.
2 - Sending the id of the Manager is handled by the <select>. Just make sure the name attribute matching the key you use in your view.
3 - To send the id of the team, you could use a <button type="submit"> with a name and a value instead of the <input type="submit">.
<button class="btn btn-raised btn-primary btn-round waves-effect" type="submit" name="team" value="{{ team.id }}">Assign</button>
</td>
Alternatively, you could use a hidden field.
4 - Finally, you have to have to set the attribute selected on the correct <option> in your <select>. You can do that like this:
<option value="{{manager.id}}" {% if team.manager.id == manager.id %}selected{% endif %}
Here is the complete template:
<html>
<head></head>
<body>
<table>
<thead>
<tr>
<th>S No.</th>
<th>COMPANY NAME</th>
<th>TEAM MEMBER</th>
<th>EMAIL</th>
<th>ASSIGN TEAM</th>
</tr>
</thead>
<tbody>
{%for team in teams%}
<tr>
<form id="form_id" method="POST" action="{% url 'accept' %}">
{% csrf_token %}
<th scope="row"> {{ forloop.counter }}</th>
<td>{{team.company_name}}</td>
<td>{{team.team_member}}</td>
<td>{{team.email}}</td>
<td>
<select name="manager">
{% for manager in managers %}
<option value="{{manager.id}}" {% if team.manager.id == manager.id %}selected{% endif %}>{{manager.name}}</option>
{% endfor %}
</select>
</td>
<td>
<button class="btn btn-raised btn-primary btn-round waves-effect" type="submit" name="team" value="{{ team.id }}">Assign</button>
</td>
</form>
</tr>
{% endfor %}
</tbody>
</table>
</body>
</html>
5 - When receiving a POST request, you can assign the manager to the team.
That means you have to use the id values to get a CreateTeam instance and a Manager instance. Then you assign the Manager to createteam.manager and save the createteam object.
from django.shortcuts import get_object_or_404, redirect, render
from .models import CreateTeam, Manager
def accept(request):
teams = CreateTeam.objects.filter(status='Accept')
managers = Manager.objects.all()
if request.method == 'POST':
createteam_id = int(request.POST.get('team', 1))
manager_id = int(request.POST.get('manager', 1))
createteam = get_object_or_404(teams, pk=createteam_id)
createteam.manager = get_object_or_404(Manager, pk=manager_id)
createteam.save()
redirect('accept')
return render(request, "admin/accept.html", {"teams": teams, "managers": managers})
There are three things worth highlighting:
We use get_object_or_404 instead of Model.objects.get. As the name implies, it returns a 404 if no model can be found. This serves as a simple error handling for edge cases like a user manipulating the form or a manager being deleted while the user has the page open. This error handling could be improved to be more user-friendly, but it's a start.
get_object_or_404 can take a model or a queryset. We load the team instance from the filtered queryset teams. Otherwise, a user could manipulate a form and assign a manager to a team that has a status other than Accept.
After saving the team, we redirect to the accept page. This is good practice and ensures that a user can reload the page without seeing the do you want to resubmit this form dialog.
Finally, make sure that this view is really only accessible by the admin, e.g. by adding an appropriate user_passes_test decorator.
I am a newbie.
I create restaurant system by using Django. I want to display data (table number, item, and quantity of the food) which has been inserted to database. I want to show the data based on the random id which has been generated while the customer doing the food ordering. Hence, I do not know how to do it.
Anyone can help me please
I have tried these codes, but it only shows the back button. I cannot retrieve the data based on the random id from database
here is my models.py
class OrderItem(models.Model):
Table_No = models.IntegerField(blank=False)
Item = models.TextField()
Qty = models.IntegerField(blank=False)
Price = models.TextField()
Status = models.TextField(max_length=100, null=True)
OrderId = models.TextField(max_length=100, null=True)
my html file:
<form action="" method="post">
{% csrf_token %}
<!--<input type="Submit" name="submit" value="See Order"/>-->
{% for order in so1 %}
<table width="800">
<tr>
<th width="800">Table Number</th>
<th width="800">Item</th>
<th width="800">Quantity</th>
<th width="800">Status</th>
<th width="800">Order Id</th>
</tr>
<tr>
<td width="800">{{ order.Table_No }}</td>
<td width="800">{{ order.Item }}</td>
<td width="800">{{ order.Qty }}</td>
<td width="800">{{ order.Status }}</td>
<td width="800">{{ order.OrderId }}</td>
</tr>
{% endfor %}
<input action="action" onclick="window.history.go(-1); return false;" type="button" value="Back" />
my view:
def see_order(request):
if request.method == "POST":
Table_No = request.POST.get("Table_No")
Item = request.POST.get("Item")
Qty = request.POST.get("Qty")
Status = request.POST.get("Status")
OrderId = request.POST.get("OrderId")
track_order = request.POST.get('textfield', None)
if(OrderItem.objects.get(OrderId)):
if(OrderId==OrderId):
try:
summary = OrderItem.objects.get(OrderId=track_order)
so1 = OrderItem.objects.filter(Table_No=Table_No)
so = OrderItem.objects.filter(Item=Item)
so = OrderItem.objects.filter(Qty=Qty)
so = OrderItem.objects.filter(Status=Status)
so = OrderItem.objects.filter(OrderId=OrderId)
html = ("<H1>%s</H1>", summary)
return render(request, 'restaurants/see_order.html', {'so1': so1 , 'so': so})
except OrderItem.DoesNotExist:
return HttpResponse("no such user")
else:
return render(request, 'restaurants/customer_page.html')
I expect the result will show the table number, item, and quantity when i input the random id. But it doesn't show anything except the back button.
Your logic makes no sense.
You make lots of queries, but ignore their result - you either do nothing with the variable at all, or overwrite the existing variable with the result of the next query.
For example, you get summary, wrap it in "h1" tags for some reason (why aren't you doing that in the template) to get a variable called html, and then completely ignore that variable.
For the rest, you get something called so by filtering on Item, then overwrite that with a completely different filter based on Qty, then Status, etc.
Not to mention, if(OrderId==OrderId) is completely pointless.
You should remove all the useless logic. Since you want to filter by OrderId, you should just do that, and return the data to the database.
if request.method == "POST":
OrderId = request.POST.get("OrderId")
so = OrderItem.objects.filter(OrderId=OrderId)
return render(request, 'restaurants/see_order.html', {'so': so})
I'm new to Flask and programming. I'm creating a simple database using Flask/SQLite. I'm having users enter the data in a form and having that data populate on an HTML table next to the form. I've managed to achieve this. However, I've like to add the ability of a user to delete a row in the table.
I've created a function in my routes.py that I've like to utilize, but I can't find a way to pass user submitted information back to my routes.py function. I've tried using an HTML link but I don't want to pass the user to another URL and back. Is there a way to achieve this?
From routes.py
#app.route("/")
#app.route('/interventions', methods=['GET', 'POST'])
#login_required
def interventions():
.....
qinter = Interventions.query.all()
def delete_entry(entry):
db.session.delete(qinter[(entry-1)])
db.session.commit()
return redirect(url_for('interventions'))
.....
From Interventions.html
.........
<table border="1">
<tr>
<th>Delete?</th>
<th>Date</th>
<th>Chart #</th>
<th>Provider</th>
<th>Pharmacist</th>
<th>COI</th>
<th>Accepted?</th>
<th>Intervention</th>
</tr
{% for q in qinter %}
<tr>
<td><delete</td>
<td>{{ q.date }}</td>
<td>{{ q.chart }}</td>
<td>{{ q.prescriber }}</td>
<td>{{ q.pharmacist }}</td>
<td>{{ q.category }}</td>
<td>{{ q.accepted }}</td>
<td>{{ q.intervention }}</td>
</tr>
{% endfor %}
</table>
What you need is some way to communicate from your HTML template to your interventions route that you want to delete a certain row in your database table. To do that you need to add some additional parameters to your route function, like this:
#app.route('/interventions', methods=['GET', 'POST'])
#app.route('/interventions/<action>/<item_id>', methods=['GET', 'POST'])
#login_required
def interventions(action=None, item_id=None):
def delete_entry(entry):
db.session.delete(entry)
db.session.commit()
if request.method == "POST":
if action == 'delete':
# Get specific row user wants to delete
qinter_row_to_delete = Interventions.query.get(item_id)
# Delete row
delete_entry(qinter_row_to_delete)
return redirect(url_for('interventions'))
elif request.method == "GET":
qinter = Interventions.query.all()
# Render template etc...
Then from Jinja template make a call to that endpoint to delete the row:
<form id="form" action="{{url_for('interventions', action='delete', item_id=q.id)}}" method="POST">