Django相关模型和UpdateView字段

时间:2014-10-08 19:23:57

标签: django forms one-to-one django-class-based-views

我创建了一个模型(UserSettings)来通过OneToOneField扩展django的用户模型(根据文档的建议):

class UserSettings(models.Model):
    user = models.OneToOneField(User, primary_key=True)
    subscribeToMails = models.BooleanField(default=True)
    [...]

我希望为用户提供一种方法来编辑他们的一些个人资料数据,其中一些存储在用户模型(电子邮件地址)中,其余部分存储在UserSettings模型中。我怎么能这样做?

我想到了两种方法:在UserSettings模型中为电子邮件地址字段添加另一个OneToOneField;或者重写UpdateView get_queryset()方法(但我不确定如何)。是否有最佳或推荐的方式来做到这一点?到目前为止,我的观点看起来如何:

class EditUser(UpdateView):
    model = UserSettings
    fields = ('emailVisible', 'subscribeToMails', 'mpPopupNotif',
              'mpEmailNotif', 'avatar', 'quote', 'website')
    template_name = 'user/edit.html'

    def get_object(self):
        return UserSettings.objects.get(user_id=self.request.user)

    def get_success_url(self):
        return reverse_lazy('user:edit')

3 个答案:

答案 0 :(得分:2)

感谢您的回复!然而,由于我无法弄清楚如何使这项工作,并且想到使用两个表最终导致我的品味过于混乱,我终于选择了更简单的路径并将子类化为AbstractUser:

# models.py
class ForumUser(AbstractUser):
    subscribeToMails = models.BooleanField(default=True)
    [...]

# views.py
class EditUser(LoginRequiredMixin, UpdateView):
    model = ForumUser
    fields = ('email', 'emailVisible', 'subscribeToMails', 'mpPopupNotif',
              'mpEmailNotif', 'avatar', 'quote', 'website')
    template_name = 'user/edit.html'
    success_url = reverse_lazy('forum:welcome')

    def get_object(self):
        return ForumUser.objects.get(username=self.request.user)

我只需要更改我的注册表格:

# forms.py
class RegisterForm(UserCreationForm):
    email = forms.EmailField(required=True)

    class Meta:
        model = ForumUser
        fields = ('username', 'email', 'password1', 'password2')

    def clean_email(self):
        "Ensure registered emails are unique."
        email = self.cleaned_data.get('email')
        username = self.cleaned_data.get('username')
        if email and ForumUser.objects.filter(email=email).exclude(
                username=username).count():
            raise forms.ValidationError('Email address already in use.')
        return email

    def clean_username(self):
        """
        UserCreationForm method where mentions of the User model are replaced
        by the custom AbstractUser model (here, ForumUser).
        https://code.djangoproject.com/ticket/19353#no1
        and https://docs.djangoproject.com/en/1.7/_modules/django/contrib/
        auth/forms/#UserCreationForm
        """
        username = self.cleaned_data["username"]
        try:
            ForumUser.objects.get(username=username)
        except ForumUser.DoesNotExist:
            return username
        raise forms.ValidationError(
            self.error_messages['duplicate_username'],
            code='duplicate_username',
        )

答案 1 :(得分:1)

使用此解决方案:

UserUserSettings混合在一起,形式如下:

class EmployeeEditForm(forms.ModelForm):
    #fields from User model that you want to edit
    first_name = forms.CharField(required=False, label=_('First Name'))
    last_name = forms.CharField(required=False, label=_('Last Name'))

    class Meta:
        model = UserSettings
        fields = ('first_name', 'last_name', 'subscribeToMails')

您可以像这样访问User中的UserSettingsviews.py对象:

user = request.user
usersettings = user.usersettings

现在您可以像这样编辑User对象:

user.first_name = request.POST['first_name']
user.last_name = request.POST['last_name']
user.save()

并像这样编辑UserSettings

usersettings.subscribeToMails = request.POST['subscribeToMails']
usersettings.save() 

答案 2 :(得分:-1)