You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Django注册成功后无法登录,提示用户名或密码错误

新用户注册后登录提示用户名或密码错误问题排查与修复

问题描述

新用户注册成功后,登录时始终提示「用户名或密码错误」,确认输入无拼写错误,怀疑问题出在密码的哈希编码环节。相关代码如下:

注册代码

@csrf_exempt
def api_register(request):
    data = json.loads(request.body)
    username = data['username']
    password_1 = data['password_1']
    password_2 = data['password_2']

    # 1,check if two pw is same
    if password_1 != password_2:
        return JsonResponse({"code": 0, "msg": "pw not consistant"})

    else:
        m = hashlib.md5()
        m.update(password_1.encode())
        password_m = m.hexdigest()

        # 2 check if username exists

        users = User.objects.filter(username=username)
        if users:
            return JsonResponse({"error": "username already exists"})
        else:
            try:
                user = User.objects.create_user(username = username, password = password_m)
                user.set_password(password_m)
                user.save()
                user.is_active = True
                user.success = True
                ret_data = {"username": user.username, 'uid': user.id, 'password': user.password}
                token = TimestampSigner(sep='.').sign_object(ret_data)
                ret_data['token'] = token
                ret = {"code": 1, "msg": ret_data}
            except Exception as e:
                print('--create user error is %s' % e)
                return JsonResponse({"error": "username already exists"})
            return JsonResponse(ret)

登录代码

@csrf_exempt
def api_login(request):
    data = json.loads(request.body)
    user = authenticate(**data) #same as authenticate(username=data['username'],password=data['password']

    if user:
        ret_data = {"username":user.username,'uid':user.id}
        token = TimestampSigner(sep='.').sign_object(ret_data)
        ret_data['token'] = token
        ret = {"code":1,"msg":ret_data}
        print("ret ", ret)
    else:
        ret = {"code":0,"msg":"username or password wrong!" }
    return JsonResponse(ret)

问题根源

  1. 重复哈希导致密码不匹配:

    • 代码先对原始密码做MD5哈希得到password_m,调用create_user时,Django内置方法会自动对传入的password参数做哈希处理;
    • 随后又调用user.set_password(password_m),把已经MD5哈希过的字符串再次用Django的密码哈希算法处理一遍;
    • 最终数据库存储的是「MD5哈希值的Django哈希值」,而登录时authenticate仅对用户输入的原始密码做一次Django哈希,两者无法匹配。
  2. 冗余操作:create_user方法默认会将is_active设为True,无需额外设置;且调用create_user后不需要再手动调用save()。

修复后的注册代码

@csrf_exempt
def api_register(request):
    data = json.loads(request.body)
    username = data['username']
    password_1 = data['password_1']
    password_2 = data['password_2']

    # 检查两次输入的密码是否一致
    if password_1 != password_2:
        return JsonResponse({"code": 0, "msg": "两次输入的密码不一致"})

    # 检查用户名是否已存在
    if User.objects.filter(username=username).exists():
        return JsonResponse({"error": "用户名已存在"})
    
    try:
        # create_user会自动处理密码哈希存储,直接传入原始密码即可
        user = User.objects.create_user(username=username, password=password_1)
        ret_data = {"username": user.username, 'uid': user.id}
        token = TimestampSigner(sep='.').sign_object(ret_data)
        ret_data['token'] = token
        ret = {"code": 1, "msg": ret_data}
    except Exception as e:
        print(f'创建用户错误:{e}')
        return JsonResponse({"error": "创建用户失败"})
    
    return JsonResponse(ret)

修复说明

  • 移除手动MD5哈希步骤,直接将原始密码传给create_user,Django会自动使用安全的内置哈希算法(默认PBKDF2)处理密码,保证登录验证匹配;
  • 删除重复的set_password和多余的save()操作,简化逻辑;
  • 调整提示信息为中文表述,更符合使用习惯。

内容的提问来源于stack exchange,提问作者Jack

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.12 06:20:25