Any help would be greatly appreciated
index.html
{% extends 'base.html' %}
{% block content %}
<div>
<h1>Welcome Home</h1>
<form action="{% url 'calc:home' %}" method="GET">
<!-- {% csrf_token %} -->
Enter 1st Number : <input type="text" name="num1"><br><br>
Enter 2nd Number : <input type="text" name="num2"><br>
<input type="submit" name="" value="Add"><br><br>
</form>
Result of the game is : {{result}}
</div>
{% endblock %}
views.py
from django.shortcuts import render
from django.http import HttpResponse
def home_view(request):
if request.GET.get('num1'):
val1 = int(request.GET.get("num1"))
val2 = int(request.GET.get("num2"))
res = val1 + val2
return render(request, 'calc/index.html',{'result':res})
urls.py
from django.urls import path
from . import views
app_name = 'calc'
urlpatterns = [
path('', views.home_view, name='home'),
]
i get this error when running the server: UnboundLocalError: local variable 'res' referenced before assignment
I hope this will help. Basically you are using a variable outside of it's scope. you defined res in "if" block but called outside "if" though it was not present in that scope.So you should first assign a default value.
def home_view(request):
res=0
if request.GET.get('num1'):
val1 = int(request.GET.get("num1"))
val2 = int(request.GET.get("num2"))
res = val1 + val2
return render(request, 'calc/index.html',{'result':res})
Related
I'm trying to clone the Instagram web page using Django(version-3.1).
My Django project has an app called 'post'.
One of its template I have a form which is posting a comment to a post. The form post request should call the path('add_comment/',views.add_comment,name='add_comment'), but It's calling path('<slug:slug>/',views.post_details,name='post_details'), instead. And raising DoesNotExist at /post/add_comment error. I added print() statement at the beginning of both add_comment() and post_details() methods to find out which is running when the request is made. I have no idea what I have done wrong.
The project GitHub link - https://github.com/mirasel/Instagram_Clone
the post_details.html template is -
{% extends 'base.html' %}
{% load static %}
{% block title %} post {% endblock %}
{% block profilephoto %} {{ propic.url }} {% endblock %}
{% block body %}
<div>
<div>
<img src="{{post.image.url}}" alt="post" height="250px" width="250px">
</div>
<div>
<a href="{% url 'instagram:profile' post.uploader %}">
<img src="{{uploader.profile_pic.url}}" alt="{{uploader}}" style="border-radius: 50%;" height="24px" width="24px">
{{ post.uploader }}
</a><br>
<p>{{ post.date_published.date }}</p>
</div>
<div>
<p>{{ post.caption }}</p>
</div>
<div>
<form action="{% url 'post:add_comment' %}" id="comment_form" method="POST">
{% csrf_token %}
<textarea name="comment" id="comment" cols="30" rows="1" placeholder="Write a comment..."></textarea>
<input type="hidden" name="slug" id="slug" value="{{post.slug}}">
<!-- <input type="submit" style="display: none;" name="submit"> -->
</form>
<script>
$(function(){
$("#comment").keypress(function (e) {
if(e.which == 13 && !e.shiftKey) {
$(this).closest("form").submit();
e.preventDefault();
}
});
});
</script>
{% endblock %}
the views.py -
from django.shortcuts import render,redirect
from instagram.views import get_nav_propic,get_profile_details
from .models import UserPost,PostComment,PostLike
from django.http import JsonResponse
def get_post_likes(post):
likes = PostLike.objects.filter(post=post)
total_likes = len(likes)
likers = []
for l in likes:
likers.append(get_profile_details(l.liker))
return {'likers':likers,'total_likes':total_likes}
def get_post_comments(post):
comments = PostComment.objects.filter(post=post)
total_comments = len(comments)
commenter = []
comment = []
for c in comments:
commenter.append(get_profile_details(c.commenter))
comment.append(c.comment)
postcomment = zip(commenter,comment)
return {'post_comment':postcomment,'total_comments':total_comments}
def upload_post(request):
if request.method == 'POST':
image = request.FILES['post_img']
caption = request.POST['caption']
uploader = request.user
UserPost.objects.create(uploader=uploader,image=image,caption=caption)
return redirect('instagram:feed')
else:
context = {
'propic' : get_nav_propic(request.user)
}
return render(request,'post/upload_post.html',context)
def post_details(request,slug):
print('I am here in post details')
post = UserPost.objects.get(slug=slug)
context = {
'propic' : get_nav_propic(request.user),
'post' : post,
'uploader' : get_profile_details(post.uploader),
'LIKES' : get_post_likes(post),
'COMMENTS' : get_post_comments(post),
}
return render(request,'post/post_details.html',context)
def add_comment(request):
print('I am here in add comment')
if request.method == 'POST':
post_slug = request.POST.get('slug')
post = UserPost.objects.get(slug=post_slug)
user = request.user
comment = request.POST.get('comment')
PostComment.objects.create(post=post,commenter=user,comment=comment)
return redirect('post:post_details',slug=post_slug)
the urls.py -
from django.urls import path
from . import views
app_name='post'
urlpatterns = [
path('upload_post/',views.upload_post,name='upload_post'),
path('<slug:slug>/',views.post_details,name='post_details'),
path('add_comment/',views.add_comment,name='add_comment'),
]
The error - Error page
Solved
I had to make the URL path of add_comment as following-
#previous one
path('add_comment/',views.add_comment,name='add_comment'),
#modified one
path('comment/add_comment/',views.add_comment,name='add_comment'),
This is because the pattern for the slug URL and add comment URL were similar.
Because Django will process the urlpatterns sequentially, from docs:
Django runs through each URL pattern, in order, and stops at the first
one that matches the requested URL, matching against path_info.
And '/add_comment' is a valid slug <slug:slug>, so post_details will be called.
So you should keep the definition of the most generic url patterns at last:
urlpatterns = [
path('upload_post/',views.upload_post,name='upload_post'),
path('add_comment/',views.add_comment,name='add_comment'),
path('<slug:slug>/',views.post_details,name='post_details'),
]
Hopefully this will work for you.
I'm new to Django.
Trying to build an app that adds two names. Pretty Basic.
Built a page that collects the names but not printing the final result.
Here is my code:
urls.py - inside the app
urlpatterns = [
path('',views.home, name='home'),
path('add',views.addname,name='add')
]
views.py
from django.shortcuts import render
from django.http import HttpResponse
def home(request):
return render(request,'input.html')
def addname(request):
val1 = (request.POST['fname'])
val2 = (request.POST['lname'])
res = 'Hi' + val1 +val2
return render(request, 'resultprint.html',{'resultprint':res})
templates/input.html
{% block content %}
<h1>Hello!</h1>
<form action='addname' method='post'>
{% csrf_token %}
Enter 1st name : <input type='text' name='fname'><br>
Enter 2nd name : <input type='text' name='lname'><br>
<input type='submit'>
</form>
{%endblock%}
templates/resultprint.html
{% block content %}
Result: {{resultprint}}
{%endblock%}
Below are the screenshots:
Couldn't really find where is the mistake happening.
I added the templates and app in the Settings file.
You have to set the same url in your urls.py :
urlpatterns = [
path('', views.home, name='home'),
path('addname', views.addname, name='addname')
]
But you can use directly the name of the url in your html file like that :
{% block content %}
<h1>Hello!</h1>
<form action='{% url 'addname' %}' method='post'>
{% csrf_token %}
Enter 1st name : <input type='text' name='fname'><br>
Enter 2nd name : <input type='text' name='lname'><br>
<input type='submit'>
</form>
{%endblock%}
New in django. Learning how to create a login page with user Authentication. All is working, but when I put wrong password for checking that the loop is working properly or not. Know that the error is due to wrong assignment of url, but can't understand how to solve it.
I am using two apps one for login(name=trevalo_app) and another for all (name=MYapp)
trevalo_app/views.py
from django.shortcuts import render,redirect
from django.http import *
from django.contrib.auth import authenticate,login,logout
from django.contrib import messages
from .models import *
def login_user(request):
if request.method=='POST':
username = request.POST['username']
password = request.POST['password']
user = authenticate(request, username=username, password=password)
if user is not None:
login(request, user)
return redirect('index')
else:
messages.success(request,('There was an error in logining. Please Try again...'))
return redirect('login')
else:
return render(request,'login_user.html',{})
MYapp/index.html
<body>
{% include 'MYapp/navebar.html' %}
<center>
<h1>{{name}}</h1>
</center>
<div class="cotainer">
{% if messages %}
{% for message in messages %}
{{message}}
{% endfor %}
{% endif %}
</div>
{% block content %}{% endblock content %}
{% include 'MYapp/footer.html' %}
</body>
trevalo_app/urls.py
from django.urls import path,include
from . import views
urlpatterns = [
path('login_user', views.login_user,name='login_user'),
]
MYapp/urls.py
from django.contrib import admin
from django.urls import path
from . import views
urlpatterns = [
path('', views.index, name='index'),
path('footer', views.footer, name='footer'),
path('navebar', views.navebar, name='navebar'),
]
trevalo_app/login_user.html
{% extends 'MYapp/index.html' %}
{% block content %}
<center>
<h3>login...</h3>
<hr>
</center>
<div class="container container-fluid ">
<form method=POST action="">
{% csrf_token %}
<div class="mb-3">
<label for="exampleInputEmail1" class="form-label"> username</label>
<input type="text" name='username' class="form-control"
placeholder="username" aria-describedby="emailHelp">
</div>
<div class="mb-3">
<label for="exampleInputPassword1" class="form-label">Password</label>
<input type="password" name='password' class="form-control" placeholder="password">
</div>
<button type="submit" class="btn btn-primary">Submit</button>
</form>
</div>
{% endblock %}
There are a few issues with your templates:
Use the correct directory structure for templates in your apps so that Django knows where to find them:
/ MYapp
- urls.py
- views.py
- ...
/ templates
/ MYapp
- index.html
/ trevalo_app
- urls.py
- views.py
- ...
/ templates
/ trevalo_app
- login_user.html
In your views pass the correct template path to the render:
def login_user(request):
if request.method=='POST':
...
else:
return render(request,'trevalo_app/login_user.html', {}) # The correct template path
Note that your code fails because in your trevalo_app/login_user.html template you are extending 'MYapp/index.html'. For this to work you must follow the directory structure Django is recommending so that it can find the correct template.
{% extends 'MYapp/index.html' %}
I have a search bar where I want to search for perfumes in a MongoDB database. I tried two ways but it never works.
Here is the HTML template for both:
search_similar.html:
{% extends "todo/base.html" %}
{% block content %}
<div class="recommendations">
<!-- <div class="login-page"> -->
<div class="form">
<form action="{% url 'search_results' %}" method="get">
<input name="q" type="text" placeholder="Perfume name...">
<input type ="submit" value="Find Similar Perfumes" />
</form>
<form class="login-form" action = "/predict" method="POST">
<input type="text" placeholder="perfume name"/> <!-- https://www.youtube.com/watch?v=TRODv6UTXpM&ab_channel=ProgrammingKnowledge -->
<input type ="submit" value="Find Similar Perfumes" />
</form>
</div>
</div>
{% endblock %}
views.py:
import pymongo
import todo.config as config
from django.db.models import Q
username = config.username
password = config.password
...
class SearchResultsView(ListView):
model = Perfume
template_name = 'todo/search_similar_results.html'
def get_queryset(self): # new
query = self.request.GET.get('q')
perfume_list = list(collection.find({'q0.Results.0.Name': {"$regex" : query}}, {'item_name': 1, 'brand': 1, 'gender': 1,
'note': 1, 'tags': 1, 'theme': 1, '_id': 0}))
print("perfume_list: ", perfume_list)
return perfume_list
But perfume_list is hopelessly empty.
But even in MongoDB Atlas, I have problems to search in nested dictionaries. Indeed the query in the image below does not give the result that we can see:
Anexo: urls.py
urls.py:
from django.contrib import admin
from django.urls import path
from todo import views
urlpatterns = [
...
# similar
path('similar', views.search_similar, name='similar'),
path('similar_results', views.SearchResultsView.as_view(), name='search_results')
]
I am creating an app using django where an user can search for definition of some things. So f.e. he is inputing a word "security" to get definition of this. He gets results and then he is pushing back button. And then he gets a website, but the search-field still stores the old data/input "security". How can i fix this?
template:
<div>
<h1>Drink drank drunk</h1>
</div>
<h1>Jakie masz skladniki?</h1>
<form action="{% url 'search_results' %}" method="get">
<input name="q" type="text" placeholder="Search...">
</form>
{% if messages %}
<ul class="messages">
{% for message in messages %}
<li{% if message.tags %} class="{{ message.tags }}"{% endif %}>{{ message }}</li>
{% endfor %}
</ul>
{% endif %}
views:
from django.shortcuts import render
from django.db.models import Q #new
from .models import Recipe
from .models import Ingredient
from django.contrib import messages
from django.shortcuts import redirect
def drink_list(request):
template = "drinks/drink_list.html"
return render(request, template)
def search_results(besos):
query = besos.GET.get('q')
if not query or query == ' ' or query == ' ' or query == ' ':
#how to write this ^ in shortest way? if string is empty then return 'drink_list'
messages.error(besos, "Search field can not be empty")
return redirect('drink_list')
else:
q = Q()
for queries in query.split():
q |= (Q(ingredients__ingredient_name__icontains=queries))
#why it look for 'sok z cytryny' and show as well sok z limonki
results = Recipe.objects.filter(q)
template = "drinks/search_results.html"
context = {
'results' : results,
}
return render(besos, template, context)
URL:
urlpatterns = [
path('', views.drink_list, name='drink_list'),
path('search/', views.search_results, name='search_results'),
path('no_name/', views.drink_list, name='drink_list'),
]
What about trying this with some javascript? You can blank out the input tag on pageload.
<script>
window.onload = function(){
document.getElementByName("q").value = "";
}
</script>
Or you can try this
<script>
if (window.performance && window.performance.navigation.type == window.performance.navigation.TYPE_BACK_FORWARD) {
document.getElementByName("q").value = "";
}
</script>
Try this
<button onclick="history.back()">Go Back</button>
Clicking Go Back.get previous sections without clear inputs..