Add a service fee per ticket sold

This commit is contained in:
Thomas Hollstegge 2019-05-20 14:54:27 +02:00 committed by Raphael Michel
parent 937651eb34
commit 315d6de155
3 changed files with 48 additions and 18 deletions

View file

@ -11,6 +11,7 @@ from pretix.base.signals import order_fee_calculation
from pretix.base.templatetags.money import money_filter
from pretix.control.signals import nav_event_settings
from pretix.presale.signals import fee_calculation_for_cart, front_page_top, order_meta_from_request
from pretix.presale.views import get_cart
@receiver(nav_event_settings, dispatch_uid='service_fee_nav_settings')
@ -26,7 +27,15 @@ def navbar_settings(sender, request, **kwargs):
}]
def get_fees(event, total, invoice_address, mod=''):
def get_fees(event, total, invoice_address, mod='', request=None, positions=[]):
if request is not None and not positions:
positions = get_cart(request)
positions = [pos for pos in positions if not pos.addon_to and pos.price != Decimal('0.00')]
fee_per_ticket = event.settings.get('service_fee_per_ticket' + mod, as_type=Decimal)
if mod and fee_per_ticket is None:
fee_per_ticket = event.settings.get('service_fee_per_ticket', as_type=Decimal)
fee_abs = event.settings.get('service_fee_abs' + mod, as_type=Decimal)
if mod and fee_abs is None:
fee_abs = event.settings.get('service_fee_abs', as_type=Decimal)
@ -35,11 +44,12 @@ def get_fees(event, total, invoice_address, mod=''):
if mod and fee_percent is None:
fee_percent = event.settings.get('service_fee_percent', as_type=Decimal)
fee_per_ticket = Decimal("0") if fee_per_ticket is None else fee_per_ticket
fee_abs = Decimal("0") if fee_abs is None else fee_abs
fee_percent = Decimal("0") if fee_percent is None else fee_percent
if (fee_abs or fee_percent) and total != Decimal('0.00'):
fee = round_decimal(fee_abs + total * (fee_percent / 100), event.currency)
if (fee_per_ticket or fee_abs or fee_percent) and total != Decimal('0.00'):
fee = round_decimal(fee_abs + total * (fee_percent / 100) + len(positions) * fee_per_ticket, event.currency)
tax_rule = event.settings.tax_rate_default or TaxRule.zero()
if tax_rule.tax_applicable(invoice_address):
tax = tax_rule.tax(fee)
@ -77,31 +87,35 @@ def cart_fee(sender: Event, request: HttpRequest, invoice_address, total, **kwar
pass
else:
mod = '_resellers'
return get_fees(sender, total, invoice_address, mod)
return get_fees(sender, total, invoice_address, mod, request)
@receiver(order_fee_calculation, dispatch_uid="service_fee_calc_order")
def order_fee(sender: Event, invoice_address, total, meta_info, **kwargs):
def order_fee(sender: Event, positions, invoice_address, total, meta_info, **kwargs):
mod = ''
if meta_info.get('servicefees_reseller_id'):
mod = '_resellers'
return get_fees(sender, total, invoice_address, mod)
return get_fees(sender, total, invoice_address, mod, positions=positions)
@receiver(front_page_top, dispatch_uid="service_fee_front_page_top")
def front_page_top_recv(sender: Event, **kwargs):
fees = []
fee_per_ticket = sender.settings.get('service_fee_per_ticket', as_type=Decimal)
if fee_per_ticket:
fees = fees + ["{} {}".format(money_filter(fee_per_ticket, sender.currency), ugettext('per ticket'))]
fee_abs = sender.settings.get('service_fee_abs', as_type=Decimal)
if fee_abs:
fees = fees + [money_filter(fee_abs, sender.currency)]
fees = fees + ["{} {}".format(money_filter(fee_abs, sender.currency), ugettext('per order'))]
fee_percent = sender.settings.get('service_fee_percent', as_type=Decimal)
if fee_percent:
fees = fees + ['{} %'.format(fee_percent)]
fees = fees + ['{} % {}'.format(fee_percent, ugettext('per order'))]
if fee_abs or fee_percent:
if fee_per_ticket or fee_abs or fee_percent:
return '<p>%s</p>' % ugettext('A service fee of {} will be added on top of each order.').format(
' + '.join(fees)
' {} '.format(ugettext('plus')).join(fees)
)

View file

@ -7,10 +7,16 @@
{% csrf_token %}
{% bootstrap_form_errors form %}
<fieldset>
{% bootstrap_field form.service_fee_abs layout="control" %}
{% bootstrap_field form.service_fee_percent layout="control" %}
{% bootstrap_field form.service_fee_abs_resellers layout="control" %}
{% bootstrap_field form.service_fee_percent_resellers layout="control" %}
<legend>{% trans "Service fees" %}</legend>
{% bootstrap_field form.service_fee_per_ticket addon_after=request.event.currency layout="control" %}
{% bootstrap_field form.service_fee_abs addon_after=request.event.currency layout="control" %}
{% bootstrap_field form.service_fee_percent addon_after="%" layout="control" %}
</fieldset>
<fieldset>
<legend>{% trans "Service fees with resellers" %}</legend>
{% bootstrap_field form.service_fee_per_ticket_resellers addon_after=request.event.currency layout="control" %}
{% bootstrap_field form.service_fee_abs_resellers addon_after=request.event.currency layout="control" %}
{% bootstrap_field form.service_fee_percent_resellers addon_after="%" layout="control" %}
</fieldset>
<div class="form-group submit-group">
<button type="submit" class="btn btn-primary btn-save">

View file

@ -5,23 +5,33 @@ from django.utils.translation import ugettext_lazy as _
from pretix.base.forms import SettingsForm
from pretix.base.models import Event
from pretix.control.views.event import EventSettingsViewMixin, EventSettingsFormView
from pretix.helpers.money import change_decimal_field
class ServiceFeeSettingsForm(SettingsForm):
service_fee_abs = forms.DecimalField(label=_('Service fee'))
service_fee_abs = forms.DecimalField(label=_('Fixed fee per order'))
service_fee_percent = forms.DecimalField(
label=_('Service fee (%)'),
label=_('Percentual fee per order'),
help_text=_('Percentage of the order total. Note that this percentage will currently only '
'be calculated on the summed price of sold tickets, not on other fees like e.'
'g. shipping fees, if there are any.')
)
service_fee_abs_resellers = forms.DecimalField(label=_('Service fee with resellers'))
service_fee_per_ticket = forms.DecimalField(
label=_('Fixed fee per ticket'),
help_text=_('This fee will be added for each ticket sold, except for free items and addons.')
)
service_fee_abs_resellers = forms.DecimalField(label=_('Fixed fee per order'))
service_fee_percent_resellers = forms.DecimalField(
label=_('Service fee with resellers (%)'),
label=_('Percentual fee per order'),
help_text=_('Percentage of the order total. Note that this percentage will currently only '
'be calculated on the summed price of sold tickets, not on other fees like e.'
'g. shipping fees, if there are any.')
)
service_fee_per_ticket_resellers = forms.DecimalField(
label=_('Fixed fee per ticket'),
help_text=_('This fee will be added for each ticket sold, except for free items and addons.')
)
class SettingsView(EventSettingsViewMixin, EventSettingsFormView):