My url is shown below like:
url(r'^register/$', views.register, name='register')
The function in my views.py is like:
from django.shortcuts import render
from django.http import HttpResponseRedirect
from django.core.urlresolvers import reverse
from django.contrib.auth import login, logout, authenticate
from django.contrib.auth.forms import UserCreationForm
def register(request):
"""register"""
if request.method != 'POST':
#we present a blank form
form = UserCreationForm()
else:
#the post the data the users have just filled
form = UserCreationForm(data=request.POST)
if form.is_valid():
new_user = form.save()
# we use the date to redirect our user to the page of login
authenticated_user = authenticate(username=new_user.username,
password=request.POST['password'])
login(request, authenticated_user)
return HttpResponseRedirect(reverse('learning_logs:index'))
context = {'form': form}
return render(request, 'users/register.html', context)
And my register.html:
{% extends "learning_logs/base.html" %}
{% block content %}
<form action="{% url 'users:register' %}" method="post">
{% csrf_token %}
{{ form.as_p }}
<button name="submmit">Register</button>
<input type="hidden" name="next" value="{% url 'learning_logs:index' %}"/>
</form>
{% endblock content %}
when I do the register, it goes wrong like, MultiValueDictKeyError: "'password'"
Can some one have a look and give me a hand? Thanks a lot!
If you check UserCreationForm, you'll see that it doesn't have a field named password, but it has two: password1 and password2. You can change your code to this:
if form.is_valid():
new_user = form.save()
# we use the date to redirect our user to the page of login
authenticated_user = authenticate(username=new_user.username,
password=form.cleaned_data['password1'])
# ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
login(request, authenticated_user)
return HttpResponseRedirect(reverse('learning_logs:index'))
However, you probably want to avoid dealing with passwords and simply use login() directly, without passing through authenticate():
if form.is_valid():
user = form.save()
login(request, user)
return HttpResponseRedirect(reverse('learning_logs:index'))
Related
so, I made the registration page with django and it doesn't show the form
register.html
<form method="post">
{{ form.as_table }}
{% csrf_token %}
<input type='submit' value="Register">
</form>
and this is the views.py
from django.shortcuts import render, redirect
from django.http import HttpResponse
from django.contrib.auth.forms import UserCreationForm
def register(request):
if request.method == 'POST':
form = UserCreationForm(request.POST)
if form.is_valid():
form.save()
return redirect('login')
else:
form = UserCreationForm()
return render(request, 'register.html', { 'form ' : form})
def login(request):
return render(request, 'login.html')
And all it shows is the register button
Could be one of two things:
Put the {% csrf_token %} before the form variable in your template.
Don't put any whitspace in the form key in your context dictionary (so instead of ' form ' it should be 'form')
I think you mistakenly wrote "form " instead of "form" and also put {% csrf_token %} in the form tag right before the rendering
def login(request):
if request.method=='POST':
user = auth.authenticate(username=request.POST['username'],password=request.POST['password1'])
if user is not None:
auth.login(request,user)
return redirect('../')
else:
return render(request,'login.html',{'error':'username or password is wrong'})
else:
return render(request,'login.html')
You need to define your login form that is to be passed to the template.
For example:
forms.py
class LoginForm(forms.Form):
username = forms.CharField(label='Your Email/Username', max_length=100)
password = forms.CharField(label='Your Password', max_length=100)
Then in your views.py, you can define a view function as:
views.py
from .forms import LoginForm
def login(request):
if request.method == "POST":
if form.is_valid:
user = auth.authenticate(username=request.POST['username'],password=request.POST['password1'])
if user is not None:
auth.login(request,user)
return redirect('../')
else:
return render(request,'login.html',{'form': form, 'error':'username or password is wrong'})
else:
form = LoginForm()
return render(request,'login.html', {'form': form})
Then in your template, you can render the form as:
<form method="post">
{% csrf_token %}
{{ form.as_p }} <--render the form in other ways as preferred-->
{% for error in form.errors %} //for displaying the fields where errors have occured
{{ error }}
{% endfor %}
<button type="submit">Login</button>
</form>
you can use django inbuilt loginview:-
in urls.py
from django.contrib.auth.views import LoginView
urlpatterns =[
path('login/' , LoginView.as_view(template_name='login.html') , name ='login')
]
in ur login.html
<h1> login page!! </h1>
<form method='POST'>
{% csrf_token %}
{{ form.as_p }}
<input type='submit' value='Login'>
</form>
I am trying to send a form to html using django. this is the form
from django import forms
class contactForm(forms.Form):
name = forms.CharField(required=False, max_length=100,help_text='100 characters max.')
email = forms.EmailField(required=True)
comment = forms.CharField(required=True, widget=forms.Textarea)
The view file is
from django.shortcuts import render
from .forms import contactForm
# Create your views here.
def contact(request):
form = contactForm(request.POST or None)
if form.is_valid():
print (request.POST)
context = locals()
template = 'contact.html'
return render(request, template, context)
and the html file which is named correctly is,
{% extends 'base.html' %}
{% block content %}
<h1> Contact </h1>
<form method='POST' action=''> {% csrf_token %}
{{ form.as_p }}
<input type='submit' value='submit form' class='btn btn-default' />
</form>
{% endblock %}
When you visit the page the only thing that shows up is the h1 tag how do i fix this?
You can try
def contact(request):
form = contactForm(request.POST or None)
if form.is_valid():
print (request.POST)
context = locals()
template = 'contact.html'
return render(request, template, context)
return render(request, 'contact.html', {'form': form})
The correct format of rendering a from is this:
from django.shortcuts import reverse
from django.http import HttpResponseRedirect
from . import models
from . import forms
def contact(request):
if request.POST == 'POST':
form = forms.contactForm(request.POST or None)
contact_model = models.contactModel() #err is here name it with appropriate model name contactModel is just an example
if form.is_valid():
contact_model.name = form.cleaned_data['name']
contact_model.email = form.cleaned_data['email']
contact_model.comment = form.cleaned_data['comment']
contact_model.save()
return HttpResponseRedirect('/success/')) #desired url to redirect, you can use reverse to call templates according to url names
else: #if request is GET
form = forms.contactForm()
context = {
'form': form
}
template = 'contact.html'
return render(request, template, context=context)
Do not use action in your template, just set your urls.py to redirect to the desired view.
I create a form using django auth forms UserCreationForm and it works without 'action' inside . Why it works?
views.py
def sign_up(request):
if request.method == 'POST':
form = UserCreationForm(request.POST)
if form.is_valid():
form.save()
username = form.cleaned_data.get('username')
password = form.cleaned_data.get('password1')
user = authenticate(username=username, password=password)
login(request, user)
return redirect('contacts:index')
else:
form = UserCreationForm()
return render(request, 'account/signup.html', {'form': form})
sgnup.html
<h2>Sign up</h2>
<form method="post">
{% csrf_token %}
{{ form.as_p }}
<button type="submit">Sign up!</button>
</form>
Because by default your browser will post the form to the current URL. So if your get view and post view share the same URL, it just works.
And that's obviously the case here, since you use the same view for POST and GET.
As said by #dirkgroten, in HTML5 it is not mandatory to specify form action, in such cases like yours, with no action specified-The form is posted to current URL.
I am beginner to python Django. And trying build an posting article website with the help of tutorials. I got stuck at UserCreationForm. I have created a form using UserCreationForm, but when I am submitting the form I am not able to neither submit the form nor getting any error message on the page.
My views.py code
from django.shortcuts import render_to_response
from django.contrib.auth import authenticate
from django.http import HttpResponseRedirect
from django.contrib import auth
from django.template.context_processors import csrf
from django.contrib.auth.forms import UserCreationForm
def register_user(request):
if request.method == 'POST':
form = UserCreationForm(request.POST)
if form.is_valid():
form.save()
return HttpResponseRedirect('/accounts/register_success')
args = {}
args.update(csrf(request))
args['form'] = UserCreationForm()
print args
return render_to_response('register.html', args)
def register_success(request):
return render_to_response('register_success.html')
register.html
{% extends "base.html" %}
{% block content %}
<h2>Register</h2>
<form action="/accounts/register/" method="post"> {% csrf_token %}
{{form}}
<input type="submit" value="Register"/>
</form>
{% endblock %}
register_success.html
{% extends "base.hml" %}
{% block content %}
<h2>You have registered!</h2>
<p>Click Here to login again</p>
{% endblock %}
The problem is that you are always creating a blank form.
args['form'] = UserCreationForm()
This means that you do not see any errors for POST requests when the form is invalid.
Instead, you should only create the blank form for GET requests.
from django.shortcuts import render
def register_user(request):
if request.method == 'POST':
form = UserCreationForm(request.POST)
if form.is_valid():
form.save()
return HttpResponseRedirect('/accounts/register_success')
else:
form = UserCreationForm()
args = {'form': form}
return render(request, 'register.html', args)
Note that I have simplified the view by using render instead of the obsolete render_to_response. That means you don't need to handle csrf manually.
You can use Django Generic Views, specifically CreateView, it will make your life a lot easier. You can use it like so:
from django.views.generic import CreateView
class CreateUserView(CreateView):
template_name = 'register.html'
form_class = UserCreationForm
success_url = '/accounts/register_success'
Add this to your urls.py and you are good to go:
from mysite.views import CreateUserView
# add this url pattern
url(r'^sign_up/$', CreateUserView.as_view(), name='signup'),