plateforme-corres2math/apps/participation/tests.py

562 lines
22 KiB
Python

from django.contrib.auth.models import User
from django.contrib.contenttypes.models import ContentType
from django.contrib.sites.models import Site
from django.test import TestCase
from django.urls import reverse
from registration.models import StudentRegistration
from .models import Participation, Question, Team
class TestStudentParticipation(TestCase):
def setUp(self) -> None:
self.superuser = User.objects.create_superuser(
username="admin",
email="admin@example.com",
password="toto1234",
)
self.user = User.objects.create(
first_name="Toto",
last_name="Toto",
email="toto@example.com",
password="toto",
)
StudentRegistration.objects.create(
user=self.user,
student_class=12,
school="Earth",
give_contact_to_animath=True,
email_confirmed=True,
)
self.team = Team.objects.create(
name="Super team",
trigram="AAA",
access_code="azerty",
grant_animath_access_videos=True,
)
self.question = Question.objects.create(participation=self.team.participation,
question="Pourquoi l'existence précède l'essence ?")
self.client.force_login(self.user)
self.second_user = User.objects.create(
first_name="Lalala",
last_name="Lalala",
email="lalala@example.com",
password="lalala",
)
StudentRegistration.objects.create(
user=self.second_user,
student_class=11,
school="Moon",
give_contact_to_animath=True,
email_confirmed=True,
)
self.second_team = Team.objects.create(
name="Poor team",
trigram="FFF",
access_code="qwerty",
grant_animath_access_videos=True,
)
def test_admin_pages(self):
"""
Load Django-admin pages.
"""
self.client.force_login(self.superuser)
# Test team pages
response = self.client.get(reverse("admin:index") + "participation/team/")
self.assertEqual(response.status_code, 200)
response = self.client.get(reverse("admin:index")
+ f"participation/team/{self.team.pk}/change/")
self.assertEqual(response.status_code, 200)
response = self.client.get(reverse("admin:index") +
f"r/{ContentType.objects.get_for_model(Team).id}/"
f"{self.team.pk}/")
self.assertRedirects(response, "http://" + Site.objects.get().domain +
str(self.team.get_absolute_url()), 302, 200)
# Test participation pages
self.team.participation.valid = True
self.team.participation.save()
response = self.client.get(reverse("admin:index") + "participation/participation/")
self.assertEqual(response.status_code, 200)
response = self.client.get(reverse("admin:index")
+ f"participation/participation/{self.team.participation.pk}/change/")
self.assertEqual(response.status_code, 200)
response = self.client.get(reverse("admin:index") +
f"r/{ContentType.objects.get_for_model(Participation).id}/"
f"{self.team.participation.pk}/")
self.assertRedirects(response, "http://" + Site.objects.get().domain +
str(self.team.participation.get_absolute_url()), 302, 200)
# Test video pages
response = self.client.get(reverse("admin:index") + "participation/video/")
self.assertEqual(response.status_code, 200)
response = self.client.get(reverse("admin:index")
+ f"participation/video/{self.team.participation.solution.pk}/change/")
self.assertEqual(response.status_code, 200)
# Test question pages
response = self.client.get(reverse("admin:index") + "participation/question/")
self.assertEqual(response.status_code, 200)
response = self.client.get(reverse("admin:index")
+ f"participation/question/{self.question.pk}/change/")
self.assertEqual(response.status_code, 200)
# Test phase pages
response = self.client.get(reverse("admin:index") + "participation/phase/")
self.assertEqual(response.status_code, 200)
response = self.client.get(reverse("admin:index") + "participation/phase/1/change/")
self.assertEqual(response.status_code, 200)
def test_create_team(self):
"""
Try to create a team.
"""
response = self.client.get(reverse("participation:create_team"))
self.assertEqual(response.status_code, 200)
response = self.client.post(reverse("participation:create_team"), data=dict(
name="Test team",
trigram="123",
grant_animath_access_videos=False,
))
self.assertEqual(response.status_code, 200)
response = self.client.post(reverse("participation:create_team"), data=dict(
name="Test team",
trigram="TES",
grant_animath_access_videos=False,
))
self.assertTrue(Team.objects.filter(trigram="TES").exists())
team = Team.objects.get(trigram="TES")
self.assertRedirects(response, reverse("participation:team_detail", args=(team.pk,)), 302, 200)
# Already in a team
response = self.client.post(reverse("participation:create_team"), data=dict(
name="Test team 2",
trigram="TET",
grant_animath_access_videos=False,
))
self.assertEqual(response.status_code, 403)
def test_join_team(self):
"""
Try to join an existing team.
"""
response = self.client.get(reverse("participation:join_team"))
self.assertEqual(response.status_code, 200)
team = Team.objects.create(name="Test", trigram="TES")
response = self.client.post(reverse("participation:join_team"), data=dict(
access_code="éééééé",
))
self.assertEqual(response.status_code, 200)
response = self.client.post(reverse("participation:join_team"), data=dict(
access_code=team.access_code,
))
self.assertRedirects(response, reverse("participation:team_detail", args=(team.pk,)), 302, 200)
self.assertTrue(Team.objects.filter(trigram="TES").exists())
# Already joined
response = self.client.post(reverse("participation:join_team"), data=dict(
access_code=team.access_code,
))
self.assertEqual(response.status_code, 403)
def test_no_myteam_redirect_noteam(self):
"""
Test redirection.
"""
response = self.client.get(reverse("participation:my_team_detail"))
self.assertTrue(response.status_code, 200)
def test_team_detail(self):
"""
Try to display the information of a team.
"""
self.user.registration.team = self.team
self.user.registration.save()
response = self.client.get(reverse("participation:my_team_detail"))
self.assertRedirects(response, reverse("participation:team_detail", args=(self.team.pk,)), 302, 200)
response = self.client.get(reverse("participation:team_detail", args=(self.team.pk,)))
self.assertEqual(response.status_code, 200)
# Can't see other teams
self.second_user.registration.team = self.second_team
self.second_user.registration.save()
self.client.force_login(self.second_user)
response = self.client.get(reverse("participation:team_detail", args=(self.team.participation.pk,)))
self.assertEqual(response.status_code, 403)
def test_request_validate_team(self):
"""
The team ask for validation.
"""
self.user.registration.team = self.team
self.user.registration.save()
second_user = User.objects.create(
first_name="Blublu",
last_name="Blublu",
email="blublu@example.com",
password="blublu",
)
StudentRegistration.objects.create(
user=second_user,
student_class=12,
school="Jupiter",
give_contact_to_animath=True,
email_confirmed=True,
team=self.team,
photo_authorization="authorization/photo/mai-linh",
)
third_user = User.objects.create(
first_name="Zupzup",
last_name="Zupzup",
email="zupzup@example.com",
password="zupzup",
)
StudentRegistration.objects.create(
user=third_user,
student_class=10,
school="Sun",
give_contact_to_animath=False,
email_confirmed=True,
team=self.team,
photo_authorization="authorization/photo/yohann",
)
self.client.force_login(self.superuser)
# Admin users can't ask for validation
resp = self.client.post(reverse("participation:team_detail", args=(self.team.pk,)), data=dict(
_form_type="RequestValidationForm",
engagement=True,
))
self.assertEqual(resp.status_code, 200)
self.client.force_login(self.user)
self.assertIsNone(self.team.participation.valid)
resp = self.client.get(reverse("participation:team_detail", args=(self.team.pk,)))
self.assertEqual(resp.status_code, 200)
self.assertFalse(resp.context["can_validate"])
# Can't validate
resp = self.client.post(reverse("participation:team_detail", args=(self.team.pk,)), data=dict(
_form_type="RequestValidationForm",
engagement=True,
))
self.assertEqual(resp.status_code, 200)
self.user.registration.photo_authorization = "authorization/photo/ananas"
self.user.registration.save()
resp = self.client.get(reverse("participation:team_detail", args=(self.team.pk,)))
self.assertEqual(resp.status_code, 200)
self.assertFalse(resp.context["can_validate"])
self.team.participation.problem = 2
self.team.participation.save()
resp = self.client.get(reverse("participation:team_detail", args=(self.team.pk,)))
self.assertEqual(resp.status_code, 200)
self.assertTrue(resp.context["can_validate"])
resp = self.client.post(reverse("participation:team_detail", args=(self.team.pk,)), data=dict(
_form_type="RequestValidationForm",
engagement=True,
))
self.assertRedirects(resp, reverse("participation:team_detail", args=(self.team.pk,)), 302, 200)
self.team.participation.refresh_from_db()
self.assertFalse(self.team.participation.valid)
self.assertIsNotNone(self.team.participation.valid)
# Team already asked for validation
resp = self.client.post(reverse("participation:team_detail", args=(self.team.pk,)), data=dict(
_form_type="RequestValidationForm",
engagement=True,
))
self.assertEqual(resp.status_code, 200)
def test_validate_team(self):
"""
A team asked for validation. Try to validate it.
"""
self.team.participation.valid = False
self.team.participation.save()
# No right to do that
resp = self.client.post(reverse("participation:team_detail", args=(self.team.pk,)), data=dict(
_form_type="ValidateParticipationForm",
message="J'ai 4 ans",
validate=True,
))
self.assertEqual(resp.status_code, 200)
self.client.force_login(self.superuser)
resp = self.client.get(reverse("participation:team_detail", args=(self.team.pk,)))
self.assertEqual(resp.status_code, 200)
resp = self.client.post(reverse("participation:team_detail", args=(self.team.pk,)), data=dict(
_form_type="ValidateParticipationForm",
message="Woops I didn't said anything",
))
self.assertEqual(resp.status_code, 200)
# Test invalidate team
resp = self.client.post(reverse("participation:team_detail", args=(self.team.pk,)), data=dict(
_form_type="ValidateParticipationForm",
message="Wsh nope",
invalidate=True,
))
self.assertRedirects(resp, reverse("participation:team_detail", args=(self.team.pk,)), 302, 200)
self.team.participation.refresh_from_db()
self.assertIsNone(self.team.participation.valid)
# Team did not ask validation
resp = self.client.post(reverse("participation:team_detail", args=(self.team.pk,)), data=dict(
_form_type="ValidateParticipationForm",
message="Bienvenue ça va être trop cool",
validate=True,
))
self.assertEqual(resp.status_code, 200)
self.team.participation.valid = False
self.team.participation.save()
# Test validate team
resp = self.client.post(reverse("participation:team_detail", args=(self.team.pk,)), data=dict(
_form_type="ValidateParticipationForm",
message="Bienvenue ça va être trop cool",
validate=True,
))
self.assertRedirects(resp, reverse("participation:team_detail", args=(self.team.pk,)), 302, 200)
self.team.participation.refresh_from_db()
self.assertTrue(self.team.participation.valid)
def test_update_team(self):
"""
Try to update team information.
"""
self.user.registration.team = self.team
self.user.registration.save()
response = self.client.get(reverse("participation:update_team", args=(self.team.pk,)))
self.assertEqual(response.status_code, 200)
# Form is invalid
response = self.client.post(reverse("participation:update_team", args=(self.team.pk,)), data=dict(
name="Updated team name",
trigram="BBB",
grant_animath_access_videos=True,
problem=42,
))
self.assertEqual(response.status_code, 200)
response = self.client.post(reverse("participation:update_team", args=(self.team.pk,)), data=dict(
name="Updated team name",
trigram="BBB",
grant_animath_access_videos=True,
problem=3,
))
self.assertRedirects(response, reverse("participation:team_detail", args=(self.team.pk,)), 302, 200)
self.assertTrue(Team.objects.filter(trigram="BBB", participation__problem=3).exists())
def test_leave_team(self):
"""
A user is in a team, and leaves it.
"""
# User is not in a team
response = self.client.post(reverse("participation:team_leave"))
self.assertEqual(response.status_code, 403)
self.user.registration.team = self.team
self.user.registration.save()
# Team is pending validation
self.team.participation.valid = False
self.team.participation.save()
response = self.client.post(reverse("participation:team_leave"))
self.assertEqual(response.status_code, 403)
# Team is valid
self.team.participation.valid = True
self.team.participation.save()
response = self.client.post(reverse("participation:team_leave"))
self.assertEqual(response.status_code, 403)
# Unauthenticated users are redirected to login page
self.client.logout()
response = self.client.get(reverse("participation:team_leave"))
self.assertRedirects(response, reverse("login") + "?next=" + reverse("participation:team_leave"), 302, 200)
self.client.force_login(self.user)
self.team.participation.valid = None
self.team.participation.save()
response = self.client.post(reverse("participation:team_leave"))
self.assertRedirects(response, reverse("index"), 302, 200)
self.user.registration.refresh_from_db()
self.assertIsNone(self.user.registration.team)
self.assertFalse(Team.objects.filter(pk=self.team.pk).exists())
def test_no_myparticipation_redirect_nomyparticipation(self):
"""
Ensure a permission denied when we search my team participation when we are in no team.
"""
response = self.client.get(reverse("participation:my_participation_detail"))
self.assertEqual(response.status_code, 403)
def test_participation_detail(self):
"""
Try to display the detail of a team participation.
"""
self.user.registration.team = self.team
self.user.registration.save()
# Can't see the participation if it is not valid
response = self.client.get(reverse("participation:my_participation_detail"))
self.assertRedirects(response,
reverse("participation:participation_detail", args=(self.team.participation.pk,)),
302, 403)
self.team.participation.valid = True
self.team.participation.save()
response = self.client.get(reverse("participation:my_participation_detail"))
self.assertRedirects(response,
reverse("participation:participation_detail", args=(self.team.participation.pk,)),
302, 200)
response = self.client.get(reverse("participation:participation_detail", args=(self.team.participation.pk,)))
self.assertEqual(response.status_code, 200)
# Can't see other participations
self.second_user.registration.team = self.second_team
self.second_user.registration.save()
self.client.force_login(self.second_user)
response = self.client.get(reverse("participation:participation_detail", args=(self.team.participation.pk,)))
self.assertEqual(response.status_code, 403)
def test_upload_video(self):
"""
Try to send a solution video link.
"""
self.user.registration.team = self.team
self.user.registration.save()
self.team.participation.valid = True
self.team.participation.save()
response = self.client.get(reverse("participation:upload_video", args=(self.team.participation.solution.pk,)))
self.assertEqual(response.status_code, 200)
response = self.client.post(reverse("participation:upload_video", args=(self.team.participation.solution.pk,)),
data=dict(link="https://youtube.com/watch?v=73nsrixx7eI"))
self.assertRedirects(response,
reverse("participation:participation_detail", args=(self.team.participation.id,)),
302, 200)
self.team.participation.refresh_from_db()
self.assertEqual(self.team.participation.solution.platform, "youtube")
self.assertEqual(self.team.participation.solution.youtube_code, "73nsrixx7eI")
response = self.client.get(reverse("participation:participation_detail", args=(self.team.participation.pk,)))
self.assertEqual(response.status_code, 200)
def test_forbidden_access(self):
"""
Load personnal pages and ensure that these are protected.
"""
self.user.registration.team = self.team
self.user.registration.save()
resp = self.client.get(reverse("participation:team_detail", args=(self.second_team.pk,)))
self.assertEqual(resp.status_code, 403)
resp = self.client.get(reverse("participation:update_team", args=(self.second_team.pk,)))
self.assertEqual(resp.status_code, 403)
resp = self.client.get(reverse("participation:team_authorizations", args=(self.second_team.pk,)))
self.assertEqual(resp.status_code, 403)
resp = self.client.get(reverse("participation:participation_detail", args=(self.second_team.pk,)))
self.assertEqual(resp.status_code, 403)
resp = self.client.get(reverse("participation:upload_video",
args=(self.second_team.participation.solution.pk,)))
self.assertEqual(resp.status_code, 403)
resp = self.client.get(reverse("participation:upload_video",
args=(self.second_team.participation.synthesis.pk,)))
self.assertEqual(resp.status_code, 403)
resp = self.client.get(reverse("participation:add_question", args=(self.second_team.pk,)))
self.assertEqual(resp.status_code, 403)
question = Question.objects.create(participation=self.second_team.participation,
question=self.question.question)
resp = self.client.get(reverse("participation:update_question", args=(question.pk,)))
self.assertEqual(resp.status_code, 403)
resp = self.client.get(reverse("participation:delete_question", args=(question.pk,)))
self.assertEqual(resp.status_code, 403)
class TestAdminForbidden(TestCase):
def setUp(self) -> None:
self.user = User.objects.create_superuser(
username="admin@example.com",
email="admin@example.com",
password="admin",
)
self.client.force_login(self.user)
def test_create_team_forbidden(self):
"""
Ensure that an admin can't create a team.
"""
response = self.client.post(reverse("participation:create_team"), data=dict(
name="Test team",
trigram="TES",
grant_animath_access_videos=False,
))
self.assertEqual(response.status_code, 403)
def test_join_team_forbidden(self):
"""
Ensure that an admin can't join a team.
"""
team = Team.objects.create(name="Test", trigram="TES")
response = self.client.post(reverse("participation:join_team"), data=dict(
access_code=team.access_code,
))
self.assertTrue(response.status_code, 403)
def test_leave_team_forbidden(self):
"""
Ensure that an admin can't leave a team.
"""
response = self.client.get(reverse("participation:team_leave"))
self.assertTrue(response.status_code, 403)
def test_my_team_forbidden(self):
"""
Ensure that an admin can't access to "My team".
"""
response = self.client.get(reverse("participation:my_team_detail"))
self.assertEqual(response.status_code, 403)
def test_my_participation_forbidden(self):
"""
Ensure that an admin can't access to "My participation".
"""
response = self.client.get(reverse("participation:my_participation_detail"))
self.assertEqual(response.status_code, 403)