'Django complex multiform views
I am not that good in coding, so take me easy. I would like to create/update view with multiple models in a single form , but need to dynamically add second and third model (need formsets) form into the view. That could be achieved by javascript , by copy empty forms.
here is model structure, need it to be scalable, but lets stack with 3 models.
What I need
1)present parent and second 2)hit resolve button , which will send ajax and all form data then I proces validate and get additional data and that generate third forms 3)save everything back to database , with appropriate ForeigKeys between models
models.py
from django.db import models
class Parrent(models.Model):
data = models.CharField(max_length=30)
class Second(models.Model):
parent = models.ForeignKey(Parrent, on_delete=models.CASCADE)
data = models.CharField(max_length=30)
class Third(models.Model):
second = models.ForeignKey(Second, on_delete=models.CASCADE)
data = models.CharField(max_length=30)
forms.py
from django.forms import ModelForm
from myapp.models import Parrent, Second, Third
class ParrentForm(ModelForm):
class Meta:
model = Parrent
fields = ['data']
class SecondForm(ModelForm):
class Meta:
model = Second
fields = ['data']
class ThirdForm(ModelForm):
class Meta:
model = Third
fields = ['data']
SecondFormSet = formset_factory(SecondForm, extra=1)
ThirdFormSet = formset_factory(ThirdForm, extra=1)
template.html
<!-- [ Template form second] start -->
<div id='template-second-form' class="card-body table-border-style hidden">
{{ forms.second}}
<br>
<button type="button" class="btn btn-danger delete_btn">Remove</button>
</div>
<!-- [ Template volume ] end -->
<!-- [ repeated for the third ] end -->
<!-- [ FORM ] start -->
<form id='multi-form' method="post">{% csrf_token %}
<div class="card-body table-border-style">
{{ forms.parrent}}
</div>
<!-- [ Second list ] start -->
<div id='second-list'>
<!-- [ list all second elements here (javascript) ] -->
</div>
<!-- [ Second list ] end -->
<div class="card-body table-border-style">
<button id='add-second'type="button" class="btn btn-primary">Add second</button>
<button id='resolve'type="button" class="btn btn-info">Resolve</button>
</div>
test.js
const addNewSecondBtn= document.getElementById('add-second')
addNewSecondBtn.addEventListener('click', add_new_second_form)
function add_new_second_form(event) {
if (event) {
event.preventDefault()
}
// add new empty form element to html form
const emptySecondFormEl = document.getElementById('template-second-form').cloneNode(true)
emptySecondFormEl.classList.remove('hidden')
const VolumeListEl = document.getElementById('second-list')
VolumeListEl.append(emptyVolumeFormEl)
}
document.addEventListener('click', ({target: btn})=>{
btn.matches('.delete_btn') && btn.parentNode.remove()
}, false);
$(document).ready(function() {
$("#resolve").click(function () {
var serialData = $("#multi_form").serializeArray()
serialData = JSON.stringify(serialData);
console.log(serialData)
$.ajax({
type: "GET",
url: "/ajax/resolve/",
data: {
serialData: serialData,
},
success: function () {
console.log("done");
},
error: function () {
console.log("error");
},
});// & ajax
});
}) //$ doc ready func
I would like to use class based view, I have browsed generic views , but seems to be not sane enought to understand what function I have to manually edit in order to get it work. Also checked some third party modules like better-forms -> not sure how to fit formsets inside and seems to be outdated (running django4) and multiform -> treat forms separately I need single form. Crypsi forms looks just for styling. I was looking at inline formset but not sure how to fit more then two models as there is always example only for two.
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|
