模型表单中的订单字段用户和个人资料并使用表单模板

时间:2018-04-18 00:56:32

标签: django forms

我发布了this question,但我无法获得提供的解决方案。我没有编辑,而是使用修改后的代码发布一个新的代码,该代码使用不同的方法(使用两种模型形式)

models.py

class Profile(models.Model):
    user = models.OneToOneField(User, on_delete=models.CASCADE, related_name='profile')
    location = models.CharField(max_length=30, blank=True)
    birth_date = models.DateField(null=True, blank=True)

    def __str__(self):
        return self.user.username



def create_profile(sender, **kwargs):
    user = kwargs["instance"]
    if kwargs["created"]:
        user_profile= Profile(user=user)
        user_profile.save()
post_save.connect(create_profile, sender=User)

forms.py

from django_superform import FormField, SuperForm

class SignUpForm(UserCreationForm):
    password1 = forms.CharField(label=("Password"), widget=forms.PasswordInput) 
    password2 = forms.CharField(label=("Confirm password"), widget=forms.PasswordInput)

    class Meta:
        model = User
        fields = ('username', 'first_name', 'last_name', 'email')
        labels = {
            'username': ('Capser name'),
        }

class ProfileForm(forms.ModelForm):
    class Meta:
        model = Profile
        fields = ('location', 'birth_date')


class SuperProfile(SuperForm):
    signupform = FormField(SignUpForm)
    profileform = FormField(ProfileForm)

看到我使用Django-superform包中的Superform。这样做的原因是我在我的html模板中使用了表单模板,稍后将在模板部分中进行说明。

模板

html页面模板:registration_form.html

<form class="form-horizontal" action="" method="POST" enctype="multipart/form-data">
    {% csrf_token %}

    <h1>Create a capser account</h1>
    <table border="1">
        {{  userform.as_table }}

        {{ profileform.as_table }}
    </table>

    {% include 'home/form-template.html' %}

    <div class="form-group">
        <div class="col-sm-offset-2 col-sm-10">
            <button type="submit" class="btn btn-success">Create account</button>
        </div>
    </div>
</form>

表单模板:form-template.html

{% if messages %}
<ul>
    {% for message in messages %}
    <li>{{ message }}</li>
    {% endfor %}
</ul>
{% endif %}

{% for field in form %}
    <div class="form-group">
        <div class="col-sm-offset-2 col-sm-10">
            <span class="text-danger small">{{ field.errors }}</span>
        </div>
        <label class="control-label col-sm-2">{{ field.label_tag }}</label>
        <div class="col-sm-10">{{ field }}</div>
        <div class="col-sm-offset-2 col-sm-10">
                <span class="text-danger small">{{ field.help_text }}</span>
        </div>
    </div>

{% endfor %}

和使用新方法的views.py(从两个模型表单中导入字段

views.py

class UserFormView(View):
    Userform_class = SignUpForm
    Profileform_class = ProfileForm
    template_name = 'home/registration_form.html'

    #display a blank form
    def get(self, request):
        userform = self.Userform_class(None)
        profileform=self.Profileform_class(None)

        return render (request, self.template_name, {'userform': userform, 'profileform': profileform})

    #process form data
    def post(self, request):
        userform = self.Userform_class(request.POST)
        profileform = self.Profileform_class(request.POST)


        if userform.is_valid() and profileform.is_valid():
            user = userform.save(commit=False)
            #user.refresh_from_db()  # load the profile instance created by the signal
            password = userform.cleaned_data['password1']
            user.set_password(password)
            username = userform.cleaned_data['username']
            first_name=userform.cleaned_data['first_name']
            last_name=userform.cleaned_data['last_name']
            email = userform.cleaned_data['email']
            user.save()

            new_profile = user_profile.objects.get(user = request.user)
            new_profile.objects.create(
                user=user,
                location=profileform.cleaned_data.get('location'),
                birth_date=profileform.cleaned_data.get('birth_date'))
            new_profile.save()

            #return user objects if credentials are correct
            user = authenticate(username=username, password=password)

            if user is not None:
                if user.is_active:
                    login(request, user)
                    return redirect('home:home')

        return render (request, self.template_name, {'userform': userform, 'profileform':profileform})

现在,当我提交表单时,出现以下错误:name 'user_profile' is not defined

我认为user_profil e是我model.py文件末尾创建的实例。 因此,如果这样做不起作用,我该如何在视图中调用我的Profile模型的实例?

我已经尝试了很多解决方案,到目前为止都没有。

另外,我最初想使用我的表单模板以便在html页面上显示我的表单,但是现在我使用了两个模型表单userform和profileform,我想知道如何使用我的表单模板(我尝试过Superform没有成功)。

1 个答案:

答案 0 :(得分:1)

错误表明它本身,user_profile未定义。 您的视图中的部分代码不正确。 您应该处理Django用户模型,并在创建实例后,从您的Profile

中调用由OneToOneField链接到用户的模型your_app.models
from your_app.models import Profile

''' codes here '''
username = userform.cleaned_data['username']
first_name=userform.cleaned_data['first_name']
last_name=userform.cleaned_data['last_name']
email = userform.cleaned_data['email']
user.last_name = last_name
user.first_name = first_name
user.username = username
user.email = email
user.save()

new_profile = Profile.objects.create(
    user=user,
    location=profileform.cleaned_data.get('location'),
    birth_date=profileform.cleaned_data.get('birth_date')
)
new_profile.save()

该问题 UNIQUE约束失败:home_profile.user_id 是因为post_save调用了信号new_profile.save()。调用它时,它会创建另一个具有相同user的个人资料,而当user调用new_profile.save()OneToOneField() User时,Sys.setenv('JAVA_HOME' = 'C:/Program Files (x86)/Java/jre1.8.0_161/') 已与个人资料相关联}}。所以只需删除信号