How to make a simple contact form using Django? - python

I am new to Django 1.9 and I am currently coding a website. I am trying to make a contact form to go on the contact page. I have used the following code - which is in the a file called email.html:
{% extends 'blog/base.html' %}
<form method="post">
{% csrf_token %}
{{ form }}
<div class="form-actions">
<button type="submit">Send</button>
</div>
</form>
I've defined it in the view.py file:
from .forms import PostForm, ContactForm
from django.http import HttpResponse, HttpResponseRedirect
from django.shortcuts import redirect
from django.core.mail import send_mail, BadHeaderError
from django.http import HttpResponse, HttpResponseRedirect
from django.shortcuts import render, redirect
def email(request):
if request.method == 'GET':
form = ContactForm()
else:
form = ContactForm(request.POST)
if form.is_valid():
subject = form.cleaned_data['subject']
from_email = form.cleaned_data['from_email']
message = form.cleaned_data['message']
try:
send_mail(subject, message, from_email, ['nmam.ltd#gmail.com'])
except BadHeaderError:
return HttpResponse('Invalid header found.')
return redirect('thanks')
return render(request, "blog/email.html", {'form': form})
def thanks(request):
return HttpResponse('Thank you for your message.')
.....
As well as in the forms.py file:
from django import forms
class ContactForm(forms.Form):
from_email = forms.EmailField(required=True)
subject = forms.CharField(required=True)
message = forms.CharField(widget=forms.Textarea)
Also, in the urls.py file:
from django.conf.urls import patterns, url
from . import views
urlpatterns = [
url(r'^general.html/$', views.general, name='general'),
url(r'^dcmain.html/$', views.dcmain, name='dcmain'),
url(r'^dcmain.html/big_data.html/$', views.big_data, name='big_data'),
url(r'^dcmain.html/Data_Architecture.html/$', views.Data_Architecture, name='Data_Architecture'),
url(r'^dcmain.html/BI_MI.html/$', views.BI_MI, name='BI_MI'),
url(r'^dcmain.html/Master_Data.html/$', views.Master_Data, name='Master_Data'),
url(r'^dcmain.html/Data_Q.html/$', views.Data_Q, name='Data_Q'),
url(r'^dcmain.html/Project_M.html/$', views.Project_M, name='Project_M'),
url(r'^email.html/$', views.email, name='email'),
url(r'^thanks/$', views.thanks, name='thanks'),
]
When I link the email.html file to the main page and click on the link and it just shows the home page even though the url says I am on the email.html page (shown below):
I am totally new to programming in Django. I have tried researching it however, I can't find a solution. Please can someone help me.

Your URLs are most likely the problem. You can read more on Django URLs here.
Note, as the Django docs mention, the first URL pattern which matches the requested URL will be used. As a basic rule of thumb, I recommend putting your more specific URL patterns before your blank url patterns. For instance:
urlpatterns = [
url(r'^email.html/$', views.email, name='email'),
url(r'^thanks/$', views.thanks, name='thanks'),
url(r'^$', views.index, name='some_name'),
]
If this urls.py file is being included from a project urls.py file, you'll want these urls to be included before your root url pattern.
urlpatterns = [
url(r'^blog/', include('blog.urls', namespace='blog'),
url(r'', views.site_home, name='site_home'),
]
Which would then make your url to this page
Email
Which would render as
Email

Related

Django HTMLForms AttributeError AttributeError: module 'polls.views' has no attribute 'index'

I'm using Django to create a simple HTML input page, right now I am just using the tutorial for Django Forms but I get the error AttributeError: module 'polls.views' has no attribute 'index'
Here are all the relevant files:
This is where the Error is happening:
$ mysite/polls/urls.py
from django.urls import path
from . import views
urlpatterns = [
path('', views.index, name='index'),
]
This is views.py:
$ polls/views.py
from django.http import HttpResponseRedirect
from django.shortcuts import render
from .forms import NameForm
def get_name(request):
# if this is a POST request we need to process the form data
if request.method == 'POST':
# create a form instance and populate it with data from the request:
form = NameForm(request.POST)
# check whether it's valid:
if form.is_valid():
# process the data in form.cleaned_data as required
# ...
# redirect to a new URL:
return HttpResponseRedirect('/thanks/')
# if a GET (or any other method) we'll create a blank form
else:
form = NameForm()
return render(request, 'name.html', {'form': form})
and this is forms.py
$ /polls/forms.py
from Django import forms
class NameForm(forms.Form):
your_name = forms.CharField(label='Your name', max_length=100)
Here is name.html:
$ /polls/name.html
<html>
<form action="/your-name/" method="post">
{% csrf_token %}
{{ form }}
<input type="submit" value="Submit">
</form>
<html>
I am so confused as to why this is happening because when I used it with the Writing your first Django app tutorial it worked but when I use a form it doesn't
Thanks in advance
Your view name is not index but get_name
urlpatterns = [
path('', views.get_name, name='index'),
]
Your polls/urls.py:
from django.urls import path
from . import views
app_name = 'polls' # add this line
urlpatterns = [
path('', views.index, name='index'),
]

Django Page not found with post request

So I am new to Django and I'm trying to create a HTML form (just following the tutorial for the name input) and I can input the name but can't direct to the /thanks.html page.
$ views.py
from django.http import HttpResponseRedirect
from django.shortcuts import render
from .forms import NameForm
def get_name(request):
# if this is a POST request we need to process the form data
if request.method == 'POST':
# create a form instance and populate it with data from the request:
form = NameForm(request.POST)
print(form)
# check whether it's valid:
if form.is_valid():
# process the data in form.cleaned_data as required
# ...
# redirect to a new URL:
return HttpResponseRedirect('/polls/thanks.html')
# if a GET (or any other method) we'll create a blank form
else:
form = NameForm()
return render(request, 'name.html', {'form': form})
$ name.html
<html>
<form action="/polls/thanks.html" method="post">
{% csrf_token %}
{{ form }}
<input type="submit" value="Submit">
</form>
<html>
$ /mysite/urls
from django.contrib import admin
from django.urls import include, path
urlpatterns = [
path('polls/', include('polls.urls')),
path('admin/', admin.site.urls),
]
$ mysite/polls/urls.py
from django.urls import path
from polls import views
urlpatterns = [
path('', views.get_name, name='index'),
]
When I go to to the page, I can enter my name fine but then when I submit i get
Using the URLconf defined in mysite.urls, Django tried these URL patterns, in this order:
polls/ [name='index']
admin/
The current path, polls/thanks.html, didn't match any of these.
Even though thanks.html is inside /polls
Sorry if the fix is super easy I just haven't used Django before.
Thanks :)
Create a view called thanks in views.py
def thanks(request):
return render(request, 'thanks.html')
Now, Link the /poll/thanks/ url to the thanks template by adding path('thanks/', views.thanks, name='thanks') to your urls.py of the polls app.
$ mysite/polls/urls.py
from django.urls import path
from polls import views
urlpatterns = [
path('thanks/', views.thanks, name='thanks'),
]
Finally change the following line in your get_name view
return HttpResponseRedirect('/polls/thanks/')
Change your main urls.py:
url(r'^polls/', include('polls.urls')),
And in your app's urls.py:
url(r'^$', views.get_name, name='index'),
And in your views.py change to:
if form.is_valid():
# process the data in form.cleaned_data as required
# ...
# redirect to a new URL:
return render(request, 'thanks.html')

Django 404 Error Raised by: blog.views.post_detail

Hello, Everyone
I'm a novice programmer trying to follow Antonio Mele tutorial on blog creation using django.
Am stuck with the post/detail.html which is not responding
below are the codes.Kindly help.
Problem: Am unable to view details of the post
404 Error: Page not found
Page not found (404)
Request Method: GET
Request URL: http://127.0.0.1:8000/blog/2020/3/13/more-post/
Raised by: blog.views.post_detail
No Post matches the given query.
You're seeing this error because you have DEBUG = True in your Django settings file. Change that to False, and Django will display a standard 404 page.
Error:Page not found
Page not found (404)
Request Method: GET
Request URL: http://127.0.0.1:8000/
Using the URLconf defined in mysite.urls, Django tried these URL patterns, in this order:
1.admin/
2.blog/
The empty path didn't match any of these.
You're seeing this error because you have DEBUG = True in your Django settings file. Change that to False, and Django will display a standard 404 page.*
urls.py/blog
urls.py/mysite
views.py
urls.py/blog
from django.urls import path
from . import views
app_name = 'blog'
urlspatterns = [
path('', views.post_list, name='post_list'),
path('<int:year>/<int:month>/<int:day>/<slug:post>/',
views.post_detail,
name='post_detail'),
]
urls.py/mysite
from django.contrib import admin
from django.urls import path, include
urlpatterns = [
path('admin/', admin.site.urls),
path('blog/', include('blog.urls', namespace='blog')),
]
views.py
from django.shortcuts import render, get_object_or_404
from .models import Post
def post_list(request):
posts = Post.objects.all()
return render(request,
'blog/post/list.html',
{'posts':posts})
def post_detail(request, year, month, day, post):
post = get_object_or_404(Post, slug=post,
status='published',
publish__year=year,
publish__month=month,
publish__day=day)
return render(request,
'blog/post/detail.html',
{'post': post})
Someone had the same problem with the previous version of the book, asked here and published his solution (there must be a much more elegant way), have a look here:
Django get_object_or_404() with DateTimeField
In addition, use the shell to debug items, you should have seen that the date in DB is recorded in UTC:
>>> post = Post.objects.get(title__startswith='who')
>>> post.publish
datetime.datetime(2020, 8, 18, 1, 18, 56, tzinfo=<UTC>)
Take a look at the admin area, where the articles have a 'draft' status. Change them to 'published' status. In the views.py in the function post_list(), change the output of posts on a page with only the status published:
def post_list(request):
posts = Post.objects.filter(status='published')
return render(request, 'blog/post/list.html', {'posts': posts})
In this case, articles with only the status published are displayed on the posts page. By clicking on the article link, you should be transferred to a full post without error.
#FOLLOW THIS PROCEDURE.I HOPE IT HELPS YOU OR ANY ONE ELSE IN THE FUTURE
#blog/models.py
from django.db import models
from django.utils import timezone
class Post(models.Model):
published = models.BooleanField(True)
created_on = models.DateTimeField(auto_now=timezone.now)
# At blog/urls.py
from django.urls import path
from .views import (post_list, post_detail)
urlspatterns = [
path('', post_list, name='post_list'),
path('<str:slug>/', post_detail, name='post_detail'),
#At mysite/urls.py
from django.contrib import admin
from django.urls import path, include
urlpatterns = [
path('admin/', admin.site.urls),
path('blog/', include('blog.urls')),
#At blog/views.py
from django.shortcuts import render, get_object_or_404
from .models import Post
def post_list(request):
posts = Post.objects.filter(published)
template_name = blog/post_list.html
context = {'posts':posts}
return render(request, template_name, context)
def post_detail(request, slug):
posts = get_object_or_404(Post, slug=slug)
template_name = blog/post_detail.html
context = {'posts':posts}
return render(request, template_name, context)
# At the template/blog/post_list.html
{% block content %}
{% for post in posts %}
<article>
<div>
<small>{{ post.created_on|date:"F d, Y" }}</small>
<h2>{{ post.title }}</h2>
<p >{{ post.body }}</p>
</div>
</article>
{% endfor %}
{% endblock content %}
# At template/blog/post_detail.html
<article>
<div>
<small>{{ posts.created_on|date:"F d, Y" }}</small>
<h2>{{ posts.title }}</h2>
<p>{{ posts.body }}</p>
</div>
</article>
#The above code should fix the the issue properly.

Django - Urls are appending to one another

I'm making a web app in django and currently I'm facing this problem. I have a dashboard page and an upload page. There's a button in dashboard page which links to the upload page. but whenever I click the button then the upload page url appends the dashboard page.
below is the code:
views.py
from django.shortcuts import render, get_object_or_404
from django.http import HttpResponse, HttpResponseRedirect
from .models import Registration
from .forms import UploadForm
from django.urls import reverse
# Create your views here.
def homepage(request):
return render(request, 'index.html', {})
def dashboard(request):
posts = Registration.objects.all()
return render(request, "dashboard.html", {'posts': posts})
def upload(request):
form = UploadForm()
return render(request, "upload.html", {'form': form})
def uploadimage(request):
if request.method == 'POST':
form=UploadForm(request.FILES['image'], request.POST)
if form.is_valid():
pic = request.FILES['image']
desc = request.POST
post = Registration(pic='pic', desc='desc')
post.save()
urls.py
from django.urls import path
from django.conf import settings
from django.conf.urls.static import static
from . import views
urlpatterns = [
path('', views.homepage, name='homepage'),
path('dashboard/', views.dashboard, name='dashboard'),
path('upload/', views.upload, name='upload'),
path('create/', views.uploadimage, name='uploadimage'),
] + static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)
dashboard.html
<div class="profile">
<div class="left-s col s12 m3 l3">
<div class="profile-overview">
<img src="{%static 'images/group.jpg' %}" alt="profile-pic" class="circle responsive-img">
<p>Daljit Singh</p>
<p>Lorem ipsum dolor sit amet.</p>
</div>
<hr>
<div class="container">
<ul>
<li>About</li>
<li>Friends</li>
<li>Photos</li>
<li>Likes</li>
</ul>
</div>
<hr>
<button>Upload post</button>
</div>
error:
Page not found (404)
Request Method: GET
Request URL: http://127.0.0.1:8000/dashboard/upload/
Using the URLconf defined in main.urls, Django tried these URL patterns, in this order:
[name='homepage']
dashboard/ [name='dashboard']
upload/ [name='upload']
create/ [name='uploadimage']
^media\/(?P<path>.*)$
The current path, dashboard/upload/, didn't match any of these.
You're seeing this error because you have DEBUG = True in your Django settings file. Change that to False, and Django will display a standard 404 page.
Help would be appreciated.
It should be - Upload post
If you enter '/' (/upload/) before the path it will append to the base URL and if '/' (upload/) doesn't exist then it will append to the existing path.
Or the Different way suggested in the comment -
Upload post

how to handle httpresponseredirect

test2/urls.py
from django.conf.urls import url
from .import views
from .forms import forms
urlpatterns=[
url(r'^$',views.index,name='index'),
url(r'^thankyou/$',views.thankyou,name='thankyou')
]
test1/urls.py
from django.contrib import admin
from django.conf.urls import url , include
urlpatterns = [
url(r'^admin/', admin.site.urls),
url(r'^test2/',include('test2.urls')),
]
views.py
this view should redirect to /test2/thankyou/ but why it is going to /thankyou
and what to do enable the view given by redirect method
from django.shortcuts import render
from django.http import HttpResponseRedirect,HttpResponse
from .forms import Get_name
# Create your views here.
def index(request):
if request.method == 'POST':
form = Get_name(request.POST)
if form.is_valid():
return HttpResponseRedirect('/thankyou/')
else:
form = Get_name()
return render(request, 'test2/name.html' , {'form':form})
def thankyou(request):
return HttpResponse('sai chaitanya')
name.html
after submitting the form it should redirect to test2/thankyou but it is going to /thankyou.
<form action="/thankyou/" method="post">
{% csrf_token %}
{{ form.as_p }}
<input type="submit" value="Submit" />
</form>
forms.py
from django import forms
user_choice =[('space',''),('passenger','Passenger'),('driver','Driver')]
class Get_name(forms.Form):
user_name = forms.CharField(label='user name',max_length='50',required=True)
pass_word1 = forms.CharField(widget=forms.PasswordInput,max_length='20',label='Password')
pass_word2 = forms.CharField(widget=forms.PasswordInput, max_length='20', label='Confirm Password')
email = forms.EmailField(label='email',max_length='100')
mobile = forms.CharField(label='contact number ',widget=forms.NumberInput,max_length='10')
address = forms.CharField(label='Address',max_length='100')
user_type = forms.CharField(label='select user type',widget=forms.Select(choices=user_choice))
It is going to /thankyou/ because you have hardcoded the URL /thankyou/:
return HttpResponseRedirect('/thankyou/')
You can redirect to /test2/thankyou/ by changing the code to:
return HttpResponseRedirect('/test2/thankyou/')
However the best practice is to reverse the URL instead of hardcoding it:
from django.urls import reverse
return HttpResponseRedirect(reverse('thankyou'))
This can be simplified using the redirect shortcut:
from django.shortcuts import redirect
return redirect('thankyou')

Categories

Resources