Django在创建用户然后登录时出现问题

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

大家好,你们这些乐于助人的人(再见,没有乐于助人的人:D)。我试图在django(1.2.4)中创建一个用户,然后在保存后登录。我的问题是我没有实现错误,并且正在查看django.contrib.auth.models.AnonymousUser提出的回溯。以下是我的视图代码的一部分:

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