import pytest import tempfile from django.urls import reverse from django.contrib.auth.models import Group, User from django.test import Client SAFE_STATUS_CODES = {200, 301, 302, 303, 403, 404, 405} @pytest.fixture def candidate_client(db): user = User.objects.create_user(username="candidate", password="password", email="candidate@test.com") client = Client() client.force_login(user) return client @pytest.fixture def superuser_client(db): user = User.objects.create_superuser(username="superuser", password="password", email="superuser@test.com") for group_name in ["longs_checker", "cid_user_manager"]: g, _ = Group.objects.get_or_create(name=group_name) user.groups.add(g) client = Client() client.force_login(user) return client @pytest.fixture def anonymous_client(db): return Client() @pytest.fixture def smoke_data(db, settings, tmp_path): from longs.models import Long, LongSeries, LongSeriesImage, Exam, UserAnswer, Examination settings.MEDIA_ROOT = str(tmp_path) create_user = User.objects.create_user(username="smoke_user", email="smoke_user@test.com") exm_name, _ = Examination.objects.get_or_create(examination="Test Examination") question = Long.objects.create( description="Test description", history="Test History", model_observations="Test Observations", model_interpretation="Test Interpretation", model_principle_diagnosis="Test Diagnosis", model_differential_diagnosis="Test Differentials", model_management="Test Management", ) series = LongSeries.objects.create( description="Test Series", examination=exm_name, ) question.series.add(series) # Mocking series image image = tempfile.NamedTemporaryFile( dir=settings.MEDIA_ROOT, suffix=".jpg", delete=False ) image.flush() image._committed = True image.write(b"12345ABCD") image.seek(0) series_image = LongSeriesImage(image=image.name, series=series) series_image.save() exam = Exam.objects.create( name="Test Longs Exam", exam_mode=True, active=True ) exam.author.add(create_user) from longs.models import ExamQuestionDetail ExamQuestionDetail.objects.create(exam=exam, question=question, sort_order=1) user_answer = UserAnswer.objects.create( user=create_user, exam=exam, question=question, answer_observations="testanswer", answer_interpretation="testanswer", answer_principle_diagnosis="testanswer", answer_differential_diagnosis="testanswer", answer_management="testanswer", ) return { "question": question, "series": series, "exam": exam, "user_answer": user_answer, } URL_SPECS = [ ("longs:author_list", None), ("longs:question_view", None), ("longs:series_view", None), ("longs:series_detail", lambda d: {"pk": d["series"].pk}), ("longs:long_series_order_dicom", lambda d: {"pk": d["series"].pk}), ("longs:long_series_download", lambda d: {"pk": d["series"].pk}), ("longs:long_series_order_dicom_instance", lambda d: {"pk": d["series"].pk}), ("longs:long_series_order_dicom_SeriesInstanceUID", lambda d: {"pk": d["series"].pk}), ("longs:long_series_order_upload_filename", lambda d: {"pk": d["series"].pk}), ("longs:long_series_delete", lambda d: {"pk": d["series"].pk}), ("longs:question_detail", lambda d: {"pk": d["question"].pk}), ("longs:question_json", lambda d: {"pk": d["question"].pk}), ("longs:question_json_unbased", lambda d: {"pk": d["question"].pk}), ("longs:question_json_recreate", lambda d: {"pk": d["question"].pk}), ("longs:long_split", lambda d: {"pk": d["question"].pk}), ("longs:long_clone", lambda d: {"pk": d["question"].pk}), ("longs:long_scrap", lambda d: {"pk": d["question"].pk}), ("longs:long_delete", lambda d: {"pk": d["question"].pk}), ("longs:mark_answer", lambda d: {"exam_id": d["exam"].pk, "question_number": 0, "answer_id": d["user_answer"].pk}), ("longs:mark_answer_override", lambda d: {"exam_id": d["exam"].pk, "question_number": 0, "answer_id": d["user_answer"].pk}), ("longs:mark", lambda d: {"exam_id": d["exam"].pk, "sk": 0}), ("longs:exam_markers", lambda d: {"pk": d["exam"].pk}), ("longs:exam_groups_edit", lambda d: {"pk": d["exam"].pk}), ("longs:exam_authors", lambda d: {"pk": d["exam"].pk}), ("longs:refresh_exam_question_json", lambda d: {"pk": d["exam"].pk}), ("longs:exam_create", None), ("longs:exam_clone", lambda d: {"exam_id": d["exam"].pk}), ("longs:exam_update", lambda d: {"pk": d["exam"].pk}), ("longs:exam_delete", lambda d: {"pk": d["exam"].pk}), ("longs:question_create", None), ("longs:series_create", None), ("longs:long_series_id_create", lambda d: {"pk": d["question"].pk}), ("longs:create_examination", None), ("longs:long_update", lambda d: {"pk": d["question"].pk}), ("longs:long_series_update", lambda d: {"pk": d["series"].pk}), ("longs:user_answer_table_view", None), ("longs:user_answer_view", lambda d: {"pk": d["user_answer"].pk}), ("longs:user_answer_delete", lambda d: {"pk": d["user_answer"].pk}), ("longs:user_answer_delete_multiple", None), ("longs:index", None), ("longs:help", None), ] @pytest.mark.django_db @pytest.mark.parametrize("url_name, kwargs_lambda", URL_SPECS) def test_url_smoke_anonymous(anonymous_client, smoke_data, url_name, kwargs_lambda): kwargs = kwargs_lambda(smoke_data) if kwargs_lambda else None url = reverse(url_name, kwargs=kwargs) response = anonymous_client.get(url, follow=False) assert response.status_code != 500, f"500 Server Error on {url_name} ({url}) for Anonymous" assert response.status_code in {200, 302, 400, 403, 404, 405}, f"Unexpected status code {response.status_code} on {url_name} for Anonymous" @pytest.mark.django_db @pytest.mark.parametrize("url_name, kwargs_lambda", URL_SPECS) def test_url_smoke_candidate(candidate_client, smoke_data, url_name, kwargs_lambda): kwargs = kwargs_lambda(smoke_data) if kwargs_lambda else None url = reverse(url_name, kwargs=kwargs) response = candidate_client.get(url, follow=False) assert response.status_code != 500, f"500 Server Error on {url_name} ({url}) for Candidate" assert response.status_code in SAFE_STATUS_CODES or response.status_code == 400, f"Unexpected status code {response.status_code} on {url_name} for Candidate" @pytest.mark.django_db @pytest.mark.parametrize("url_name, kwargs_lambda", URL_SPECS) def test_url_smoke_superuser(superuser_client, smoke_data, url_name, kwargs_lambda): kwargs = kwargs_lambda(smoke_data) if kwargs_lambda else None url = reverse(url_name, kwargs=kwargs) response = superuser_client.get(url, follow=False) assert response.status_code != 500, f"500 Server Error on {url_name} ({url}) for Superuser" assert response.status_code in {200, 301, 302, 303, 400, 403, 404, 405}, f"Unexpected status code {response.status_code} on {url_name} for Superuser"