Skip to content

Commit

Permalink
API: Fix CSRF support for session-based usage
Browse files Browse the repository at this point in the history
  • Loading branch information
raphaelm committed Jan 26, 2024
1 parent 11e922b commit 2354aff
Show file tree
Hide file tree
Showing 2 changed files with 44 additions and 1 deletion.
2 changes: 1 addition & 1 deletion src/pretix/settings.py
Original file line number Diff line number Diff line change
Expand Up @@ -398,7 +398,7 @@
'DEFAULT_AUTHENTICATION_CLASSES': (
'pretix.api.auth.token.TeamTokenAuthentication',
'pretix.api.auth.device.DeviceTokenAuthentication',
'rest_framework.authentication.SessionAuthentication',
'pretix.api.auth.session.SessionAuthentication',
'oauth2_provider.contrib.rest_framework.OAuth2Authentication',
),
'DEFAULT_RENDERER_CLASSES': (
Expand Down
43 changes: 43 additions & 0 deletions src/tests/api/test_auth.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,11 @@
import time

import pytest
from bs4 import BeautifulSoup
from django.test import Client

from pretix.base.models import Organizer
from tests.base import extract_form_fields


@pytest.mark.django_db
Expand Down Expand Up @@ -63,6 +66,46 @@ def test_session_auth_relative_timeout(client, user, team):
assert resp.status_code == 403


@pytest.mark.django_db
def test_session_auth_csrf(user, team):
team.members.add(user)
client = Client(enforce_csrf_checks=True)
client.login(email=user.email, password='dummy')

resp = client.post('/api/v1/organizers/dummy/events/', secure=True, headers={
'Referer': 'https://localhost',
'Host': 'localhost',
})
assert resp.status_code == 403
assert "CSRF Failed: CSRF cookie not set." in str(resp.data)

resp = client.get('/control/events/add', secure=True)
assert resp.status_code == 200
doc = BeautifulSoup(resp.render().content, "lxml")
form_data = extract_form_fields(doc.select('form')[0])

resp = client.post('/api/v1/organizers/dummy/events/', secure=True, headers={
'Referer': 'https://localhost',
'Host': 'localhost',
})
assert resp.status_code == 403
assert "CSRF Failed: CSRF token missing." in str(resp.data)

resp = client.post('/api/v1/organizers/dummy/events/', headers={
'X-CSRFToken': form_data['csrfmiddlewaretoken'],
'Host': 'localhost',
}, secure=True)
assert resp.status_code == 403
assert "CSRF Failed: Referer checking failed - no Referer." in str(resp.data)

resp = client.post('/api/v1/organizers/dummy/events/', headers={
'X-CSRFToken': form_data['csrfmiddlewaretoken'],
'Referer': 'https://localhost',
'Host': 'localhost',
}, secure=True)
assert resp.status_code == 400


@pytest.mark.django_db
def test_token_invalid(client):
client.credentials(HTTP_AUTHORIZATION='Token ABCDE')
Expand Down

0 comments on commit 2354aff

Please sign in to comment.