如何使唯一 = true 的外键在 Django 中成为“可选”?

Posted

技术标签:

【中文标题】如何使唯一 = true 的外键在 Django 中成为“可选”?【英文标题】:How to make a Foreign Key with unique=true to be "optional" in Django? 【发布时间】:2012-08-09 01:46:02 【问题描述】:

我有一个用户模型(由 Django 预定义)和一个通过 ForeignKey 连接的 UserProfile 模型。

我正在创建两个单独的 ModelForm 以在单个模板中用作各种注册表单。

models.py

class UserProfile(models.Model):
    # This field is required.
    user = models.ForeignKey(User, unique=True, related_name="connector")
    location = models.CharField(max_length=20, blank=True, null=True)

forms.py

class UserForm(ModelForm):
    class Meta:
        model = User

class UserProfileForm(ModelForm):
    class Meta:
        model = UserProfile

但是,当我加载页面并填写表单信息时,UserProfileForm 要求我选择/填写用户字段以进行验证。

但是,此“用户”是当前正在创建的用户,因此我无法选择“用户”,因为它尚未创建/仍在创建中。

我知道此用户的字段具有属性 unique=true 但有办法使此字段为“可选”吗?

我的视图(如下)应该处理它,以便在创建用户对象后,我会将 UserProfile 的外键设置为这个新创建的用户对象(除非我的 views.py 也做错了什么)。

views.py

@csrf_protect
def register(request):
    if request.method == 'POST':
        form1 = UserForm(request.POST)
        form2 = UserProfileForm(request.POST)
        if form1.is_valid() and form2.is_valid():
            #create initial entry for user
            username = form1.cleaned_data["username"]
            password = form1.cleaned_data["password"]
            new_user = User.objects.create_user(username, password)
            new_user.save()

            #create entry for UserProfile (extension of new_user object)      
            profile = form2.save(commit = False)
            profile.user = new_user
            profile.save()
            return HttpResponseRedirect("/books/")
    else:
        form1 = UserForm()
        form2 = UserProfileForm()
    c = 
        'form1':form1,
        'form2':form2,
    
    c.update(csrf(request))
    return render_to_response("registration/register.html", c)

【问题讨论】:

【参考方案1】:

你可以设置:

user = models.ForeignKey(User, unique=True, blank=True, null=True, related_name="connector")

这将使用户关系成为可选的,但我认为这不是您所需要的。相反,为什么不从UserProfile 表单中删除user 字段并手动分配它,而不是让用户看到下拉列表。那么就不会有验证错误了。

class UserProfileForm(ModelForm):
    class Meta:
        model = UserProfile
        exclude = ("user", )

【讨论】:

【参考方案2】:

只需从表单中排除该字段。

class UserProfileForm(ModelForm):
  class Meta:
    model = UserProfile
    exclude = ('user',)

【讨论】:

以上是关于如何使唯一 = true 的外键在 Django 中成为“可选”?的主要内容,如果未能解决你的问题,请参考以下文章

java - 如何根据Java Servlet中的外键在一列中显示多个值?

如何遍历 Django 字典中的外键?

如何从 Django 模板中的外键访问值

如何在Django中加入非主键和外键列的查询

django bulk_create 查询中的外键关系?

Django 之 ORM表之间的外键关联与多对多