首页 > 解决方案 > 如何让 django-all auth 将数据传递给自定义用户模型?

问题描述

我正在使用 django-allauth 在 Django 中创建一个站点进行身份验证。

我在 accounts.models 中创建了一个自定义用户类来添加一个自定义字段 FavouriteTeam。

我遇到的问题是表单呈现正常并为 fav_team 提交表单数据很好(如在 Chrome 开发工具中检查的那样),但 fav_team 条目没有存储到 user.FavouriteTeam,我不知道为什么。

我可以进入 Django shell,从 accounts.models 导入我的 User 类,查询用户,添加 .FavouriteTeam,然后保存就好了。只是由于某种原因,表单似乎没有将数据保存到新的 User 实例中。

我猜这是由于 django-allauth 与自定义用户模型交互的方式,但我一生都无法弄清楚。我看过一些类似的帖子,但没有一个有这样的情况或有一个似乎对我有用的解决方案。

有任何想法吗?

帐户模型:-

from django.db import models
from django.contrib.auth.models import AbstractUser

class User(AbstractUser):
    FavouriteTeam = models.ForeignKey('predictor.Team', on_delete=models.CASCADE, blank=True, null=True)

    def __str__(self):
        return self.email

account.forms: -

from django import forms
from django.contrib.auth.forms import UserCreationForm, UserChangeForm
from .models import User
from allauth.account.forms import SignupForm
from predictor.models import Team
from django.contrib.auth import get_user_model

class CustomSignupForm(SignupForm):
    first_name = forms.CharField(max_length=30, label='First Name')
    last_name = forms.CharField(max_length=30, label='Last Name')
    fav_team = forms.ModelChoiceField(queryset=Team.objects.all(), empty_label=None, label='Favourite Team')

    class Meta:
        model = get_user_model()

    def signup(self, request, user):
        user.first_name = self.cleaned_data['first_name']
        user.last_name = self.cleaned_data['last_name']
        user.FavouriteTeam = self.cleaned_data['fav_team']
        user.save()
        return user

predictor.models:-

class Team(models.Model):
    ShortName = models.CharField(max_length=4, primary_key=True)
    Town = models.CharField(max_length=20)
    Nickname = models.CharField(max_length=20)
    Conference = models.CharField(max_length=3, null=True, blank=True)
    Division  = models.CharField(max_length=5, null=True, blank=True)
    ConfDiv = models.CharField(max_length=9, null=True, blank=True)
    Logo = models.ImageField(default='football.png', upload_to='logos')


    def __str__(self):
        return('{} {}'.format(self.Town, self.Nickname))

    def save(self, *args, **kwargs):
        self.ConfDiv = str(self.Conference)+" "+str(self.Division)
        super(Team, self).save(*args, **kwargs)

标签: pythondjangodjango-allauth

解决方案


对于任何看到这个并遇到同样问题的人,我最终发现解决方案如下。

首先,我必须在我的帐户应用程序中创建 adpaters.py 并填写以下内容:-

from allauth.account.adapter import DefaultAccountAdapter

class AccountAdapter(DefaultAccountAdapter):
    def save_user(self, request, user, form, commit=False):
        data = form.cleaned_data
        user.email = data['email']
        user.first_name = data['first_name']
        user.last_name = data['last_name']
        user.FavouriteTeam = data['fav_team']
        if 'password1' in data:
            user.set_password(data['password1'])
        else:
            user.set_unusable_password()
        self.populate_username(request, user)
        user.save()
        return user

然后我必须在我的项目的 settings.py 文件中引用新的帐户适配器,如下所示: -

ACCOUNT_ADAPTER = "accounts.adapters.AccountAdapter"

希望对将来的人有所帮助。


推荐阅读