使用 Initial 预填充 django 表单不起作用
Pre populating a django form using Initial not working
我正在尝试通过预填充 'template_name' 字段来保存模型。根据 django 文档和其他线程,很明显初始参数应该有效,但我不能让它适用于我的代码。我收到 template_name 字段为空的错误。任何关于我缺少什么的帮助以及任何其他方法都会很棒。这是代码
models.py
class TemplateNameModel(models.Model):
"Model to add the template name"
id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)
tna_template_name = models.CharField(verbose_name="Template name",max_length = 128, unique = True,
null = False, blank = False, help_text="please enter name of the new tna template")
description = models.CharField(verbose_name="template description", max_length = 256,
null = True, blank = True, help_text ="Please enter the description(optional)")
created_by = models.TextField(verbose_name="Template created by", max_length= 128,
null = False, blank = False,help_text ="Please enter the name of creator")
date_created = models.DateTimeField(auto_created= True, null = True, blank = True)
is_active = models.BooleanField(verbose_name="Template status",null = False , blank= False)
def __str__(self):
return self.tna_template_name
class TnaTemplateModel(models.Model):
id = models.AutoField(primary_key=True, editable=False)
template_name = models.ForeignKey(TemplateNameModel, verbose_name="template name", null=False,
blank=False, on_delete=models.CASCADE, help_text="Select the template")
process_name = models.ForeignKey(ProcessModel, verbose_name="process name", null=False,
blank=False, on_delete=models.CASCADE, help_text="Select the process")
sequence = models.IntegerField(verbose_name="Process Sequence",null = False,blank = False)
is_base = models.BooleanField()
formula = models.IntegerField(verbose_name="Formula", null= True,blank = True)
remarks = models.CharField(verbose_name="Process remarks", null= True, blank = True,max_length= 300)
class Meta:
unique_together = ["template_name", "process_name"]
def __str__(self):
return str(self.template_name)
forms.py
class ProcessModelformNew(forms.ModelForm):
class Meta:
model = TnaTemplateModel
fields =('__all__')
views.py
def processcreatenew(request,pk):
template_name = TemplateNameModel.objects.get(id=pk)
if request.method == 'POST':
form = ProcessModelformNew(request.POST)
if form.is_valid():
form.save()
else:
data = {'template_name': template_name}
form = ProcessModelformNew(initial= data)
return render (request,"tna/template_tna/baseprocessmodel_create.html",{'form':form})
Html 模板
<form role="form" method="POST" enctype="multipart/form-data">
{% csrf_token %}
<div class="card-body">
<div class="row">
<div class="col-md-6 col-sm-12">
<!-- text input -->
<div class="form-group">
{{form.process_name|as_crispy_field}}
</div>
</div>
</div>
<div class="row">
<div class="col-md-6 col-sm-12">
<!-- text input -->
<div class="form-group">
{{form.sequence|as_crispy_field}}
</div>
</div>
</div>
<div class="row">
<div class="col-md-6 col-sm-12">
<!-- text input -->
<div class="form-group">
{{form.is_base|as_crispy_field}}
</div>
</div>
<div class="col-md-6 col-sm-12">
<!-- text input -->
<div class="form-group">
{{form.formula|as_crispy_field}}
</div>
</div>
</div>
<div class="row">
<div class="col-md-6 col-sm-12">
<!-- text input -->
<div class="form-group">
{{form.remarks|as_crispy_field}}
</div>
</div>
</div>
</div>
<!-- /.card-body -->
<div class="card-footer">
<button type="submit" class="btn btn-primary">Save</button>
</div>
</form>
forms.py
def __init__(self, *args, **kwargs):
template_name = kwargs.pop('template_name',None)
self.fields['template_name']= template_name
views.py
在您的模型表单中
def processcreatenew(request,pk):
template_name = TemplateNameModel.objects.get(id=pk)
if request.method == 'POST':
form = ProcessModelformNew(request.POST or None, template_name= template_name)
你必须执行这样的操作
第一种方法
- 在您的 HTML 中包含
{{ form.template_name }}
即使您不想编辑它,也只是将其隐藏
第二种方法
- 在你的 forms.py 中你可以把
exclude = ['template_name']
代替 fields =('__all__')
这样它就不再需要了,然后在 views.py
obj = form.save(commit=False)
obj.template_name = template_name
obj.save()
- 所以如果你不想在 HTML 中包含 template_name 第二种方法很好,你也不必启动表单
您需要在模板中呈现 template_name 字段,以便将所选值传递到 POST 数据中。
{{ form.template_name }}
我怀疑您不想显示该字段,您应该用 forms.HiddenInput
覆盖它的小部件,这样用户就看不到它了
class ProcessModelformNew(forms.ModelForm):
class Meta:
model = TnaTemplateModel
fields = '__all__'
widgets = {'template_name': forms.HiddenInput()}
我正在尝试通过预填充 'template_name' 字段来保存模型。根据 django 文档和其他线程,很明显初始参数应该有效,但我不能让它适用于我的代码。我收到 template_name 字段为空的错误。任何关于我缺少什么的帮助以及任何其他方法都会很棒。这是代码
models.py
class TemplateNameModel(models.Model):
"Model to add the template name"
id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)
tna_template_name = models.CharField(verbose_name="Template name",max_length = 128, unique = True,
null = False, blank = False, help_text="please enter name of the new tna template")
description = models.CharField(verbose_name="template description", max_length = 256,
null = True, blank = True, help_text ="Please enter the description(optional)")
created_by = models.TextField(verbose_name="Template created by", max_length= 128,
null = False, blank = False,help_text ="Please enter the name of creator")
date_created = models.DateTimeField(auto_created= True, null = True, blank = True)
is_active = models.BooleanField(verbose_name="Template status",null = False , blank= False)
def __str__(self):
return self.tna_template_name
class TnaTemplateModel(models.Model):
id = models.AutoField(primary_key=True, editable=False)
template_name = models.ForeignKey(TemplateNameModel, verbose_name="template name", null=False,
blank=False, on_delete=models.CASCADE, help_text="Select the template")
process_name = models.ForeignKey(ProcessModel, verbose_name="process name", null=False,
blank=False, on_delete=models.CASCADE, help_text="Select the process")
sequence = models.IntegerField(verbose_name="Process Sequence",null = False,blank = False)
is_base = models.BooleanField()
formula = models.IntegerField(verbose_name="Formula", null= True,blank = True)
remarks = models.CharField(verbose_name="Process remarks", null= True, blank = True,max_length= 300)
class Meta:
unique_together = ["template_name", "process_name"]
def __str__(self):
return str(self.template_name)
forms.py
class ProcessModelformNew(forms.ModelForm):
class Meta:
model = TnaTemplateModel
fields =('__all__')
views.py
def processcreatenew(request,pk):
template_name = TemplateNameModel.objects.get(id=pk)
if request.method == 'POST':
form = ProcessModelformNew(request.POST)
if form.is_valid():
form.save()
else:
data = {'template_name': template_name}
form = ProcessModelformNew(initial= data)
return render (request,"tna/template_tna/baseprocessmodel_create.html",{'form':form})
Html 模板
<form role="form" method="POST" enctype="multipart/form-data">
{% csrf_token %}
<div class="card-body">
<div class="row">
<div class="col-md-6 col-sm-12">
<!-- text input -->
<div class="form-group">
{{form.process_name|as_crispy_field}}
</div>
</div>
</div>
<div class="row">
<div class="col-md-6 col-sm-12">
<!-- text input -->
<div class="form-group">
{{form.sequence|as_crispy_field}}
</div>
</div>
</div>
<div class="row">
<div class="col-md-6 col-sm-12">
<!-- text input -->
<div class="form-group">
{{form.is_base|as_crispy_field}}
</div>
</div>
<div class="col-md-6 col-sm-12">
<!-- text input -->
<div class="form-group">
{{form.formula|as_crispy_field}}
</div>
</div>
</div>
<div class="row">
<div class="col-md-6 col-sm-12">
<!-- text input -->
<div class="form-group">
{{form.remarks|as_crispy_field}}
</div>
</div>
</div>
</div>
<!-- /.card-body -->
<div class="card-footer">
<button type="submit" class="btn btn-primary">Save</button>
</div>
</form>
forms.py
def __init__(self, *args, **kwargs):
template_name = kwargs.pop('template_name',None)
self.fields['template_name']= template_name
views.py
在您的模型表单中
def processcreatenew(request,pk):
template_name = TemplateNameModel.objects.get(id=pk)
if request.method == 'POST':
form = ProcessModelformNew(request.POST or None, template_name= template_name)
你必须执行这样的操作
第一种方法
- 在您的 HTML 中包含
{{ form.template_name }}
即使您不想编辑它,也只是将其隐藏
第二种方法
- 在你的 forms.py 中你可以把
exclude = ['template_name']
代替fields =('__all__')
这样它就不再需要了,然后在 views.py
obj = form.save(commit=False)
obj.template_name = template_name
obj.save()
- 所以如果你不想在 HTML 中包含 template_name 第二种方法很好,你也不必启动表单
您需要在模板中呈现 template_name 字段,以便将所选值传递到 POST 数据中。
{{ form.template_name }}
我怀疑您不想显示该字段,您应该用 forms.HiddenInput
覆盖它的小部件,这样用户就看不到它了
class ProcessModelformNew(forms.ModelForm):
class Meta:
model = TnaTemplateModel
fields = '__all__'
widgets = {'template_name': forms.HiddenInput()}