Skip to content
This repository was archived by the owner on Jan 20, 2022. It is now read-only.
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion aldryn_forms/__init__.py
Original file line number Diff line number Diff line change
@@ -1 +1 @@
__version__ = '6.2.1'
__version__ = '6.2.2'
2 changes: 1 addition & 1 deletion aldryn_forms/action_backends.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import logging

from django.utils.translation import ugettext_lazy as _
from django.utils.translation import gettext_lazy as _

from .action_backends_base import BaseAction

Expand Down
6 changes: 3 additions & 3 deletions aldryn_forms/admin/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
from django.contrib import admin
from django.template.loader import render_to_string
from django.urls import reverse
from django.utils.translation import ugettext_lazy as _
from django.utils.translation import gettext_lazy as _


str_dunder_method = '__str__'
Expand Down Expand Up @@ -51,11 +51,11 @@ def get_recipients_for_display(self, obj):
get_recipients_for_display.short_description = _('people notified')

def get_urls(self):
from django.conf.urls import url
from django.urls import re_path

def pattern(regex, fn, name):
args = [regex, self.admin_site.admin_view(fn)]
return url(*args, name=self.get_admin_url(name))
return re_path(*args, name=self.get_admin_url(name))

url_patterns = [
pattern(r'export/$', self.get_form_export_view(), 'export'),
Expand Down
6 changes: 3 additions & 3 deletions aldryn_forms/admin/forms.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@
from django.contrib.admin.widgets import AdminDateWidget
from django.utils import timezone
from django.utils.text import slugify
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
from django.utils.translation import gettext
from django.utils.translation import gettext_lazy as _

from ..models import FormSubmission
from .exporter import Exporter
Expand Down Expand Up @@ -129,6 +129,6 @@ def clean(self):
fields = self.get_fields()

if not fields:
message = ugettext('Please select at least one field to export.')
message = gettext('Please select at least one field to export.')
raise forms.ValidationError(message)
return self.cleaned_data
4 changes: 2 additions & 2 deletions aldryn_forms/admin/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
from django.contrib import messages
from django.http import HttpResponse
from django.shortcuts import redirect
from django.utils.translation import get_language_from_request, ugettext
from django.utils.translation import get_language_from_request, gettext

from ..compat import SessionWizardView
from .exporter import Exporter
Expand Down Expand Up @@ -65,7 +65,7 @@ def render_next_step(self, form, **kwargs):

if next_step == self.steps.last and not form.get_queryset().exists():
self.storage.reset()
self.admin.message_user(self.request, ugettext("No records found"), level=messages.WARNING)
self.admin.message_user(self.request, gettext("No records found"), level=messages.WARNING)
export_url = 'admin:{}'.format(self.admin.get_admin_url('export'))
return redirect(export_url)
return super(FormExportWizardView, self).render_next_step(form, **kwargs)
Expand Down
2 changes: 1 addition & 1 deletion aldryn_forms/cms_apps.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
from django.utils.translation import ugettext_lazy as _
from django.utils.translation import gettext_lazy as _

from cms.app_base import CMSApp
from cms.apphook_pool import apphook_pool
Expand Down
102 changes: 65 additions & 37 deletions aldryn_forms/cms_plugins.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
import io
from typing import Dict

from PIL import Image
from django.core.files.uploadedfile import InMemoryUploadedFile

from aldryn_forms.models import FormPlugin
from cms.plugin_base import CMSPluginBase
from cms.plugin_pool import plugin_pool
Expand All @@ -9,8 +12,8 @@
from django.core.validators import MinLengthValidator
from django.db.models import query
from django.template.loader import select_template
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
from django.utils.translation import gettext
from django.utils.translation import gettext_lazy as _
from emailit.api import send_mail
from filer.models import filemodels
from filer.models import imagemodels
Expand All @@ -32,15 +35,17 @@
from .forms import TextAreaFieldForm
from .forms import TextFieldForm
from .helpers import get_user_name
from .models import FileUploadFieldPlugin
from .models import SerializedFormField
from .signals import form_post_save
from .signals import form_pre_save
from .sizefield.utils import filesizeformat
from .utils import get_action_backends
from .validators import MaxChoicesValidator
from .validators import MinChoicesValidator
from .validators import is_valid_recipient
from .validators import (
MaxChoicesValidator,
MinChoicesValidator,
is_valid_recipient,
generate_file_extension_validator,
)


class FormElement(CMSPluginBase):
Expand Down Expand Up @@ -286,7 +291,7 @@ class Field(FormElement):

def serialize_value(self, instance, value, is_confirmation=False):
if isinstance(value, query.QuerySet):
value = u', '.join(map(str, value))
value = ', '.join(map(str, value))
elif value is None:
value = '-'
return str(value)
Expand Down Expand Up @@ -543,9 +548,9 @@ class EmailField(BaseTextField):
form_field_widget = forms.EmailInput
form_field_widget_input_type = 'email'
fieldset_advanced_fields = [
'email_send_notification',
'email_subject',
'email_body',
"email_send_notification",
"email_subject",
"email_body",
] + Field.fieldset_advanced_fields
email_template_base = 'aldryn_forms/emails/user/notification'

Expand Down Expand Up @@ -586,11 +591,14 @@ class FileField(Field):
'validators',
]
fieldset_general_fields = [
'upload_to',
"upload_to",
] + Field.fieldset_general_fields
fieldset_advanced_fields = [
'store_to_filer',
'help_text',
'max_size',
'allowed_extensions',
'invalid_extension_message',
'required_message',
'custom_classes',
]
Expand All @@ -602,52 +610,70 @@ def get_form_field_kwargs(self, instance):
kwargs['help_text'] = kwargs['help_text'].replace(
'MAXSIZE', filesizeformat(instance.max_size))
kwargs['max_size'] = instance.max_size
if instance.allowed_extensions:
kwargs['allowed_extensions'] = instance.allowed_extensions
return kwargs

def get_form_field_validators(self, instance: models.FileFieldPluginBase):
validators = super().get_form_field_validators(instance)
validators.append(
generate_file_extension_validator(
instance.allowed_extensions, instance.invalid_extension_message
)
)
return validators

def serialize_value(self, instance, value, is_confirmation=False):
if value:
if value and hasattr(value, "absolute_uri"):
return value.absolute_uri
else:
return '-'

def form_pre_save(self, instance, form, **kwargs):
def form_pre_save(self, instance: models.FileUploadFieldPlugin, form, **kwargs):
"""Save the uploaded file to django-filer

The type of model (file or image) is automatically chosen by trying to
open the uploaded file.
"""

request = kwargs['request']

field_name = form.form_plugin.get_form_field_name(field=instance)

uploaded_file = form.cleaned_data[field_name]
uploaded_file: InMemoryUploadedFile = form.cleaned_data[field_name]
copy = io.BytesIO(uploaded_file.read())
uploaded_file.seek(0)

if uploaded_file is None:
return

try:
with Image.open(uploaded_file) as img:
img.verify()
except: # noqa
model = filemodels.File
else:
model = imagemodels.Image

filer_file = model(
folder=instance.upload_to,
file=uploaded_file,
name=uploaded_file.name,
original_filename=uploaded_file.name,
is_public=True,
)
filer_file.save()
if instance.store_to_filer:
try:
with Image.open(uploaded_file) as img:
img.verify()
except: # noqa
model = filemodels.File
else:
model = imagemodels.Image

filer_file = model(
folder=instance.upload_to,
file=uploaded_file,
name=uploaded_file.name,
original_filename=uploaded_file.name,
is_public=True,
)
filer_file.save()

# NOTE: This is a hack to make the full URL available later when we
# need to serialize this field. We avoid to serialize it here directly
# as we could still need access to the original filer File instance.
filer_file.absolute_uri = request.build_absolute_uri(filer_file.url)

# NOTE: This is a hack to make the full URL available later when we
# need to serialize this field. We avoid to serialize it here directly
# as we could still need access to the original filer File instance.
filer_file.absolute_uri = request.build_absolute_uri(filer_file.url)
form.cleaned_data[field_name] = filer_file

form.cleaned_data[field_name] = filer_file
uploaded_file.close()
form.cleaned_data[f"{field_name}__in_memory"] = {"name": uploaded_file.name, "file": copy}


class ImageField(FileField):
Expand All @@ -658,9 +684,10 @@ class ImageField(FileField):
form_field = RestrictedImageField
form_field_widget = RestrictedImageField.widget
fieldset_general_fields = [
'upload_to',
"upload_to",
] + Field.fieldset_general_fields
fieldset_advanced_fields = [
'store_to_filer',
'help_text',
'max_size',
('max_width', 'max_height',),
Expand Down Expand Up @@ -713,7 +740,7 @@ class BooleanField(Field):
]

def serialize_value(self, instance, value, is_confirmation=False):
return ugettext('Yes') if value else ugettext('No')
return gettext('Yes') if value else gettext('No')


class SelectOptionInline(TabularInline):
Expand Down Expand Up @@ -859,6 +886,7 @@ def serialize_field(self, *args, **kwargs):
# None means don't serialize me
return None


plugin_pool.register_plugin(CaptchaField)


Expand Down
65 changes: 49 additions & 16 deletions aldryn_forms/contrib/email_notifications/cms_plugins.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,9 @@
from django.contrib import admin
from django.core.mail import get_connection
from django.template.defaultfilters import safe
from django.utils.translation import ugettext_lazy as _

from django.utils.html import format_html
from django.utils.translation import gettext_lazy as _

from cms.plugin_pool import plugin_pool

Expand Down Expand Up @@ -43,23 +45,31 @@ class ExistingEmailNotificationInline(admin.StackedInline):
model = EmailNotification

fieldsets = (
(None, {
'fields': (
'theme',
)
}),
(_('Recipients'), {
'fields': (
'text_variables',
'to_user',
('to_name', 'to_email'),
('from_name', 'from_email'),
'reply_to_email',
)
}),
(None, {"fields": ("theme",)}),
(
_("Recipients"),
{
"fields": (
"text_variables",
"to_user",
("to_name", "to_email"),
("from_name", "from_email"),
"reply_to_email",
)
},
),
(
_("Attaching files to email"),
{
"fields": (
"file_variables",
"files_to_attach_to_email",
)
},
),
)

readonly_fields = ['text_variables']
readonly_fields = ['text_variables', 'file_variables']

text_variables_help_text = _(
'the variables can be used within the email body, email sender,'
Expand Down Expand Up @@ -120,6 +130,29 @@ def text_variables(self, obj: EmailNotification) -> str:
text_variables.allow_tags = True
text_variables.short_description = _('available text variables')

def file_variables(self, obj: EmailNotification) -> str:
if obj.pk is None:
return ''

# list of tuples - [('category', [('value', 'label')])]
choices_by_category = obj.form.get_notification_text_context_file_keys_as_choices()

var_items: List[str] = []
for category, choices in choices_by_category:
for choice_tuple in choices:
field_value = choice_tuple[0]
var_items += '<li>' + field_value + '</li>'

vars_html_list = f'<p>{"".join(var_items)}</p>'
help_text = (
f'<p class="help">'
f'{_("these are the valid file fields that can be attached to the email")}'
f'</p>'
)
return safe(vars_html_list + u'\n' + help_text)
file_variables.allow_tags = True
file_variables.short_description = _('available file variables')

class Media:
css = {
'all': ['email_notifications/admin/email-notifications.css']
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
# Generated by Django 4.2.4 on 2023-08-20 15:56

from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
("email_notifications", "0005_add_field_reply_to_email"),
]

operations = [
migrations.AlterField(
model_name="emailnotification",
name="id",
field=models.BigAutoField(
auto_created=True, primary_key=True, serialize=False, verbose_name="ID"
),
),
]
Loading