From ed055e0892ee67d35b718b87b487c3a424026565 Mon Sep 17 00:00:00 2001 From: Serghei Mihai Date: Tue, 24 Nov 2020 10:51:58 +0100 Subject: [PATCH] authentic2_idp_oidc: verify next url againts clients redirect_uris (#48739) --- src/authentic2_idp_oidc/apps.py | 4 ++++ src/authentic2_idp_oidc/utils.py | 13 +++++++++++++ tests/test_idp_oidc.py | 9 ++++++++- 3 files changed, 25 insertions(+), 1 deletion(-) diff --git a/src/authentic2_idp_oidc/apps.py b/src/authentic2_idp_oidc/apps.py index ed5082c19..d4a086f62 100644 --- a/src/authentic2_idp_oidc/apps.py +++ b/src/authentic2_idp_oidc/apps.py @@ -156,3 +156,7 @@ class AppConfig(django.apps.AppConfig): qs = qs.distinct() return qs + + def a2_hook_good_next_url(self, next_url): + from .utils import good_next_url + return good_next_url(next_url) diff --git a/src/authentic2_idp_oidc/utils.py b/src/authentic2_idp_oidc/utils.py index 954ad8bb3..e60553788 100644 --- a/src/authentic2_idp_oidc/utils.py +++ b/src/authentic2_idp_oidc/utils.py @@ -31,6 +31,7 @@ from django.utils.six.moves.urllib import parse as urlparse from authentic2 import hooks, crypto from authentic2.attributes_ng.engine import get_attributes from authentic2.utils.template import Template +from authentic2.decorators import GlobalCache from . import app_settings @@ -251,3 +252,15 @@ def add_oidc_session(request, client): oidc_sessions[uri] = oidc_session # force session save request.session.modified = True + + +@GlobalCache(timeout=60) +def good_next_url(next_url): + from authentic2.utils import same_origin + from .models import OIDCClient + + for oidc_client in OIDCClient.objects.all(): + for url in oidc_client.redirect_uris.split(): + if same_origin(url, next_url): + return True + return None diff --git a/tests/test_idp_oidc.py b/tests/test_idp_oidc.py index 3bb06f471..c158a536c 100644 --- a/tests/test_idp_oidc.py +++ b/tests/test_idp_oidc.py @@ -43,7 +43,7 @@ from authentic2_idp_oidc.utils import get_first_rsa_sig_key from authentic2_idp_oidc.utils import get_first_ec_sig_key from authentic2_idp_oidc.utils import make_sub from authentic2.a2_rbac.utils import get_default_ou -from authentic2.utils import make_url +from authentic2.utils import make_url, good_next_url from authentic2_auth_oidc.utils import parse_timestamp from django_rbac.utils import get_ou_model from django_rbac.utils import get_role_model @@ -1689,3 +1689,10 @@ def test_oidc_authorized_oauth_services_view(app, oidc_client, simple_user): 'button', {'class': 'authorized-oauth-services--revoke-button'})) == 1 assert OIDCAuthorization.objects.filter( client_ct=ContentType.objects.get_for_model(OU)).count() == 0 + + +def test_oidc_good_next_url_hook(app, oidc_client): + from django.test.client import RequestFactory + rf = RequestFactory() + request = rf.get('/') + assert good_next_url(request, 'https://example.com/')