my forms.py:
from django import forms
from django.contrib.auth import authenticate, get_user_model
from django.contrib.auth.models import User
from django.forms import ModelForm
from django.utils.text import capfirst
from .models import Classname, Sectionname, Teachername, Attendancename
class AuthenticationForm(forms.Form):
username = forms.CharField(max_length=20)
password = forms.CharField(widget=forms.PasswordInput)
error_messages = {
'invalid_login': ("Please enter a correct %(username)s and password."
"Note that both fields may be case-sensitive."),
'inactive': ("This account is inactive"),
}
def __init__(self, request=None, *args, **kwargs):
self.request = request
self.user_cache = None
super(AuthenticationForm, self).__init__(*args, **kwargs)
UserModel = get_user_model()
self.username_field = UserModel._meta.get_field(UserModel.USERNAME_FIELD)
if self.fields['username'].label is None:
self.fields['username'].label = capfirst(self.username_field.verbose_name)
def clean(self):
username = self.cleaned_data.get('username')
password = self.cleaned_data.get('password')
if username and password:
self.user_cache = authenticate(username=username, password=password)
if self.user_cache is None:
raise forms.ValidationError(
self.error_messages['invalid_login'],
code='invalid_login',
params={'username': self.username_field.verbose_name},
)
else:
self.confirm_login_allowed(self.user_cache)
return self.cleaned_data
def confirm_login_allowed(self, user):
if not user.is_active:
raise forms.ValidationError(
self.error_messages['inactive'],
code='inactive',
)
def get_user_id(self):
if self.user_cache:
return self.user_cache.id
return None
def get_user(self):
return self.user_cache
views.py:
#csrf_protect
#never_cache
def login(request, template_name='login.html',
authentication_form=AuthenticationForm,
extra_context=None):
if request.method == "POST":
form = authentication_form(request, data=request.POST)
if form.is_valid():
return HttpResponseRedirect(reverse('student:mains'))
else:
print(form.errors)
else:
form = authentication_form(request)
context = {
'form': form,
}
return TemplateResponse(request, template_name, context)
my login template:
<html>
<head><title>Login</title></head>
<strong> Mysite Login </strong>
<br><br>
<h3> Please Enter your credentials carefully </h3>
<body>
{% if form.errors %}
<p>NOT VALID</p>
{% for errors in form.errors %}
{{ errors }}
{% endfor %}
{% endif %}
<form method="post">
{% csrf_token %}
<label>Username: </label>
<input type="text">
<br>
<label>Password: </label>
<input type="password">
<br>
<input type="submit" value="Login">
</form>
</body>
</html>
my urls.py:
from django.conf.urls import url, patterns
from django.contrib.auth import views as auth_views
from . import views
urlpatterns = [
url(r'^register/$', views.register, name='register'),
url(r'^login/$', views.login, name='login'),
url(r'^logout/$', views.logout, name='logout'),
url(r'^password_change/$', auth_views.password_change, {'template_name': 'password_change_form.html', 'post_change_redirect': '/stu/password_change/done/'}, name="password_change"),
url(r'^password_change/done/$', auth_views.password_change_done, {'template_name': 'password_change_done.html'}, name="password_change_done"),
url(r'^restricted/', views.restricted, name='restricted'),
url(r'^mains/', views.mains, name = 'mains'),
]
I'm trying to implement django-authentication on my project. I have read some docs and made the above authentication views and forms.
The problem is that when I'm submitting my login form with correct credentials it doesn't redirect me to the redirect location as specified in my views. It doesn't do anything.
Is it the correct way in which I'm trying to do it? As I'm not using here model form.
Please suggest me the way to correct it...
Thanks! in Advance...
Still facing the same issue...
Change this:
<form method="post">
<label>Username: </label>
<input name="name">
<label>Password: </label>
<input name="phone">
to,
<form method="post" action="{% url 'login_url_name' %}">
<label>Username: </label>
<input name="username">
<label>Password: </label>
<input name="password">
Debugging suggestions:
Make sure you’re hitting the correct view when you submit the form. How? Add debug logging1 at the beginning of login(). If you don’t see the logging when you submit then make sure to set <form>’s action attribute to proper URL.
Make sure your form passes is_valid() test. Add debug logging inside if form.is_valid(): branch in your view. If it doesn’t work, make sure credentials are correct. Dump request.POST to see what might be wrong with data submitted by the form.
1 Debug logging may be a simple Exception("HEYY!!") in your code. The purpose is simply to see if your code reaches the branch in question. You’ll be sure it does if you see Django yelling at you.
Related
I have not used any middleware, when i click on logout button on my Home Page template, the logout function execute without any error.but when i go back to main page without jumping to login page.. i see myself as logged in user
here is my authentiCation/views.py
from django.shortcuts import render
from django.http import request,HttpResponseRedirect
# for user creation & login form
from django.contrib.auth.forms import UserCreationForm
from django.contrib.auth import authenticate, login
# for user related Queries
from django.contrib.auth.models import User
# imports for test purpose
from django.http import HttpResponse
# Create your views here.
# register page
def register_Page(request):
if request.method == 'POST':
form= UserCreationForm(request.POST)
if form.is_valid():
form.save()
username= request.POST['username']
password= request.POST['password1']
user= authenticate(request,username=username,password=password)
login(request,user)
return HttpResponseRedirect('/')
else:
return HttpResponse('Either the user name is not available or you may have filled the form incorrectly')
else:
form = UserCreationForm()
context= {'form':form}
return render(request,'authentication/register_Page.html',context)
# login page
def login_page(request):
if request.method == 'POST':
username= request.POST['username']
password= request.POST['password']
# returns user if credentials are valid
user= authenticate(request, username=username, password= password)
# check if user var contains the user
if user is not None:
login(request, user)
return HttpResponseRedirect('/')
else:
return HttpResponse('Invalid credentials')
return render(request,'authentication/login.html')
# logout Page
def log_out(request):
logout(request)
return HttpResponseRedirect('logout_page')
authentiCation/urls.py
from django.urls import path
from authentiCation import views
urlpatterns = [
path('register/',views.register_Page),
path('login/',views.login_page,name='login_page'),
path('logout/',views.log_out),
]
Main App Files
urls
from django.contrib import admin
from django.urls import path,include
urlpatterns = [
path('admin/', admin.site.urls),
path('',include('App_wfi_Community.urls')),
path('Ask/',include('askQuestion.urls')),
path('auth/',include('authentiCation.urls')),
]
Home.html
{% extends "basic.html" %}
{% load humanize %}
{% block title %}WFI-Community{% endblock title %}
{% block body %}
<!-- search button -->
<h5>Welcome {{username}},<h5> <!-- I see my username here -->
<form action="/search" method="get">
<div class="container py-3 row">
<div class="col-md-8 offset-2">
<div class="input-group">
<input name="searchfieldText" type="text" class="form-control" placeholder="Search">
<button class="btn btn-danger" type="submit">Search</button>
<span>Logout</span>
</div>
</div>
</div>
</form>
<!-- and some more HTML stuff which is irrelavent here -->
Give a name to this eg
path('logout/',views.log_out, name="logout" ) and change it in the home.html.
eg "{% url 'logout' %}">Logout
I do know that this is a repeated question. I did refer those answers but still I couldn't get my issue fixed. Kindly do help. Registration works just fine. The registered users gets added to the DB fine. Logout works fine. The issue is with login. Whenever I try logging in , I keep getting the response "Invalid login details".
views.py
from django.shortcuts import render, redirect
from . forms import *
from django.http import HttpResponse
from django.contrib.auth import authenticate, login, logout
from django.contrib.auth.decorators import login_required
# USER LOGIN
def user_login(request):
if request.method == 'POST':
username = request.POST.get('username')
password = request.POST.get('password')
user =authenticate( username=username, password=password)
if user is not None:
if user.is_active:
login(request,user)
return redirect('home')
else:
return HttpResponse("Account not active")
else:
return HttpResponse("Invalid login details") #whenever I try to login, I always gets this response.
else:
return render(request, 'basic_app/login.html')
#USER LOGOUT
#login_required
def user_logout(request):
logout(request)
return redirect('login')
urls.py(application).
from django.urls import path
from . import views
urlpatterns = [
path('',views.index, name='home'),
path('register/',views.register, name='register'),
path('login/',views.user_login, name='login'),
path('logout/',views.user_logout, name='logout'),
]
login.html
{% extends 'basic_app/base.html' %}
{% block body_block %}
<div class='jumbotron'>
<h2>User Login</h2>
<form action="{% url 'login' %}" method="post">
{% csrf_token %}
<label for="username">Username:</label>
<input id="username" type="text" placeholder="Enter Username">
<label for="password">Password</label>
<input id="password" type="password" placeholder="Enter Password">
<input type="submit" value="Login">
</form>
</div>
{% endblock %}
settings.py
LOGIN_URL = '/basic_app/login/'
Try this:-
Make a copy of your Project in another folder. AND delete the current database and
create a new Database as usual like :- IN Terminal - Create Superuser command is :-
python manage.py createsuperuser.
In your views.py, in the user_login function you are checking if the user.is_active.
Instead try checking if the user is authenticated in the if statement.
Because I think that the user would probably be inactive before being logged in or authenticated.
For example, this is from the documentation:
if request.user.is_authenticated:
# Do something for authenticated users.
...
else:
# Do something for anonymous users.
...
Check the documentation here
Edit
Sorry, I was lookin at the wrong if block.
You don't seem to have assigned anything to the user variable. That maybe why the user is returned as none.
Also you can try:
user = request.user
I have created a login and registration page using the same code. The registration page shows username input fields and other fields but the login page only shows the button. Can anyone help me in this
Code:
Login Page:
<div class="content-section">
<form method="POST">
{% csrf_token %}
<fieldset class="form-group">
<legend class="border-bottom mb-4">Join Today</legend>
{{ form|crispy }}
</fieldset>
<div class="form-group">
<button class="btn btn-outline-info" type="submit">Sign Up</button>
</div>
</form>
<div class="border-top pt-3">
<small class="text-muted">
Already Have An Account? <a class="ml-2" href="{% url 'login' %}">Sign In</a>
</small>
</div>
</div>
Registration Page:
<div class="site-section">
<form method="POST">
{% csrf_token %}
<fieldset class="form-group">
<legend class="border-bottom mb-4">Log In </legend>
{{ form|crispy }}
</fieldset>
<div class="form-group">
<button class="btn btn-outline-info" type="submit">Login</button>
</div>
</form>
<div class="border-top pt-3">
<small class="text-muted">
Need An Account? <a class="ml-2" href="{% url 'register' %}">Sign Up Now</a>
</small>
</div>
</div>
Registration page
Login page
This is the views of the project
Views.py
from django.shortcuts import render, redirect
from django.contrib import messages
from .forms import UserRegisterForm
from .models import Post
from django.contrib.auth.decorators import login_required
def home(request):
context = {
'posts': Post.objects.all()
}
return render(request, 'blog/home.html', context)
def about(request):
return render(request, 'blog/about.html', {'title': 'About'})
def gallery(request):
return render(request, 'blog/gallery.html', {'title': 'Gallery'})
def foodopedia(request):
return render(request, 'blog/foodopedia.html', {'title': 'Foodopedia'})
def register(request):
if request.method == 'POST':
form = UserRegisterForm(request.POST)
if form.is_valid():
form.save()
username = form.cleaned_data.get('username')
messages.success(request, f'Account created for {username}!')
return redirect('blog-home')
else:
form = UserRegisterForm()
return render(request, 'blog/register.html', {'form': form})
def login(request):
return render(request, 'blog/login.html', {'title': 'Login'})
#login_required
def profile(request):
return render(request, 'blog/profile.html', {'title': 'Profile'})
def upload(request):
context = {}
if request.method == 'POST':
uploaded_file = request.FILES['document']
fs = FileSystemStorage()
name = fs.save(uploaded_file.name, uploaded_file)
context['url'] = fs.url(name)
context['filename'] = name
pred, probability = process_image(name)
context['prediction'] = pred
context['probability'] = probability
return render(request, 'blog/foodopedia.html', context)
This is the urls.py of the project
from django.contrib import admin
from django.urls import path, include
from blog import views as blog_views
from django.contrib.auth import views as auth_views
from blog import views as blog_views
urlpatterns = [
path('admin/', admin.site.urls),
path('register/', blog_views.register, name='register'),
path('profile/', blog_views.profile, name='profile'),
path('', include('blog.urls')),
path('login/', auth_views.LoginView.as_view(template_name='blog/login.html'), name='login'),
path('logout/', auth_views.LogoutView.as_view(template_name='blog/logout.html'), name='logout'),
]
This is the form.py file:
from django import forms
from django.contrib.auth.models import User
from django.contrib.auth.forms import UserCreationForm
class UserRegisterForm(UserCreationForm):
email = forms.EmailField()
class Meta:
model = User
fields = ['username', 'email', 'password1', 'password2']
You forgot to create a new form in forms.py, then also dont forget to enhance your login view.
You could try using this, adapted from the example in this tutorial:
from django.shortcuts import render, redirect
from django.contrib.auth import authenticate, login
from django.contrib.auth.forms import AuthenticationForm
def login(request):
if request.user.is_authenticated:
return redirect('/')
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('/')
else:
form = AuthenticationForm(request.POST)
return render(request, 'blog/login.html', {'form': form, 'title': 'Login'})
else:
form = AuthenticationForm()
return render(request, 'blog/login.html', {'form': form, 'title': 'Login'})
To use that you would have to change the login line in your urls.py to this:
path('login/', blog_views.login, name='login'),
//forms.py :
//This is the forms part of my app.
from django import forms
from django.contrib.auth import (
authenticate,
login,
get_user_model,
logout,
)
User=get_user_model()
class UserLoginForm(forms.Form):
username=forms.CharField()
password=forms.CharField(widget=forms.PasswordInput)
def clean(self):
username=self.cleaned_data.get('username')
password=self.cleaned_data.get('password')
user=authenticate(username=username,password=password)
if not user:
raise forms.ValidationError("This user does not exist")
if not user.check_password(password):
raise forms.ValidationError("Incorrect password")
if not user.is_active:
raise forms.ValidationError("This user is no longer active")
return super(UserLoginForm,self).clean()
// views.py :
//views part where in , i used the UserLoginForm created in the form.
from django.shortcuts import render
from django.contrib.auth import (
authenticate,
login,
get_user_model,
logout,
)
from .forms import UserLoginForm
def login_view(request):
if request.method=='POST':
form=UserLoginForm(request.POST or None)
if form.is_valid():
username=form.cleaned_data.get("username")
password=form.cleaned_data.get("password")
return render(request,"accounts/home.html")
else:
form=UserLoginForm()
return render(request,"accounts/login.html",{"form":form})
def register_view(request):
return render(request,"form.html",{})
def logout_view(request):
return render(request,"form.html",{})
//login.html :
//login.html which opens up as home page.
<div>
<form method='POST' action=''>{% csrf_token %}
<input type="text" name="username" placeholder="Username"/>
<input type="password" name="password" placeholder="Password"/>
<input type="submit" value="Login"/>
</form>
</div>
There are no errors, but neither the raise errors show up on invalid //stuff nor the page redirects to home.html on valid user. Please help me fix the problem. I am unable to find the problem.
Please Rendering form error messages to display the error messages...
<form method='POST' action=''>{% csrf_token %}
{{ form.non_field_errors }}
<input type="text" name="username" placeholder="Username"/>
I am having issues with an error being "not raised" within a register form page. It seems to pulling the form again but without "passwords do not matched" message.
my form handler code
from django import forms
from accounts.models import User
class RegistrationForm(forms.ModelForm):
"""
Form for registering a new account.
"""
email = forms.EmailField(widget=forms.TextInput,label="Email")
password1 = forms.CharField(widget=forms.PasswordInput,
label="Password")
password2 = forms.CharField(widget=forms.PasswordInput,
label="Password (again)")
class Meta:
model = User
fields = ['email', 'password1', 'password2']
def clean(self):
"""
Verifies that the values entered into the password fields match
NOTE: Errors here will appear in ``non_field_errors()`` because it applies to more than one field.
"""
cleaned_data = super(RegistrationForm, self).clean()
if 'password1' in self.cleaned_data and 'password2' in self.cleaned_data:
if self.cleaned_data['password1'] != self.cleaned_data['password2']:
raise forms.ValidationError("Passwords don't match. Please enter both fields again.")
return self.cleaned_data
def save(self, commit=True):
user = super(RegistrationForm, self).save(commit=False)
user.set_password(self.cleaned_data['password1'])
if commit:
user.save()
return user
my views code:
def register(request):
"""
User registration view.
"""
if request.method == 'POST':
form = RegistrationForm(data=request.POST)
if form.is_valid():
user = form.save()
return redirect('/')
else:
form = RegistrationForm()
return render_to_response('accounts/register.html', {
'form': form,
}, context_instance=RequestContext(request))
I setup the register to be in the root of the app '/'
patterns in account app
from django.conf.urls import url
from accounts import views
urlpatterns = [
url(r'^$', views.register, name='register'),
#url(r'^register$', views.register, name='register'),
url(r'^login$', views.login, name='login'),
url(r'^logout$', views.logout, name='logout'),
]
in main:
urlpatterns = [
url(r'^accounts/', include('accounts.urls', namespace='accounts')),
# sets login/register to root url
url(r'^', include('accounts.urls', namespace ='accounts')),
url(r'^admin/', include(admin.site.urls))
]
The accounts app sets the username to be an email for djangos built in userAuth. All other fields fill in on the html page such as "invalid email address"
I have tried multiple things but have failed so far, any help would be appreciated at this stage.
Thank you.
I am using ubuntu 14, python 3.4 django 1.8, virtualenv
Use This Code to registration/signup.html
{% if form.errors %}
{% for field in form %}
{% for error in field.errors %}
<div class="alert alert-danger">
<strong>{{ error|escape }}</strong>
</div>
{% endfor %}
{% endfor %}
{% for error in form.non_field_errors %}
<div class="alert alert-danger">
<strong>{{ error|escape }}</strong>
</div>
{% endfor %}
{% endif %}
You are using:
raise forms.ValidationError("Passwords don't match...')
so this is a global error; it won't show next to a specific field. Make sure that your template accounts/register.html show these errors.
Also just to make sure; you can print something just before that raise (just for debugging) so you can confirm that the validation occurred in the first place.