Skip to content

Commit

Permalink
Merge pull request #2356 from uktrade/LTD-5907
Browse files Browse the repository at this point in the history
LTD-5907 Add notes flow
  • Loading branch information
markj0hnst0n authored Feb 17, 2025
2 parents fc3e033 + 806ef54 commit 331fbd8
Show file tree
Hide file tree
Showing 9 changed files with 217 additions and 0 deletions.
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
class FormSteps:
NOTES_FOR_CASEWORKER = "NOTES_FOR_CASEWORKER"
17 changes: 17 additions & 0 deletions exporter/f680/application_sections/additional_information/forms.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
from django import forms

from core.common.forms import BaseForm


class NotesForCaseOfficerForm(BaseForm):
class Layout:
TITLE = "Notes"
SUBMIT_BUTTON_TEXT = "Save and continue"

note = forms.CharField(
label="Add note",
widget=forms.Textarea(attrs={"cols": "80"}),
)

def get_layout_fields(self):
return ("note",)
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,153 @@
import pytest

from django.urls import reverse

from core import client

from ..forms import NotesForCaseOfficerForm
from ..constants import FormSteps


@pytest.fixture()
def unset_f680_feature_flag(settings):
settings.FEATURE_FLAG_ALLOW_F680 = False


@pytest.fixture(autouse=True)
def setup(mock_exporter_user_me, settings):
settings.FEATURE_FLAG_ALLOW_F680 = True


@pytest.fixture
def missing_application_id():
return "6bb0828c-1520-4624-b729-7f3e6e5b9f5d"


@pytest.fixture
def missing_f680_application_wizard_url(missing_application_id):
return reverse(
"f680:additional_information:notes_wizard",
kwargs={"pk": missing_application_id},
)


@pytest.fixture
def f680_application_wizard_url(data_f680_case):
return reverse(
"f680:additional_information:notes_wizard",
kwargs={"pk": data_f680_case["id"]},
)


@pytest.fixture
def mock_f680_application_get_404(requests_mock, missing_application_id):
url = client._build_absolute_uri(f"/exporter/f680/application/{missing_application_id}/")
return requests_mock.get(url=url, json={}, status_code=404)


@pytest.fixture
def mock_f680_application_get(requests_mock, data_f680_case):
application_id = data_f680_case["id"]
url = client._build_absolute_uri(f"/exporter/f680/application/{application_id}/")
return requests_mock.get(url=url, json=data_f680_case)


@pytest.fixture
def mock_f680_application_get_existing_data(requests_mock, data_f680_case):
data_f680_case["application"] = {
"additional_information": {"answers": {"note": "Some note text"}, "questions": {"note": "Add note"}}
}
application_id = data_f680_case["id"]
url = client._build_absolute_uri(f"/exporter/f680/application/{application_id}/")
return requests_mock.get(url=url, json=data_f680_case)


@pytest.fixture
def mock_patch_f680_application(requests_mock, data_f680_case):
application_id = data_f680_case["id"]
url = client._build_absolute_uri(f"/exporter/f680/application/{application_id}/")
return requests_mock.patch(url=url, json=data_f680_case)


@pytest.fixture
def post_to_step(post_to_step_factory, f680_application_wizard_url):
return post_to_step_factory(f680_application_wizard_url)


@pytest.fixture
def goto_step(goto_step_factory, f680_application_wizard_url):
return goto_step_factory(f680_application_wizard_url)


class TestAdditionalInformationView:

def test_GET_no_application_404(
self,
authorized_client,
missing_f680_application_wizard_url,
mock_f680_application_get_404,
):
response = authorized_client.get(missing_f680_application_wizard_url)
assert response.status_code == 404

def test_GET_success(
self,
authorized_client,
mock_f680_application_get,
f680_application_wizard_url,
):
response = authorized_client.get(f680_application_wizard_url)
assert response.status_code == 200
assert isinstance(response.context["form"], NotesForCaseOfficerForm)

def test_GET_no_feature_flag_forbidden(
self,
authorized_client,
mock_f680_application_get,
f680_application_wizard_url,
unset_f680_feature_flag,
):
response = authorized_client.get(f680_application_wizard_url)
assert response.status_code == 200
assert response.context["title"] == "Forbidden"

def test_POST_approval_type_and_submit_wizard_success(
self, post_to_step, goto_step, mock_f680_application_get, mock_patch_f680_application
):
response = post_to_step(
FormSteps.NOTES_FOR_CASEWORKER,
{"note": "Some information"},
)
assert response.status_code == 302
assert mock_patch_f680_application.called_once
assert mock_patch_f680_application.last_request.json() == {
"application": {
"name": "F680 Test 1",
"additional_information": {"answers": {"note": "Some information"}, "questions": {"note": "Add note"}},
}
}

def test_POST_to_step_validation_error(
self,
post_to_step,
goto_step,
mock_f680_application_get,
):
goto_step(FormSteps.NOTES_FOR_CASEWORKER)
response = post_to_step(
FormSteps.NOTES_FOR_CASEWORKER,
{},
)
assert response.status_code == 200
assert response.context["form"]["note"].errors == ["This field is required."]

def test_GET_with_existing_data_success(
self,
authorized_client,
mock_f680_application_get_existing_data,
f680_application_wizard_url,
):
response = authorized_client.get(f680_application_wizard_url)
assert response.status_code == 200
assert isinstance(response.context["form"], NotesForCaseOfficerForm)
assert response.context["form"]["note"].initial == "Some note text"
10 changes: 10 additions & 0 deletions exporter/f680/application_sections/additional_information/urls.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
from django.urls import path

from . import views


app_name = "additional_information"

urlpatterns = [
path("notes/", views.NotesForCaseOfficersView.as_view(), name="notes_wizard"),
]
11 changes: 11 additions & 0 deletions exporter/f680/application_sections/additional_information/views.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
from exporter.f680.application_sections.views import F680ApplicationSectionWizard

from .constants import FormSteps
from .forms import NotesForCaseOfficerForm


class NotesForCaseOfficersView(F680ApplicationSectionWizard):
form_list = [
(FormSteps.NOTES_FOR_CASEWORKER, NotesForCaseOfficerForm),
]
section = "additional_information"
4 changes: 4 additions & 0 deletions exporter/f680/urls.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,4 +12,8 @@
"<uuid:pk>/general-application-details/",
include("exporter.f680.application_sections.general_application_details.urls"),
),
path(
"<uuid:pk>/additional-information/",
include("exporter.f680.application_sections.additional_information.urls"),
),
]
20 changes: 20 additions & 0 deletions exporter/templates/f680/summary.html
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,26 @@ <h2 class="lite-task-list__section">
</div>
</li>
</ul>
<h2 class="lite-task-list__section">
<span class="lite-task-list__section-number">4. </span>
Additional Information
</h2>
<ul class="lite-task-list__items">
<li class="lite-task-list__item">
<div class="lite-task-list__item-header">
<a class="govuk-link govuk-link--no-visited-state" href="{% url "f680:additional_information:notes_wizard" pk=application.id %}">Notes for case officers</a>
{% if application.application.additional_information.answers.note %}
<div class="lite-tag lite-tag--blue">
Completed
</div>
{% else %}
<div class="lite-tag lite-tag--grey">
Not Started
</div>
{% endif %}
</div>
</li>
</ul>
</li>
</ol>
<div class="app-submit-bar">
Expand Down

0 comments on commit 331fbd8

Please sign in to comment.