Django在创建用户然后登录时出现问题
大家好,你们这些乐于助人的人(再见,没有乐于助人的人:D)。我试图在django(1.2.4)中创建一个用户,然后在保存后登录。我的问题是我没有实现错误,并且正在查看django.contrib.auth.models.AnonymousUser提出的回溯。以下是我的视图代码的一部分:Django在创建用户然后登录时出现问题,django,django-views,django-authentication,Django,Django Views,Django Authentication,大家好,你们这些乐于助人的人(再见,没有乐于助人的人:D)。我试图在django(1.2.4)中创建一个用户,然后在保存后登录。我的问题是我没有实现错误,并且正在查看django.contrib.auth.models.AnonymousUser提出的回溯。以下是我的视图代码的一部分: def signup(request): if request.method == 'POST': # If the form has been submitted... p = requ
def signup(request):
if request.method == 'POST': # If the form has been submitted...
p = request.POST
if not request.user.is_authenticated():
form = UserForm(request.POST) # A form bound to the POST data
if form.is_valid(): # All validation rules pass
# Process the data in form.cleaned_data
# ...
form.save()
user=authenticate(username=p['username'],password=p['password'])
login(request,user)
return HttpResponseRedirect('/') # Redirect after POST
所以在我看来,它试图登录anymouse用户,而不是我正在验证的用户,我如何克服这个问题
谢谢
另外,用户是在数据库中创建的,它不会使用此代码让他们登录
回溯:
环境:请求方式:POST
请求URL:
Django版本:1.2.4
Python版本:2.6.1
已安装的应用程序:
['django.contrib.auth',
“django.contrib.contenttypes”,
“django.contrib.sessions”,
“django.contrib.sites”,
“django.contrib.messages”,
“django.contrib.admin”,
“django.contrib.admindocs”,
“django_扩展名”,
“修订的应用程序”, 已安装的中间件: ('django.middleware.common.CommonMiddleware', 'django.middleware.locale.LocaleMiddleware', “django.contrib.sessions.middleware.SessionMiddleware”, 'django.contrib.auth.middleware.AuthenticationMiddleware', 'django.contrib.messages.middleware.MessageMiddleware', 'django.contrib.sessions.middleware.SessionMiddleware')
我认为这里发生的是
authenticate
返回None
,因此login
使用request.user
(一个匿名用户
)
看起来用于创建用户的信息与您传递给authenticate
的信息不同。我会仔细检查用户是否正确保存(尤其是密码)
编辑:从其他答案中,我看到您正在使用自定义用户表单。您应该使用django.contrib.auth.forms.UserCreationForm
,它的save()
方法将正确设置密码
如果不手动设置backend属性,下面的内容将无法工作,这将给后人带来更多麻烦
最简单的方法是在这里跳过身份验证步骤(它没有添加任何重要内容)
不确定是否有帮助,但最好提取如下表单字段:
username = form.cleaned_data['username']
password = form.cleaned_data['password']
hashed_password = hashlib.md5(password).hexdigest()
user = authenticate(username=username, password=hashed_password)
if user:
login(request, user)
return HttpResponseRedirect('/')
通过使用当前代码创建的用户,您可以在系统中验证他们的身份吗
这里有一种使用登录表单创建和登录以及手动创建用户的替代方法:
# forms.py
from django import forms
class LoginForm(forms.Form):
username = forms.CharField(max_length=20)
password = forms.CharField(widget=forms.PasswordInput)
# views.py
import hashlib
username = form.cleaned_data['username']
password = form.cleaned_data['password']
hashed_password = hashlib.md5(password).hexdigest()
# assuming username is unique
User.objects.get_or_create(username=username, defaults={'password': hashed_password, 'is_active': True})
# If password doesn't work, try hashed_password next
user = authenticate(username=username, password=password)
if user:
login(request, user)
return HttpResponseRedirect('/')
使用form.save()创建用户不是一个好方法…因为,由于密码是以哈希格式保存的,所以pasword通过使用
user.passord = password
简单地将未保存的数据写入数据库,django auth无法正确检查它…您需要的是:
username = form.cleaned_data['username']
password = form.cleaned_data['password']
user = User.objects.create(username=username)
if password:
user.set_password(password)
else:
user.set_unusable_password()
user.save()
在Django 2.2中,我使用以下代码注册
def signup(request):
if request.method == 'POST':
user_form = UserRegistrationForm(request.POST)
if user_form.is_valid():
# Create a new user object but avoid saving it yet
new_user = user_form.save(commit=False)
# Set the chosen password
new_user.set_password(
user_form.cleaned_data['password'])
# Save the User object
new_user.save()
# Create the user profile
Profile.objects.create(user=new_user)
return render(request,
'account/register_done.html',
{'new_user': new_user})
else:
user_form = UserRegistrationForm()
return render(request,
'account/register.html',
{'user_form': user_form})
在这里,我们可以通过调用Django散列方法来进一步增强它
以下是django散列方法:
PASSWORD_HASHERS = [
'django.contrib.auth.hashers.BCryptSHA256PasswordHasher',
'django.contrib.auth.hashers.PBKDF2PasswordHasher',
'django.contrib.auth.hashers.PBKDF2SHA1PasswordHasher',
'django.contrib.auth.hashers.Argon2PasswordHasher',
]
我们可以按如下方式调用上述哈希器:
from django.contrib.auth.hashers import PBKDF2PasswordHasher
class MyPBKDF2PasswordHasher(PBKDF2PasswordHasher):
"""
A subclass of PBKDF2PasswordHasher that uses 100 times more iterations.
"""
iterations = PBKDF2PasswordHasher.iterations * 100
为了进一步散列像argon2/bcrypt这样的新方法,我们需要安装argon2
请参阅:部分正确,它没有返回任何结果。我尝试了您的解决方案,但它不起作用,因为根据文档“调用authenticate()首先手动登录用户时,必须调用authenticate(),然后才能调用login()。authenticate())在用户上设置一个属性,说明哪个身份验证后端成功验证了该用户(有关详细信息,请参阅后端文档),稍后在登录过程中需要此信息。”谢谢,其他答案很好,但UserCreationForm绝对是一个不错的选择。尝试过使用form.cleaned_数据会得到相同的原始错误。您可以详细说明其他方法来验证新创建的用户吗?这就是我想知道的。您正在创建和验证这些用户,但代码失败。使用新用户的用户名和密码,你能认证到网站或管理员吗?谢谢,现在我们有进展了!我只检查了他们在indead创建的地方,但试图登录到后端,我发现它也没有在那里进行认证。所以我查看后端的密码,发现它没有自动加密他们,所以这可能是I问题就在这里。在保存userform之前,我应该如何加密密码。在这一点上,我应该注意userform是我制作的一个模型表单,如果有默认表单,我需要导入什么来访问它?我添加了一种创建和验证的替代方法,请参见上文。非常感谢@ThierryLam,您用这个答案拯救了我的一天,非常有效好
PASSWORD_HASHERS = [
'django.contrib.auth.hashers.BCryptSHA256PasswordHasher',
'django.contrib.auth.hashers.PBKDF2PasswordHasher',
'django.contrib.auth.hashers.PBKDF2SHA1PasswordHasher',
'django.contrib.auth.hashers.Argon2PasswordHasher',
]
from django.contrib.auth.hashers import PBKDF2PasswordHasher
class MyPBKDF2PasswordHasher(PBKDF2PasswordHasher):
"""
A subclass of PBKDF2PasswordHasher that uses 100 times more iterations.
"""
iterations = PBKDF2PasswordHasher.iterations * 100