Skip to content

Commit

Permalink
Merge pull request #375 from jcushman/cache-anon-fix
Browse files Browse the repository at this point in the history
Avoid caching requests from failed auth attempts
  • Loading branch information
bensteinberg committed Jul 12, 2018
2 parents a175e44 + a51cf6e commit fdc93c9
Show file tree
Hide file tree
Showing 2 changed files with 29 additions and 4 deletions.
11 changes: 8 additions & 3 deletions capstone/capapi/middleware.py
Original file line number Diff line number Diff line change
Expand Up @@ -53,9 +53,14 @@ def middleware(request):
# - No cookies are set by this view.
view_tests = {
'user_safe': (
not hasattr(request, 'user')
or request.user.is_anonymous
or (
(
# if user failed to authenticate, we can only cache if they
# didn't supply a bad sessionid cookie or authorization header
'HTTP_AUTHORIZATION' not in request.META
and settings.SESSION_COOKIE_NAME not in request.COOKIES
) if (not hasattr(request, 'user') or request.user.is_anonymous) else (
# if user successfully authenticated, we can only cache if we
# didn't access any user-specific data in preparing this view
hasattr(request.user, '_self_accessed_attrs')
and not (request.user._self_accessed_attrs - _capuser_cache_safe_attributes)
)
Expand Down
22 changes: 21 additions & 1 deletion capstone/capapi/tests/test_cache.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import pytest
from django.http import SimpleCookie
from django.urls import reverse

from capapi.tests.helpers import is_cached
Expand Down Expand Up @@ -46,4 +47,23 @@ def test_cache_headers(case, request, settings,
client_fixture_name,
"" if cache_expected else "not ",
"" if cache_actual else "not ",
)
)

@pytest.mark.django_db
def test_cache_headers_with_bad_auth(client, case, settings):
settings.SET_CACHE_CONTROL_HEADER = True

# visiting homepage when logged out is cached ...
response = client.get(reverse('home'))
assert is_cached(response)

# ... but visiting with a bad Authorization header is not cached
client.credentials(HTTP_AUTHORIZATION='Token fake')
response = client.get(reverse('home'))
assert not is_cached(response)

# ... and visiting with a bad session cookie is not cached
client.credentials()
client.cookies = SimpleCookie({settings.SESSION_COOKIE_NAME: 'fake'})
response = client.get(reverse('home'))
assert not is_cached(response)

0 comments on commit fdc93c9

Please sign in to comment.