如何在自定义用户配置文件创建表单中正确覆盖保存方法?

时间:2016-04-01 12:22:52

标签: python django django-models django-forms

我试图在Django中覆盖自定义创建表单的save方法。我有模型UserProfile,它有许多属性。我创建了UserProfileCreationForm,应创建并保存UserUserProfile。现在,它会保存User,但不能保存UserProfile(我已覆盖属性date_of_birth,以便能够选择而不是写入字段的日期)。

所以我想要的是让这个表单同时保存UserUserProfile,或者在UserProfileCreationForm_object.save()

时出错

这是我的表格:

class UserProfileCreationForm(UserCreationForm):
    username = forms.CharField(label="Username",max_length=40)
    email = forms.EmailField(label="Email address", max_length=40)
    first_name = forms.CharField(label='First name', max_length=40)
    last_name = forms.CharField(label='Last name', max_length=40)
    date_of_birth = forms.DateField(label='Date of birth',
                                    widget=SelectDateWidget(years=[y for y in range(1930,2050)]),
                                    required=False)
    password1 = forms.CharField(label="Password", widget=forms.PasswordInput)
    password2 = forms.CharField(label="Password confirmation", widget=forms.PasswordInput)

    class Meta():
        model = UserProfile
        fields = ('username','email','first_name','last_name','password1','password2','date_of_birth','telephone','IBAN',)

    def clean_password2(self):
        # Check that the two password entries match
        password1 = self.cleaned_data.get("password1")
        password2 = self.cleaned_data.get("password2")
        if password1 and password2 and password1 != password2:
            msg = "Passwords don't match"
            raise forms.ValidationError("Password mismatch")
        return password2

    def save(self, commit=True):
        user = User(username=self.cleaned_data['username'],
                    first_name=self.cleaned_data['first_name'],
                    last_name=self.cleaned_data['last_name'],
                    email=self.cleaned_data['email'])
        user.save()
        # user = super(UserCreationForm, self).save(commit=False)
        user.set_password(self.cleaned_data["password1"])
        user_profile = super(self).save()
        if commit:
            user.save()
            user_profile.save()
        return user

如果有必要,这是模型:

class UserProfile(models.Model):
    # ATRIBUTY KTORE BUDE MAT KAZDY
    user = models.OneToOneField(User, on_delete=models.CASCADE, related_name='user_profile')
    iban = models.CharField(max_length=40, blank=True,verbose_name='IBAN')
    telephone = models.CharField(max_length=40, null=True, blank=True)

    HOW_DO_YOU_KNOW_ABOUT_US_CHOICES = (
        ('coincidence', u'It was coincidence'),
        ('relative_or_friends', 'From my relatives or friends'),
    )
    how_do_you_know_about_us = models.CharField(max_length=40, choices=HOW_DO_YOU_KNOW_ABOUT_US_CHOICES, null=True,
                                                blank=True)

    MARITAL_STATUS_CHOICES = (
        ('single', 'Single'),
        ('married', 'Married'),
        ('separated', 'Separated'),
        ('divorced', 'Divorced'),
        ('widowed', 'Widowed'),
    )
    marital_status = models.CharField(max_length=40, choices=MARITAL_STATUS_CHOICES, null=True, blank=True)

    # TRANSLATORs ATTRIBUTES

    # jobs = models.Model(Job)

    language_tuples = models.ManyToManyField(LanguageTuple)

    rating = models.IntegerField(default=0)

    number_of_ratings = models.BigIntegerField(default=0)

    def __unicode__(self):
        return '{} {}'.format(self.user.first_name, self.user.last_name)

    def __str__(self):
        return '{} {}'.format(self.user.first_name, self.user.last_name)

1 个答案:

答案 0 :(得分:1)

首先,您不需要重新划分某些字段,例如usernameemail等... 这是一个带有save ovride的完整示例:

class RegisterForm(UserCreationForm):
    email = forms.EmailField()

    def __init__(self, *args, **kwargs):
        super(RegisterForm, self).__init__(*args, **kwargs)
        #self.error_class = BsErrorList

    def clean_email(self):
        email = self.cleaned_data["email"]

        try:
            User._default_manager.get(email__iexact=email)
        except User.DoesNotExist:
            return email
        raise forms.ValidationError(
            'A user with that email already exists',
            code='duplicate_email',
        )

    def save(self, commit=True):
        user = super(RegisterForm, self).save(commit=False)
        user.email = self.cleaned_data["email"]

        # Create user_profile here

        if commit:
            user.save()

        return user

修改:此解决方案重复使用django的User表单注册新的User,然后您必须创建自定义配置文件。