Skip to content

Commit 7107a6c

Browse files
miriam-zThemitchell
authored andcommitted
PPHA-264: Add sex-at-birth page
1 parent 1d3e841 commit 7107a6c

File tree

17 files changed

+336
-19
lines changed

17 files changed

+336
-19
lines changed

lung_cancer_screening/core/tests/acceptance/helpers/user_interaction_helpers.py

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,3 +52,11 @@ def fill_in_and_submit_weight_imperial(page, stone, pounds):
5252
page.get_by_label("Pounds").fill(str(pounds))
5353

5454
page.click("text=Continue")
55+
56+
def fill_in_and_submit_sex_at_birth(page, sex):
57+
expect(page.locator("legend")).to_have_text(
58+
"What was your sex at birth?")
59+
60+
page.get_by_label(sex, exact=True).check()
61+
62+
page.click("text=Continue")

lung_cancer_screening/core/tests/acceptance/test_cannot_change_answers_after_submission.py

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,8 @@
99
fill_in_and_submit_weight_metric,
1010
fill_in_and_submit_participant_id,
1111
fill_in_and_submit_smoking_eligibility,
12-
fill_in_and_submit_date_of_birth
12+
fill_in_and_submit_date_of_birth,
13+
fill_in_and_submit_sex_at_birth
1314
)
1415

1516
class TestQuestionnaire(StaticLiveServerTestCase):
@@ -40,6 +41,7 @@ def test_cannot_change_responses_once_checked_and_submitted(self):
4041
fill_in_and_submit_date_of_birth(page, age)
4142
fill_in_and_submit_height_metric(page, "170")
4243
fill_in_and_submit_weight_metric(page, "25.4")
44+
fill_in_and_submit_sex_at_birth(page, "Male")
4345

4446
page.click("text=Submit")
4547

lung_cancer_screening/core/tests/acceptance/test_questionnaire.py

Lines changed: 15 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,8 @@
1111
fill_in_and_submit_smoking_eligibility,
1212
fill_in_and_submit_date_of_birth,
1313
fill_in_and_submit_weight_metric,
14-
fill_in_and_submit_weight_imperial
14+
fill_in_and_submit_weight_imperial,
15+
fill_in_and_submit_sex_at_birth
1516
)
1617

1718
from .helpers.assertion_helpers import expect_back_link_to_have_url
@@ -49,43 +50,45 @@ def test_full_questionnaire_user_journey(self):
4950

5051
expect(page).to_have_url(
5152
f"{self.live_server_url}/have-you-ever-smoked")
52-
53+
expect_back_link_to_have_url(page, "/start")
5354
fill_in_and_submit_smoking_eligibility(page, smoking_status)
5455

5556
expect(page).to_have_url(f"{self.live_server_url}/date-of-birth")
5657
expect_back_link_to_have_url(page, "/have-you-ever-smoked")
57-
5858
fill_in_and_submit_date_of_birth(page, age)
5959

6060
expect(page).to_have_url(f"{self.live_server_url}/height")
61-
61+
expect_back_link_to_have_url(page, "/date-of-birth")
6262
fill_in_and_submit_height_metric(page, height)
6363

64-
expect(page).to_have_url(f"{self.live_server_url}/weight")
65-
6664
page.click("text=Back")
67-
6865
expect(page).to_have_url(f"{self.live_server_url}/height")
69-
7066
page.click("text=Switch to imperial")
71-
7267
fill_in_and_submit_height_imperial(page, feet, inches)
7368

7469
expect(page).to_have_url(f"{self.live_server_url}/weight")
75-
70+
expect_back_link_to_have_url(page, "/height")
7671
fill_in_and_submit_weight_metric(page, weight_metric)
77-
78-
expect(page).to_have_url(f"{self.live_server_url}/responses")
7972
page.click("text=Back")
73+
74+
expect(page).to_have_url(f"{self.live_server_url}/weight")
8075
page.get_by_role("link", name="Switch to stone and pounds").click()
8176
fill_in_and_submit_weight_imperial(page, weight_stone, weight_pound)
77+
78+
expect(page).to_have_url(f"{self.live_server_url}/sex-at-birth")
79+
expect_back_link_to_have_url(page, "/weight")
80+
fill_in_and_submit_sex_at_birth(page, "Male")
81+
8282
expect(page).to_have_url(f"{self.live_server_url}/responses")
83+
expect_back_link_to_have_url(page, "/sex-at-birth")
84+
8385
responses = page.locator(".responses")
8486
expect(responses).to_contain_text("Have you ever smoked? Yes, I used to smoke regularly")
8587
expect(responses).to_contain_text(
8688
age.strftime("What is your date of birth? %Y-%m-%d"))
8789
expect(responses).to_contain_text(f"What is your height? {feet} feet {inches} inches")
8890
expect(responses).to_contain_text(f"What is your weight? {weight_stone} stone {weight_pound} pound")
91+
expect(responses).to_contain_text("What was your sex at birth? Male")
8992

9093
page.click("text=Submit")
9194

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
from django import forms
2+
3+
from ...nhsuk_forms.typed_choice_field import TypedChoiceField
4+
from ..models.response_set import ResponseSet, SexAtBirthValues
5+
6+
class SexAtBirthForm(forms.ModelForm):
7+
8+
def __init__(self, *args, **kwargs):
9+
self.participant = kwargs.pop('participant')
10+
super().__init__(*args, **kwargs)
11+
self.instance.participant = self.participant
12+
13+
self.fields["sex_at_birth"] = TypedChoiceField(
14+
choices=SexAtBirthValues.choices,
15+
widget=forms.RadioSelect,
16+
label="What was your sex at birth?",
17+
label_classes="nhsuk-fieldset__legend--m",
18+
hint="Your sex may impact your chances of developing lung cancer.",
19+
error_messages={
20+
'required': 'Select your sex at birth.'
21+
}
22+
)
23+
24+
class Meta:
25+
model = ResponseSet
26+
fields = ['sex_at_birth']

lung_cancer_screening/questions/jinja2/have_you_ever_smoked.jinja

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,16 @@
11
{% extends 'layout.jinja' %}
22
{% from 'nhsuk/components/button/macro.jinja' import button %}
33
{% from 'nhsuk/components/radios/macro.jinja' import radios %}
4+
{% from 'nhsuk/components/back-link/macro.jinja' import backLink %}
5+
6+
{% block beforeContent %}
7+
{{
8+
backLink({
9+
"href": url("questions:start"),
10+
"text": "Back"
11+
})
12+
}}
13+
{% endblock beforeContent %}
414

515
{% block content %}
616
<div class="nhsuk-grid-row">

lung_cancer_screening/questions/jinja2/responses.jinja

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
{% block beforeContent %}
66
{{
77
backLink({
8-
"href": url("questions:weight"),
8+
"href": url("questions:sex_at_birth"),
99
"text": "Back"
1010
})
1111
}}
@@ -20,6 +20,7 @@
2020
<li>What is your date of birth? {{ response_set.date_of_birth }}</li>
2121
<li>What is your height? {{ response_set.formatted_height }}</li>
2222
<li>What is your weight? {{ response_set.formatted_weight }}</li>
23+
<li>What was your sex at birth? {{ response_set.get_sex_at_birth_display() }}</li>
2324
</ul>
2425

2526
<form action="{{ request.path }}" method="post">
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
{% extends 'layout.jinja' %}
2+
{% from 'nhsuk/components/button/macro.jinja' import button %}
3+
{% from 'nhsuk/components/back-link/macro.jinja' import backLink %}
4+
5+
{% block beforeContent %}
6+
{{
7+
backLink({
8+
"href": url("questions:weight"),
9+
"text": "Back"
10+
})
11+
}}
12+
{% endblock beforeContent %}
13+
14+
{% block page_content %}
15+
<div class="nhsuk-grid-row">
16+
<div class="nhsuk-grid-column-two-thirds">
17+
<form action="{{ request.path }}" method="POST">
18+
{{ csrf_input }}
19+
20+
{{ form }}
21+
22+
{{ button({
23+
"text": "Continue"
24+
}) }}
25+
</form>
26+
</div>
27+
</div>
28+
{% endblock %}
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
# Generated by Django 5.2.7 on 2025-10-28 11:09
2+
3+
from django.db import migrations, models
4+
5+
6+
class Migration(migrations.Migration):
7+
8+
dependencies = [
9+
('questions', '0012_responseset_weight_imperial_and_more'),
10+
]
11+
12+
operations = [
13+
migrations.AddField(
14+
model_name='responseset',
15+
name='sex_at_birth',
16+
field=models.CharField(blank=True, choices=[('F', 'Female'), ('M', 'Male')], max_length=1, null=True),
17+
),
18+
]

lung_cancer_screening/questions/models/response_set.py

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,10 @@ class HaveYouEverSmokedValues(models.IntegerChoices):
1414
YES_BUT_ONLY_A_FEW_TIMES = 2, 'Yes, but only a few times'
1515
NO_I_HAVE_NEVER_SMOKED = 3, 'No, I have never smoked'
1616

17+
class SexAtBirthValues(models.TextChoices):
18+
FEMALE = "F", 'Female'
19+
MALE = "M", 'Male'
20+
1721
class ResponseSet(BaseModel):
1822
participant = models.ForeignKey(Participant, on_delete=models.CASCADE)
1923

@@ -54,6 +58,14 @@ class ResponseSet(BaseModel):
5458
MaxValueValidator(
5559
MAX_WEIGHT_IMPERIAL, message="Weight must be between 4 stone and 50 stone"),
5660
])
61+
62+
sex_at_birth = models.CharField(
63+
max_length=1,
64+
choices=SexAtBirthValues.choices,
65+
null=True,
66+
blank=True
67+
)
68+
5769
submitted_at = models.DateTimeField(null=True, blank=True)
5870

5971
class Meta:
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
from django.test import TestCase
2+
3+
from ....models.response_set import SexAtBirthValues
4+
from ....models.participant import Participant
5+
from ....forms.sex_at_birth_form import SexAtBirthForm
6+
7+
class TestSexAtBirthForm(TestCase):
8+
def setUp(self):
9+
self.participant = Participant.objects.create(unique_id="1234567890")
10+
11+
def test_is_valid_with_a_valid_value(self):
12+
form = SexAtBirthForm(
13+
participant=self.participant,
14+
data={
15+
"sex_at_birth": SexAtBirthValues.FEMALE
16+
}
17+
)
18+
self.assertTrue(form.is_valid())
19+
self.assertEqual(
20+
form.cleaned_data["sex_at_birth"],
21+
SexAtBirthValues.FEMALE.value
22+
)
23+
24+
def test_is_invalid_with_an_invalid_value(self):
25+
form = SexAtBirthForm(
26+
participant=self.participant,
27+
data={
28+
"sex_at_birth": "invalid"
29+
}
30+
)
31+
self.assertFalse(form.is_valid())
32+
self.assertEqual(
33+
form.errors["sex_at_birth"],
34+
["Select a valid choice. invalid is not one of the available choices."]
35+
)
36+
37+
def test_is_invalid_when_no_option_is_selected(self):
38+
form = SexAtBirthForm(
39+
participant=self.participant,
40+
data={
41+
"sex_at_birth": None
42+
}
43+
)
44+
self.assertFalse(form.is_valid())
45+
self.assertEqual(
46+
form.errors["sex_at_birth"],
47+
["Select your sex at birth."]
48+
)

0 commit comments

Comments
 (0)