Skip to content

Commit

Permalink
Referer: show reasons for items in the list in parentheses
Browse files Browse the repository at this point in the history
  • Loading branch information
vanschelven committed Sep 29, 2024
1 parent f24625f commit 79ccddd
Show file tree
Hide file tree
Showing 2 changed files with 19 additions and 6 deletions.
10 changes: 7 additions & 3 deletions verbose_csrf_middleware/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -375,20 +375,23 @@ def _check_referer(self, request):
return

else:
non_matched_domains.extend(self.csrf_trusted_origins_hosts)
non_matched_domains.extend(["'" + host + "' (trusted)" for host in self.csrf_trusted_origins_hosts])

# Allow matching the configured cookie domain.
good_referer = (
settings.SESSION_COOKIE_DOMAIN
if settings.CSRF_USE_SESSIONS
else settings.CSRF_COOKIE_DOMAIN
)
good_referer_source = "session_cookie" if settings.CSRF_USE_SESSIONS else "csrf_cookie"

if good_referer is None:
# If no cookie domain is configured, allow matching the current
# host:port exactly if it's permitted by ALLOWED_HOSTS.
try:
# request.get_host() includes the port.
good_referer = request.get_host()
good_referer_source = "host"
except DisallowedHost:
raise RejectRequest(REASON_BAD_REFERER_DISALLOWED_HOST)
else:
Expand All @@ -397,8 +400,9 @@ def _check_referer(self, request):
good_referer = "%s:%s" % (good_referer, server_port)

if not is_same_domain(referer.netloc, good_referer):
non_matched_domains.append(good_referer)
raise RejectRequest(REASON_BAD_REFERER_NOT_SAME % (referer.netloc, non_matched_domains))
non_matched_domains.append("'" + good_referer + "' (" + good_referer_source + ")")
non_matched_domains_s = "[" + (", ".join(non_matched_domains)) + "]"
raise RejectRequest(REASON_BAD_REFERER_NOT_SAME % (referer.netloc, non_matched_domains_s))

def _bad_token_message(self, reason, token_source):
if token_source != "POST":
Expand Down
15 changes: 12 additions & 3 deletions verbose_csrf_middleware/tests.py
Original file line number Diff line number Diff line change
Expand Up @@ -103,15 +103,15 @@ def test_referer_non_matching(self):
# (while not sending an Origin header at all)
self._test(
referer='https://www.wrong.org/', secure=True,
reason="Referer checking failed - 'www.wrong.org' does not match any of ['testserver'].",
reason="Referer checking failed - 'www.wrong.org' does not match any of ['testserver' (host)].",
)

@override_settings(CSRF_TRUSTED_ORIGINS=["https://csrf_trusted_origin.org"])
def test_referer_matches_neither_host_nor_explicitly_trusted_origins(self):
self._test(
referer='https://refererheader.org/', secure=True,
reason="Referer checking failed - 'refererheader.org' does not match any of "
"['csrf_trusted_origin.org', 'testserver'].",
"['csrf_trusted_origin.org' (trusted), 'testserver' (host)].",
)

@override_settings(CSRF_TRUSTED_ORIGINS=["http://domainmatchestoo.org"]) # note: http, not https
Expand All @@ -132,7 +132,16 @@ def test_crsf_trusted_origins_with_exact_match_and_referer(self):
def test_csrf_cookie_domain_configured_but_not_matching_referer(self):
self._test(
referer='https://nonmatching.example.org/', secure=True,
reason="Referer checking failed - 'nonmatching.example.org' does not match any of ['expected.example.org']."
reason="Referer checking failed - 'nonmatching.example.org' does not match any of "
"['expected.example.org' (csrf_cookie)]."
)

@override_settings(CSRF_USE_SESSIONS=True, SESSION_COOKIE_DOMAIN="expected.example.org")
def test_session_cookie_domain_configured_but_not_matching_referer(self):
self._test(
referer='https://nonmatching.example.org/', secure=True,
reason="Referer checking failed - 'nonmatching.example.org' does not match any of "
"['expected.example.org' (session_cookie)]."
)

@override_settings(CSRF_COOKIE_DOMAIN="expected.example.org")
Expand Down

0 comments on commit 79ccddd

Please sign in to comment.