I am trying to create a page where various data corresponding to mutliple models can be input by the user, and to have an option to dynamically add additional forms. I have been attempting to use htmx for this and am able to dynamically add forms, however when I save it is only the last entered form that is saved. I haven't used formsets as this wont integrate well with htmx https://justdjango.com/blog/dynamic-forms-in-django-htmx#django-formsets-vs-htmx.
Code below any suggestion as to how to get all the dynamically created forms to be save would be most appreciated!
models.py
from django.db import models
class Author(models.Model):
name = models.CharField(max_length=50)
class Book(models.Model):
author = models.ForeignKey(Author, on_delete=models.CASCADE)
title = models.CharField(max_length=100)
forms.py
from django import forms
from .models import Book, Author
from crispy_forms.helper import FormHelper
class AuthorForm(forms.ModelForm):
class Meta:
model = Author
fields = ['name']
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.helper = FormHelper()
self.helper.form_id = 'id-CaseForm'
self.helper.form_class = 'blueForms'
self.helper.form_method = 'post'
self.helper.form_tag = False
class BookForm(forms.ModelForm):
class Meta:
model = Book
fields = ('title',)
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.helper = FormHelper()
self.helper.form_method = 'post'
self.helper.form_tag = False
self.helper.form_show_labels = False
views.py
class create_book(TemplateView):
template_name = 'create_book.html'
def get(self, *args, **kwargs):
author_form = AuthorForm
book_form = BookForm
return self.render_to_response(
{'book_form': BookForm,
"author_form": AuthorForm,}
)
def post(self, *args, **kwargs):
author_form = AuthorForm(data=self.request.POST)
book_form = BookForm(data=self.request.POST)
if author_form.is_valid():
author = author_form.save()
if book_form.is_valid():
book = book_form.save(commit=False)
book.author = author
book.save()
def create_book_form(request):
form = BookForm()
context = {
"form": form
}
return render(request, "partials/book_form.html", context)
urls.py
urlpatterns = [
path('create_book/', create_book.as_view(), name='create-book'),
path('htmx/create-book-form/', create_book_form, name='create-book-form'),]
create_book.html
{% extends "base.html" %}
{% block content %}
{% load crispy_forms_tags %}
<form class="blueForms" id="id-CaseForm" method="post" >
{% crispy author_form %}
{% crispy book_form %}
<button type="button" hx-get="{% url 'create-book-form' %}" hx-target="#bookforms" hx-swap="beforeend">
Add book form
</button>
<div id="bookforms"></div>
</form>
partials/book_form.html
{% load crispy_forms_tags %}
<div hx-target="this" hx-swap="outerHTML">
{% csrf_token %}
{% crispy form %}
{{ form.management_form }}
</div>