-
-
Save teacherSsamko/8d079a6a03836147020d0cbe60ea38da to your computer and use it in GitHub Desktop.
Django multiple forms code with sample usage
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
{% extends "base.html" %} | |
{% block content %} | |
<form method="post">{% csrf_token %} | |
{{ forms.subscription }} | |
<input type="submit" value="Subscribe"> | |
</form> | |
<form method="post">{% csrf_token %} | |
{{ forms.contact }} | |
<input type="submit" value="Send"> | |
</form> | |
{% endblock content %} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from django import forms | |
class MultipleForm(forms.Form): | |
action = forms.CharField(max_length=60, widget=forms.HiddenInput()) | |
class ContactForm(MultipleForm): | |
title = forms.CharField(max_length=150) | |
message = forms.CharField(max_length=200, widget=forms.TextInput) | |
class SubscriptionForm(MultipleForm): | |
email = forms.EmailField() |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from django.views.generic.base import ContextMixin, TemplateResponseMixin | |
from django.views.generic.edit import ProcessFormView | |
class MultiFormMixin(ContextMixin): | |
form_classes = {} | |
prefixes = {} | |
success_urls = {} | |
initial = {} | |
prefix = None | |
success_url = None | |
def get_form_classes(self): | |
return self.form_classes | |
def get_forms(self, form_classes): | |
return dict([(key, self._create_form(key, class_name)) \ | |
for key, class_name in form_classes.items()]) | |
def get_form_kwargs(self, form_name): | |
kwargs = {} | |
kwargs.update({'initial':self.get_initial(form_name)}) | |
kwargs.update({'prefix':self.get_prefix(form_name)}) | |
if self.request.method in ('POST', 'PUT'): | |
kwargs.update({ | |
'data': self.request.POST, | |
'files': self.request.FILES, | |
}) | |
return kwargs | |
def forms_valid(self, forms, form_name): | |
form_valid_method = '%s_form_valid' % form_name | |
if hasattr(self, form_valid_method): | |
return getattr(self, form_valid_method)(forms[form_name]) | |
else: | |
return HttpResponseRedirect(self.get_success_url(form_name)) | |
def forms_invalid(self, forms): | |
return self.render_to_response(self.get_context_data(forms=forms)) | |
def get_initial(self, form_name): | |
initial_method = 'get_%s_initial' % form_name | |
if hasattr(self, initial_method): | |
return getattr(self, initial_method)() | |
else: | |
return {'action': form_name} | |
def get_prefix(self, form_name): | |
return self.prefixes.get(form_name, self.prefix) | |
def get_success_url(self, form_name=None): | |
return self.success_urls.get(form_name, self.success_url) | |
def _create_form(self, form_name, form_class): | |
form_kwargs = self.get_form_kwargs(form_name) | |
form = form_class(**form_kwargs) | |
return form | |
class ProcessMultipleFormsView(ProcessFormView): | |
def get(self, request, *args, **kwargs): | |
form_classes = self.get_form_classes() | |
forms = self.get_forms(form_classes) | |
return self.render_to_response(self.get_context_data(forms=forms)) | |
def post(self, request, *args, **kwargs): | |
form_classes = self.get_form_classes() | |
form_name = request.POST.get('action') | |
return self._process_individual_form(form_name, form_classes) | |
def _process_individual_form(self, form_name, form_classes): | |
forms = self.get_forms(form_classes) | |
form = forms.get(form_name) | |
if not form: | |
return HttpResponseForbidden() | |
elif form.is_valid(): | |
return self.forms_valid(forms, form_name) | |
else: | |
return self.forms_invalid(forms) | |
class BaseMultipleFormsView(MultiFormMixin, ProcessMultipleFormsView): | |
""" | |
A base view for displaying several forms. | |
""" | |
class MultiFormsView(TemplateResponseMixin, BaseMultipleFormsView): | |
""" | |
A view for displaying several forms, and rendering a template response. | |
""" |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from django.http import HttpResponse, HttpResponseRedirect | |
from django.shortcuts import render | |
from django.urls import reverse, reverse_lazy | |
from .forms import ContactForm, SubscriptionForm | |
from .multiforms import MultiFormsView | |
def form_redir(request): | |
return render(request, 'pages/form_redirect.html') | |
def multiple_forms(request): | |
if request.method == 'POST': | |
contact_form = ContactForm(request.POST) | |
subscription_form = SubscriptionForm(request.POST) | |
if contact_form.is_valid() or subscription_form.is_valid(): | |
# Do the needful | |
return HttpResponseRedirect(reverse('form-redirect') ) | |
else: | |
contact_form = ContactForm() | |
subscription_form = SubscriptionForm() | |
return render(request, 'pages/multiple_forms.html', { | |
'contact_form': contact_form, | |
'subscription_form': subscription_form, | |
}) | |
class MultipleFormsDemoView(MultiFormsView): | |
template_name = "pages/cbv_multiple_forms.html" | |
form_classes = {'contact': ContactForm, | |
'subscription': SubscriptionForm, | |
} | |
success_urls = { | |
'contact': reverse_lazy('form-redirect'), | |
'subscription': reverse_lazy('form-redirect'), | |
} | |
def contact_form_valid(self, form): | |
title = form.cleaned_data.get('title') | |
form_name = form.cleaned_data.get('action') | |
print(title) | |
return HttpResponseRedirect(self.get_success_url(form_name)) | |
def subscription_form_valid(self, form): | |
email = form.cleaned_data.get('email') | |
form_name = form.cleaned_data.get('action') | |
print(email) | |
return HttpResponseRedirect(self.get_success_url(form_name)) | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment