Skip to content

Commit ab74586

Browse files
dylantackauvipy
andauthored
Require redirect_uri if multiple URIs are registered (#981)
* Require redirect_uri if multiple uris are registered * update changelog for #981 Co-authored-by: Asif Saif Uddin <[email protected]>
1 parent 4384566 commit ab74586

File tree

5 files changed

+30
-3
lines changed

5 files changed

+30
-3
lines changed

CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
1818
* Remove support for Django 3.0
1919
* Add support for Django 3.2
2020
* #989 Change any HttpResponse to JsonResponse if possible
21+
* #981 redirect_uri is now required in authorization requests when multiple URIs are registered.
2122

2223
### Added
2324
* #712, #636, #808. Calls to `django.contrib.auth.authenticate()` now pass a `request`

oauth2_provider/models.py

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
from django.utils.translation import gettext_lazy as _
1313
from jwcrypto import jwk
1414
from jwcrypto.common import base64url_encode
15+
from oauthlib.oauth2.rfc6749 import errors
1516

1617
from .generators import generate_client_id, generate_client_secret
1718
from .scopes import get_scopes_backend
@@ -107,11 +108,13 @@ def __str__(self):
107108
@property
108109
def default_redirect_uri(self):
109110
"""
110-
Returns the default redirect_uri extracting the first item from
111-
the :attr:`redirect_uris` string
111+
Returns the default redirect_uri, *if* only one is registered.
112112
"""
113113
if self.redirect_uris:
114-
return self.redirect_uris.split().pop(0)
114+
uris = self.redirect_uris.split()
115+
if len(uris) == 1:
116+
return self.redirect_uris.split().pop(0)
117+
raise errors.MissingRedirectURIError()
115118

116119
assert False, (
117120
"If you are using implicit, authorization_code "

tests/test_authorization_code.py

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -257,6 +257,8 @@ def test_pre_auth_default_redirect(self):
257257
Test for default redirect uri if omitted from query string with response_type: code
258258
"""
259259
self.client.login(username="test_user", password="123456")
260+
self.application.redirect_uris = "http://localhost"
261+
self.application.save()
260262

261263
query_data = {
262264
"client_id": self.application.client_id,
@@ -269,6 +271,21 @@ def test_pre_auth_default_redirect(self):
269271
form = response.context["form"]
270272
self.assertEqual(form["redirect_uri"].value(), "http://localhost")
271273

274+
def test_pre_auth_missing_redirect(self):
275+
"""
276+
Test response if redirect_uri is missing and multiple URIs are registered.
277+
@see https://datatracker.ietf.org/doc/html/rfc6749#section-3.1.2.3
278+
"""
279+
self.client.login(username="test_user", password="123456")
280+
281+
query_data = {
282+
"client_id": self.application.client_id,
283+
"response_type": "code",
284+
}
285+
286+
response = self.client.get(reverse("oauth2_provider:authorize"), data=query_data)
287+
self.assertEqual(response.status_code, 400)
288+
272289
def test_pre_auth_forbibben_redirect(self):
273290
"""
274291
Test error when passing a forbidden redirect_uri in query string with response_type: code
@@ -293,6 +310,7 @@ def test_pre_auth_wrong_response_type(self):
293310
query_data = {
294311
"client_id": self.application.client_id,
295312
"response_type": "WRONG",
313+
"redirect_uri": "http://example.org",
296314
}
297315

298316
response = self.client.get(reverse("oauth2_provider:authorize"), data=query_data)

tests/test_hybrid.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -370,6 +370,8 @@ def test_pre_auth_default_redirect(self):
370370
Test for default redirect uri if omitted from query string with response_type: code
371371
"""
372372
self.client.login(username="hy_test_user", password="123456")
373+
self.application.redirect_uris = "http://localhost"
374+
self.application.save()
373375

374376
query_string = urlencode(
375377
{
@@ -413,6 +415,7 @@ def test_pre_auth_wrong_response_type(self):
413415
{
414416
"client_id": self.application.client_id,
415417
"response_type": "WRONG",
418+
"redirect_uri": "http://example.org",
416419
}
417420
)
418421
url = "{url}?{qs}".format(url=reverse("oauth2_provider:authorize"), qs=query_string)

tests/test_implicit.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -110,6 +110,8 @@ def test_pre_auth_default_redirect(self):
110110
Test for default redirect uri if omitted from query string with response_type: token
111111
"""
112112
self.client.login(username="test_user", password="123456")
113+
self.application.redirect_uris = "http://localhost"
114+
self.application.save()
113115

114116
query_data = {
115117
"client_id": self.application.client_id,

0 commit comments

Comments
 (0)