I'm trying to adopt 'extra-views' as an advanced means of handling formsets, and want to have a link on each row of my formset template to redirect to a relevant object-based page, for which I need the initial value of that object's id
field as url parameter.
Here's the view:
from extra_views import ModelFormSetView
from .models import Course
class CourseFormSetView(ModelFormSetView):
model = Course
fields = ['id', 'ceName', 'ceExtName', 'ceDuration']
template_name = 'course_view.html'
factory_kwargs = {'extra': 1, 'max_num': None, 'can_order': False, 'can_delete': True}
Here's the relevant section of the template:
<form method="post">
{% csrf_token %}
{% for form in formset %}
<p>{{ form.ceName }} {{ form.ceExtName }} {{ form.DELETE }} <a href="{% url 'booksys:coursesetup_view' 1 %}" class="btn btn-info" role="button">Edit</a></p>
{% endfor %}
{{ formset.management_form }}
<input type="submit" value="Submit" />
</form>
For url parameter, I've tried {{ form.fields.id.value }}
but it doesn't render into the template at all, and {{ form.id }}
which renders as a hidden field but won't work with the url template directive and the template rendering then fails.
Any help much appreciated.
I worked out the answer to this, and I think it is useful enough to share:
Since form.id
is a hidden field, my template url needs to include form.id.value
in order to properly render and bind into the url part of the template.
With 'extra': 1
in my factory_kwargs
, I needed it to read form.id.value|default_if_none:0
and then handle the special case of zero for kwargs['pk'] in the linked view, since otherwise for new formset rows this field reads None
.
The relevant portion of my template now reads:
<form method="post">
{% csrf_token %}
{% for form in formset %}
<p>{{ form.ceName }} {{ form.ceExtName }} {{ form.DELETE }} <a href="{% url 'booksys:coursesetup_view' form.id.value|default_if_none:0 %}" class="btn btn-info" role="button">Edit</a></p>
{% endfor %}
{{ formset.management_form }}
<input type="submit" value="Submit" />
</form>