Как использовать экземпляры формы модели formset в шаблоне Django
Я пытаюсь получить доступ к экземплярам форм в наборе форм, но это не работает. Я могу получить к ним доступ, используя нотацию переменной, как в {{ form }}, но не в коде, как в {% url 'section' form.instance.pk %}. Мне нужно перебирать формы в наборе форм вместе с соответствующим экземпляром модели
Мое мнение:
# views.py
def sec(request, companyurl):
company = get_if_exists(Company, author=request.user)
SectionFormSet = modelformset_factory(Section, form=SectionForm, can_delete=True)
sections = Section.objects.filter(company=company).order_by('order')
formset = SectionFormSet(request.POST or None,
initial=[{'company': company}],
queryset=sections
context = {
'sections': sections,
'formset': formset,
}
return render(request, 'questions/sections.html', context)
Моя модель:
# models.py
class Section(models.Model):
section = models.CharField(max_length=100)
company = models.ForeignKey(Company, on_delete=models.CASCADE)
order = models.PositiveIntegerField(default=1000000)
show = models.BooleanField(default=True)
def __str__(self):
return self.section
Моя форма (я использую django-crispy forms):
# forms.py
class SectionForm(forms.ModelForm):
class Meta:
model = Section
fields = ['company', 'section', 'show', 'order']
labels = {
'section': '',
'show': 'Show'
}
def __init__(self, *args, **kwargs):
super(SectionForm, self).__init__(*args, **kwargs)
self.helper = FormHelper()
self.helper.form_tag = False
self.helper.layout = Layout(
Div(
Div(HTML("##"), css_class = 'my-handle col-auto'),
Div('section', css_class='col-3'),
Div('show', css_class = 'col-auto'),
Div('DELETE', css_class = 'col-auto'),
Field('company', type='hidden'),
Field('order', type='hidden'),
css_class='row',
),
)
Мой шаблон ( именно в нем проявляется проблема):
<form action="#" method="post">
{% csrf_token %}
{{ formset.management_form }}
<div id="simpleList" class="list-group">
{% for fo in formset %}
<div class="list-group-item hold">
{% crispy fo %}
<!-- TESTING TO SEE IF THIS WORKS, AND IT DOES! -->
{{ fo.instance }} + {{ fo.instance.pk }} + {{ fo.instance.section }}
<!-- THE PROBLEM OCCRURS WHEN THIS IS ADDED -->
<a href="{% url 'section' fo.instance.pk fo.instance.section %}">
{{ fo.instance }}
</a>
<!-------------------------------------------->
<input type="hidden" name="order" value="{{ section.pk }}">
{% for hid in fo.hidden_fields %}
{{ hid }}
{% endfor %}
</div>
{% endfor %}
<button type="submit" class="btn btn-outline-primary">Save changes</button>
</form>
Когда я добавляю строку <a href="{% url 'section' fo.instance.pk fo.instance.section %}>link</a>, я получаю
Reverse for 'section' with arguments '(None, '')' not found. 1 pattern(s) tried: ['section/(?P<pk>[0-9]+)/(?P<section>[^/]+)\\Z']
Ошибка очевидна. fo.instance.pk - это None, а fo.instance.section - это пустая строка. Однако, когда я удаляю тег якоря, появляется строка выше и показывает правильные значения для обоих этих значений. Я думаю знаю разницу между {{ }} и {% %}, и я думал, что знаю, как экземпляры формы модели привязаны к модели, но я что-то упускаю.
Спасибо за любую помощь.
Наборы форм создают пустые формы
Ответ предстал передо мной, когда я распечатал результаты. Последняя форма, пустая, конечно выдавала мне None и пустую строку, так как у нее не было данных для заполнения. Таким образом, простым решением является проверка на это перед попыткой сформировать url с информацией. Таким образом, это не имеет никакого отношения ни к различиям между и {{ }}, ни к экземплярам форм.{% %}
{% for fo in formset %}
<div class="list-group-item hold">
{% crispy fo %}
<!-- TESTING TO SEE IF THIS WORKS, AND IT DOES! -->
{{ fo.instance }} + {{ fo.instance.pk }} + {{ fo.instance.section }}
<!-- THE PROBLEM OCCURED WHEN THIS WAS ADDED -->
<!-- THE SIMPLE SOLUTION: --------------------->
{% if fo.instance.pk %}
<a href="{% url 'section' fo.instance.pk fo.instance.section %}">
{{ fo.instance }}
</a>
{% endif %}
<!-------------------------------------------->
<input type="hidden" name="order" value="{{ section.pk }}">
{% for hid in fo.hidden_fields %}
{{ hid }}
{% endfor %}
</div>
{% endfor %}
<button type="submit" class="btn btn-outline-primary">Save changes</button>
</form>