error reporting
[redakcja.git] / apps / forms_builder / forms / views.py
1 from __future__ import unicode_literals
2
3 import json
4
5 from django.conf import settings
6 from django.contrib.auth import REDIRECT_FIELD_NAME
7 from django.core.urlresolvers import reverse
8 from django.http import HttpResponse
9 from django.shortcuts import get_object_or_404, redirect, render_to_response
10 from django.template import RequestContext
11 from django.utils.http import urlquote
12 from django.views.generic.base import TemplateView
13 from email_extras.utils import send_mail_template
14
15 from forms_builder.forms.forms import FormForForm
16 from forms_builder.forms.models import Form
17 from forms_builder.forms.settings import EMAIL_FAIL_SILENTLY
18 from forms_builder.forms.signals import form_invalid, form_valid
19 from forms_builder.forms.utils import split_choices
20
21
22 class FormDetail(TemplateView):
23
24     template_name = "forms/form_detail.html"
25
26     def get_context_data(self, **kwargs):
27         context = super(FormDetail, self).get_context_data(**kwargs)
28         published = Form.objects.published(for_user=self.request.user)
29         context["form"] = get_object_or_404(published, slug=kwargs["slug"])
30         return context
31
32     def get(self, request, *args, **kwargs):
33         context = self.get_context_data(**kwargs)
34         login_required = context["form"].login_required
35         if login_required and not request.user.is_authenticated():
36             path = urlquote(request.get_full_path())
37             bits = (settings.LOGIN_URL, REDIRECT_FIELD_NAME, path)
38             return redirect("%s?%s=%s" % bits)
39         return self.render_to_response(context)
40
41     def post(self, request, *args, **kwargs):
42         published = Form.objects.published(for_user=request.user)
43         form = get_object_or_404(published, slug=kwargs["slug"])
44         form_for_form = FormForForm(form, RequestContext(request),
45                                     request.POST or None,
46                                     request.FILES or None)
47         if not form_for_form.is_valid():
48             form_invalid.send(sender=request, form=form_for_form)
49         else:
50             # Attachments read must occur before model save,
51             # or seek() will fail on large uploads.
52             attachments = []
53             for f in form_for_form.files.values():
54                 f.seek(0)
55                 attachments.append((f.name, f.read()))
56             entry = form_for_form.save()
57             form_valid.send(sender=request, form=form_for_form, entry=entry)
58             self.send_emails(request, form_for_form, form, entry, attachments)
59             if not self.request.is_ajax():
60                 return redirect(form.redirect_url or
61                     reverse("form_sent", kwargs={"slug": form.slug}))
62         context = {"form": form, "form_for_form": form_for_form}
63         return self.render_to_response(context)
64
65     def render_to_response(self, context, **kwargs):
66         if self.request.is_ajax():
67             json_context = json.dumps({
68                 "errors": context["form_for_form"].errors,
69                 "form": context["form_for_form"].as_p(),
70                 "message": context["form"].response,
71             })
72             return HttpResponse(json_context, content_type="application/json")
73         return super(FormDetail, self).render_to_response(context, **kwargs)
74
75     def send_emails(self, request, form_for_form, form, entry, attachments):
76         subject = form.email_subject
77         if not subject:
78             subject = "%s - %s" % (form.title, entry.entry_time)
79         fields = []
80         for (k, v) in form_for_form.fields.items():
81             value = form_for_form.cleaned_data[k]
82             if isinstance(value, list):
83                 value = ", ".join([i.strip() for i in value])
84             fields.append((v.label, value))
85         context = {
86             "fields": fields,
87             "message": form.email_message,
88             "request": request,
89         }
90         email_from = form.email_from or settings.DEFAULT_FROM_EMAIL
91         email_to = form_for_form.email_to()
92         if email_to and form.send_email:
93             send_mail_template(subject, "form_response", email_from,
94                                [email_to], context=context,
95                                fail_silently=EMAIL_FAIL_SILENTLY)
96         headers = None
97         if email_to:
98             headers = {"Reply-To": email_to}
99         email_copies = split_choices(form.email_copies)
100         if email_copies:
101             send_mail_template(subject, "form_response_copies", email_from,
102                                email_copies, context=context,
103                                attachments=attachments,
104                                fail_silently=EMAIL_FAIL_SILENTLY,
105                                headers=headers)
106
107 form_detail = FormDetail.as_view()
108
109
110 def form_sent(request, slug, template="forms/form_sent.html"):
111     """
112     Show the response message.
113     """
114     published = Form.objects.published(for_user=request.user)
115     context = {"form": get_object_or_404(published, slug=slug)}
116     return render_to_response(template, context, RequestContext(request))