forked from CGM_Public/pretix_original
Allow multiple returnurl prefixes (Z#23145768) (#3941)
* Allow multiple returnurl prefixes, improve validation and docs. * Fix typo * Allow URL prefixes starting with http://localhost * Add more explanation
This commit is contained in:
@@ -94,7 +94,9 @@ If you want the user to return to your application after the payment is complete
|
|||||||
"Plugins". Enable the plugin "Redirection from order page". Then, go to the new page "Settings", then "Redirection".
|
"Plugins". Enable the plugin "Redirection from order page". Then, go to the new page "Settings", then "Redirection".
|
||||||
Enter the base URL of your web application. This will allow you to redirect to pages under this base URL later on.
|
Enter the base URL of your web application. This will allow you to redirect to pages under this base URL later on.
|
||||||
For example, if you want users to be redirected to ``https://example.org/order/return?tx_id=1234``, you could now
|
For example, if you want users to be redirected to ``https://example.org/order/return?tx_id=1234``, you could now
|
||||||
either enter ``https://example.org`` or ``https://example.org/order/``.
|
either enter ``https://example.org/order/`` or ``https://example.org/``.
|
||||||
|
Please note that in the latter case the trailing slash is required, ``https://example.org`` is not allowed to prevent.
|
||||||
|
Only base URLs with a secure (``https://``) or local (``http://localhost``) origin are permitted.
|
||||||
|
|
||||||
The user will be redirected back to your page instead of pretix' order confirmation page after the payment,
|
The user will be redirected back to your page instead of pretix' order confirmation page after the payment,
|
||||||
**regardless of whether it was successful or not**. We will append an ``error=…`` query parameter with an error
|
**regardless of whether it was successful or not**. We will append an ``error=…`` query parameter with an error
|
||||||
|
|||||||
@@ -71,11 +71,15 @@ def returnurl_process_request(sender, request, **kwargs):
|
|||||||
u = request.GET.get('return_url')
|
u = request.GET.get('return_url')
|
||||||
if not sender.settings.returnurl_prefix:
|
if not sender.settings.returnurl_prefix:
|
||||||
raise PermissionDenied('No return URL prefix set.')
|
raise PermissionDenied('No return URL prefix set.')
|
||||||
elif not u.startswith(sender.settings.returnurl_prefix):
|
elif not check_against_prefix_list(u, sender.settings.returnurl_prefix):
|
||||||
raise PermissionDenied('Invalid return URL.')
|
raise PermissionDenied('Invalid return URL.')
|
||||||
request.session[key] = u
|
request.session[key] = u
|
||||||
|
|
||||||
|
|
||||||
|
def check_against_prefix_list(u, allowlist):
|
||||||
|
return any(u.startswith(allow.strip()) for allow in allowlist.split("\n") if allow.strip() != "")
|
||||||
|
|
||||||
|
|
||||||
@receiver(nav_event_settings, dispatch_uid='returnurl_nav')
|
@receiver(nav_event_settings, dispatch_uid='returnurl_nav')
|
||||||
def navbar_info(sender, request, **kwargs):
|
def navbar_info(sender, request, **kwargs):
|
||||||
url = resolve(request.path_info)
|
url = resolve(request.path_info)
|
||||||
|
|||||||
@@ -19,6 +19,8 @@
|
|||||||
# You should have received a copy of the GNU Affero General Public License along with this program. If not, see
|
# You should have received a copy of the GNU Affero General Public License along with this program. If not, see
|
||||||
# <https://www.gnu.org/licenses/>.
|
# <https://www.gnu.org/licenses/>.
|
||||||
#
|
#
|
||||||
|
import re
|
||||||
|
|
||||||
from django import forms
|
from django import forms
|
||||||
from django.urls import reverse
|
from django.urls import reverse
|
||||||
from django.utils.translation import gettext_lazy as _
|
from django.utils.translation import gettext_lazy as _
|
||||||
@@ -31,10 +33,14 @@ from pretix.control.views.event import (
|
|||||||
|
|
||||||
|
|
||||||
class ReturnSettingsForm(SettingsForm):
|
class ReturnSettingsForm(SettingsForm):
|
||||||
returnurl_prefix = forms.URLField(
|
returnurl_prefix = forms.RegexField(
|
||||||
label=_("Base redirection URL"),
|
label=_("Base redirection URLs"),
|
||||||
help_text=_("Redirection will only be allowed to URLs that start with this prefix."),
|
help_text=_("Redirection will only be allowed to URLs that start with one of these prefixes. "
|
||||||
|
"Enter one or more allowed URL prefix per line. "
|
||||||
|
"URL prefixes must include a slash after the hostname."),
|
||||||
required=False,
|
required=False,
|
||||||
|
widget=forms.Textarea,
|
||||||
|
regex=re.compile(r'^((https://.*/.*|http://localhost[:/].*)\n*)*$')
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user