diff --git a/AdminWebsite/AdminWebsite.UnitTests/Controllers/AudioPlatformControllerTests.cs b/AdminWebsite/AdminWebsite.UnitTests/Controllers/AudioPlatformControllerTests.cs index 107cfe0bc..07c7c0267 100644 --- a/AdminWebsite/AdminWebsite.UnitTests/Controllers/AudioPlatformControllerTests.cs +++ b/AdminWebsite/AdminWebsite.UnitTests/Controllers/AudioPlatformControllerTests.cs @@ -1,5 +1,4 @@ using System.Threading.Tasks; -using AdminWebsite.Configuration; using AdminWebsite.Controllers; using AdminWebsite.Models; using BookingsApi.Client; @@ -20,16 +19,14 @@ public class AudioPlatformControllerTests private readonly Mock _bookingsApiClientMock; private readonly Mock> _loggerMock; - private readonly Mock _featureTogglesMock; public AudioPlatformControllerTests() { _videoApiClientMock = new Mock(); _bookingsApiClientMock = new Mock(); _loggerMock = new Mock>(); - _featureTogglesMock = new Mock(); - _controller = new AudioPlatformController(_videoApiClientMock.Object, _loggerMock.Object, _bookingsApiClientMock.Object, _featureTogglesMock.Object); + _controller = new AudioPlatformController(_videoApiClientMock.Object, _loggerMock.Object, _bookingsApiClientMock.Object); } [Test] @@ -41,7 +38,6 @@ public async Task Should_return_ok() }; _videoApiClientMock.Setup(x => x.GetAudioRecordingLinkAsync(It.IsAny())).ReturnsAsync(audioResponse); - _featureTogglesMock.Setup(x => x.HrsEnabled()).Returns(false); var result = await _controller.GetAudioRecordingLinkAsync(It.IsAny()); @@ -55,7 +51,7 @@ public async Task Should_return_ok() } [Test] - public async Task Should_return_hrs_file_format_with_hrs_toggle_on() + public async Task Should_return_hrs_file_format() { var audioResponse = new AudioRecordingResponse { @@ -72,7 +68,6 @@ public async Task Should_return_hrs_file_format_with_hrs_toggle_on() }; _videoApiClientMock.Setup(x => x.GetAudioRecordingLinkAsync(It.IsAny())).ReturnsAsync(audioResponse); - _featureTogglesMock.Setup(x => x.HrsEnabled()).Returns(true); _bookingsApiClientMock.Setup(x => x.GetHearingDetailsByIdV2Async(It.IsAny())).ReturnsAsync(hearing); var result = await _controller.GetAudioRecordingLinkAsync(It.IsAny()); diff --git a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/BookNewHearingTests.cs b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/BookNewHearingTests.cs index 83f910067..ff839ce5d 100644 --- a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/BookNewHearingTests.cs +++ b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/BookNewHearingTests.cs @@ -47,313 +47,9 @@ public void Setup() TelephoneConferenceId = "expected_conference_phone_id" } }); - _mocker.Mock().Setup(x => x.BookAndConfirmToggle()).Returns(true); _controller = _mocker.Create(); } - [Test] - public async Task Should_book_hearing_for_single_day() - { - // Arrange - var bookingDetails = InitHearingForTest(); - - var bookingRequest = new BookHearingRequest - { - BookingDetails = bookingDetails - }; - - var hearingDetailsResponse = HearingResponseBuilder.Build() - .WithEndPoints(2) - .WithParticipant("Representative", "username1@hmcts.net") - .WithParticipant("Individual", "fname2.lname2@hmcts.net") - .WithParticipant("Individual", "fname3.lname3@hmcts.net") - .WithParticipant("Judicial Office Holder", "fname4.lname4@hmcts.net") - .WithParticipant("Staff Member","staff.member@hmcts.net") - .WithParticipant("Judge", "judge.fudge@hmcts.net"); - _mocker.Mock().Setup(x => x.BookNewHearingAsync(It.IsAny())) - .ReturnsAsync(hearingDetailsResponse); - - - _mocker.Mock().Setup(x => x.GetUserIdentityName()).Returns(_expectedUserIdentityName); - - // Act - var result = await _controller.Post(bookingRequest); - - // Assert - result.Result.Should().BeOfType(); - var createdObjectResult = (CreatedResult) result.Result; - createdObjectResult.StatusCode.Should().Be(201); - createdObjectResult.Value.Should().BeEquivalentTo(hearingDetailsResponse, - options => options.ExcludingMissingMembers()); - - bookingDetails.Participants.Exists(x => string.IsNullOrWhiteSpace(x.Username)).Should().BeFalse(); - - bookingDetails.CreatedBy.Should().Be(_expectedUserIdentityName); - - _mocker.Mock().Verify(x => x.AssignEndpointDefenceAdvocates(It.IsAny>(), It.Is>(x => x.SequenceEqual(bookingDetails.Participants.AsReadOnly()))), Times.Once); - - _mocker.Mock().Verify(x => x.BookNewHearingAsync(It.IsAny()), Times.Once); - } - - [Test] - public async Task Should_book_hearing_without_judge() - { - // Arrange - var bookingDetails = InitHearingForTest(); - //remove judge - bookingDetails.Participants.Remove(bookingDetails.Participants.Find(e => e.HearingRoleName == "Judge")); - var bookingRequest = new BookHearingRequest - { - BookingDetails = bookingDetails - }; - var hearingDetailsResponse = HearingResponseBuilder.Build() - .WithEndPoints(2) - .WithParticipant("Representative", "username1@hmcts.net") - .WithParticipant("Individual", "fname2.lname2@hmcts.net") - .WithParticipant("Individual", "fname3.lname3@hmcts.net") - .WithParticipant("Judicial Office Holder", "fname4.lname4@hmcts.net") - .WithParticipant("Staff Member", "staff.member@hmcts.net"); - - _mocker.Mock().Setup(x => x.BookNewHearingAsync(It.IsAny())) - .ReturnsAsync(hearingDetailsResponse); - - _mocker.Mock().Setup(x => x.GetUserIdentityName()).Returns(_expectedUserIdentityName); - - // Act - var result = await _controller.Post(bookingRequest); - - // Assert - result.Result.Should().BeOfType(); - var createdObjectResult = (CreatedResult) result.Result; - createdObjectResult.StatusCode.Should().Be(201); - createdObjectResult.Value.Should().BeEquivalentTo(hearingDetailsResponse, - options => options.ExcludingMissingMembers()); - - bookingDetails.Participants.Exists(x => string.IsNullOrWhiteSpace(x.Username)).Should().BeFalse(); - - bookingDetails.CreatedBy.Should().Be(_expectedUserIdentityName); - - _mocker.Mock().Verify(x => x.AssignEndpointDefenceAdvocates(It.IsAny>(), It.Is>(x => x.SequenceEqual(bookingDetails.Participants.AsReadOnly()))), Times.Once); - - _mocker.Mock().Verify(x => x.BookNewHearingAsync(It.IsAny()), Times.Once); - } - - [Test] - public async Task Should_book_hearing_for_single_day_without_endpoints() - { - // Arrange - var bookingDetails = InitHearingForTest(); - bookingDetails.Endpoints = null; - - var bookingRequest = new BookHearingRequest - { - BookingDetails = bookingDetails - }; - - var hearingDetailsResponse = HearingResponseBuilder.Build() - .WithEndPoints(2) - .WithParticipant("Representative", "username1@hmcts.net") - .WithParticipant("Individual", "fname2.lname2@hmcts.net") - .WithParticipant("Individual", "fname3.lname3@hmcts.net") - .WithParticipant("Judicial Office Holder", "fname4.lname4@hmcts.net") - .WithParticipant("Judge", "judge.fudge@hmcts.net"); - _mocker.Mock().Setup(x => x.BookNewHearingAsync(It.IsAny())) - .ReturnsAsync(hearingDetailsResponse); - - _mocker.Mock().Setup(x => x.GetUserIdentityName()).Returns(_expectedUserIdentityName); - - // Act - var result = await _controller.Post(bookingRequest); - - // Assert - result.Result.Should().BeOfType(); - var createdObjectResult = (CreatedResult) result.Result; - createdObjectResult.StatusCode.Should().Be(201); - createdObjectResult.Value.Should().BeEquivalentTo(hearingDetailsResponse, - options => options.ExcludingMissingMembers()); - - bookingDetails.CreatedBy.Should().Be(_expectedUserIdentityName); - bookingDetails.Participants.Exists(x => string.IsNullOrWhiteSpace(x.Username)).Should().BeFalse(); - - _mocker.Mock().Verify(x => x.AssignEndpointDefenceAdvocates(It.IsAny>(), It.Is>(x => x.SequenceEqual(bookingDetails.Participants.AsReadOnly()))), Times.Never); - - _mocker.Mock().Verify(x => x.BookNewHearingAsync(It.IsAny()), Times.Once); - } - - [Test] - public async Task Should_book_hearing_for_multi_day() - { - // Arrange - const int expectedMultiDayHearingDuration = 3; - DateTime expectedStartDate = new DateTime(2021, 5, 10, 0, 0, 1, DateTimeKind.Utc); - DateTime expectedEndDate = expectedStartDate.AddDays(expectedMultiDayHearingDuration - 1); - - var bookingDetails = InitHearingForTest(); - - var bookingRequest = new BookHearingRequest - { - IsMultiDay = true, - MultiHearingDetails = new MultiHearingRequest - { - StartDate = expectedStartDate, - EndDate = expectedEndDate - }, - BookingDetails = bookingDetails - }; - - _mocker.Mock().Setup(x => x.GetAdUserIdForUsername(It.IsAny())).ReturnsAsync(Guid.NewGuid().ToString()); - - _mocker.Mock().Setup(x => x.GetUserIdentityName()).Returns(_expectedUserIdentityName); - - // setup response - var hearingDetailsResponse = HearingResponseBuilder.Build() - .WithEndPoints(2) - .WithParticipant("Representative", "username1@hmcts.net") - .WithParticipant("Individual", "fname2.lname2@hmcts.net") - .WithParticipant("Individual", "fname3.lname3@hmcts.net") - .WithParticipant("Judicial Office Holder", "fname4.lname4@hmcts.net") - .WithParticipant("Judge", "judge.fudge@hmcts.net"); - - _mocker.Mock() - .Setup(x => x.BookNewHearingAsync(It.IsAny())) - .ReturnsAsync(hearingDetailsResponse); - - // Act - var result = await _controller.Post(bookingRequest); - - // Assert - result.Result.Should().BeOfType(); - var createdObjectResult = (CreatedResult) result.Result; - createdObjectResult.StatusCode.Should().Be(201); - createdObjectResult.Value.Should().BeEquivalentTo(hearingDetailsResponse, - options => options.ExcludingMissingMembers()); - - bookingDetails.CreatedBy.Should().Be(_expectedUserIdentityName); - bookingDetails.Participants.Exists(x => string.IsNullOrWhiteSpace(x.Username)).Should().BeFalse(); - - _mocker.Mock().Verify(x => x.AssignEndpointDefenceAdvocates(It.IsAny>(), It.Is>(x => x.SequenceEqual(bookingDetails.Participants.AsReadOnly()))), Times.Once); - - _mocker.Mock().Verify(x => x.BookNewHearingAsync(It.IsAny()), Times.Once); - } - - [Test] - public async Task Should_book_hearing_with_use_v2_api_flag_on() - { - // Arrange - _mocker.Mock().Setup(x => x.UseV2Api()).Returns(true); - var bookingDetails = InitHearingForV2Test(); - - var bookingRequest = new BookHearingRequest - { - BookingDetails = bookingDetails - }; - - var hearingDetailsResponse = HearingResponseV2Builder.Build() - .WithEndPoints(2) - .WithParticipant("Representative", "username1@hmcts.net") - .WithParticipant("Individual", "fname2.lname2@hmcts.net") - .WithParticipant("Individual", "fname3.lname3@hmcts.net") - .WithParticipant("Judicial Office Holder", "fname4.lname4@hmcts.net") - .WithParticipant("Judge", "judge.fudge@hmcts.net"); - - _mocker.Mock().Setup(x => x.BookNewHearingWithCodeAsync(It.IsAny())) - .ReturnsAsync(hearingDetailsResponse); - - - _mocker.Mock().Setup(x => x.GetUserIdentityName()).Returns(_expectedUserIdentityName); - - // Act - var result = await _controller.Post(bookingRequest); - - // Assert - result.Result.Should().BeOfType(); - var createdObjectResult = (CreatedResult) result.Result; - createdObjectResult.StatusCode.Should().Be(201); - createdObjectResult.Value.Should().BeEquivalentTo(hearingDetailsResponse, options => options.ExcludingMissingMembers()); - - bookingDetails.Participants.Exists(x => string.IsNullOrWhiteSpace(x.Username)).Should().BeFalse(); - - bookingDetails.CreatedBy.Should().Be(_expectedUserIdentityName); - - _mocker.Mock().Verify(x - => x.AssignEndpointDefenceAdvocates(It.IsAny>(), - It.Is>(x => x.SequenceEqual(bookingDetails.Participants.AsReadOnly()))), Times.Once); - - _mocker.Mock().Verify(x => x.BookNewHearingWithCodeAsync(It.IsAny()), Times.Once); - } - - [Test] - public async Task Should_catch_bookings_api_exceptions_and_return_bad_request_if_that_was_the_status_code() - { - // Arrange - var bookingDetails = InitHearingForTest(); - - var bookingRequest = new BookHearingRequest - { - BookingDetails = bookingDetails - }; - - _mocker.Mock().Setup(x => x.GetAdUserIdForUsername(It.IsAny())).ReturnsAsync(Guid.NewGuid().ToString()); - - const string key = "ScheduledDateTime"; - const string errorMessage = "ScheduledDateTime cannot be in the past"; - var validationProblemDetails = new ValidationProblemDetails(new Dictionary - { - {key, [errorMessage] }, - }); - _mocker.Mock().Setup(x => x.BookNewHearingAsync(It.IsAny())) - .Throws(ClientException.ForBookingsAPIValidation(validationProblemDetails)); - - // Act - var result = await _controller.Post(bookingRequest); - - // Assert - result.Result.Should().NotBeNull(); - var objectResult = (ObjectResult)result.Result; - - var validationProblems = (ValidationProblemDetails)objectResult.Value; - validationProblems.Should().NotBeNull(); - validationProblems!.Errors.ContainsKey(key).Should().BeTrue(); - validationProblems.Errors[key][0].Should().Be(errorMessage); - - _mocker.Mock().Verify(x => x.AssignEndpointDefenceAdvocates(It.IsAny>(), It.Is>(x => x.SequenceEqual(bookingDetails.Participants.AsReadOnly()))), Times.Once); - - _mocker.Mock().Verify(x => x.BookNewHearingAsync(It.IsAny()), Times.Once); - } - - [Test] - public async Task Should_handle_failed_booking_request() - { - var bookingDetails = InitHearingForTest(); - - var bookingRequest = new BookHearingRequest - { - BookingDetails = bookingDetails - }; - - var hearingDetailsResponse = - HearingResponseBuilder.Build() - .WithParticipant("Judge", "manual.judge@hmcts.net"); - - hearingDetailsResponse.Status = BookingStatus.Failed; - - _mocker.Mock().Setup(x => x.BookNewHearingAsync(It.IsAny())) - .ReturnsAsync(hearingDetailsResponse); - - _mocker.Mock().Setup(x => x.GetUserIdentityName()).Returns(_expectedUserIdentityName); - - var result = await _controller.Post(bookingRequest); - - var response = ((ObjectResult)result.Result)?.Value as HearingDetailsResponse; - - response.Status.Should().Be((AdminWebsite.Contracts.Enums.BookingStatus)BookingStatus.Failed); - - ((ObjectResult)result.Result).StatusCode.Should().Be(201); - - _mocker.Mock().Verify(x => x.BookNewHearingAsync(It.IsAny()), Times.Once); - } - - private BookingDetailsRequest InitHearingForTest() { // request with existing person, new user, existing user in AD but not in persons table diff --git a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/CancelMultiDayHearingTests.cs b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/CancelMultiDayHearingTests.cs index 8189e072e..b06f32d87 100644 --- a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/CancelMultiDayHearingTests.cs +++ b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/CancelMultiDayHearingTests.cs @@ -24,69 +24,10 @@ protected override void Setup() UserIdentity.Setup(x => x.GetUserIdentityName()).Returns(UpdatedBy); } - [TestCase(false)] - [TestCase(true)] - public async Task should_cancel_multi_day_hearing_for_v1(bool updateFutureDays) - { - // Arrange - var hearingId = Guid.NewGuid(); - var groupId = Guid.NewGuid(); - var hearingDates = new List - { - DateTime.Today.AddDays(1).AddHours(10), - DateTime.UtcNow.AddDays(2).AddHours(10), - DateTime.UtcNow.AddDays(3).AddHours(10), - DateTime.UtcNow.AddDays(4).AddHours(10), - DateTime.UtcNow.AddDays(5).AddHours(10), - }; - var existingHearingsInMultiDayGroup = CreateListOfV1HearingsInMultiDayGroup(groupId, hearingId, scheduledDates: hearingDates); - existingHearingsInMultiDayGroup[3].Status = BookingStatus.Cancelled; - existingHearingsInMultiDayGroup[4].Status = BookingStatus.Failed; - BookingsApiClient.Setup(x => x.GetHearingsByGroupIdAsync(groupId)).ReturnsAsync(existingHearingsInMultiDayGroup); - var hearing = existingHearingsInMultiDayGroup.First(x => x.Id == hearingId); - BookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(hearingId)).ReturnsAsync(hearing); - - var request = CreateRequest(); - request.UpdateFutureDays = updateFutureDays; - - FeatureToggle.Setup(e => e.UseV2Api()).Returns(false); - - // Act - var response = await Controller.CancelMultiDayHearing(hearing.Id, request); - - // Assert - var result = (OkObjectResult)response; - result.StatusCode.Should().Be(StatusCodes.Status200OK); - result.Value.Should().NotBeNull().And.BeAssignableTo().Subject.Success.Should().BeTrue(); - - var expectedUpdatedHearings = new List(); - if (updateFutureDays) - { - expectedUpdatedHearings.AddRange(existingHearingsInMultiDayGroup); - } - else - { - expectedUpdatedHearings.Add(hearing); - } - - expectedUpdatedHearings = expectedUpdatedHearings - .Where(h => - h.Status != BookingStatus.Cancelled && - h.Status != BookingStatus.Failed) - .ToList(); - - BookingsApiClient.Verify(x => x.CancelHearingsInGroupAsync( - groupId, - It.Is(r => - r.UpdatedBy == UpdatedBy && - r.CancelReason == request.CancelReason && - r.HearingIds.SequenceEqual(expectedUpdatedHearings.Select(h => h.Id)))), - Times.Once); - } [TestCase(false)] [TestCase(true)] - public async Task should_cancel_multi_day_hearing_for_v2(bool updateFutureDays) + public async Task should_cancel_multi_day_hearing(bool updateFutureDays) { // Arrange var hearingId = Guid.NewGuid(); @@ -109,9 +50,7 @@ public async Task should_cancel_multi_day_hearing_for_v2(bool updateFutureDays) var request = CreateRequest(); request.UpdateFutureDays = updateFutureDays; - - FeatureToggle.Setup(e => e.UseV2Api()).Returns(true); - + // Act var response = await Controller.CancelMultiDayHearing(hearing.Id, request); @@ -145,9 +84,8 @@ public async Task should_cancel_multi_day_hearing_for_v2(bool updateFutureDays) Times.Once); } - [TestCase(false)] - [TestCase(true)] - public async Task Should_forward_not_found_from_bookings_api(bool useV2) + [Test] + public async Task Should_forward_not_found_from_bookings_api() { // Arrange var hearingId = Guid.NewGuid(); @@ -159,17 +97,8 @@ public async Task Should_forward_not_found_from_bookings_api(bool useV2) null, errorMessage, null); - if (useV2) - { - BookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(hearingId)) + BookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(hearingId)) .ThrowsAsync(apiException); - } - else - { - BookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(hearingId)) - .ThrowsAsync(apiException); - } - FeatureToggle.Setup(e => e.UseV2Api()).Returns(useV2); // Act var result = await Controller.CancelMultiDayHearing(hearingId, request); @@ -179,9 +108,8 @@ public async Task Should_forward_not_found_from_bookings_api(bool useV2) notFoundResult.Value.Should().Be(errorMessage); } - [TestCase(false)] - [TestCase(true)] - public async Task Should_return_bad_request_when_hearing_is_not_multi_day(bool useV2) + [Test] + public async Task Should_return_bad_request_when_hearing_is_not_multi_day() { // Arrange var hearingId = Guid.NewGuid(); @@ -189,16 +117,9 @@ public async Task Should_return_bad_request_when_hearing_is_not_multi_day(bool u var existingHearingsInMultiDayGroup = CreateListOfV1HearingsInMultiDayGroup(groupId, hearingId); var hearing = existingHearingsInMultiDayGroup.First(x => x.Id == hearingId); hearing.GroupId = null; - if (useV2) - { - var mappedHearing = MapHearingDetailsForV2(hearing); - BookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(hearingId)).ReturnsAsync(mappedHearing); - } - else - { - BookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(hearingId)).ReturnsAsync(hearing); - } - FeatureToggle.Setup(e => e.UseV2Api()).Returns(useV2); + + var mappedHearing = MapHearingDetailsForV2(hearing); + BookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(hearingId)).ReturnsAsync(mappedHearing); var request = CreateRequest(); @@ -218,55 +139,6 @@ public async Task Should_return_bad_request_when_hearing_is_not_multi_day(bool u errors.Should().BeEquivalentTo(validationProblemDetails.Errors); } - [Test] - public async Task Should_forward_bad_request_from_bookings_api() - { - // Arrange - var hearingId = Guid.NewGuid(); - var request = new CancelMultiDayHearingRequest(); - var validationProblemDetails = new ValidationProblemDetails(new Dictionary - { - {"id", ["Please provide a valid id"] } - }); - var apiException = new BookingsApiException("BadRequest", - (int)HttpStatusCode.BadRequest, - "Please provide a valid id", - null, - validationProblemDetails, - null); - BookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(hearingId)) - .ThrowsAsync(apiException); - - // Act - var result = await Controller.CancelMultiDayHearing(hearingId, request); - - var objectResult = (ObjectResult)result; - var validationProblems = (ValidationProblemDetails)objectResult.Value; - - var errors = validationProblems.Errors; - errors.Should().BeEquivalentTo(validationProblemDetails.Errors); - } - - [Test] - public void Should_forward_unhandled_error_from_bookings_api() - { - // Arrange - var hearingId = Guid.NewGuid(); - var request = new CancelMultiDayHearingRequest(); - var errorMessage = "Unexpected error for unit test"; - var apiException = new BookingsApiException("Server Error", - (int) HttpStatusCode.InternalServerError, - "Server Error", null, errorMessage, null); - BookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(hearingId)) - .ThrowsAsync(apiException); - - // Act & Assert - var response = Controller.CancelMultiDayHearing(hearingId, request); - - ((ObjectResult) response.Result).StatusCode.Should().Be(500); - - } - private static CancelMultiDayHearingRequest CreateRequest() => new() { diff --git a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/EditHearingTests.cs b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/EditHearingTests.cs index d16248841..aaec43083 100644 --- a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/EditHearingTests.cs +++ b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/EditHearingTests.cs @@ -66,7 +66,6 @@ public void Setup() _editHearingRequestValidator = new Mock>(); _conferencesServiceMock = new Mock(); _featureToggle = new Mock(); - _featureToggle.Setup(e => e.BookAndConfirmToggle()).Returns(true); _conferencesServiceMock.Setup(cs => cs.GetConferenceDetailsByHearingId(It.IsAny(), false)) .ReturnsAsync(new ConferenceDetailsResponse { @@ -86,14 +85,13 @@ public void Setup() _kinlyOptionsMock.Setup((op) => op.Value).Returns(_kinlyConfigurationMock.Object); _participantGroupLogger = new Mock>(); - _hearingsService = new HearingsService(_bookingsApiClient.Object, _participantGroupLogger.Object, _featureToggle.Object); + _hearingsService = new HearingsService(_bookingsApiClient.Object, _participantGroupLogger.Object); _controller = new AdminWebsite.Controllers.HearingsController(_bookingsApiClient.Object, _userIdentity.Object, _editHearingRequestValidator.Object, new Mock>().Object, _hearingsService, - _conferencesServiceMock.Object, - _featureToggle.Object); + _conferencesServiceMock.Object); _validId = Guid.NewGuid(); _addNewParticipantRequest = new EditHearingRequest @@ -412,146 +410,8 @@ public async Task Should_return_bad_request_if_no_participants_are_given() } [Test] - public async Task Should_return_not_found_if_hearing_is_missing() + public async Task Should_return_updated_hearing2() { - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .Throws(ClientException.ForBookingsAPI(HttpStatusCode.NotFound)); - - var result = await _controller.EditHearing(_validId, _addNewParticipantRequest); - var notFoundResult = (NotFoundObjectResult)result.Result; - notFoundResult.Value.Should().Be($"No hearing with id found [{_validId}]"); - } - - [Test] - public void Should_throw_if_hearing_exception_is_not_of_type_not_found() - { - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .Throws(ClientException.ForBookingsAPI(HttpStatusCode.InternalServerError)); - - Assert.ThrowsAsync(async () => await _controller.EditHearing(_validId, _addNewParticipantRequest)); - } - - [Test] - public async Task Should_return_bad_request_if_editing_hearing_fails_with_bad_request_status_code() - { - //Arrange - _addNewParticipantRequest.Participants = new List(); - - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_existingHearingWithLinkedParticipants); - var validationProblemDetails = new ValidationProblemDetails(new Dictionary - { - {"Hearing", ["Cannot remove a participant from hearing that is close to start time"] }, - }); - - _bookingsApiClient.Setup(x => x.UpdateHearingParticipantsAsync(It.IsAny(), It.IsAny())) - .Throws(ClientException.ForBookingsAPIValidation(validationProblemDetails)); - - //Act - var response = await _controller.EditHearing(_validId, _addNewParticipantRequest); - - //Assert - response.Result.Should().BeOfType(); - } - - [Test] - public void Should_throw_if_editing_hearing_fails_with_non_bad_request() - { - - if (true) - { - //execute - } - - if (false) - { - //execute - } - - //Arrange - _addNewParticipantRequest.Participants = new List(); - - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_existingHearingWithLinkedParticipants); - _bookingsApiClient.Setup(x => x.UpdateHearingParticipantsAsync(It.IsAny(), It.IsAny())) - .Throws(ClientException.ForBookingsAPI(HttpStatusCode.InternalServerError)); - - //Act/Assert - - var response = _controller.EditHearing(_validId, _addNewParticipantRequest); - - ((ObjectResult)response.Result.Result).StatusCode.Should().Be(500); - } - - [TestCase("Confirmed By")] - [TestCase("")] - public async Task Should_add_panel_members_for_a_hearing(string confirmedBy) - { - //Arrange - var updatedHearing = new HearingDetailsResponse - { - Participants = _updatedExistingParticipantHearingOriginal.Participants, - Cases = _updatedExistingParticipantHearingOriginal.Cases, - CaseTypeName = "Unit Test", - ConfirmedBy = confirmedBy - }; - - _addNewParticipantRequest.Participants = new List {new EditParticipantRequest - { - HearingRoleName = RoleNames.PanelMember, - ContactEmail = "new.contactactemail@domain.net", - DisplayName = "new.displayName@domain.net", - CaseRoleName = RoleNames.PanelMember - } }; - - _bookingsApiClient.SetupSequence(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_updatedExistingParticipantHearingOriginal) - .ReturnsAsync(updatedHearing) - .ReturnsAsync(updatedHearing); - - //Act - var result = await _controller.EditHearing(_validId, _addNewParticipantRequest); - - //Assert - ((OkObjectResult)result.Result).StatusCode.Should().Be(200); - _bookingsApiClient.Verify(x => x.UpdateHearingDetailsAsync(It.IsAny(), It.IsAny())); - } - - [Test] - public async Task Should_return_updated_hearing() - { - var updatedHearing = new HearingDetailsResponse - { - Id = _validId, - Participants = _updatedExistingParticipantHearingOriginal.Participants, - Cases = _updatedExistingParticipantHearingOriginal.Cases, - CaseTypeName = "Unit Test" - }; - updatedHearing.Participants.Add(new ParticipantResponse - { - Id = Guid.NewGuid(), - ContactEmail = "new@domain.net", - Username = "new@domain.net", - UserRoleName = "Individual" - }); - - _bookingsApiClient.SetupSequence(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_updatedExistingParticipantHearingOriginal) - .ReturnsAsync(updatedHearing) - .ReturnsAsync(updatedHearing); - var result = await _controller.EditHearing(_validId, _addNewParticipantRequest); - var hearing = (AdminWebsite.Contracts.Responses.HearingDetailsResponse)((OkObjectResult)result.Result).Value; - hearing.Id.Should().Be(_updatedExistingParticipantHearingOriginal.Id); - _bookingsApiClient.Verify(x => x.UpdateHearingDetailsAsync(It.IsAny(), - It.Is(u => - u.Cases.Count > 0)), - Times.Once); - } - - [Test] - public async Task Should_return_updated_hearingV2() - { - _featureToggle.Setup(e => e.UseV2Api()).Returns(true); var updatedHearing = _v2HearingDetailsResponse; _bookingsApiClient.SetupSequence(x => x.GetHearingDetailsByIdV2Async(It.IsAny())) .ReturnsAsync(updatedHearing) @@ -636,9 +496,8 @@ public async Task Should_return_updated_hearingV2() } [Test] - public async Task Should_return_updated_hearingV2_with_no_participants_provided() + public async Task Should_return_updated_hearingV2() { - _featureToggle.Setup(e => e.UseV2Api()).Returns(true); var updatedHearing = _v2HearingDetailsResponse; updatedHearing.Participants.Clear(); _bookingsApiClient.SetupSequence(x => x.GetHearingDetailsByIdV2Async(It.IsAny())) @@ -680,7 +539,6 @@ public async Task Should_return_updated_hearingV2_with_no_participants_provided( [Test] public async Task Should_return_updated_hearingV2_with_no_judiciary_participants_provided() { - _featureToggle.Setup(e => e.UseV2Api()).Returns(true); var updatedHearing = _v2HearingDetailsResponse; updatedHearing.Participants.Clear(); updatedHearing.JudiciaryParticipants.Clear(); @@ -715,7 +573,6 @@ public async Task Should_return_updated_hearingV2_with_no_judiciary_participants [Test] public async Task Should_return_updated_hearingV2_with_new_judge_different_to_old_judge() { - _featureToggle.Setup(e => e.UseV2Api()).Returns(true); var updatedHearing = _v2HearingDetailsResponse; updatedHearing.Participants.Clear(); _bookingsApiClient.SetupSequence(x => x.GetHearingDetailsByIdV2Async(It.IsAny())) @@ -762,7 +619,6 @@ public async Task Should_return_updated_hearingV2_with_new_judge_different_to_ol [Test] public async Task Should_return_updated_hearingV2_with_new_judge_and_no_old_judge() { - _featureToggle.Setup(e => e.UseV2Api()).Returns(true); var updatedHearing = _v2HearingDetailsResponse; updatedHearing.Participants.Clear(); updatedHearing.JudiciaryParticipants.Clear(); @@ -801,7 +657,6 @@ public async Task Should_return_updated_hearingV2_with_new_judge_and_no_old_judg [Test] public async Task Should_return_updated_hearingV2_with_old_judge_and_no_new_judge() { - _featureToggle.Setup(e => e.UseV2Api()).Returns(true); var updatedHearing = _v2HearingDetailsResponse; updatedHearing.Participants.Clear(); _bookingsApiClient.SetupSequence(x => x.GetHearingDetailsByIdV2Async(It.IsAny())) @@ -832,7 +687,6 @@ public async Task Should_return_updated_hearingV2_with_old_judge_and_no_new_judg [Test] public async Task Should_reassign_a_generic_judge_booked_with_v1_to_ejud_judge_on_v2() { - _featureToggle.Setup(e => e.UseV2Api()).Returns(true); var updatedHearing = _v2HearingDetailsResponse; updatedHearing.Participants.Add(new () { @@ -878,7 +732,6 @@ public async Task Should_reassign_a_generic_judge_booked_with_v1_to_ejud_judge_o [Test] public async Task Should_return_updated_hearingV2_with_participants_unchanged_and_hearing_close_to_start_time() { - _featureToggle.Setup(e => e.UseV2Api()).Returns(true); var updatedHearing = _v2HearingDetailsResponse; updatedHearing.Participants.Clear(); _bookingsApiClient.SetupSequence(x => x.GetHearingDetailsByIdV2Async(It.IsAny())) @@ -952,184 +805,31 @@ private void AssertJudiciaryJudgeReassigned( It.IsAny>()), Times.Never); } - - [Test] - public async Task Should_pass_on_bad_request_from_bookings_api() - { - var validationProblemDetails = new ValidationProblemDetails(new Dictionary - { - {"Hearing", ["Cannot remove a participant from hearing that is close to start time"] }, - }); - - _bookingsApiClient.Setup(x => - x.UpdateHearingDetailsAsync(It.IsAny(), It.IsAny())) - .ThrowsAsync(ClientException.ForBookingsAPIValidation(validationProblemDetails)); - - var response = await _controller.EditHearing(_validId, _addNewParticipantRequest); - response.Result.Should().BeOfType(); - } - - [Test] - public async Task Should_pass_on_not_found_request_from_bookings_api() - { - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ThrowsAsync(ClientException.ForBookingsAPI(HttpStatusCode.NotFound)); - - var response = await _controller.EditHearing(_validId, _addNewParticipantRequest); - response.Result.Should().BeOfType(); - } - - [Test] - public async Task Should_replace_judge_based_on_email() - { - var existingJudgeId = Guid.NewGuid(); - _updatedExistingParticipantHearingOriginal.Participants.Add(new ParticipantResponse - { - FirstName = "Existing", - LastName = "Judge", - ContactEmail = "existing@domain.net", - Username = "existing@domain.net", - CaseRoleName = "Judge", - UserRoleName = "Judge", - HearingRoleName = "Judge", - Id = existingJudgeId - }); - - const string newJudgeEmail = "new@domain.net"; - _addNewParticipantRequest.Participants.Add(new EditParticipantRequest - { - CaseRoleName = "Judge", - HearingRoleName = "Judge", - FirstName = "New", - LastName = "Judge", - ContactEmail = newJudgeEmail - }); - - var newPats = _updatedExistingParticipantHearingOriginal.Participants.Where(x => x.Id != existingJudgeId) - .ToList(); - newPats.Add(new ParticipantResponse - { - Id = Guid.NewGuid(), - ContactEmail = "new@domain.net", - Username = "new@domain.net", - UserRoleName = "Individual" - }); - newPats.Add(new ParticipantResponse - { - FirstName = "New", - LastName = "Judge", - ContactEmail = newJudgeEmail, - Username = newJudgeEmail, - UserRoleName = "Judge", - CaseRoleName = "Judge", - HearingRoleName = "Judge", - }); - var updatedHearing = new HearingDetailsResponse - { - Participants = newPats, - Cases = _updatedExistingParticipantHearingOriginal.Cases, - CaseTypeName = "Unit Test" - }; - - _bookingsApiClient.SetupSequence(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_updatedExistingParticipantHearingOriginal) - .ReturnsAsync(updatedHearing) - .ReturnsAsync(updatedHearing); - - var response = await _controller.EditHearing(_validId, _addNewParticipantRequest); - response.Result.Should().BeOfType(); - - _bookingsApiClient.Verify(x => x.UpdateHearingParticipantsAsync(_validId, - It.Is( - participants => participants.NewParticipants.Any(p => p.Username == newJudgeEmail))), Times.Once); - _bookingsApiClient.Verify(x => x.UpdateHearingDetailsAsync(It.IsAny(), - It.Is(u => - u.Cases.Count > 0)), - Times.Once); - } - - [Test] - public async Task Should_add_endpoint_if_new_endpoint_is_added_to_endpoint_list() - { - _addEndpointToHearingRequest.Participants = new List(); - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_existingHearingWithEndpointsOriginal); - var result = await _controller.EditHearing(_validId, _addEndpointToHearingRequest); - ((OkObjectResult)result.Result).StatusCode.Should().Be(200); - _bookingsApiClient.Verify( - x => x.AddEndPointToHearingAsync(It.IsAny(), It.IsAny()), Times.Once); - _bookingsApiClient.Verify(x => x.UpdateHearingDetailsAsync(It.IsAny(), - It.Is(u => - u.Cases.Count > 0)), - Times.Once); - _bookingsApiClient.Verify( - x => x.UpdateDisplayNameForEndpointAsync(It.IsAny(), It.IsAny(), - It.IsAny()), Times.Never); - _bookingsApiClient.Verify( - x => x.RemoveEndPointFromHearingAsync(It.IsAny(), It.IsAny()), Times.Never); - } - - [Test] - public async Task Should_update_endpoint_if_an_endpoint_is_updates_in_endpoint_list() - { - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_existingHearingWithEndpointsOriginal); - var result = await _controller.EditHearing(_validId, _editEndpointOnHearingRequestWithJudge); - ((OkObjectResult)result.Result).StatusCode.Should().Be(200); - _bookingsApiClient.Verify(x => x.AddEndPointToHearingAsync(It.IsAny(), It.IsAny()), Times.Never); - _bookingsApiClient.Verify(x => x.UpdateHearingDetailsAsync(It.IsAny(), - It.Is(u => - u.Cases.Count > 0)), Times.Once); - _bookingsApiClient.Verify( - x => x.UpdateDisplayNameForEndpointAsync(It.IsAny(), It.IsAny(), - It.IsAny()), Times.Once); - _bookingsApiClient.Verify(x => x.RemoveEndPointFromHearingAsync(It.IsAny(), It.IsAny()), - Times.Never); - - } - [TestCase(false)] - [TestCase(true)] - public async Task Should_update_endpoint_to_be_linked_to_new_defence_advocate_when_endpoint_is_not_currently_linked(bool useV2) + [Test] + public async Task Should_update_endpoint_to_be_linked_to_new_defence_advocate_when_endpoint_is_not_currently_linked() { // ie there is an endpoint currently not linked to a defence advocate // as part of the request we add a new participant and link them to this endpoint as a defence advocate - // Arrange - _featureToggle.Setup(x => x.UseV2Api()).Returns(useV2); - Guid hearingId; var request = _editEndpointOnHearingRequestWithJudge; var endpointInRequestToUpdate = request.Endpoints[0]; - if (useV2) + var hearing = _v2HearingDetailsResponse; + hearingId = hearing.Id; + var existingEndpointToUpdate = new EndpointResponseV2 { - var hearing = _v2HearingDetailsResponse; - hearingId = hearing.Id; - var existingEndpointToUpdate = new EndpointResponseV2 - { - Id = endpointInRequestToUpdate.Id.Value, - DisplayName = "Endpoint A", - DefenceAdvocateId = null - }; - hearing.Endpoints.RemoveAll(e => e.Id != existingEndpointToUpdate.Id); - hearing.Endpoints.Add(existingEndpointToUpdate); - - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(It.IsAny())) - .ReturnsAsync(hearing); - } - else - { - var hearing = _existingHearingWithEndpointsOriginal; - hearingId = hearing.Id; - var existingEndpointToUpdate = hearing.Endpoints[0]; - existingEndpointToUpdate.DefenceAdvocateId = null; - hearing.Endpoints.RemoveAll(e => e.Id != existingEndpointToUpdate.Id); - - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(hearing); - } - + Id = endpointInRequestToUpdate.Id.Value, + DisplayName = "Endpoint A", + DefenceAdvocateId = null + }; + hearing.Endpoints.RemoveAll(e => e.Id != existingEndpointToUpdate.Id); + hearing.Endpoints.Add(existingEndpointToUpdate); + + _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(It.IsAny())) + .ReturnsAsync(hearing); + var newParticipantDefenceAdvocate = new EditParticipantRequest { ContactEmail = "legalrep@email.com", @@ -1158,576 +858,5 @@ public async Task Should_update_endpoint_to_be_linked_to_new_defence_advocate_wh r.DefenceAdvocateContactEmail == newParticipantDefenceAdvocate.ContactEmail)), Times.Exactly(expectedUpdatedEndpointCount)); } - - [Test] - public async Task Should_remove_endpoint_if_endpoint_is_removed_from_the_endpoint_list() - { - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_existingHearingWithEndpointsOriginal); - var result = await _controller.EditHearing(_validId, _removeEndpointOnHearingRequest); - ((OkObjectResult)result.Result).StatusCode.Should().Be(200); - - _bookingsApiClient.Verify( - x => x.AddEndPointToHearingAsync(It.IsAny(), It.IsAny()), Times.Never); - - _bookingsApiClient.Verify(x => x.RemoveEndPointFromHearingAsync(It.IsAny(), It.IsAny()), - Times.Once); - - _bookingsApiClient.Verify(x => x.UpdateHearingDetailsAsync(It.IsAny(), - It.Is(u => - u.Cases.Count > 0)), Times.Once); - - _bookingsApiClient.Verify( - x => x.UpdateDisplayNameForEndpointAsync(It.IsAny(), It.IsAny(), - It.IsAny()), Times.Never); - } - - [Test] - public async Task If_Judge_Added_To_Hearing_And_Saved_Should_Auto_confirm_booking() - { - // arrange - original hearing - var hearingId = _updatedExistingParticipantHearingOriginal.Id; - var originalHearing = _updatedExistingParticipantHearingOriginal.Duplicate(); - var updatedHearing = _updatedExistingParticipantHearingOriginal.Duplicate(); - updatedHearing.Participants.Add(new ParticipantResponse{ - DisplayName = "newJudge", - HearingRoleName = RoleNames.Judge, - CaseRoleName = RoleNames.Judge, - UserRoleName = RoleNames.Judge, - ContactEmail = "judge@moj.gov.uk" - }); - originalHearing.Status = BookingStatus.Booked; - _bookingsApiClient.Setup(x => x.GetHearingsByGroupIdAsync(originalHearing.GroupId.Value)) - .ReturnsAsync(new List {originalHearing}); - _bookingsApiClient.SetupSequence(x => x.GetHearingDetailsByIdAsync(hearingId)) - .ReturnsAsync(originalHearing) - .ReturnsAsync(updatedHearing); - // arrange - request - var request = new EditHearingRequest(); - request.Case = new EditCaseRequest(); - request.Participants.Add(new EditParticipantRequest - { - DisplayName = "newJudge", - HearingRoleName = RoleNames.Judge, - CaseRoleName = RoleNames.Judge, - ContactEmail = "judge@moj.gov.uk" - }); - //Act - var result = await _controller.EditHearing(hearingId, request); - ((OkObjectResult)result.Result).StatusCode.Should().Be(200); - - } - - [Test] - public async Task Should_not_update_DisplayName_if_no_matching_endpoint_exists_in_list() - { - _existingHearingWithEndpointsOriginal.Endpoints[0].Id = Guid.NewGuid(); - _existingHearingWithEndpointsOriginal.Endpoints[0].DisplayName = "data1-edit"; - _existingHearingWithEndpointsOriginal.Endpoints[0].DefenceAdvocateId = null; - _existingHearingWithEndpointsOriginal.Endpoints[3].DisplayName = "data4-edit"; - _existingHearingWithEndpointsOriginal.Endpoints[3].DefenceAdvocateId = null; - - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_existingHearingWithEndpointsOriginal); - - var result = await _controller.EditHearing(_validId, _addEndpointToHearingRequest); - - ((OkObjectResult)result.Result).StatusCode.Should().Be(200); - - _bookingsApiClient.Verify( - x => x.AddEndPointToHearingAsync(It.IsAny(), It.IsAny()), Times.Once); - - // The old Endpoints[0] has no matching Id now, and so it will be removed - _bookingsApiClient.Verify( - x => x.RemoveEndPointFromHearingAsync(It.IsAny(), It.IsAny()), Times.Once); - - _bookingsApiClient.Verify(x => x.UpdateHearingDetailsAsync(It.IsAny(), - It.Is(u => - u.Cases.Count > 0)), Times.Once); - - // Endpoints[3] has had their details changed, and so will be updated - _bookingsApiClient.Verify( - x => x.UpdateDisplayNameForEndpointAsync(It.IsAny(), It.IsAny(), - It.IsAny()), Times.Once); - } - - [Test] - public async Task Should_process_participants() - { - //Arrange - var existingLinkedParticipantOne = - _existingHearingWithLinkedParticipants.Participants.Find(x => x.LinkedParticipants.Count > 0); - var existingLinkedParticipantTwo = - _existingHearingWithLinkedParticipants.Participants - .SingleOrDefault(x => x.Id == existingLinkedParticipantOne.LinkedParticipants[0].LinkedId); - - var editPrefix = "Edited"; - var updatedExistingLinkedParticipantOne = new EditParticipantRequest - { - Id = existingLinkedParticipantOne.Id, - ContactEmail = existingLinkedParticipantOne.ContactEmail, - FirstName = editPrefix + existingLinkedParticipantOne.FirstName, - LastName = editPrefix + existingLinkedParticipantOne.LastName, - LinkedParticipants = new List - { - new LinkedParticipant - { - LinkedId = existingLinkedParticipantTwo.Id, - LinkedParticipantContactEmail = existingLinkedParticipantTwo.ContactEmail, - ParticipantContactEmail = existingLinkedParticipantOne.ContactEmail - } - } - }; - - var updatedExistingLinkedParticipantTwo = new EditParticipantRequest - { - Id = existingLinkedParticipantTwo.Id, - ContactEmail = existingLinkedParticipantTwo.ContactEmail, - FirstName = editPrefix + existingLinkedParticipantTwo.FirstName, - LastName = editPrefix + existingLinkedParticipantTwo.LastName, - LinkedParticipants = new List - { - new LinkedParticipant - { - LinkedId = existingLinkedParticipantOne.Id, - LinkedParticipantContactEmail = existingLinkedParticipantTwo.ContactEmail, - ParticipantContactEmail = existingLinkedParticipantTwo.ContactEmail - } - } - }; - - var newParticipant = new EditParticipantRequest - { - ContactEmail = "ContactEmail", - FirstName = "Hi", - LastName = "Hello", - }; - - _addNewParticipantRequest.Participants = new List - { - updatedExistingLinkedParticipantOne, - updatedExistingLinkedParticipantTwo, - newParticipant - }; - - var removedParticipantIds = _existingHearingWithLinkedParticipants.Participants - .Where(p => _addNewParticipantRequest.Participants.TrueForAll(rp => rp.Id != p.Id)).Select(x => x.Id).ToList(); - - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_existingHearingWithLinkedParticipants); - - //Act - var response = await _controller.EditHearing(_validId, _addNewParticipantRequest); - response.Result.Should().BeOfType(); - - Func, List, bool> areRemovedParticipantIdsCorrect = (List listOne, List listTwo) => - { - foreach (var guid in listOne) - { - if (!listTwo.Contains(guid)) - return false; - } - - return true; - }; - - //Assert - _bookingsApiClient.Verify(x => x.UpdateHearingParticipantsAsync(_validId, - It.Is(participants => - participants.NewParticipants.Count == 1 - && participants.NewParticipants[0].ContactEmail == newParticipant.ContactEmail - && participants.NewParticipants[0].FirstName == newParticipant.FirstName - && participants.NewParticipants[0].LastName == newParticipant.LastName - - && participants.RemovedParticipantIds.Count == removedParticipantIds.Count - && areRemovedParticipantIdsCorrect(participants.RemovedParticipantIds, removedParticipantIds) - - && participants.ExistingParticipants.Count == 2 - - && participants.LinkedParticipants.Count == 1 - && participants.LinkedParticipants[0].ParticipantContactEmail == existingLinkedParticipantOne.ContactEmail - && participants.LinkedParticipants[0].LinkedParticipantContactEmail == existingLinkedParticipantTwo.ContactEmail - )), Times.Once); - } - - [Test] - public async Task Should_add_a_new_participant_and_link_to_existing_interpreter_when_editing_a_hearing() - { - var newUserContactEmail = "newindividual4.user@email.com"; - var interpreter = - _existingHearingWithLinkedParticipants.Participants.First(p => - p.HearingRoleName.Equals("interpreter",StringComparison.CurrentCultureIgnoreCase)); - - var partipant4 = Guid.NewGuid(); - - var _existingHearingWithNewLinkedParticipants = new HearingDetailsResponse - { - Id = _validId, - GroupId = _validId, - Cases = _existingHearingWithLinkedParticipants.Cases, - CaseTypeName = "case type", - HearingTypeName = "hearing type", - Participants = new List - { - new ParticipantResponse - { - Id = _existingHearingWithLinkedParticipants.Participants[0].Id, CaseRoleName = "judge", HearingRoleName = "hearingrole", - ContactEmail = "judge.user@email.com", UserRoleName = "Judge", FirstName = "Judge", - LinkedParticipants = null - }, - new ParticipantResponse - { - Id = _existingHearingWithLinkedParticipants.Participants[1].Id, CaseRoleName = "caserole", HearingRoleName = "litigant in person", - ContactEmail = "individual.user@email.com", UserRoleName = "Individual", - FirstName = "testuser1", LinkedParticipants = null - }, - new ParticipantResponse - { - Id = interpreter.Id, CaseRoleName = "caserole", HearingRoleName = "interpreter", - ContactEmail = "interpreter.user@email.com", UserRoleName = "Individual", - FirstName = "testuser1", - LinkedParticipants = new List - { - new LinkedParticipantResponse - {Type = LinkedParticipantType.Interpreter, LinkedId = partipant4} - } - }, - new ParticipantResponse - { - Id = partipant4, CaseRoleName = "caserole", HearingRoleName = "litigant in person", - ContactEmail = "individual4.user@email.com", UserRoleName = "Individual4", - FirstName = "testuser4", LinkedParticipants = null - } - }, - ScheduledDateTime = DateTime.UtcNow.AddHours(3), - OtherInformation = "|JudgeEmail|judge@email.com|JudgePhone|0123454678" - }; - - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())).ReturnsAsync(_existingHearingWithNewLinkedParticipants); - - - var addParticipantLinksToHearingRequest = new EditHearingRequest - { - Case = new EditCaseRequest { Name = "Case", Number = "123" }, - Participants = new List - { - new EditParticipantRequest - { - Id = _existingHearingWithLinkedParticipants.Participants[0].Id, CaseRoleName = "judge", HearingRoleName = "hearingrole", - ContactEmail = "judge.user@email.com", FirstName = "Judge", TelephoneNumber = "003" - }, - new EditParticipantRequest - { - Id = _existingHearingWithLinkedParticipants.Participants[1].Id, CaseRoleName = "caserole", HearingRoleName = "litigant in person", - ContactEmail = "individual.user@email.com", - FirstName = "testuser1", TelephoneNumber = "001" - }, - new EditParticipantRequest - { - Id = partipant4, CaseRoleName = "caserole", HearingRoleName = "litigant in person", - ContactEmail = "individual4.user@email.com", - FirstName = "testuser4", TelephoneNumber = "000" - }, - new EditParticipantRequest - { - CaseRoleName = "caserole", HearingRoleName = "litigant in person", - ContactEmail = "newindividual4.user@email.com", DisplayName = "NewIndividual4", FirstName = "NewIndividual4", - LastName = "newIndividual4", TelephoneNumber = "000", - }, - new EditParticipantRequest - { - Id = interpreter.Id, - CaseRoleName = "caserole", HearingRoleName = "interpreter", - ContactEmail = "interpreter.user@email.com", DisplayName = "newUser", FirstName = "firstName", - LastName = "lastName", TelephoneNumber = "000", - LinkedParticipants = new List - { - new LinkedParticipant - { - ParticipantContactEmail = "interpreter.user@email.com", - LinkedParticipantContactEmail = newUserContactEmail, - Type = AdminWebsite.Contracts.Enums.LinkedParticipantType.Interpreter - } - } - } - }, - OtherInformation = "|JudgeEmail|judge@email.com|JudgePhone|0123454678" - }; - - var result = await _controller.EditHearing(_validId, addParticipantLinksToHearingRequest); - - ((OkObjectResult)result.Result).StatusCode.Should().Be(200); - - _bookingsApiClient.Verify( - x => x.UpdateHearingParticipantsAsync(It.IsAny(), It.Is(x => x.LinkedParticipants.Any(x => x.LinkedParticipantContactEmail == newUserContactEmail))), Times.Once); - - _bookingsApiClient.Verify(x => x.UpdateHearingDetailsAsync(It.IsAny(), - It.Is(u => u.Cases.Count > 0)), Times.Once); - } - - [Test] - public async Task Should_create_a_new_judge_and_set_username_to_contact_email() - { - var _existingHearing = new HearingDetailsResponse - { - Id = _validId, - GroupId = _validId, - Cases = _existingHearingWithLinkedParticipants.Cases, - CaseTypeName = "case type", - HearingTypeName = "hearing type", - Participants = new List(), - ScheduledDateTime = DateTime.UtcNow.AddHours(3) - }; - - _bookingsApiClient.Setup(x - => x.GetHearingDetailsByIdAsync(It.IsAny())).ReturnsAsync(_existingHearing); - - var addParticipantLinksToHearingRequest = new EditHearingRequest - { - Case = new EditCaseRequest { Name = "Case", Number = "123" }, - Participants = new List - { - new EditParticipantRequest - { - CaseRoleName = "Judge", - HearingRoleName = "Judge", - ContactEmail = "judge@email.com", - FirstName = "Judge", - TelephoneNumber = "0123454678" - } - }, - OtherInformation = "|JudgeEmail|notify_judge@email.com|JudgePhone|9876" - }; - - var result = await _controller.EditHearing(_validId, addParticipantLinksToHearingRequest); - - ((OkObjectResult)result.Result).StatusCode.Should().Be(200); - - _bookingsApiClient.Verify(x - => x.UpdateHearingDetailsAsync(It.IsAny(), - It.Is(uhpr => HearingRequestValidation(uhpr)))); - - _bookingsApiClient.Verify(x - => x.UpdateHearingParticipantsAsync(It.IsAny(), - It.Is(uhpr => JudgeRequestValidation(uhpr)))); - } - - private static bool HearingRequestValidation(UpdateHearingRequest request) - { - request.OtherInformation.Should().Be("|JudgeEmail|notify_judge@email.com|JudgePhone|9876"); - return true; - } - - private static bool JudgeRequestValidation(UpdateHearingParticipantsRequest request) - { - request.NewParticipants[0].Username.Should().Be("judge@email.com"); - request.NewParticipants[0].ContactEmail.Should().Be("judge@email.com"); - request.NewParticipants[0].TelephoneNumber.Should().Be("0123454678"); - return true; - } - - [Test] - public async Task Returns_Valid_When_Linked_Contact_Email_Is_Null_When_Adding_A_New_Participant_To_Existing_Hearing() - { - var linkedParticipantEmail = "individual4.user@email.com"; - var interpreter = - _existingHearingWithLinkedParticipants.Participants.First(p => - p.HearingRoleName.Equals("interpreter", StringComparison.CurrentCultureIgnoreCase)); - - var partipant4 = Guid.NewGuid(); - - var _existingHearingWithNewLinkedParticipants = new HearingDetailsResponse - { - Id = _validId, - GroupId = _validId, - Cases = _existingHearingWithLinkedParticipants.Cases, - CaseTypeName = "case type", - HearingTypeName = "hearing type", - Participants = new List - { - new ParticipantResponse - { - Id = _existingHearingWithLinkedParticipants.Participants[0].Id, CaseRoleName = "judge", HearingRoleName = "hearingrole", - ContactEmail = "judge.user@email.com", UserRoleName = "Judge", FirstName = "Judge", - LinkedParticipants = null - }, - new ParticipantResponse - { - Id = _existingHearingWithLinkedParticipants.Participants[1].Id, CaseRoleName = "caserole", HearingRoleName = "litigant in person", - ContactEmail = "individual.user@email.com", UserRoleName = "Individual", - FirstName = "testuser1", LinkedParticipants = null - }, - new ParticipantResponse - { - Id = interpreter.Id, CaseRoleName = "caserole", HearingRoleName = "interpreter", - ContactEmail = "interpreter.user@email.com", UserRoleName = "Individual", - FirstName = "testuser1", - LinkedParticipants = new List - { - new LinkedParticipantResponse - {Type = LinkedParticipantType.Interpreter, LinkedId = partipant4} - } - }, - new ParticipantResponse - { - Id = partipant4, CaseRoleName = "caserole", HearingRoleName = "litigant in person", - ContactEmail = linkedParticipantEmail, UserRoleName = "Individual4", - FirstName = "testuser4", LinkedParticipants = null - } - }, - ScheduledDateTime = DateTime.UtcNow.AddHours(3), - OtherInformation = "" - }; - - _bookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())).ReturnsAsync(_existingHearingWithNewLinkedParticipants); - - - var addParticipantLinksToHearingRequest = new EditHearingRequest - { - Case = new EditCaseRequest { Name = "Case", Number = "123" }, - Participants = new List - { - new EditParticipantRequest - { - Id = _existingHearingWithLinkedParticipants.Participants[0].Id, CaseRoleName = "judge", HearingRoleName = "hearingrole", - ContactEmail = "judge.user@email.com", FirstName = "Judge", TelephoneNumber = "003" - }, - new EditParticipantRequest - { - Id = _existingHearingWithLinkedParticipants.Participants[1].Id, CaseRoleName = "caserole", HearingRoleName = "litigant in person", - ContactEmail = "individual.user@email.com", - FirstName = "testuser1", TelephoneNumber = "001" - }, - new EditParticipantRequest - { - Id = partipant4, CaseRoleName = "caserole", HearingRoleName = "litigant in person", - ContactEmail = "individual4.user@email.com", - FirstName = "testuser4", TelephoneNumber = "000" - }, - new EditParticipantRequest - { - CaseRoleName = "caserole", HearingRoleName = "litigant in person", - ContactEmail = "newindividual4.user@email.com", DisplayName = "NewIndividual4", FirstName = "NewIndividual4", - LastName = "newIndividual4", TelephoneNumber = "000", - }, - new EditParticipantRequest - { - Id = interpreter.Id, - CaseRoleName = "caserole", HearingRoleName = "interpreter", - ContactEmail = "interpreter.user@email.com", DisplayName = "newUser", FirstName = "firstName", - LastName = "lastName", TelephoneNumber = "000", - LinkedParticipants = new List - { - new LinkedParticipant - { - LinkedId = partipant4, - Type = AdminWebsite.Contracts.Enums.LinkedParticipantType.Interpreter, - LinkedParticipantContactEmail = null - } - } - } - }, - OtherInformation = "" - }; - - var result = await _controller.EditHearing(_validId, addParticipantLinksToHearingRequest); - - ((OkObjectResult)result.Result).StatusCode.Should().Be(200); - - _bookingsApiClient.Verify( - x => x.UpdateHearingParticipantsAsync(It.IsAny(), It.Is(x => x.LinkedParticipants.Any(x => x.LinkedParticipantContactEmail == linkedParticipantEmail))), Times.Once); - - _bookingsApiClient.Verify(x => x.UpdateHearingDetailsAsync(It.IsAny(), - It.Is(u => u.Cases.Count > 0)), Times.Once); - } - - [TestCase(BookingStatus.Booked, 0)] - [TestCase(BookingStatus.Created, 1)] - public async Task - Should_correctly_decide_when_to_send_judge_hearing_confirm_email_on_edit_when_email_has_been_updated( - BookingStatus status, int timeSent) - { - // arrange - var hearingId = _updatedExistingParticipantHearingOriginal.Id; - var newJudgeEmailOtherInfo = new OtherInformationDetails { JudgeEmail = "judgene@domain.net" }; - var updatedHearing = _updatedExistingParticipantHearingOriginal.Duplicate(); - updatedHearing.Participants.Add(new ParticipantResponse - { - Id = Guid.NewGuid(), - UserRoleName = "Judge" - }); - updatedHearing.CaseTypeName = "Unit Test"; - updatedHearing.Cases[0].Name = "Case"; - updatedHearing.Cases[0].Number = "123"; - updatedHearing.OtherInformation = newJudgeEmailOtherInfo.ToOtherInformationString(); - updatedHearing.Status = status; - - _bookingsApiClient.SetupSequence(x => x.GetHearingDetailsByIdAsync(hearingId)) - .ReturnsAsync(_updatedExistingParticipantHearingOriginal) - .ReturnsAsync(updatedHearing) - .ReturnsAsync(updatedHearing); - - _bookingsApiClient.Setup(x => x.GetHearingsByGroupIdAsync(updatedHearing.GroupId.Value)) - .ReturnsAsync(new List { updatedHearing }); - var request = new EditHearingRequest - { - Case = new EditCaseRequest { Name = "Case", Number = "123" }, - OtherInformation = updatedHearing.OtherInformation - }; - - // act - var result = await _controller.EditHearing(hearingId, request); - - // assert - ((OkObjectResult)result.Result).StatusCode.Should().Be(200); - } - - [Test] - public async Task Should_handle_failed_booking_request_on_retry() - { - _existingHearingWithJudge.ScheduledDateTime = DateTime.UtcNow.AddMinutes(10); - _existingHearingWithJudge.Status = BookingStatus.Failed; - _bookingsApiClient.SetupSequence(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_existingHearingWithJudge) - .ReturnsAsync(_existingHearingWithJudge); - - var request = FailedHearingRequest(); - - var result = await _controller.EditHearing(_validId, request); - - var response = ((ObjectResult)result.Result)?.Value as AdminWebsite.Contracts.Responses.HearingDetailsResponse; - - response.Status.Should().Be((AdminWebsite.Contracts.Enums.BookingStatus)BookingStatus.Failed); - - ((ObjectResult)result.Result).StatusCode.Should().Be(200); - - _bookingsApiClient.Verify(x => x.UpdateHearingParticipantsAsync( - It.IsAny(), - It.IsAny()), - Times.Once); - } - - private EditHearingRequest FailedHearingRequest() - { - return new EditHearingRequest - { - Case = new EditCaseRequest - { - Name = "Case", - Number = "123" - }, - Participants = new List - { - new EditParticipantRequest - { - ContactEmail = "test@domain.net.", - FirstName = "FirstName", - LastName = "LastName", - HearingRoleName = HearingRoleName.Judge - } - } - }; - } - } } \ No newline at end of file diff --git a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/EditMultiDayHearingTests.cs b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/EditMultiDayHearingTests.cs index 5c16dd0d8..4e7d1e789 100644 --- a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/EditMultiDayHearingTests.cs +++ b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/EditMultiDayHearingTests.cs @@ -23,7 +23,7 @@ public class EditMultiDayHearingTests : HearingsControllerTests { [TestCase(false)] [TestCase(true)] - public async Task Should_update_multi_day_hearing_for_v2(bool updateFutureDays) + public async Task Should_update_multi_day_hearing(bool updateFutureDays) { // Arrange var hearingId = Guid.NewGuid(); @@ -53,7 +53,6 @@ public async Task Should_update_multi_day_hearing_for_v2(bool updateFutureDays) ScheduledDateTime = hearingInGroup.ScheduledDateTime.AddDays(1) }); } - FeatureToggle.Setup(e => e.UseV2Api()).Returns(true); // Change the judge var judge = request.JudiciaryParticipants.First(x => x.Role == "Judge"); @@ -200,7 +199,7 @@ public async Task Should_update_multi_day_hearing_for_v2(bool updateFutureDays) } [Test] - public async Task should_update_multi_day_hearing_for_v2_when_judiciary_participants_are_unchanged() + public async Task should_update_multi_day_hearing_when_judiciary_participants_are_unchanged() { // Arrange var hearingId = Guid.NewGuid(); @@ -219,7 +218,6 @@ public async Task should_update_multi_day_hearing_for_v2_when_judiciary_particip ScheduledDateTime = hearingInGroup.ScheduledDateTime }); } - FeatureToggle.Setup(e => e.UseV2Api()).Returns(true); var updatedHearing = MapUpdatedHearingV2(hearing, request); BookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(hearingId)).ReturnsAsync(updatedHearing); @@ -246,7 +244,7 @@ public async Task should_update_multi_day_hearing_for_v2_when_judiciary_particip } [Test] - public async Task Should_not_overwrite_data_for_future_days_when_only_specific_details_are_changed_for_v2() + public async Task Should_not_overwrite_data_for_future_days_when_only_specific_details_are_changed() { // Scenario - we have a 2 day hearing // Day 2 has been individually edited, and so has different details, participants and endpoints to Day 1 @@ -339,8 +337,6 @@ public async Task Should_not_overwrite_data_for_future_days_when_only_specific_d request.AudioRecordingRequired = day1Hearing.AudioRecordingRequired; request.UpdateFutureDays = true; - FeatureToggle.Setup(e => e.UseV2Api()).Returns(true); - var updatedHearing = MapUpdatedHearingV2(day1Hearing, request); BookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(hearingId)).ReturnsAsync(updatedHearing); @@ -406,7 +402,7 @@ public async Task Should_not_overwrite_data_for_future_days_when_only_specific_d } [Test] - public async Task Should_update_multi_day_hearing_when_updated_participants_and_endpoints_do_not_exist_on_future_days_for_v2() + public async Task Should_update_multi_day_hearing_when_updated_participants_and_endpoints_do_not_exist_on_future_days() { // Scenario - we have a 2 day hearing // Day 1 has been individually edited, and has additional participants and endpoints not on Day 2 @@ -463,8 +459,6 @@ public async Task Should_update_multi_day_hearing_when_updated_participants_and_ } request.UpdateFutureDays = true; - FeatureToggle.Setup(e => e.UseV2Api()).Returns(true); - var updatedHearing = MapUpdatedHearingV2(day1Hearing, request); BookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(hearingId)).ReturnsAsync(updatedHearing); @@ -518,7 +512,7 @@ public async Task Should_update_multi_day_hearing_when_updated_participants_and_ } [Test] - public async Task Should_remove_linked_participants_for_v2() + public async Task Should_remove_linked_participants() { // Arrange var hearingId = Guid.NewGuid(); @@ -548,8 +542,6 @@ public async Task Should_remove_linked_participants_for_v2() } request.UpdateFutureDays = true; - FeatureToggle.Setup(e => e.UseV2Api()).Returns(true); - var updatedHearing = MapUpdatedHearingV2(day1Hearing, request); BookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(hearingId)).ReturnsAsync(updatedHearing); @@ -576,7 +568,7 @@ public async Task Should_remove_linked_participants_for_v2() } [Test] - public async Task Should_update_multi_day_hearing_when_participant_is_new_to_edited_hearing_but_exists_on_future_days_for_v2() + public async Task Should_update_multi_day_hearing_when_participant_is_new_to_edited_hearing_but_exists_on_future_days() { // Arrange var hearingId = Guid.NewGuid(); @@ -626,8 +618,6 @@ public async Task Should_update_multi_day_hearing_when_participant_is_new_to_edi }); request.UpdateFutureDays = true; - FeatureToggle.Setup(e => e.UseV2Api()).Returns(true); - var updatedHearing = MapUpdatedHearingV2(day1Hearing, request); BookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(hearingId)).ReturnsAsync(updatedHearing); @@ -706,8 +696,6 @@ public async Task Should_reassign_judge_when_future_day_hearing_is_assigned_to_d newJudge.PersonalCode = Guid.NewGuid().ToString(); request.UpdateFutureDays = true; - FeatureToggle.Setup(e => e.UseV2Api()).Returns(true); - var updatedHearing = MapUpdatedHearingV2(day1Hearing, request); BookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(hearingId)).ReturnsAsync(updatedHearing); @@ -751,7 +739,7 @@ public async Task Should_reassign_judge_when_future_day_hearing_is_assigned_to_d } [Test] - public async Task Should_forward_not_found_from_bookings_api_for_v2() + public async Task Should_forward_not_found_from_bookings_api() { // Arrange var hearingId = Guid.NewGuid(); @@ -765,7 +753,6 @@ public async Task Should_forward_not_found_from_bookings_api_for_v2() null); BookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(hearingId)) .ThrowsAsync(apiException); - FeatureToggle.Setup(e => e.UseV2Api()).Returns(true); // Act var result = await Controller.EditMultiDayHearing(hearingId, request); @@ -776,7 +763,7 @@ public async Task Should_forward_not_found_from_bookings_api_for_v2() } [Test] - public async Task Should_return_bad_request_when_hearing_is_not_multi_day_for_v2() + public async Task Should_return_bad_request_when_hearing_is_not_multi_day() { // Arrange var hearingId = Guid.NewGuid(); @@ -786,8 +773,7 @@ public async Task Should_return_bad_request_when_hearing_is_not_multi_day_for_v2 var request = CreateV2EditMultiDayHearingRequest(hearing); hearing.GroupId = null; - FeatureToggle.Setup(e => e.UseV2Api()).Returns(true); - + var updatedHearing = MapUpdatedHearingV2(hearing, request); BookingsApiClient.Setup(x => x.GetHearingDetailsByIdV2Async(hearingId)).ReturnsAsync(updatedHearing); @@ -808,55 +794,7 @@ public async Task Should_return_bad_request_when_hearing_is_not_multi_day_for_v2 } private static readonly string[] value = ["Please provide a valid id"]; - - [Test] - public async Task Should_forward_bad_request_from_bookings_api() - { - // Arrange - var hearingId = Guid.NewGuid(); - var request = new EditMultiDayHearingRequest(); - var validationProblemDetails = new ValidationProblemDetails(new Dictionary - { - {"id", value } - }); - var apiException = new BookingsApiException("BadRequest", - (int)HttpStatusCode.BadRequest, - "Please provide a valid id", - null, - validationProblemDetails, - null); - BookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(hearingId)) - .ThrowsAsync(apiException); - - // Act - var result = await Controller.EditMultiDayHearing(hearingId, request); - - var objectResult = (ObjectResult)result.Result; - var validationProblems = (ValidationProblemDetails)objectResult.Value; - - var errors = validationProblems.Errors; - errors.Should().BeEquivalentTo(validationProblemDetails.Errors); - } - [Test] - public void Should_forward_unhandled_error_from_bookings_api() - { - // Arrange - var hearingId = Guid.NewGuid(); - var request = new EditMultiDayHearingRequest(); - var errorMessage = "Unexpected error for unit test"; - var apiException = new BookingsApiException("Server Error", - (int) HttpStatusCode.InternalServerError, - "Server Error", null, errorMessage, null); - BookingsApiClient.Setup(x => x.GetHearingDetailsByIdAsync(hearingId)) - .ThrowsAsync(apiException); - - // Act & Assert - var response = Controller.EditMultiDayHearing(hearingId, request); - - ((ObjectResult)response.Result.Result).StatusCode.Should().Be(500); - } - private static HearingDetailsResponseV2 MapUpdatedHearingV2( HearingDetailsResponseV2 hearing, EditMultiDayHearingRequest request) => new() diff --git a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/FailHearingTests.cs b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/FailHearingTests.cs index 35a6dc790..1b61dec19 100644 --- a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/FailHearingTests.cs +++ b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/FailHearingTests.cs @@ -48,7 +48,6 @@ public void Setup() new ParticipantResponse {HearingRoleName = "Judge"} } }); - _mocker.Mock().Setup(e => e.BookAndConfirmToggle()).Returns(true); _controller = _mocker.Create(); } diff --git a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/GetHearingTests.cs b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/GetHearingTests.cs index af2c119ec..94b440c4d 100644 --- a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/GetHearingTests.cs +++ b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/GetHearingTests.cs @@ -148,31 +148,12 @@ public void Initialise() _mocker.Mock().Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) .ReturnsAsync(_vhExistingHearingV1); } + [Test] public async Task Should_return_ok_status_if_hearing_id_is_valid() { // Arrange - _mocker.Mock().Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_vhExistingHearingV1); - - // Act - var result = await _controller.GetHearingById(_v1HearingId); - - // Assert - var okRequestResult = (OkObjectResult) result; - okRequestResult.StatusCode.Should().Be(200); - - var hearing = (HearingDetailsResponse) ((OkObjectResult) result).Value; - hearing.Id.Should().Be(_vhExistingHearingV1.Id); - } - - [Test] - public async Task Should_return_ok_status_if_hearing_id_is_validV2() - { - // Arrange - _mocker.Mock().Setup(x => x.UseV2Api()) - .Returns(true); _mocker.Mock().Setup(x => x.GetHearingDetailsByIdV2Async(It.IsAny())).ReturnsAsync(_vhExistingHearingV2); @@ -186,67 +167,11 @@ public async Task Should_return_ok_status_if_hearing_id_is_validV2() var hearing = (HearingDetailsResponse) ((OkObjectResult) result).Value; hearing.Id.Should().Be(_vhExistingHearingV2.Id); } - - [Test] - public async Task Should_return_ok_status_for_multi_day_hearing_V1() - { - // Arrange - _mocker.Mock().Setup(x => x.UseV2Api()) - .Returns(false); - var groupId = _vhExistingHearingV1.Id; - _vhExistingHearingV1.GroupId = groupId; - _mocker.Mock().Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_vhExistingHearingV1); - - var dates = new List - { - _vhExistingHearingV1.ScheduledDateTime.AddDays(1), - _vhExistingHearingV1.ScheduledDateTime.AddDays(2), - _vhExistingHearingV1.ScheduledDateTime.AddDays(3), - _vhExistingHearingV1.ScheduledDateTime.AddDays(4) - }; - var multiDayHearings = new List - { - _vhExistingHearingV1 - }; - multiDayHearings.AddRange(dates.Select(date => new BookingsApi.Contract.V1.Responses.HearingDetailsResponse - { - Id = Guid.NewGuid(), - ScheduledDateTime = date, - ScheduledDuration = _vhExistingHearingV1.ScheduledDuration, - GroupId = groupId, - Status = BookingStatus.Created - })); - // Set some to cancelled and failed so we can test they are filtered out - multiDayHearings[2].Status = BookingStatus.Cancelled; - multiDayHearings[3].Status = BookingStatus.Failed; - _mocker.Mock().Setup(x => x.GetHearingsByGroupIdAsync(groupId)) - .ReturnsAsync(multiDayHearings); - - // Act - var result = await _controller.GetHearingById(_v1HearingId); - - // Assert - var okRequestResult = (OkObjectResult) result; - okRequestResult.StatusCode.Should().Be(200); - - var response = (HearingDetailsResponse) ((OkObjectResult) result).Value; - var expectedActiveHearingsInGroup = multiDayHearings - .Where(h => - h.Status != BookingStatus.Cancelled && - h.Status != BookingStatus.Failed) - .ToList(); - var expectedHearingLastDay = expectedActiveHearingsInGroup[^1]; - response.MultiDayHearingLastDayScheduledDateTime.Should().Be(expectedHearingLastDay.ScheduledDateTime); - response.HearingsInGroup.Should().BeEquivalentTo(multiDayHearings.Select(x => x.Map())); - } [Test] - public async Task Should_return_ok_status_for_multi_day_hearing_V2() + public async Task Should_return_ok_status_for_multi_day_hearing() { // Arrange - _mocker.Mock().Setup(x => x.UseV2Api()) - .Returns(true); var groupId = _vhExistingHearingV2.Id; _vhExistingHearingV2.GroupId = groupId; _mocker.Mock().Setup(x => x.GetHearingDetailsByIdV2Async(It.IsAny())) @@ -296,61 +221,11 @@ public async Task Should_return_ok_status_for_multi_day_hearing_V2() } [Test] - public async Task Should_return_ok_status_for_cancelled_multi_day_hearing_V1() - { - // Scenario - all days in the multi day hearing are cancelled - - // Arrange - _mocker.Mock().Setup(x => x.UseV2Api()) - .Returns(false); - var groupId = _vhExistingHearingV1.Id; - _vhExistingHearingV1.GroupId = groupId; - _vhExistingHearingV1.Status = BookingStatus.Cancelled; - _mocker.Mock().Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ReturnsAsync(_vhExistingHearingV1); - - var dates = new List - { - _vhExistingHearingV1.ScheduledDateTime.AddDays(1), - _vhExistingHearingV1.ScheduledDateTime.AddDays(2), - _vhExistingHearingV1.ScheduledDateTime.AddDays(3), - _vhExistingHearingV1.ScheduledDateTime.AddDays(4), - }; - var multiDayHearings = new List - { - _vhExistingHearingV1 - }; - multiDayHearings.AddRange(dates.Select(date => new BookingsApi.Contract.V1.Responses.HearingDetailsResponse - { - Id = Guid.NewGuid(), - ScheduledDateTime = date, - ScheduledDuration = _vhExistingHearingV2.ScheduledDuration, - GroupId = groupId, - Status = BookingStatus.Cancelled - })); - _mocker.Mock().Setup(x => x.GetHearingsByGroupIdAsync(groupId)) - .ReturnsAsync(multiDayHearings); - - // Act - var result = await _controller.GetHearingById(_v1HearingId); - - // Assert - var okRequestResult = (OkObjectResult) result; - okRequestResult.StatusCode.Should().Be(200); - - var response = (HearingDetailsResponse) ((OkObjectResult) result).Value; - response.MultiDayHearingLastDayScheduledDateTime.Should().BeNull(); - response.HearingsInGroup.Should().BeEquivalentTo(multiDayHearings.Select(x => x.Map())); - } - - [Test] - public async Task Should_return_ok_status_for_cancelled_multi_day_hearing_V2() + public async Task Should_return_ok_status_for_cancelled_multi_day_hearing() { // Scenario - all days in the multi day hearing are cancelled // Arrange - _mocker.Mock().Setup(x => x.UseV2Api()) - .Returns(true); var groupId = _vhExistingHearingV2.Id; _vhExistingHearingV2.GroupId = groupId; _vhExistingHearingV2.Status = BookingStatusV2.Cancelled; @@ -390,27 +265,5 @@ public async Task Should_return_ok_status_for_cancelled_multi_day_hearing_V2() response.MultiDayHearingLastDayScheduledDateTime.Should().BeNull(); response.HearingsInGroup.Should().BeEquivalentTo(multiDayHearings.Select(x => x.Map())); } - - [Test] - public async Task Should_return_bad_request_if_hearing_id_is_empty() - { - // Arrange - GivenApiThrowsExceptionOnGetHearing(HttpStatusCode.BadRequest); - - var invalidId = Guid.Empty; - - // Act - var result = await _controller.GetHearingById(invalidId); - - // Assert - var badRequestResult = (BadRequestObjectResult) result; - badRequestResult.StatusCode.Should().Be(400); - } - - private void GivenApiThrowsExceptionOnGetHearing(HttpStatusCode code) - { - _mocker.Mock().Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())) - .ThrowsAsync(ClientException.ForBookingsAPI(code)); - } } } diff --git a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/GetStatusHearingTests.cs b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/GetStatusHearingTests.cs index 63ba8f9e8..d3eeaf20d 100644 --- a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/GetStatusHearingTests.cs +++ b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/GetStatusHearingTests.cs @@ -44,8 +44,7 @@ public void Setup() new Mock>().Object, new Mock>().Object, _hearingServiceMock.Object, - _conferenceDetailsServiceMock.Object, - _featureFlag.Object); + _conferenceDetailsServiceMock.Object); Initialise(); @@ -106,76 +105,6 @@ public void Initialise() .ReturnsAsync(GetHearingDetailsResponseV2(BookingsApi.Contract.V2.Enums.BookingStatusV2.Booked)); } - [Test] - public async Task Should_return_ok_true_status_when_booking_status_is_created_and_has_valid_room() - { - ConferenceDetailsResponse conferenceResponse = new() { MeetingRoom = new() { - AdminUri = "AdminUri", ParticipantUri = "ParticipantUri", JudgeUri = "JudgeUri", PexipNode = "PexipNode"} }; - - // Arrange - _conferenceDetailsServiceMock.Setup(x => x.GetConferenceDetailsByHearingId(_guid, false)) - .ReturnsAsync(conferenceResponse); - _vhExistingHearing.Status = BookingStatus.Created; - - // Act - var result = await _controller.GetHearingConferenceStatus(_guid); - - // Assert - var okRequestResult = (OkObjectResult)result; - okRequestResult.StatusCode.Should().Be(200); - - var hearing = (UpdateBookingStatusResponse)((OkObjectResult)result).Value; - hearing.Success.Should().Be(true); - _conferenceDetailsServiceMock.Verify(x => x.GetConferenceDetailsByHearingId(It.IsAny(), false), Times.Once); - _bookingsApiClientMock.Verify(x => x.GetHearingDetailsByIdAsync(It.IsAny()), Times.Once); - } - - [Test] - public async Task Should_return_ok_with_false_when_hearing_status_is_created_and_invalid_room() - { - ConferenceDetailsResponse conferenceResponse = new() { MeetingRoom = new MeetingRoomResponse() }; - - // Arrange - _conferenceDetailsServiceMock.Setup(x => x.GetConferenceDetailsByHearingId(It.IsAny(), false)) - .ReturnsAsync(conferenceResponse); - _vhExistingHearing.Status = BookingStatus.Created; - - // Act - var result = await _controller.GetHearingConferenceStatus(_guid); - - // Assert - var okRequestResult = (OkObjectResult)result; - okRequestResult.StatusCode.Should().Be(200); - - var hearing = (UpdateBookingStatusResponse)((OkObjectResult)result).Value; - hearing.Success.Should().Be(false); - _conferenceDetailsServiceMock.Verify(x => x.GetConferenceDetailsByHearingId(It.IsAny(), false), Times.Once); - _bookingsApiClientMock.Verify(x => x.GetHearingDetailsByIdAsync(It.IsAny()), Times.Once); - } - - [Test] - public async Task Should_return_ok_status_if_hearing_has_not_valid_room_and_status_is_booked() - { - ConferenceDetailsResponse conferenceResponse = new() { MeetingRoom = new MeetingRoomResponse() }; - - // Arrange - _conferenceDetailsServiceMock.Setup(x => x.GetConferenceDetailsByHearingId(It.IsAny(), false)) - .ReturnsAsync(conferenceResponse); - _bookingsApiClientMock.Setup(x => x.GetBookingStatusByIdAsync(It.IsAny())).ReturnsAsync(BookingStatus.Booked); - - // Act - var result = await _controller.GetHearingConferenceStatus(_guid); - - // Assert - var okRequestResult = (OkObjectResult)result; - okRequestResult.StatusCode.Should().Be(200); - - var hearing = (UpdateBookingStatusResponse)((OkObjectResult)result).Value; - hearing.Success.Should().Be(false); - _conferenceDetailsServiceMock.Verify(x => x.GetConferenceDetailsByHearingId(It.IsAny(), false), Times.Never); - _bookingsApiClientMock.Verify(x => x.GetHearingDetailsByIdAsync(It.IsAny()), Times.Once); - } - [Test] public async Task Should_return_false_when_hearing_not_be_found() { @@ -190,44 +119,7 @@ public async Task Should_return_false_when_hearing_not_be_found() notFoundResult.StatusCode.Should().Be(200); ((UpdateBookingStatusResponse)notFoundResult.Value)?.Success.Should().BeFalse(); } - - [Test] - public async Task Should_return_BadRequest_when_issue_with_finding_hearing_with_bookings_api() - { - - ConferenceDetailsResponse conferenceResponse = new ConferenceDetailsResponse(); - conferenceResponse.MeetingRoom = new MeetingRoomResponse(); - - - // Arrange - _bookingsApiClientMock.Setup(x => x.GetHearingDetailsByIdAsync(It.IsAny())).Throws(new BookingsApiException("Error", 400, null, null, null)); - // Act - var result = await _controller.GetHearingConferenceStatus(_guid); - - // Assert - var badRequest = (BadRequestObjectResult)result; - badRequest.StatusCode.Should().Be(400); - } - - [Test] - public async Task Should_return_BadRequest_when_issue_with_finding_hearing_with_video_api() - { - - ConferenceDetailsResponse conferenceResponse = new ConferenceDetailsResponse(); - conferenceResponse.MeetingRoom = new MeetingRoomResponse(); - - - // Arrange - _vhExistingHearing.Status = BookingStatus.Created; - _conferenceDetailsServiceMock.Setup(x => x.GetConferenceDetailsByHearingId(It.IsAny(), false)).Throws(new VideoApiException("Error", 400, null, null, null)); - // Act - var result = await _controller.GetHearingConferenceStatus(_guid); - - // Assert - var badRequest = (BadRequestObjectResult)result; - badRequest.StatusCode.Should().Be(400); - } - + [Test] public async Task Should_return_not_found_if_hearing_failed_to_be_found() { @@ -263,7 +155,7 @@ public async Task Should_return_badRequest_if_hearing_failed_to_fail() } [Test] - public async Task Should_return_ok_status_with_success_when_V2flag_on() + public async Task Should_return_ok_status_with_success() { // Arrange ConferenceDetailsResponse conferenceResponse = new() @@ -277,7 +169,6 @@ public async Task Should_return_ok_status_with_success_when_V2flag_on() } }; - _featureFlag.Setup(x => x.UseV2Api()).Returns(true); _conferenceDetailsServiceMock.Setup(x => x.GetConferenceDetailsByHearingId(_guid, false)) .ReturnsAsync(conferenceResponse); _vhExistingHearingV2.Status = BookingsApi.Contract.V2.Enums.BookingStatusV2.Created; @@ -296,59 +187,6 @@ public async Task Should_return_ok_status_with_success_when_V2flag_on() } - [TestCase(false)] - [TestCase(true)] - public async Task Should_return_ok_status_with_success_when_users_not_created_for_successful_multi_day_booking_with_notify_flag_on(bool v2FlagOn) - { - // When the notify flag is enabled, users for multi day bookings are created as part of the clone process rather than the first day of the multi-day, - // so don't wait for them to be created - - // Arrange - _featureFlag.Setup(x => x.UsePostMay2023Template()).Returns(true); - _featureFlag.Setup(x => x.UseV2Api()).Returns(v2FlagOn); - - if (v2FlagOn) - { - _vhExistingHearingV2.GroupId = _vhExistingHearingV2.Id; // Multi day hearing - _vhExistingHearingV2.Status = BookingStatusV2.Created; - } - else - { - _vhExistingHearing.GroupId = _vhExistingHearing.Id; // Multi day hearing - _vhExistingHearing.Status = BookingStatus.Created; - } - - foreach (var participant in _vhExistingHearing.Participants) - { - // Contact email is same as username, so user not created - participant.Username = participant.ContactEmail; - } - - // Indicate a successful booking - var conferenceResponse = new ConferenceDetailsResponse - { - MeetingRoom = new() - { - AdminUri = "AdminUri", - ParticipantUri = "ParticipantUri", - JudgeUri = "JudgeUri", - PexipNode = "PexipNode" - } - }; - _conferenceDetailsServiceMock.Setup(x => x.GetConferenceDetailsByHearingId(_guid, false)) - .ReturnsAsync(conferenceResponse); - - // Act - var result = await _controller.GetHearingConferenceStatus(_guid); - - // Assert - var okRequestResult = (OkObjectResult)result; - okRequestResult.StatusCode.Should().Be(200); - - var hearing = (UpdateBookingStatusResponse)((OkObjectResult)result).Value; - hearing.Success.Should().Be(true); - } - private HearingDetailsResponseV2 GetHearingDetailsResponseV2(BookingsApi.Contract.V2.Enums.BookingStatusV2 status) { _guid = Guid.NewGuid(); diff --git a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/HearingsControllerTests.cs b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/HearingsControllerTests.cs index 7a6cfae7a..e9357e5e0 100644 --- a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/HearingsControllerTests.cs +++ b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/HearingsControllerTests.cs @@ -60,15 +60,14 @@ protected virtual void Setup() _kinlyOptionsMock.Setup((op) => op.Value).Returns(_kinlyConfigurationMock.Object); _participantGroupLogger = new Mock>(); - _hearingsService = new HearingsService(BookingsApiClient.Object, _participantGroupLogger.Object, FeatureToggle.Object); + _hearingsService = new HearingsService(BookingsApiClient.Object, _participantGroupLogger.Object); Controller = new AdminWebsite.Controllers.HearingsController(BookingsApiClient.Object, UserIdentity.Object, _editHearingRequestValidator.Object, new Mock>().Object, _hearingsService, - _conferencesServiceMock.Object, - FeatureToggle.Object); + _conferencesServiceMock.Object); } protected static List CreateListOfV1HearingsInMultiDayGroup( diff --git a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/PostHearingTests.cs b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/PostHearingTests.cs index c0196403b..4a6d32ceb 100644 --- a/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/PostHearingTests.cs +++ b/AdminWebsite/AdminWebsite.UnitTests/Controllers/HearingsController/PostHearingTests.cs @@ -54,146 +54,8 @@ public void Setup() }, CaseTypeName = "Generic" }); - _mocker.Mock().Setup(e => e.BookAndConfirmToggle()).Returns(true); _controller = _mocker.Create(); } - - [Test] - public async Task Should_create_a_hearing_with_endpoints() - { - - var newHearingRequest = new BookingDetailsRequest - { - Participants = new List - { - new () - { - CaseRoleName = "CaseRole", - ContactEmail = "contact1@hmcts.net", - HearingRoleName = "HearingRole", - DisplayName = "display name1", - FirstName = "fname", - MiddleNames = "", - LastName = "lname1", - Username = "username1@hmcts.net", - OrganisationName = "", - Representee = "", - TelephoneNumber = "" - }, - new () - { - CaseRoleName = "CaseRole", ContactEmail = "contact2@hmcts.net", - HearingRoleName = "HearingRole", DisplayName = "display name2", - FirstName = "fname2", MiddleNames = "", LastName = "lname2", - Username = "username2@hmcts.net", OrganisationName = "", Representee = "", - TelephoneNumber = "" - }, - }, - Endpoints = new List - { - new () {DisplayName = "displayname1", DefenceAdvocateContactEmail = "username1@hmcts.net"}, - new () {DisplayName = "displayname2", DefenceAdvocateContactEmail = "username2@hmcts.net"}, - } - }; - - var bookingRequest = new BookHearingRequest - { - BookingDetails = newHearingRequest - }; - - // setup response - var hearingDetailsResponse = HearingResponseBuilder.Build() - .WithEndPoints(2) - .WithParticipant("Representative", "username1@hmcts.net") - .WithParticipant("Individual", "username2@hmcts.net"); - _mocker.Mock().Setup(x => x.BookNewHearingAsync(It.IsAny())) - .ReturnsAsync(hearingDetailsResponse); - _mocker.Mock().Setup(x => x.GetAdUserIdForUsername(It.IsAny())).ReturnsAsync(Guid.NewGuid().ToString()); - - var result = await _controller.Post(bookingRequest); - - result.Result.Should().BeOfType(); - var createdObjectResult = (CreatedResult)result.Result; - createdObjectResult.StatusCode.Should().Be(201); - } - - [Test] - public async Task Should_create_a_hearing_with_LinkedParticipants() - { - // request. - var newHearingRequest = new BookingDetailsRequest() - { - Participants = new List - { - new () { CaseRoleName = "CaseRole", ContactEmail = "firstName1.lastName1@email.com", - DisplayName = "firstName1 lastName1", FirstName = "firstName1", HearingRoleName = "Litigant in person", LastName = "lastName1", MiddleNames = "", - OrganisationName = "", Representee = "", TelephoneNumber = "1234567890", Title = "Mr.", Username = "firstName1.lastName1@email.net" }, - new () { CaseRoleName = "CaseRole", ContactEmail = "firstName2.lastName2@email.com", - DisplayName = "firstName2 lastName2", FirstName = "firstName2", HearingRoleName = "Interpreter", LastName = "lastName2", MiddleNames = "", - OrganisationName = "", Representee = "", TelephoneNumber = "1234567890", Title = "Mr.", Username = "firstName2.lastName2@email.net" }, - - }, - LinkedParticipants = new List - { - new () { ParticipantContactEmail = "firstName1.lastName1@email.com", LinkedParticipantContactEmail = "firstName2.lastName2@email.com", Type = LinkedParticipantType.Interpreter }, - new () { ParticipantContactEmail = "firstName2.lastName2@email.com", LinkedParticipantContactEmail = "firstName1.lastName1@email.com", Type = LinkedParticipantType.Interpreter } - } - }; - - var bookingRequest = new BookHearingRequest - { - BookingDetails = newHearingRequest - }; - // set response. - var linkedParticipant1 = new List { new () { LinkedId = Guid.NewGuid(), Type = V1.Enums.LinkedParticipantType.Interpreter } }; - var participant1 = Builder.CreateNew().With(x => x.Id = Guid.NewGuid()) - .With(x => x.UserRoleName = "Individual").With(x => x.Username = "firstName1.lastName1@email.net") - .With(x => x.LinkedParticipants = linkedParticipant1) - .Build(); - var linkedParticipant2 = new List() { new () { LinkedId = Guid.NewGuid(), Type = V1.Enums.LinkedParticipantType.Interpreter } }; - var participant2 = Builder.CreateNew().With(x => x.Id = Guid.NewGuid()) - .With(x => x.UserRoleName = "Individual").With(x => x.Username = "firstName1.lastName1@email.net") - .With(x => x.LinkedParticipants = linkedParticipant2) - .Build(); - var hearingDetailsResponse = Builder.CreateNew() - .With(x => x.Cases = Builder.CreateListOfSize(2).Build().ToList()) - .With(x => x.Endpoints = Builder.CreateListOfSize(2).Build().ToList()) - .With(x => x.Participants = new List { participant1, participant2 }).Build(); - _mocker.Mock().Setup(x => x.BookNewHearingAsync(It.IsAny())) - .ReturnsAsync(hearingDetailsResponse); - _mocker.Mock().Setup(x => x.GetAdUserIdForUsername(It.IsAny())).ReturnsAsync(Guid.NewGuid().ToString()); - - var result = await _controller.Post(bookingRequest); - result.Result.Should().BeOfType(); - var createdObjectResult = (CreatedResult)result.Result; - createdObjectResult.StatusCode.Should().Be(201); - } - - [Test] - public async Task Should_pass_bad_request_from_bookings_api() - { - var hearing = new BookingDetailsRequest() - { - Participants = new List() - }; - - var bookingRequest = new BookHearingRequest - { - BookingDetails = hearing - }; - - const string key = "ScheduledDateTime"; - const string errorMessage = "ScheduledDateTime cannot be in the past"; - var validationProblemDetails = new ValidationProblemDetails(new Dictionary - { - {key, [errorMessage] }, - }); - _mocker.Mock().Setup(x => x.BookNewHearingAsync(It.IsAny())) - .Throws(ClientException.ForBookingsAPIValidation(validationProblemDetails)); - - var result = await _controller.Post(bookingRequest); - result.Result.Should().BeOfType(); - } [Test] public void Should_throw_BookingsApiException() @@ -236,31 +98,7 @@ public void Should_throw_Exception() ((ObjectResult) response.Result.Result).StatusCode.Should().Be(500); } - - [Test] - public async Task Should_pass_current_user_as_created_by_to_service() - { - const string CURRENT_USERNAME = "test@hmcts.net"; - _mocker.Mock().Setup(x => x.GetUserIdentityName()).Returns(CURRENT_USERNAME); - - // setup response - var hearingDetailsResponse = HearingResponseBuilder.Build() - .WithParticipant("Representative") - .WithParticipant("Individual"); - _mocker.Mock().Setup(x => x.BookNewHearingAsync(It.IsAny())) - .ReturnsAsync(hearingDetailsResponse); - - var result = await PostNewHearing(); - - result.Result.Should().BeOfType(); - var createdResult = (CreatedResult)result.Result; - createdResult.Location.Should().Be(""); - - _mocker.Mock().Verify(x => x.BookNewHearingAsync(It.Is( - request => request.CreatedBy == CURRENT_USERNAME)), Times.Once); - _mocker.Mock().Verify(x => x.AssignParticipantToGroup(It.IsAny(), It.IsAny()), Times.Never); - } - + [Test] public async Task Should_clone_hearing() { diff --git a/AdminWebsite/AdminWebsite.UnitTests/Controllers/ReferenceDataControllerTests.cs b/AdminWebsite/AdminWebsite.UnitTests/Controllers/ReferenceDataControllerTests.cs index 84054e8c0..b69991603 100644 --- a/AdminWebsite/AdminWebsite.UnitTests/Controllers/ReferenceDataControllerTests.cs +++ b/AdminWebsite/AdminWebsite.UnitTests/Controllers/ReferenceDataControllerTests.cs @@ -1,4 +1,4 @@ -using System.Linq; +using System.Linq; using System.Threading.Tasks; using AdminWebsite.Configuration; using Autofac.Extras.Moq; @@ -19,7 +19,6 @@ public class ReferenceDataControllerTests { private Mock _bookingsApiClientMock; private Mock _userIdentityMock; - private Mock _featureTogglesMock; private ReferenceDataController _controller; private AutoMock _mocker; @@ -29,7 +28,6 @@ public void Setup() _mocker = AutoMock.GetLoose(); _bookingsApiClientMock = _mocker.Mock(); _userIdentityMock = _mocker.Mock(); - _featureTogglesMock = _mocker.Mock(); _controller = _mocker.Create(); } @@ -47,8 +45,6 @@ public void Should_return_a_list_of_venues() [Test] public async Task Should_return_all_hearing_types_and_case_types_where_hearing_type_is_empty() { - - _featureTogglesMock.Setup(x => x.UseV2Api()).Returns(true); // Arrange var includeDeleted = true; _userIdentityMock.Setup(x => x.IsATeamLead()) @@ -66,17 +62,12 @@ public async Task Should_return_all_hearing_types_and_case_types_where_hearing_t _bookingsApiClientMock.Verify(x => x.GetCaseTypesAsync(includeDeleted), Times.Once); } - [TestCase(true)] - [TestCase(false)] - public async Task Should_return_participants_roles(bool refDataFeatureToggle) + [Test] + public async Task Should_return_participants_roles() { - _featureTogglesMock.Setup(x => x.ReferenceDataToggle()).Returns(refDataFeatureToggle); List listTypes; - if(refDataFeatureToggle) - listTypes = new List { new CaseRoleResponseV2 { Name = "type1" } }; - else - listTypes = new List { new CaseRoleResponse { Name = "type1" } }; - SetTestCase(listTypes, refDataFeatureToggle); + listTypes = new List { new CaseRoleResponseV2 { Name = "type1" } }; + SetTestCase(listTypes); var response = await _controller.GetParticipantRoles("type1"); response.Should().NotBeNull(); @@ -115,27 +106,17 @@ public async Task Should_return_empty_list_of_participants_roles_if_list_types_i caseRoles.Count.Should().Be(0); } - private void SetTestCase(List listTypes, bool refDataToggle = false) + private void SetTestCase(List listTypes) { - var listHearingRoles = new List { new HearingRoleResponse { Name = "type1", UserRole = "role1"} }; var listHearingRoles2 = new List { new HearingRoleResponseV2 { Name = "type1", UserRole = "role1"} }; _userIdentityMock.Setup(x => x.GetAdministratorCaseTypes()).Returns(new List { "type1", "type2" }); - if (refDataToggle) - { - //v2 endpoints - var casetypeV2Response = listTypes?.Select(e => (CaseRoleResponseV2)e).ToList(); - _bookingsApiClientMock.Setup(x => x.GetCaseRolesForCaseServiceAsync(It.IsAny())).ReturnsAsync(casetypeV2Response); - _bookingsApiClientMock.Setup(x => x.GetHearingRolesForCaseRoleV2Async(It.IsAny(), It.IsAny())).ReturnsAsync(listHearingRoles2); - } - else - { - //V1 endpoints - var casetypeV1Response = listTypes?.Select(e => (CaseRoleResponse)e).ToList(); - _bookingsApiClientMock.Setup(x => x.GetCaseRolesForCaseTypeAsync(It.IsAny())).ReturnsAsync(casetypeV1Response); - _bookingsApiClientMock.Setup(x => x.GetHearingRolesForCaseRoleAsync(It.IsAny(), It.IsAny())).ReturnsAsync(listHearingRoles); - - } + + //v2 endpoints + var casetypeV2Response = listTypes?.Select(e => (CaseRoleResponseV2)e).ToList(); + _bookingsApiClientMock.Setup(x => x.GetCaseRolesForCaseServiceAsync(It.IsAny())).ReturnsAsync(casetypeV2Response); + _bookingsApiClientMock.Setup(x => x.GetHearingRolesForCaseRoleV2Async(It.IsAny(), It.IsAny())).ReturnsAsync(listHearingRoles2); + } private static List GetCaseTypesList() diff --git a/AdminWebsite/AdminWebsite.UnitTests/Services/HearingServiceTests.cs b/AdminWebsite/AdminWebsite.UnitTests/Services/HearingServiceTests.cs index 98a445fe0..2d3ac80d1 100644 --- a/AdminWebsite/AdminWebsite.UnitTests/Services/HearingServiceTests.cs +++ b/AdminWebsite/AdminWebsite.UnitTests/Services/HearingServiceTests.cs @@ -47,8 +47,7 @@ public void Setup() _mocker.Mock() .Setup(c => c.GetHearingsByGroupIdAsync(It.IsAny())) .ReturnsAsync(new List { _hearing }); - _mocker.Mock() - .Setup(x => x.BookAndConfirmToggle()).Returns(true); + _service = _mocker.Create(); _hearing = InitHearing(); } diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/app-routing.module.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/app-routing.module.ts index c7e6348fc..78a6403e7 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/app-routing.module.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/app-routing.module.ts @@ -12,11 +12,9 @@ import { EditParticipantSearchComponent } from './edit-participant/edit-particip import { EditParticipantComponent } from './edit-participant/edit-participant/edit-participant.component'; import { HomeComponent } from './home/home.component'; import { AdminGuard } from './security/guards/admin.guard'; -import { WorkAllocationFeatureGuard } from './security/guards/work-allocation-feature.guard'; import { VhOfficerAdminGuard } from './security/guards/vh-officer-admin.guard'; import { LoginComponent } from './security/login.component'; import { ReformLoginComponent } from './security/reform-login.component'; -import { AudioSearchGuard } from './security/audio-search.guard'; import { ManageTeamFeatureGuard } from './security/guards/manage-team-feature.guard'; import { AuthGuard } from './security/guards/auth.guard'; @@ -32,13 +30,13 @@ export const routes: Routes = [ { path: 'error', component: ErrorComponent }, { path: 'unsupported-browser', component: UnsupportedBrowserComponent }, { path: 'change-password', component: ChangePasswordComponent, canActivate: [AuthGuard, AdminGuard] }, - { path: 'get-audio-file', component: GetAudioFileComponent, canActivate: [AuthGuard, AdminGuard, AudioSearchGuard] }, + { path: 'get-audio-file', component: GetAudioFileComponent, canActivate: [AuthGuard, AdminGuard] }, { path: 'delete-participant', component: DeleteParticipantSearchComponent, canActivate: [AuthGuard, AdminGuard] }, { path: 'edit-participant-search', component: EditParticipantSearchComponent, canActivate: [AuthGuard, AdminGuard] }, { path: 'edit-participant', component: EditParticipantComponent, canActivate: [AuthGuard, AdminGuard] }, { path: 'work-allocation', - canActivate: [AuthGuard, VhOfficerAdminGuard, WorkAllocationFeatureGuard], + canActivate: [AuthGuard, VhOfficerAdminGuard], loadChildren: () => import('./work-allocation/work-allocation.module').then(m => m.WorkAllocationModule) }, { diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/app.module.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/app.module.ts index f8977088c..4c9a20477 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/app.module.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/app.module.ts @@ -36,13 +36,11 @@ import { AuthConfigModule } from './security/auth-config.module'; import { FontAwesomeModule } from '@fortawesome/angular-fontawesome'; import { UnallocatedHearingsComponent } from './dashboard/unallocated-hearings/unallocated-hearings.component'; import { HomeComponent } from './home/home.component'; -import { WorkAllocationFeatureGuard } from './security/guards/work-allocation-feature.guard'; import { VhOfficerAdminGuard } from './security/guards/vh-officer-admin.guard'; import { LastMinuteAmendmentsGuard } from './security/guards/last-minute-amendments.guard'; import { AdminGuard } from './security/guards/admin.guard'; import { AuthGuard } from './security/guards/auth.guard'; import { ReformLoginComponent } from './security/reform-login.component'; -import { AudioSearchGuard } from './security/audio-search.guard'; import { ManageTeamFeatureGuard } from './security/guards/manage-team-feature.guard'; export function loadConfig(configService: ConfigService) { @@ -101,9 +99,7 @@ export function loadConfig(configService: ConfigService) { PageTrackerService, AppInsightsLogger, WindowRef, - WorkAllocationFeatureGuard, - ManageTeamFeatureGuard, - AudioSearchGuard + ManageTeamFeatureGuard ], exports: [UnallocatedHearingsComponent], bootstrap: [AppComponent] diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/add-participant/add-participant.component.html b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/add-participant/add-participant.component.html index f5e9f7048..ae048fde7 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/add-participant/add-participant.component.html +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/add-participant/add-participant.component.html @@ -36,24 +36,6 @@

There is a probl

Add a participant

-
- - - {{ constants.Error.PartyErrorMsg }} - - - - -
-
@@ -77,7 +59,7 @@

Add a participant

> -
+
- - - - -
- Please select a hearing type -
-
-
diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/create-hearing/create-hearing.component.spec.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/create-hearing/create-hearing.component.spec.ts index 7e4108eb7..c8794a2fe 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/create-hearing/create-hearing.component.spec.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/create-hearing/create-hearing.component.spec.ts @@ -23,7 +23,6 @@ import { createMultiDayHearing } from 'src/app/testing/helpers/hearing.helpers'; function initHearingRequest(): HearingModel { const newHearing = new HearingModel(); - newHearing.hearing_type_id = -1; newHearing.hearing_venue_id = -1; newHearing.scheduled_duration = 0; return newHearing; @@ -31,7 +30,6 @@ function initHearingRequest(): HearingModel { function initExistingHearingRequest(): HearingModel { const existingRequest = new HearingModel(); - existingRequest.hearing_type_id = 2; existingRequest.hearing_venue_id = 1; existingRequest.case_type = 'Generic'; @@ -57,7 +55,6 @@ describe('CreateHearingComponent with multiple case types', () => { beforeEach(() => { launchDarklyServiceSpy = jasmine.createSpyObj('LaunchDarklyService', ['getFlag']); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.useV2Api).and.returnValue(of(false)); launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.multiDayBookingEnhancements).and.returnValue(of(false)); videoHearingsServiceSpy = jasmine.createSpyObj('VideoHearingsService', [ @@ -97,19 +94,9 @@ describe('CreateHearingComponent with multiple case types', () => { hearingTypeControl = component.form.controls['hearingType']; }); - it('should create', () => { - fixture.detectChanges(); - expect(component).toBeTruthy(); - expect(component.caseNumber.value).toBeNull(); - expect(component.caseName.value).toBeNull(); - expect(component.caseType.value).toBe('Please select'); - expect(component.hearingType.value).toBe(null); - }); - it('should not set case type when multiple items returned', () => { fixture.detectChanges(); expect(component).toBeTruthy(); - expect(component.availableHearingTypes.length).toBe(3); }); it('should fail validation when form is empty', () => { @@ -144,44 +131,6 @@ describe('CreateHearingComponent with multiple case types', () => { component.failedSubmission = true; expect(component.caseNumberInvalid).toBeTruthy(); }); - it('should validate case type', () => { - const caseTypeValue = 'Tax'; - expect(caseNumberControl.valid).toBeFalsy(); - caseTypeControl.setValue(caseTypeValue); - expect(component.selectedCaseType).toBe(caseTypeValue); - expect(caseTypeControl.valid).toBeTruthy(); - }); - - it('should validate hearing type', () => { - expect(hearingTypeControl.valid).toBeFalsy(); - hearingTypeControl.setValue(2); - expect(hearingTypeControl.valid).toBeTruthy(); - }); - - it('should set hearing type to please select when case type changes', () => { - const caseTypeValue = 'Generic'; - caseTypeControl.setValue(caseTypeValue); - expect(component.selectedCaseType).toBe(caseTypeValue); - expect(caseTypeControl.valid).toBeTruthy(); - expect(component.hearingType.value).toBe(null); - expect(hearingTypeControl.valid).toBeFalsy(); - }); - - it('should update hearing request when form is valid', () => { - expect(component.form.valid).toBeFalsy(); - - caseNameControl.setValue('Captain America vs The World'); - caseNumberControl.setValue('12345'); - caseTypeControl.setValue('Tax'); - hearingTypeControl.setValue(2); - - expect(component.form.valid).toBeTruthy(); - component.saveHearingDetails(); - expect(component.hearing.hearing_type_id).toBe(2); - const hearingTypeName = MockValues.HearingTypesList.find(c => c.id === component.hearing.hearing_type_id).name; - expect(component.hearing.hearing_type_name).toBe(hearingTypeName); - expect(component.hearing.cases.length).toBe(1); - }); }); describe('CreateHearingComponent with single case type', () => { @@ -191,7 +140,6 @@ describe('CreateHearingComponent with single case type', () => { beforeEach(() => { launchDarklyServiceSpy = jasmine.createSpyObj('LaunchDarklyService', ['getFlag']); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.useV2Api).and.returnValue(of(false)); launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.multiDayBookingEnhancements).and.returnValue(of(false)); videoHearingsServiceSpy = jasmine.createSpyObj('VideoHearingsService', [ @@ -226,15 +174,6 @@ describe('CreateHearingComponent with single case type', () => { fixture.detectChanges(); }); - it('should set case type when single item returned', fakeAsync(() => { - videoHearingsServiceSpy.getHearingTypes.and.returnValue(of(MockValues.HearingTypesSingle)); - fixture.detectChanges(); - tick(); - fixture.detectChanges(); - expect(component.availableHearingTypes.length).toBe(1); - expect(component.selectedCaseType).toBeDefined(); - })); - it('should show cancel booking confirmation pop up', () => { component.editMode = false; component.form.markAsDirty(); @@ -244,68 +183,15 @@ describe('CreateHearingComponent with single case type', () => { }); }); -describe('CreateHearingComponent with ref data toggle on', () => { - let component: CreateHearingComponent; - let fixture: ComponentFixture; - let hearingTypeControl: AbstractControl; - const newHearing = initHearingRequest(); - - beforeEach(() => { - launchDarklyServiceSpy = jasmine.createSpyObj('LaunchDarklyService', ['getFlag']); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.useV2Api).and.returnValue(of(true)); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.multiDayBookingEnhancements).and.returnValue(of(false)); - - videoHearingsServiceSpy = jasmine.createSpyObj('VideoHearingsService', [ - 'getHearingTypes', - 'getCurrentRequest', - 'updateHearingRequest', - 'cancelRequest', - 'setBookingHasChanged' - ]); - routerSpy = jasmine.createSpyObj('Router', ['navigate']); - bookingServiceSpy = jasmine.createSpyObj('BookingSErvice', ['isEditMode', 'resetEditMode', 'removeEditMode']); - videoHearingsServiceSpy.getCurrentRequest.and.returnValue(newHearing); - videoHearingsServiceSpy.getHearingTypes.and.returnValue(of(MockValues.HearingTypesSingle)); - - TestBed.configureTestingModule({ - imports: [HttpClientModule, ReactiveFormsModule, RouterTestingModule], - providers: [ - { provide: VideoHearingsService, useValue: videoHearingsServiceSpy }, - { provide: Router, useValue: routerSpy }, - { provide: ErrorService, useValue: errorService }, - { provide: BookingService, useValue: bookingServiceSpy }, - { provide: Logger, useValue: loggerSpy }, - { provide: LaunchDarklyService, useValue: launchDarklyServiceSpy } - ], - declarations: [CreateHearingComponent, BreadcrumbComponent, CancelPopupComponent, DiscardConfirmPopupComponent] - }).compileComponents(); - - fixture = TestBed.createComponent(CreateHearingComponent); - component = fixture.componentInstance; - component.ngOnInit(); - fixture.detectChanges(); - - hearingTypeControl = component.form.controls['hearingType']; - }); - - it('should pass validation when no hearing type is not set', () => { - expect(hearingTypeControl.valid).toBeTruthy(); - hearingTypeControl.setValue(2); - expect(hearingTypeControl.valid).toBeTruthy(); - }); -}); - describe('CreateHearingComponent with existing request in session', () => { let component: CreateHearingComponent; let fixture: ComponentFixture; let caseNameElement: HTMLInputElement; let caseNumberElement: HTMLInputElement; const existingRequest = initExistingHearingRequest(); - existingRequest.hearing_type_name = 'Automated Test'; beforeEach(() => { launchDarklyServiceSpy = jasmine.createSpyObj('LaunchDarklyService', ['getFlag']); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.useV2Api).and.returnValue(of(false)); launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.multiDayBookingEnhancements).and.returnValue(of(false)); videoHearingsServiceSpy = jasmine.createSpyObj('VideoHearingsService', [ @@ -357,12 +243,6 @@ describe('CreateHearingComponent with existing request in session', () => { sessionStorage.clear(); }); - it('should repopulate form with existing request', fakeAsync(() => { - expect(component.caseNumber.value).toBe(existingRequest.cases[0].number); - expect(component.caseName.value).toBe(existingRequest.cases[0].name); - expect(component.hearingType.value).toBe(existingRequest.hearing_type_id); - })); - it('should hide cancel and discard pop up confirmation', () => { component.attemptingCancellation = true; component.attemptingDiscardChanges = true; diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/create-hearing/create-hearing.component.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/create-hearing/create-hearing.component.ts index 29b55d0ce..0675551dc 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/create-hearing/create-hearing.component.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/create-hearing/create-hearing.component.ts @@ -35,7 +35,6 @@ export class CreateHearingComponent extends BookingBaseComponent implements OnIn isExistingHearing: boolean; destroyed$ = new Subject(); - refDataEnabled: boolean; private multiDayEnhancementsEnabled: boolean; constructor( @@ -53,18 +52,6 @@ export class CreateHearingComponent extends BookingBaseComponent implements OnIn } ngOnInit() { - this.launchDarklyService - .getFlag(FeatureFlags.useV2Api) - .pipe(takeUntil(this.destroyed$)) - .subscribe(flag => { - this.refDataEnabled = flag; - this.checkForExistingRequestOrCreateNew(); - this.initForm(); - this.retrieveHearingTypes(); - if (this.form) { - this.form.get('hearingType').setValidators(this.refDataEnabled ? [] : [Validators.required, Validators.min(1)]); - } - }); this.launchDarklyService .getFlag(FeatureFlags.multiDayBookingEnhancements) .pipe(takeUntil(this.destroyed$)) @@ -91,13 +78,15 @@ export class CreateHearingComponent extends BookingBaseComponent implements OnIn this.isExistingHearing = this.hearing?.hearing_id && this.hearing?.hearing_id?.length > 0; this.logger.debug(`${this.loggerPrefix} Checking for existing hearing.`); - if (this.hearing.case_type && this.refDataEnabled) { + this.selectedCaseType = this.hearing.case_type; + if (this.hearing.case_type) { this.selectedCaseType = this.hearing.case_type; return; } else { this.selectedCaseType = Constants.PleaseSelect; } - if (!!this.hearing.hearing_type_name && !!this.hearing.case_type && !this.refDataEnabled) { + + if (!!this.hearing.hearing_type_name && !!this.hearing.case_type) { this.selectedCaseType = this.hearing.case_type; this.logger.debug(`${this.loggerPrefix} Updating selected case type to current hearing case type.`, { hearing: this.hearing.hearing_id @@ -126,7 +115,7 @@ export class CreateHearingComponent extends BookingBaseComponent implements OnIn [Validators.required, Validators.pattern(Constants.TextInputPattern), Validators.maxLength(255)] ], caseType: [this.selectedCaseType, [Validators.required, Validators.pattern('^((?!Please select).)*$')]], - hearingType: [this.hearing.hearing_type_id, this.refDataEnabled ? [] : [Validators.required, Validators.min(1)]] + hearingType: [this.hearing.hearing_type_id, []] }); if (this.isExistingHearingOrParticipantsAdded()) { diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/hearing-schedule/hearing-schedule.component.spec.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/hearing-schedule/hearing-schedule.component.spec.ts index 29236da4c..e99ac820d 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/hearing-schedule/hearing-schedule.component.spec.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/hearing-schedule/hearing-schedule.component.spec.ts @@ -30,7 +30,6 @@ function initExistingHearingRequest(): HearingModel { today.setHours(10, 30); const existingRequest = new HearingModel(); - existingRequest.hearing_type_id = 2; existingRequest.hearing_venue_id = 1; existingRequest.scheduled_date_time = today; existingRequest.scheduled_duration = 80; @@ -85,7 +84,6 @@ describe('HearingScheduleComponent first visit', () => { referenceDataServiceServiceSpy = jasmine.createSpyObj('ReferenceDataService', ['getCourts']); referenceDataServiceServiceSpy.getCourts.and.returnValue(of(MockValues.Courts)); videoHearingsServiceSpy = jasmine.createSpyObj('VideoHearingsService', [ - 'getHearingTypes', 'getCurrentRequest', 'updateHearingRequest', 'cancelRequest', @@ -95,7 +93,6 @@ describe('HearingScheduleComponent first visit', () => { videoHearingsServiceSpy.getCurrentRequest.and.returnValue(newHearing); launchDarklyServiceSpy = jasmine.createSpyObj('LaunchDarklyService', ['getFlag']); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.useV2Api).and.returnValue(of(false)); launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.multiDayBookingEnhancements).and.returnValue(of(false)); TestBed.configureTestingModule({ @@ -416,7 +413,6 @@ describe('HearingScheduleComponent returning to page', () => { referenceDataServiceServiceSpy = jasmine.createSpyObj('ReferenceDataService', ['getCourts']); referenceDataServiceServiceSpy.getCourts.and.returnValue(of(MockValues.Courts)); videoHearingsServiceSpy = jasmine.createSpyObj('VideoHearingsService', [ - 'getHearingTypes', 'getCurrentRequest', 'updateHearingRequest', 'cancelRequest', @@ -426,7 +422,6 @@ describe('HearingScheduleComponent returning to page', () => { videoHearingsServiceSpy.getCurrentRequest.and.returnValue(existingRequest); launchDarklyServiceSpy = jasmine.createSpyObj('LaunchDarklyService', ['getFlag']); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.useV2Api).and.returnValue(of(false)); launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.multiDayBookingEnhancements).and.returnValue(of(false)); TestBed.configureTestingModule({ @@ -544,8 +539,6 @@ describe('HearingScheduleComponent returning to page', () => { referenceDataServiceServiceSpy.getCourts.and.returnValue(of(courts)); const existingHearingRequest = { ...existingRequest }; existingHearingRequest.hearing_id = '123455555900'; - existingHearingRequest.hearing_type_name = 'HearingTypeName'; - existingHearingRequest.hearing_type_code = null; existingHearingRequest.court_name = selectedCourt.name; existingHearingRequest.court_id = selectedCourt.id; videoHearingsServiceSpy.getCurrentRequest.and.returnValue(existingHearingRequest); @@ -584,7 +577,6 @@ describe('HearingScheduleComponent multi days hearing', () => { referenceDataServiceServiceSpy = jasmine.createSpyObj('ReferenceDataService', ['getCourts']); referenceDataServiceServiceSpy.getCourts.and.returnValue(of(MockValues.Courts)); videoHearingsServiceSpy = jasmine.createSpyObj('VideoHearingsService', [ - 'getHearingTypes', 'getCurrentRequest', 'updateHearingRequest', 'cancelRequest', @@ -594,7 +586,6 @@ describe('HearingScheduleComponent multi days hearing', () => { videoHearingsServiceSpy.getCurrentRequest.and.returnValue(existingRequest); launchDarklyServiceSpy = jasmine.createSpyObj('LaunchDarklyService', ['getFlag']); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.useV2Api).and.returnValue(of(false)); launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.multiDayBookingEnhancements).and.returnValue(of(false)); TestBed.configureTestingModule({ diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/hearing-schedule/hearing-schedule.component.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/hearing-schedule/hearing-schedule.component.ts index dc4c27ffc..d8778c797 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/hearing-schedule/hearing-schedule.component.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/hearing-schedule/hearing-schedule.component.ts @@ -50,7 +50,6 @@ export class HearingScheduleComponent extends BookingBaseComponent implements On newDatesFormArray: FormArray; private destroyed$ = new Subject(); - private addJudciaryMembersFeatureEnabled: boolean; multiDayBookingEnhancementsEnabled: boolean; @ViewChild('editHearingDates') editHearingDates: EditHearingDatesComponent; @@ -70,12 +69,6 @@ export class HearingScheduleComponent extends BookingBaseComponent implements On } ngOnInit() { - this.ldService - .getFlag(FeatureFlags.useV2Api) - .pipe(takeUntil(this.destroyed$)) - .subscribe(result => { - this.addJudciaryMembersFeatureEnabled = result; - }); this.ldService .getFlag(FeatureFlags.multiDayBookingEnhancements) .pipe(takeUntil(this.destroyed$)) @@ -536,12 +529,9 @@ export class HearingScheduleComponent extends BookingBaseComponent implements On if (this.editMode) { this.logger.debug(`${this.loggerPrefix} In edit mode. Returning to summary page.`); this.router.navigate([PageUrls.Summary]); - } else if (this.addJudciaryMembersFeatureEnabled) { + } else { this.logger.debug(`${this.loggerPrefix} Navigating to add joh page.`); this.router.navigate([PageUrls.AddJudicialOfficeHolders]); - } else { - this.logger.debug(`${this.loggerPrefix} Navigating to judge assignment.`); - this.router.navigate([PageUrls.AssignJudge]); } } diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/other-information/other-information.component.spec.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/other-information/other-information.component.spec.ts index 013f3b171..ca5b0b41c 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/other-information/other-information.component.spec.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/other-information/other-information.component.spec.ts @@ -29,7 +29,6 @@ function initHearingRequest(): HearingModel { const today = new Date(); today.setHours(14, 30); - newHearing.hearing_type_id = -1; newHearing.hearing_venue_id = -1; newHearing.scheduled_date_time = today; newHearing.scheduled_duration = 0; @@ -60,7 +59,6 @@ describe('OtherInformationComponent', () => { let component: OtherInformationComponent; let fixture: ComponentFixture; launchDarklyServiceSpy = jasmine.createSpyObj('LaunchDarklyService', ['getFlag']); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.useV2Api).and.returnValue(of(false)); videoHearingsServiceSpy = jasmine.createSpyObj('VideoHearingsService', [ 'getCurrentRequest', 'cancelRequest', diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/participant/item/participant-item.component.html b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/participant/item/participant-item.component.html index 70aac56a2..f60abd96f 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/participant/item/participant-item.component.html +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/participant/item/participant-item.component.html @@ -21,7 +21,7 @@
diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/participant/item/participant-item.component.spec.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/participant/item/participant-item.component.spec.ts index 9f8937bd9..554dda652 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/participant/item/participant-item.component.spec.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/participant/item/participant-item.component.spec.ts @@ -9,7 +9,6 @@ import { VideoHearingsService } from 'src/app/services/video-hearings.service'; import { Constants } from 'src/app/common/constants'; import { ParticipantModel } from 'src/app/common/model/participant.model'; import { PageUrls } from 'src/app/shared/page-url.constants'; -import { LaunchDarklyService } from '../../../services/launch-darkly.service'; import { of } from 'rxjs'; const router = { @@ -20,15 +19,12 @@ const router = { const loggerSpy = jasmine.createSpyObj('Logger', ['error', 'debug', 'warn']); let bookingServiceSpy: jasmine.SpyObj; let videoHearingsServiceSpy: jasmine.SpyObj; -const ldServiceSpy = jasmine.createSpyObj('LaunchDarklyService', ['getFlag']); - describe('ParticipantItemComponent', () => { let component: ParticipantItemComponent; let fixture: ComponentFixture; let debugElement: DebugElement; bookingServiceSpy = jasmine.createSpyObj('BookingService', ['setEditMode', 'setParticipantEmail']); - ldServiceSpy.getFlag.and.returnValue(of(true)); const participant: any = { title: 'Mrs', first_name: 'Sam', @@ -45,8 +41,7 @@ describe('ParticipantItemComponent', () => { { provide: Logger, useValue: loggerSpy }, { provide: BookingService, useValue: bookingServiceSpy }, { provide: Router, useValue: router }, - { provide: VideoHearingsService, useValue: videoHearingsServiceSpy }, - { provide: LaunchDarklyService, useValue: ldServiceSpy } + { provide: VideoHearingsService, useValue: videoHearingsServiceSpy } ], imports: [RouterTestingModule] }).compileComponents(); diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/participant/item/participant-item.component.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/participant/item/participant-item.component.ts index 310152082..6143404c6 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/participant/item/participant-item.component.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/participant/item/participant-item.component.ts @@ -9,7 +9,6 @@ import { HearingModel } from '../../../common/model/hearing.model'; import { VideoHearingsService } from 'src/app/services/video-hearings.service'; import { Constants } from 'src/app/common/constants'; import { HearingRoleCodes } from '../../../common/model/hearing-roles.model'; -import { FeatureFlags, LaunchDarklyService } from '../../../services/launch-darkly.service'; @Component({ selector: 'app-participant-item', @@ -30,19 +29,13 @@ export class ParticipantItemComponent implements OnInit { staffMemberRole = Constants.HearingRoles.StaffMember; showParticipantActions: boolean; showJudicaryActions: boolean; - isV2 = false; constructor( private bookingService: BookingService, private logger: Logger, private router: Router, - private videoHearingsService: VideoHearingsService, - private ldService: LaunchDarklyService - ) { - this.ldService.getFlag(FeatureFlags.useV2Api).subscribe((result: boolean) => { - this.isV2 = result; - }); - } + private videoHearingsService: VideoHearingsService + ) {} ngOnInit(): void { this.showParticipantActions = this.router.url.includes(PageUrls.AddParticipants) || this.router.url.includes(PageUrls.Summary); diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/summary/summary.component.spec.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/summary/summary.component.spec.ts index 98763f401..af64d981b 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/summary/summary.component.spec.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/summary/summary.component.spec.ts @@ -10,7 +10,7 @@ import { RemoveInterpreterPopupComponent } from 'src/app/popups/remove-interpret import { SaveFailedPopupComponent } from 'src/app/popups/save-failed-popup/save-failed-popup.component'; import { PipeStringifierService } from 'src/app/services/pipe-stringifier.service'; import { BreadcrumbStubComponent } from 'src/app/testing/stubs/breadcrumb-stub'; -import { LongDatetimePipe } from '../../../app/shared/directives/date-time.pipe'; +import { LongDatetimePipe } from '../../shared/directives/date-time.pipe'; import { CaseModel } from '../../common/model/case.model'; import { HearingModel } from '../../common/model/hearing.model'; import { ParticipantModel } from '../../common/model/participant.model'; @@ -54,7 +54,6 @@ function initExistingHearingRequest(): HearingModel { newCaseRequest.number = 'TX/12345/2018'; const existingRequest = new HearingModel(); - existingRequest.hearing_type_id = 2; existingRequest.cases.push(newCaseRequest); existingRequest.hearing_venue_id = 2; existingRequest.scheduled_date_time = today; @@ -62,8 +61,6 @@ function initExistingHearingRequest(): HearingModel { existingRequest.other_information = '|OtherInformation|some notes'; existingRequest.audio_recording_required = true; existingRequest.court_room = '123W'; - const hearingTypeName = MockValues.HearingTypesList.find(c => c.id === existingRequest.hearing_type_id).name; - existingRequest.hearing_type_name = hearingTypeName; const courtString = MockValues.Courts.find(c => c.id === existingRequest.hearing_venue_id).name; existingRequest.court_name = courtString; existingRequest.isMultiDayEdit = false; @@ -89,7 +86,6 @@ function initBadHearingRequest(): HearingModel { newCaseRequest.number = 'TX/12345/2018'; const existingRequest = new HearingModel(); - existingRequest.hearing_type_id = 2; existingRequest.cases.push(newCaseRequest); existingRequest.hearing_venue_id = 2; existingRequest.scheduled_date_time = today; @@ -108,7 +104,6 @@ recordingGuardServiceSpy = jasmine.createSpyObj('Recordin ]); const videoHearingsServiceSpy: jasmine.SpyObj = jasmine.createSpyObj('VideoHearingsService', [ - 'getHearingTypes', 'getCurrentRequest', 'updateHearingRequest', 'saveHearing', @@ -123,7 +118,6 @@ const videoHearingsServiceSpy: jasmine.SpyObj = jasmine.cr 'updateMultiDayHearing' ]); const launchDarklyServiceSpy = jasmine.createSpyObj('LaunchDarklyService', ['getFlag']); -launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.useV2Api).and.returnValue(of(true)); launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.multiDayBookingEnhancements).and.returnValue(of(false)); const bookingStatusService = new BookingStatusService(videoHearingsServiceSpy); @@ -139,7 +133,6 @@ describe('SummaryComponent with valid request', () => { const mockResp = new UpdateBookingStatusResponse(); mockResp.success = true; videoHearingsServiceSpy.getCurrentRequest.and.returnValue(existingRequest); - videoHearingsServiceSpy.getHearingTypes.and.returnValue(of(MockValues.HearingTypesList)); videoHearingsServiceSpy.saveHearing.and.returnValue(Promise.resolve(ResponseTestData.getHearingResponseTestData())); videoHearingsServiceSpy.cloneMultiHearings.and.callThrough(); videoHearingsServiceSpy.getStatus.and.returnValue(Promise.resolve(mockResp)); @@ -273,8 +266,6 @@ describe('SummaryComponent with valid request', () => { expect(component.otherInformation.OtherInformation).toEqual( stringifier.decode(existingRequest.other_information).OtherInformation ); - const hearingstring = MockValues.HearingTypesList.find(c => c.id === existingRequest.hearing_type_id).name; - expect(component.caseHearingType).toEqual(hearingstring); expect(component.hearingDate).toEqual(existingRequest.scheduled_date_time); const courtString = MockValues.Courts.find(c => c.id === existingRequest.hearing_venue_id); expect(component.courtRoomAddress).toEqual(`${courtString.name}, 123W`); @@ -629,7 +620,6 @@ describe('SummaryComponent with invalid request', () => { initExistingHearingRequest(); const existingRequest = initBadHearingRequest(); videoHearingsServiceSpy.getCurrentRequest.and.returnValue(existingRequest); - videoHearingsServiceSpy.getHearingTypes.and.returnValue(of(MockValues.HearingTypesList)); const validationProblem = new ValidationProblemDetails({ errors: { @@ -682,16 +672,6 @@ describe('SummaryComponent with invalid request', () => { expect(component.showErrorSaving).toBeTruthy(); expect(component.showWaitSaving).toBeFalsy(); }); - - it('should not save booking, when no judge assigned and Ejud flag off', async () => { - component.ngOnInit(); - fixture.detectChanges(); - component.useApiV2 = false; - await component.bookHearing(); - expect(videoHearingsServiceSpy.saveHearing).toHaveBeenCalledTimes(0); - expect(component.showWaitSaving).toBeFalsy(); - expect(component.showErrorSaving).toBeTruthy(); - }); }); describe('SummaryComponent with existing request', () => { @@ -702,7 +682,6 @@ describe('SummaryComponent with existing request', () => { const existingRequest = initExistingHearingRequest(); existingRequest.hearing_id = '12345ty'; videoHearingsServiceSpy.getCurrentRequest.and.returnValue(existingRequest); - videoHearingsServiceSpy.getHearingTypes.and.returnValue(of(MockValues.HearingTypesList)); videoHearingsServiceSpy.updateHearing.and.returnValue(of(new HearingDetailsResponse())); videoHearingsServiceSpy.updateMultiDayHearing.and.returnValue(of(new HearingDetailsResponse())); @@ -749,15 +728,7 @@ describe('SummaryComponent with existing request', () => { fixture.detectChanges(); expect(component.isExistingBooking).toBeTruthy(); }); - it('should retrieve hearing data', () => { - component.ngOnInit(); - fixture.detectChanges(); - expect(component.caseNumber).toBe('TX/12345/2018'); - expect(component.caseName).toBe('Mr. Test User vs HMRC'); - expect(component.caseHearingType).toBe('Automated Test'); - expect(component.courtRoomAddress).toBeTruthy(); - expect(component.hearingDuration).toBe('listed for 1 hour 20 minutes'); - }); + it('should hide pop up if continue booking pressed', () => { component.continueBooking(); fixture.detectChanges(); @@ -932,7 +903,6 @@ describe('SummaryComponent with multi days request', () => { existingRequest.isMultiDayEdit = true; existingRequest.hearing_id = '12345ty'; videoHearingsServiceSpy.getCurrentRequest.and.returnValue(existingRequest); - videoHearingsServiceSpy.getHearingTypes.and.returnValue(of(MockValues.HearingTypesList)); videoHearingsServiceSpy.updateHearing.and.returnValue(of(new HearingDetailsResponse())); const participantServiceSpy = jasmine.createSpyObj('ParticipantService', ['removeParticipant']); diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/summary/summary.component.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/summary/summary.component.ts index d0925db26..c56e281d0 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/summary/summary.component.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/booking/summary/summary.component.ts @@ -72,7 +72,6 @@ export class SummaryComponent implements OnInit, OnDestroy { @ViewChild(RemovePopupComponent) removePopupComponent: RemovePopupComponent; @ViewChild(RemoveInterpreterPopupComponent) removeInterpreterPopupComponent: RemoveInterpreterPopupComponent; judgeAssigned: boolean; - useApiV2 = false; saveFailedMessages: string[]; multiDayBookingEnhancementsEnabled: boolean; @@ -90,15 +89,6 @@ export class SummaryComponent implements OnInit, OnDestroy { ) { this.attemptingCancellation = false; this.showErrorSaving = false; - - this.$subscriptions.push( - this.featureService - .getFlag(FeatureFlags.useV2Api) - .pipe(first()) - .subscribe(result => { - this.useApiV2 = result; - }) - ); } ngOnInit() { @@ -222,7 +212,6 @@ export class SummaryComponent implements OnInit, OnDestroy { private retrieveHearingSummary() { this.caseNumber = this.hearing.cases.length > 0 ? this.hearing.cases[0].number : ''; this.caseName = this.hearing.cases.length > 0 ? this.hearing.cases[0].name : ''; - this.caseHearingType = this.hearing.hearing_type_name; this.hearingDate = this.hearing.scheduled_date_time; this.hearingDuration = `listed for ${FormatShortDuration(this.hearing.scheduled_duration)}`; this.courtRoomAddress = this.formatCourtRoom(this.hearing.court_name, this.hearing.court_room); @@ -296,12 +285,6 @@ export class SummaryComponent implements OnInit, OnDestroy { } else { this.setDurationOfMultiHearing(); try { - if (!this.judgeAssigned && !this.useApiV2) { - const error = new Error('Ejud Feature flag must be true, to book without a judge'); - this.logger.error(`${this.loggerPrefix} Failed to save booking.`, error); - this.setError(error); - return; - } this.logger.info(`${this.loggerPrefix} Attempting to book a new hearing.`, { caseName: this.hearing.cases[0].name, caseNumber: this.hearing.cases[0].number @@ -554,10 +537,6 @@ export class SummaryComponent implements OnInit, OnDestroy { } navToAddJudge() { - if (this.useApiV2) { - this.router.navigate([PageUrls.AddJudicialOfficeHolders]); - } else { - this.router.navigate([PageUrls.AssignJudge]); - } + this.router.navigate([PageUrls.AddJudicialOfficeHolders]); } } diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/booking-details/booking-details.component.html b/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/booking-details/booking-details.component.html index 62794fe5f..9f07633a0 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/booking-details/booking-details.component.html +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/booking-details/booking-details.component.html @@ -46,7 +46,7 @@

id="edit-button" (click)="editHearing()" > - {{ hearing.isMultiDay && this.multiDayBookingEnhancementsEnabled && this.useV2Api ? 'Edit this day/date only' : 'Edit' }} + {{ hearing.isMultiDay && this.multiDayBookingEnhancementsEnabled ? 'Edit this day/date only' : 'Edit' }}

-
+
-
+
-
+
Search bookings

{{ title }}

-
@@ -178,7 +173,7 @@

{{ title }}

-
+
Allocated to: {{ detail.AllocatedTo }}
diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/bookings-list/bookings-list.component.spec.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/bookings-list/bookings-list.component.spec.ts index 3b336f310..0896e610f 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/bookings-list/bookings-list.component.spec.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/bookings-list/bookings-list.component.spec.ts @@ -590,10 +590,6 @@ describe('BookingsListComponent', () => { videoHearingServiceSpy.getHearingTypes.and.returnValue(of(new Array())); configServiceSpy.getConfig.and.returnValue({}); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.adminSearch).and.returnValue(of(true)); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.vhoWorkAllocation).and.returnValue(of(true)); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.useV2Api).and.returnValue(of(false)); - referenceDataServiceSpy.getCourts.and.returnValue(of(new Array())); featureFlagServiceSpy.getFeatureFlagByName.and.returnValue(of(false)); @@ -664,22 +660,9 @@ describe('BookingsListComponent', () => { expect(component.loaded).toBeTruthy(); }); - it('should onSearch (admin_search flag off)', () => { + it('should onSearch', () => { bookingsListServiceSpy.getBookingsList.calls.reset(); setFormValue(); - component.enableSearchFeature = false; - component.onSearch(); - expect(bookingPersistService.caseNumber).toMatch('CASE_NUMBER'); - expect(bookingPersistService.startDate).toEqual(moment().startOf('day').add(1, 'days').toDate()); - expect(bookingPersistService.endDate).toEqual(moment().startOf('day').add(2, 'days').toDate()); - expect(component.bookings.length).toBeGreaterThan(0); - expect(bookingsListServiceSpy.getBookingsList).toHaveBeenCalledWith(undefined, component.limit); - }); - - it('should onSearch (admin_search flag on)', () => { - bookingsListServiceSpy.getBookingsList.calls.reset(); - setFormValue(); - component.enableSearchFeature = true; component.onSearch(); expect(bookingPersistService.caseNumber).toMatch('CASE_NUMBER'); expect(bookingPersistService.participantLastName).toMatch('PARTICIPANT_LAST_NAME'); @@ -704,7 +687,6 @@ describe('BookingsListComponent', () => { it('should onSearch (admin_search flag on) with populated endDate and empty startDate', () => { bookingsListServiceSpy.getBookingsList.calls.reset(); setFormValue(); - component.enableSearchFeature = true; component.searchForm.controls['startDate'].setValue(null); component.onSearch(); expect(bookingPersistService.caseNumber).toMatch('CASE_NUMBER'); @@ -730,7 +712,6 @@ describe('BookingsListComponent', () => { it('should onSearch (admin_search flag on) with populated startDate and empty endDate', () => { bookingsListServiceSpy.getBookingsList.calls.reset(); setFormValue(); - component.enableSearchFeature = true; component.searchForm.controls['endDate'].setValue(null); component.onSearch(); expect(bookingPersistService.caseNumber).toMatch('CASE_NUMBER'); @@ -756,7 +737,6 @@ describe('BookingsListComponent', () => { it('should onSearch (admin_search flag on) with no judge option selected', () => { bookingsListServiceSpy.getBookingsList.calls.reset(); setFormValue(true); - component.enableSearchFeature = true; component.searchForm.controls['endDate'].setValue(null); component.onSearch(); expect(bookingPersistService.noJugdeInHearings).toBeTruthy(); @@ -795,7 +775,6 @@ describe('BookingsListComponent', () => { let startDateElement: HTMLInputElement; beforeEach(() => { - component.enableSearchFeature = true; component.openSearchPanel(); fixture.detectChanges(); startDateControl = component.searchForm.controls['startDate']; @@ -855,7 +834,6 @@ describe('BookingsListComponent', () => { let endDateElement: HTMLInputElement; beforeEach(() => { - component.enableSearchFeature = true; component.openSearchPanel(); fixture.detectChanges(); startDateControl = component.searchForm.controls['startDate']; @@ -909,18 +887,6 @@ describe('BookingsListComponent', () => { }); }); - it('should onClear (if workAllocation feature on)', () => { - spyOn(component, 'workAllocationEnabled').and.returnValue(true); - const csoMenu = onClearTest(); - expect(csoMenu).toHaveBeenCalledTimes(1); - }); - - it('should onClear (if workAllocation feature off)', () => { - spyOn(component, 'workAllocationEnabled').and.returnValue(false); - const csoMenu = onClearTest(); - expect(csoMenu).toHaveBeenCalledTimes(0); - }); - function onClearTest() { const formBuilder = new FormBuilder(); const bookingPersistServiceSpy = jasmine.createSpyObj('BookingPersistService', [ @@ -973,7 +939,6 @@ describe('BookingsListComponent', () => { component.venueMenu = new VenuesMenuComponent(bookingPersistServiceSpy, referenceDataServiceSpy, formBuilder, loggerSpy); setFormValue(); - component.enableSearchFeature = true; component.onSearch(); expect(component.title).toEqual('Search results'); component.onClear(); @@ -983,7 +948,6 @@ describe('BookingsListComponent', () => { it('should disable search button if all fields are empty', () => { component.openSearchPanel(); clearSearch(); - component.enableSearchFeature = true; fixture.detectChanges(); const searchButton = document.getElementById('searchButton') as HTMLButtonElement; expect(searchButton.disabled).toBe(false); @@ -993,7 +957,6 @@ describe('BookingsListComponent', () => { component.openSearchPanel(); clearSearch(); component.searchForm.controls['caseNumber'].setValue('CASE_NUMBER'); - component.enableSearchFeature = true; fixture.detectChanges(); const searchButton = document.getElementById('searchButton') as HTMLButtonElement; expect(searchButton.disabled).toBe(false); @@ -1003,7 +966,6 @@ describe('BookingsListComponent', () => { component.openSearchPanel(); clearSearch(); component.searchForm.controls['participantLastName'].setValue('PARTICIPANT_LAST_NAME'); - component.enableSearchFeature = true; fixture.detectChanges(); const searchButton = document.getElementById('searchButton') as HTMLButtonElement; expect(searchButton.disabled).toBe(false); @@ -1013,7 +975,6 @@ describe('BookingsListComponent', () => { component.openSearchPanel(); clearSearch(); component.searchForm.controls['startDate'].setValue(new Date(2022, 3, 25)); - component.enableSearchFeature = true; fixture.detectChanges(); const searchButton = document.getElementById('searchButton') as HTMLButtonElement; expect(searchButton.disabled).toBe(false); @@ -1023,7 +984,6 @@ describe('BookingsListComponent', () => { component.openSearchPanel(); clearSearch(); component.searchForm.controls['endDate'].setValue(new Date(2022, 3, 25)); - component.enableSearchFeature = true; fixture.detectChanges(); const searchButton = document.getElementById('searchButton') as HTMLButtonElement; expect(searchButton.disabled).toBe(false); @@ -1031,7 +991,6 @@ describe('BookingsListComponent', () => { it('should close search panel when close search button clicked', () => { component.openSearchPanel(); - component.enableSearchFeature = true; fixture.detectChanges(); let searchPanel = document.getElementById('searchPanel') as HTMLDivElement; expect(searchPanel).not.toBeNull(); @@ -1055,33 +1014,7 @@ describe('BookingsListComponent', () => { expect(component.showSearch).toBe(false); }); - it('should not load venues when search feature is disabled', fakeAsync(() => { - referenceDataServiceSpy.getCourts.calls.reset(); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.adminSearch).and.returnValue(of(false)); - - component.subscribeToFeatureFlags(); - tick(); - - expect(component.enableSearchFeature).toBeFalsy(); - })); - - it('should load venues when search feature is enabled', () => { - referenceDataServiceSpy.getCourts.calls.reset(); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.adminSearch).and.returnValue(of(true)); - - fixture.detectChanges(); - expect(component.enableSearchFeature).toBeTruthy(); - }); - - it('should hide the search panel on initial load when search feature enabled', () => { - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.adminSearch).and.returnValue(of(true)); - component.ngOnInit(); - fixture.detectChanges(); - expect(component.showSearch).toBe(false); - }); - - it('should hide the search panel on initial load when search feature disabled', () => { - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.adminSearch).and.returnValue(of(false)); + it('should hide the search panel on initial load', () => { component.ngOnInit(); fixture.detectChanges(); expect(component.showSearch).toBe(false); @@ -1279,21 +1212,5 @@ describe('BookingsListComponent', () => { component.onChangeNoAllocated(); expect(bookingPersistService.selectedUsers.length).toEqual(count); }); - - it('should not show allocated to label if work allocation feature flag is off', async () => { - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.vhoWorkAllocation).and.returnValue(of(false)); - await component.ngOnInit(); - fixture.detectChanges(); - const divToHide = fixture.debugElement.query(By.css('#allocated-to-' + bookingData.BookingsDetails[0].HearingId)); - expect(divToHide).toBeFalsy(); - }); - - it('should show allocated label to if work allocation feature flag is on', async () => { - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.vhoWorkAllocation).and.returnValue(of(true)); - await component.ngOnInit(); - fixture.detectChanges(); - const divToHide = fixture.debugElement.query(By.css('#allocated-to-' + bookingData.BookingsDetails[0].HearingId)); - expect(divToHide).toBeTruthy(); - }); }); }); diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/bookings-list/bookings-list.component.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/bookings-list/bookings-list.component.ts index 4888861c0..aebd7be44 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/bookings-list/bookings-list.component.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/bookings-list/bookings-list.component.ts @@ -10,7 +10,6 @@ import { BookingsListService } from '../../services/bookings-list.service'; import { BookingPersistService } from '../../services/bookings-persist.service'; import { BookingsResponse, JusticeUserResponse } from '../../services/clients/api-client'; import { VideoHearingsService } from '../../services/video-hearings.service'; -import { FeatureFlags, LaunchDarklyService } from '../../services/launch-darkly.service'; import { PageUrls } from '../../shared/page-url.constants'; import * as moment from 'moment'; import { ReturnUrlService } from 'src/app/services/return-url.service'; @@ -40,15 +39,12 @@ export class BookingsListComponent implements OnInit, OnDestroy { bookingResponse: BookingsModel; $subcription: Subscription; searchForm: FormGroup; - enableSearchFeature: boolean; title = this.initialTitle; selectedVenueIds: []; selectedCaseTypes: string[]; selectedUserIds: []; showSearch = false; today = new Date(); - vhoWorkAllocationFeature = false; - isV2 = false; destroyed$ = new Subject(); @@ -62,7 +58,6 @@ export class BookingsListComponent implements OnInit, OnDestroy { private bookingPersistService: BookingPersistService, private videoHearingService: VideoHearingsService, private formBuilder: FormBuilder, - private lanchDarklyService: LaunchDarklyService, private router: Router, private logger: Logger, private datePipe: DatePipe, @@ -70,7 +65,6 @@ export class BookingsListComponent implements OnInit, OnDestroy { ) {} ngOnInit() { - this.subscribeToFeatureFlags(); this.searchForm = this.initializeForm(); this.showSearch = this.bookingPersistService.showSearch; this.logger.debug(`${this.loggerPrefix} Loading bookings list component`); @@ -181,27 +175,19 @@ export class BookingsListComponent implements OnInit, OnDestroy { if (endDate && !startDate) { startDate = moment(endDate).startOf('day').toDate(); } - let bookingsList$: Observable; - - if (this.enableSearchFeature) { - // new feature - bookingsList$ = this.bookingsListService.getBookingsList( - this.cursor, - this.limit, - caseNumber, - venueIds, - caseTypes, - users, - startDate, - endDate, - lastName, - noJudge, - noAllocated - ); - } else { - // previous implementation - bookingsList$ = this.bookingsListService.getBookingsList(this.cursor, this.limit); - } + const bookingsList$: Observable = this.bookingsListService.getBookingsList( + this.cursor, + this.limit, + caseNumber, + venueIds, + caseTypes, + users, + startDate, + endDate, + lastName, + noJudge, + noAllocated + ); this.$subcription = bookingsList$.subscribe({ next: book => self.loadData(book), @@ -256,9 +242,7 @@ export class BookingsListComponent implements OnInit, OnDestroy { this.bookingPersistService.selectedCaseTypes = []; this.caseTypeMenu.clear(); this.bookingPersistService.selectedUsers = []; - if (this.workAllocationEnabled()) { - this.csoMenu.clear(); - } + this.csoMenu.clear(); this.bookingPersistService.startDate = null; this.bookingPersistService.endDate = null; this.bookingPersistService.participantLastName = ''; @@ -479,10 +463,6 @@ export class BookingsListComponent implements OnInit, OnDestroy { } } - workAllocationEnabled(): boolean { - return this.vhoWorkAllocationFeature; - } - selectedCaseTypesEmitter($event: string[]) { this.bookingPersistService.selectedCaseTypes = $event; } @@ -490,27 +470,4 @@ export class BookingsListComponent implements OnInit, OnDestroy { selectedVenueEmitter($event: number[]) { this.bookingPersistService.selectedVenueIds = $event; } - - subscribeToFeatureFlags() { - this.lanchDarklyService - .getFlag(FeatureFlags.adminSearch) - .pipe(takeUntil(this.destroyed$)) - .subscribe(flag => { - this.enableSearchFeature = flag; - }); - - this.lanchDarklyService - .getFlag(FeatureFlags.vhoWorkAllocation) - .pipe(takeUntil(this.destroyed$)) - .subscribe(flag => { - this.vhoWorkAllocationFeature = flag; - }); - - this.lanchDarklyService - .getFlag(FeatureFlags.useV2Api) - .pipe(takeUntil(this.destroyed$)) - .subscribe(flag => { - this.isV2 = flag; - }); - } } diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/hearing-details/hearing-details.component.html b/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/hearing-details/hearing-details.component.html index f4337edff..0de1c0285 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/hearing-details/hearing-details.component.html +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/hearing-details/hearing-details.component.html @@ -45,11 +45,7 @@

Booki

-
+
Allocated to:
diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/hearing-details/hearing-details.component.spec.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/hearing-details/hearing-details.component.spec.ts index 9400ea538..482ea7495 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/hearing-details/hearing-details.component.spec.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/hearing-details/hearing-details.component.spec.ts @@ -11,14 +11,9 @@ import { ClientSettingsResponse } from 'src/app/services/clients/api-client'; import { Logger } from '../../services/logger'; import { OtherInformationModel } from '../../common/model/other-information.model'; import { ConfigService } from 'src/app/services/config.service'; -import { of } from 'rxjs'; -import { FeatureFlags, LaunchDarklyService } from '../../services/launch-darkly.service'; import { SharedModule } from 'src/app/shared/shared.module'; -const launchDarklyServiceSpy = jasmine.createSpyObj('LaunchDarklyService', ['getFlag']); - describe('HearingDetailsComponent', () => { - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.vhoWorkAllocation).and.returnValue(of(true)); let component: HearingDetailsComponent; let fixture: ComponentFixture; let debugElement: DebugElement; @@ -59,11 +54,7 @@ describe('HearingDetailsComponent', () => { TestBed.configureTestingModule({ declarations: [HearingDetailsComponent, LongDatetimePipe], imports: [RouterTestingModule, SharedModule], - providers: [ - Logger, - { provide: ConfigService, useValue: configServiceSpy }, - { provide: LaunchDarklyService, useValue: launchDarklyServiceSpy } - ] + providers: [Logger, { provide: ConfigService, useValue: configServiceSpy }] }).compileComponents(); })); @@ -150,23 +141,6 @@ describe('HearingDetailsComponent', () => { const result = component.getDefenceAdvocateByContactEmail('madeup@doesnotexist.com'); expect(result).toBe(''); }); - describe('feature flag turn on and off ', () => { - it('should not show allocated to label if work allocation feature flag is off', async () => { - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.vhoWorkAllocation).and.returnValue(of(false)); - await component.ngOnInit(); - fixture.detectChanges(); - const divToHide = fixture.debugElement.query(By.css('#hearing-allocated-to')); - expect(divToHide).toBeFalsy(); - }); - - it('should show allocated to label if work allocation feature flag is on', async () => { - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.vhoWorkAllocation).and.returnValue(of(true)); - await component.ngOnInit(); - fixture.detectChanges(); - const divToHide = fixture.debugElement.query(By.css('#hearing-allocated-to')); - expect(divToHide).toBeTruthy(); - }); - }); }); describe('HearingDetailsComponent join by phone', () => { const clientSettings = new ClientSettingsResponse({ @@ -204,7 +178,7 @@ describe('HearingDetailsComponent join by phone', () => { '1234567' ); it('should display option to join by phone if config has not the set date', () => { - const component = new HearingDetailsComponent(activatedRoute, loggerSpy, configServiceSpy, launchDarklyServiceSpy); + const component = new HearingDetailsComponent(activatedRoute, loggerSpy, configServiceSpy); component.hearing = hearing; const result = component.isJoinByPhone(); expect(result).toBe(true); @@ -212,7 +186,7 @@ describe('HearingDetailsComponent join by phone', () => { it('should not display option to join by phone if booking has not confirmation date', () => { clientSettings.join_by_phone_from_date = '2020-10-22'; hearing.ConfirmedDate = null; - const component = new HearingDetailsComponent(activatedRoute, loggerSpy, configServiceSpy, launchDarklyServiceSpy); + const component = new HearingDetailsComponent(activatedRoute, loggerSpy, configServiceSpy); component.hearing = hearing; const result = component.isJoinByPhone(); expect(result).toBe(false); @@ -220,7 +194,7 @@ describe('HearingDetailsComponent join by phone', () => { it('should not display option to join by phone if booking confirmation date less than config date', () => { clientSettings.join_by_phone_from_date = '2020-10-22'; hearing.ConfirmedDate = new Date('2020-10-21'); - const component = new HearingDetailsComponent(activatedRoute, loggerSpy, configServiceSpy, launchDarklyServiceSpy); + const component = new HearingDetailsComponent(activatedRoute, loggerSpy, configServiceSpy); component.hearing = hearing; const result = component.isJoinByPhone(); expect(result).toBe(false); @@ -228,7 +202,7 @@ describe('HearingDetailsComponent join by phone', () => { it('should display option to join by phone if booking confirmation date greater than config date', () => { clientSettings.join_by_phone_from_date = '2020-10-22'; hearing.ConfirmedDate = new Date('2020-10-23'); - const component = new HearingDetailsComponent(activatedRoute, loggerSpy, configServiceSpy, launchDarklyServiceSpy); + const component = new HearingDetailsComponent(activatedRoute, loggerSpy, configServiceSpy); component.hearing = hearing; const result = component.isJoinByPhone(); expect(result).toBe(true); diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/hearing-details/hearing-details.component.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/hearing-details/hearing-details.component.ts index 0744642ca..3f03e89a7 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/hearing-details/hearing-details.component.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/bookings-list/hearing-details/hearing-details.component.ts @@ -6,7 +6,6 @@ import { Logger } from '../../services/logger'; import { OtherInformationModel } from '../../common/model/other-information.model'; import { ConfigService } from 'src/app/services/config.service'; import { Subject, Subscription, takeUntil } from 'rxjs'; -import { FeatureFlags, LaunchDarklyService } from '../../services/launch-darkly.service'; @Component({ selector: 'app-hearing-details', @@ -24,28 +23,15 @@ export class HearingDetailsComponent implements OnInit, OnDestroy { private readonly loggerPrefix = '[HearingDetails] -'; phoneConferenceDetails = ''; - vhoWorkAllocationFeature = false; $subcription: Subscription; destroyed$ = new Subject(); enableSearchFeature: boolean; ejudFeatureFlag: boolean; - constructor( - private route: ActivatedRoute, - private logger: Logger, - private configService: ConfigService, - private lanchDarklyService: LaunchDarklyService - ) {} + constructor(private route: ActivatedRoute, private logger: Logger, private configService: ConfigService) {} - ngOnInit() { - this.lanchDarklyService - .getFlag(FeatureFlags.vhoWorkAllocation) - .pipe(takeUntil(this.destroyed$)) - .subscribe(flag => { - this.vhoWorkAllocationFeature = flag; - }); - } + ngOnInit() {} ngOnDestroy(): void { this.destroyed$.next(); diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/common/model/hearing.model.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/common/model/hearing.model.ts index 5b4454223..9eb48eb07 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/common/model/hearing.model.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/common/model/hearing.model.ts @@ -26,8 +26,6 @@ export class HearingModel { case_type?: string; case_type_service_id?: string; other_information?: string; - judge_email?: string; - judge_phone?: string; court_room?: string; hearing_venue_id?: number; case_type_id?: number; diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/dashboard/dashboard.component.spec.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/dashboard/dashboard.component.spec.ts index 2d16f3f55..86ce6c863 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/dashboard/dashboard.component.spec.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/dashboard/dashboard.component.spec.ts @@ -16,8 +16,6 @@ describe('DashboardComponent', () => { const loggerSpy = jasmine.createSpyObj('Logger', ['error', 'debug', 'warn']); beforeEach(waitForAsync(() => { - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.vhoWorkAllocation).and.returnValue(of(true)); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.audioSearch).and.returnValue(of(false)); launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.dom1Integration).and.returnValue(of(false)); TestBed.configureTestingModule({ @@ -132,36 +130,6 @@ describe('DashboardComponent', () => { expect(component.showWorkAllocation).toBeFalsy(); }); - it('should not show work allocation tile if feature is switched off', async () => { - userIdentitySpy.getUserInformation.and.returnValue( - of( - new UserProfileResponse({ - is_case_administrator: true, - is_vh_officer_administrator_role: true - }) - ) - ); - - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.vhoWorkAllocation).and.returnValue(of(false)); - - await component.ngOnInit(); - expect(component.showWorkAllocation).toBeFalsy(); - }); - - it('should show work allocation tile if feature is switched on and user is Team Leader', async () => { - userIdentitySpy.getUserInformation.and.returnValue( - of( - new UserProfileResponse({ - is_vh_team_leader: true - }) - ) - ); - - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.vhoWorkAllocation).and.returnValue(of(true)); - await component.ngOnInit(); - expect(component.showWorkAllocation).toBeTruthy(); - }); - it('should unsubscribe from launch darkly flag changes', () => { const unsubscribeSpy = spyOn(component.destroyed$, 'next'); @@ -182,7 +150,7 @@ describe('DashboardComponent', () => { await component.ngOnInit(); expect(component.showWorkAllocation).toBeFalsy(); }); - it('should not show link to audio file if feature is switched on', async () => { + it('should not show link to audio file', async () => { userIdentitySpy.getUserInformation.and.returnValue( of( new UserProfileResponse({ @@ -191,22 +159,7 @@ describe('DashboardComponent', () => { ) ); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.audioSearch).and.returnValue(of(true)); await component.ngOnInit(); expect(component.showAudioFileLink).toBeFalsy(); }); - - it('should show link to audio file if feature is switched off', async () => { - userIdentitySpy.getUserInformation.and.returnValue( - of( - new UserProfileResponse({ - is_vh_officer_administrator_role: true - }) - ) - ); - - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.audioSearch).and.returnValue(of(false)); - await component.ngOnInit(); - expect(component.showAudioFileLink).toBeTruthy(); - }); }); diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/dashboard/dashboard.component.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/dashboard/dashboard.component.ts index fc6f497b2..515b7f9f0 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/dashboard/dashboard.component.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/dashboard/dashboard.component.ts @@ -24,9 +24,7 @@ export class DashboardComponent implements OnInit, OnDestroy { showCheckList = false; showBooking = false; showWorkAllocation = false; - vhoWorkAllocationFeature = false; dom1Feature = false; - audioSearchFeature: boolean; showManageTeam = false; showAudioFileLink = false; @@ -34,31 +32,23 @@ export class DashboardComponent implements OnInit, OnDestroy { destroyed$ = new Subject(); ngOnInit() { - const workAllocationFlag$ = this.launchDarklyService - .getFlag(FeatureFlags.vhoWorkAllocation) - .pipe(takeUntil(this.destroyed$)); - const audioSearchFlag$ = this.launchDarklyService.getFlag(FeatureFlags.audioSearch).pipe(takeUntil(this.destroyed$)); const dom1FeatureFlag$ = this.launchDarklyService.getFlag(FeatureFlags.dom1Integration).pipe(takeUntil(this.destroyed$)); - combineLatest([workAllocationFlag$, audioSearchFlag$, dom1FeatureFlag$]).subscribe( - ([workAllocationFlag, audioSearchFlag, dom1FeatureFlag]) => { - this.vhoWorkAllocationFeature = workAllocationFlag; - this.audioSearchFeature = audioSearchFlag; - this.dom1Feature = dom1FeatureFlag; - lastValueFrom(this.userIdentityService.getUserInformation()).then(profile => { - this.showCheckList = profile.is_vh_officer_administrator_role; - this.showWorkAllocation = profile.is_vh_team_leader && this.vhoWorkAllocationFeature; - this.showAudioFileLink = this.showCheckList && !this.audioSearchFeature; - this.showBooking = profile.is_case_administrator || profile.is_vh_officer_administrator_role; - this.showManageTeam = profile.is_vh_team_leader && this.dom1Feature; - this.logger.debug(`${this.loggerPrefix} Landed on dashboard`, { - showCheckList: this.showCheckList, - showBooking: this.showBooking, - showWorkAllocation: this.showWorkAllocation - }); + combineLatest([dom1FeatureFlag$]).subscribe(([dom1FeatureFlag]) => { + this.dom1Feature = dom1FeatureFlag; + lastValueFrom(this.userIdentityService.getUserInformation()).then(profile => { + this.showCheckList = profile.is_vh_officer_administrator_role; + this.showWorkAllocation = profile.is_vh_team_leader; + this.showAudioFileLink = this.showCheckList; + this.showBooking = profile.is_case_administrator || profile.is_vh_officer_administrator_role; + this.showManageTeam = profile.is_vh_team_leader && this.dom1Feature; + this.logger.debug(`${this.loggerPrefix} Landed on dashboard`, { + showCheckList: this.showCheckList, + showBooking: this.showBooking, + showWorkAllocation: this.showWorkAllocation }); - } - ); + }); + }); } ngOnDestroy() { diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/security/audio-search.guard.spec.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/security/audio-search.guard.spec.ts deleted file mode 100644 index 39a2d6377..000000000 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/security/audio-search.guard.spec.ts +++ /dev/null @@ -1,42 +0,0 @@ -import { fakeAsync, TestBed } from '@angular/core/testing'; -import { Router } from '@angular/router'; -import { Logger } from '../services/logger'; -import { AudioSearchGuard } from './audio-search.guard'; -import { LaunchDarklyService } from '../services/launch-darkly.service'; -import { MockLaunchDarklyService } from '../testing/mocks/MockLaunchDarklyService'; - -describe('audiosearchguard', () => { - let audioSearchGuard: AudioSearchGuard; - let launchDarklyService; - const loggerSpy = jasmine.createSpyObj('Logger', ['error', 'debug', 'warn']); - const router = { - navigate: jasmine.createSpy('navigate') - }; - - beforeEach(() => { - TestBed.configureTestingModule({ - providers: [ - AudioSearchGuard, - { provide: LaunchDarklyService, useClass: MockLaunchDarklyService }, - { provide: Router, useValue: router }, - { provide: Logger, useValue: loggerSpy } - ] - }).compileComponents(); - launchDarklyService = TestBed.inject(LaunchDarklyService); - audioSearchGuard = TestBed.inject(AudioSearchGuard); - }); - - describe('when toggle off with successful authentication', () => { - it('canActivate should return true', () => { - launchDarklyService.setAudioSearchFlag(false); - audioSearchGuard.canActivate().subscribe(result => expect(result).toBeTruthy()); - }); - }); - - describe('when toggle is on with successful authentication', () => { - it('canActivate should return false', fakeAsync(() => { - launchDarklyService.setAudioSearchFlag(true); - audioSearchGuard.canActivate().subscribe(result => expect(result).toBeFalsy()); - })); - }); -}); diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/security/audio-search.guard.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/security/audio-search.guard.ts deleted file mode 100644 index 2ef964f91..000000000 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/security/audio-search.guard.ts +++ /dev/null @@ -1,27 +0,0 @@ -import { Injectable } from '@angular/core'; -import { Router } from '@angular/router'; -import { Observable } from 'rxjs'; -import { map } from 'rxjs/operators'; -import { PageUrls } from '../shared/page-url.constants'; -import { Logger } from '../services/logger'; -import { FeatureFlags, LaunchDarklyService } from '../services/launch-darkly.service'; - -@Injectable() -export class AudioSearchGuard { - private readonly loggerPrefix = '[AudioSearchGuard] -'; - constructor(private launchDarklyService: LaunchDarklyService, private router: Router, private logger: Logger) {} - - canActivate(): Observable { - return this.launchDarklyService.getFlag(FeatureFlags.audioSearch).pipe( - map(result => { - if (result) { - this.logger.warn(`${this.loggerPrefix} - canActivate isAuthorized: false`); - this.router.navigate([`/${PageUrls.Login}`]); - return false; - } - this.logger.debug(`${this.loggerPrefix} - canActivate isAuthorized: true`); - return true; - }) - ); - } -} diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/last-minute-amendments.guard.spec.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/last-minute-amendments.guard.spec.ts index 8528c5074..f07b6fb43 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/last-minute-amendments.guard.spec.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/last-minute-amendments.guard.spec.ts @@ -2,9 +2,7 @@ import { TestBed } from '@angular/core/testing'; import { ActivatedRouteSnapshot, Data, Router, RouterStateSnapshot, UrlSegment } from '@angular/router'; import { LastMinuteAmendmentsGuard } from './last-minute-amendments.guard'; import { VideoHearingsService } from '../../services/video-hearings.service'; -import { of } from 'rxjs'; import { Logger } from '../../services/logger'; -import { FeatureFlags, LaunchDarklyService } from '../../services/launch-darkly.service'; describe('LastMinuteAmendmentsGuard', () => { let guard: LastMinuteAmendmentsGuard; @@ -15,8 +13,6 @@ describe('LastMinuteAmendmentsGuard', () => { const loggerSpy = jasmine.createSpyObj('Logger', ['warn', 'debug']); const videoHearingsServiceSpy = jasmine.createSpyObj(['isConferenceClosed', 'isHearingAboutToStart']); const redirectPath = '/summary'; - const launchDarklyServiceSpy = jasmine.createSpyObj('LaunchDarklyService', ['getFlag']); - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.useV2Api).and.returnValue(of(true)); beforeEach(() => { TestBed.configureTestingModule({ @@ -24,7 +20,6 @@ describe('LastMinuteAmendmentsGuard', () => { LastMinuteAmendmentsGuard, { provide: VideoHearingsService, useValue: videoHearingsServiceSpy }, { provide: Router, useValue: router }, - { provide: LaunchDarklyService, useValue: launchDarklyServiceSpy }, { provide: Logger, useValue: loggerSpy } ] }).compileComponents(); @@ -63,39 +58,4 @@ describe('LastMinuteAmendmentsGuard', () => { expect(router.navigate).toHaveBeenCalledTimes(1); }); }); - - describe('when accessing assign-judge; last minute', () => { - it('ejudFeature flag off should override last-minute-amendment-guard and block assign-judge url to be reach', () => { - // setup - guard.isV2 = false; - const url = 'assign-judge'; - const dataSnapshot = { exceptionToRuleCheck: true } as Data; - const urlSegmentArray = [{ path: url }] as UrlSegment[]; - // execute - const returned = guard.canActivate( - { url: urlSegmentArray, data: dataSnapshot }, - { url: url } - ); - // assert - expect(returned).toBe(false); - expect(router.navigate).toHaveBeenCalledWith([redirectPath]); - }); - - it('ejudFeature flag on should allow last-minute-amendment-guard and allow assign-judge url to be reached', () => { - // setup - const url = 'assign-judge'; - const dataSnapshot = { exceptionToRuleCheck: true } as Data; - const urlSegmentArray = [{ path: url }] as UrlSegment[]; - // execute - const returned = guard.canActivate( - { url: urlSegmentArray, data: dataSnapshot }, - { url: url } - ); - // assert - expect(returned).toBe(true); - }); - afterEach(() => { - guard.isV2 = true; - }); - }); }); diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/last-minute-amendments.guard.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/last-minute-amendments.guard.ts index 8eac4c053..4b2f64250 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/last-minute-amendments.guard.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/last-minute-amendments.guard.ts @@ -2,31 +2,16 @@ import { Injectable } from '@angular/core'; import { ActivatedRouteSnapshot, Router, RouterStateSnapshot } from '@angular/router'; import { VideoHearingsService } from '../../services/video-hearings.service'; import { Observable } from 'rxjs'; -import { first } from 'rxjs/operators'; import { Logger } from '../../services/logger'; -import { FeatureFlags, LaunchDarklyService } from '../../services/launch-darkly.service'; @Injectable() export class LastMinuteAmendmentsGuard { - isV2: boolean; - constructor( - private videoHearingsService: VideoHearingsService, - private router: Router, - private featureService: LaunchDarklyService, - private logger: Logger - ) { - this.featureService - .getFlag(FeatureFlags.useV2Api) - .pipe(first()) - .subscribe(result => { - this.isV2 = result; - }); - } + constructor(private videoHearingsService: VideoHearingsService, private router: Router, private logger: Logger) {} canActivate(route: ActivatedRouteSnapshot, _state: RouterStateSnapshot): Observable | Promise | boolean { const exceptionToRuleCheck = route.data?.exceptionToRuleCheck as boolean; if (!this.videoHearingsService.isConferenceClosed() && this.videoHearingsService.isHearingAboutToStart()) { - if (exceptionToRuleCheck && this.isV2) { + if (exceptionToRuleCheck) { return true; } this.router.navigate(['/summary']); diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/work-allocation-feature.guard.spec.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/work-allocation-feature.guard.spec.ts deleted file mode 100644 index e30422e43..000000000 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/work-allocation-feature.guard.spec.ts +++ /dev/null @@ -1,41 +0,0 @@ -import { TestBed } from '@angular/core/testing'; -import { Router } from '@angular/router'; -import { of } from 'rxjs'; -import { FeatureFlags, LaunchDarklyService } from '../../services/launch-darkly.service'; -import { WorkAllocationFeatureGuard } from './work-allocation-feature.guard'; - -describe('WorkAllocationFeatureGuard', () => { - let workAllocationFeatureGuard: WorkAllocationFeatureGuard; - - const launchDarklyServiceSpy = jasmine.createSpyObj('LaunchDarklyService', ['getFlag']); - - const routerSpy = jasmine.createSpyObj('Router', ['navigate']); - - beforeEach(() => { - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.vhoWorkAllocation).and.returnValue(of(true)); - - TestBed.configureTestingModule({ - providers: [ - WorkAllocationFeatureGuard, - { provide: Router, useValue: routerSpy }, - { provide: LaunchDarklyService, useValue: launchDarklyServiceSpy } - ] - }).compileComponents(); - workAllocationFeatureGuard = TestBed.inject(WorkAllocationFeatureGuard); - }); - - it('should return true if feature toggle is on', () => { - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.vhoWorkAllocation).and.returnValue(of(true)); - workAllocationFeatureGuard.canActivate(null, null).subscribe(result => { - expect(result).toBeTruthy(); - }); - }); - - it('should redirect to home page if feature toggle is off', () => { - launchDarklyServiceSpy.getFlag.withArgs(FeatureFlags.vhoWorkAllocation).and.returnValue(of(false)); - workAllocationFeatureGuard.canActivate(null, null).subscribe(result => { - expect(result).toBeFalsy(); - expect(routerSpy.navigate).toHaveBeenCalledWith(['/']); - }); - }); -}); diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/work-allocation-feature.guard.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/work-allocation-feature.guard.ts deleted file mode 100644 index bf90d4673..000000000 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/security/guards/work-allocation-feature.guard.ts +++ /dev/null @@ -1,25 +0,0 @@ -import { Injectable } from '@angular/core'; -import { ActivatedRouteSnapshot, Router, RouterStateSnapshot } from '@angular/router'; -import { Observable } from 'rxjs'; -import { FeatureFlags, LaunchDarklyService } from '../../services/launch-darkly.service'; -import { map, take } from 'rxjs/operators'; - -@Injectable() -export class WorkAllocationFeatureGuard { - private readonly loggerPrefix = '[WorkAllocationFeatureGuard] -'; - - constructor(private launchDarklyService: LaunchDarklyService, private router: Router) {} - - canActivate(route: ActivatedRouteSnapshot, state: RouterStateSnapshot): Observable { - return this.launchDarklyService.getFlag(FeatureFlags.vhoWorkAllocation).pipe( - take(1), - map(featureEnabled => { - if (featureEnabled) { - return true; - } - this.router.navigate(['/']); - return false; - }) - ); - } -} diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/services/launch-darkly.service.spec.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/services/launch-darkly.service.spec.ts index baae26ce8..408a4ed40 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/services/launch-darkly.service.spec.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/services/launch-darkly.service.spec.ts @@ -33,19 +33,4 @@ describe('LaunchDarklyService', () => { expect(ldClientSpy.close).toHaveBeenCalled(); }); - - it('should return a given flag', fakeAsync(() => { - service.client = ldClientSpy; - const flagKey = FeatureFlags.useV2Api; - const keyParam = `change:${flagKey}`; - ldClientSpy.on.withArgs(keyParam, jasmine.anything()).and.returnValue(); - ldClientSpy.waitUntilReady.and.returnValue(Promise.resolve()); - ldClientSpy.variation.withArgs(flagKey, jasmine.any(Boolean)).and.returnValue(true); - - let result: boolean; - service.getFlag(flagKey).subscribe(val => (result = val)); - tick(); - - expect(result).toBe(true); - })); }); diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/services/launch-darkly.service.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/services/launch-darkly.service.ts index fef74de91..df70236b9 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/services/launch-darkly.service.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/services/launch-darkly.service.ts @@ -5,13 +5,7 @@ import { Observable, Subject } from 'rxjs'; import { first, map } from 'rxjs/operators'; export const FeatureFlags = { - adminSearch: 'admin_search', - vhoWorkAllocation: 'vho-work-allocation', dom1Integration: 'dom1', - hrsIntegration: 'hrs-integration', - referenceData: 'reference-data', - audioSearch: 'hide-audio-search-tile', - useV2Api: 'use-bookings-api-v2', multiDayBookingEnhancements: 'multi-day-booking-enhancements' }; diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/services/video-hearings.service.spec.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/services/video-hearings.service.spec.ts index 794f26b84..3057db430 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/services/video-hearings.service.spec.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/services/video-hearings.service.spec.ts @@ -145,7 +145,6 @@ describe('Video hearing service', () => { caseModel.number = 'Number 1'; const model = new HearingModel(); model.case_type = 'Tax'; - model.hearing_type_name = 'hearing type'; model.scheduled_date_time = new Date(date); model.scheduled_duration = 30; model.court_name = 'court address'; @@ -168,7 +167,6 @@ describe('Video hearing service', () => { caseModel.number = 'Number 1'; const model = new HearingModel(); model.case_type = 'Tax'; - model.hearing_type_name = 'hearing type'; model.scheduled_date_time = new Date(date); model.scheduled_duration = 30; model.court_name = 'court address'; diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/services/video-hearings.service.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/services/video-hearings.service.ts index dcc00e6f7..d2bb4271f 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/services/video-hearings.service.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/services/video-hearings.service.ts @@ -127,8 +127,7 @@ export class VideoHearingsService { localRequest.scheduled_date_time && localRequest.scheduled_duration > 0 && localRequest.participants.length > 1 && - localRequest.hearing_venue_id > 0 && - localRequest.hearing_type_id > 0 + localRequest.hearing_venue_id > 0 ); } @@ -323,8 +322,6 @@ export class VideoHearingsService { newHearingRequest.cases = this.mapCases(newRequest); newHearingRequest.case_type_name = newRequest.case_type; newHearingRequest.case_type_service_id = newRequest.case_type_service_id; - newHearingRequest.hearing_type_name = newRequest.hearing_type_name; - newHearingRequest.hearing_type_code = newRequest.hearing_type_code; newHearingRequest.scheduled_date_time = new Date(newRequest.scheduled_date_time); newHearingRequest.scheduled_duration = newRequest.scheduled_duration; newHearingRequest.hearing_venue_name = newRequest.court_name; @@ -344,8 +341,6 @@ export class VideoHearingsService { const hearing = new HearingModel(); hearing.hearing_id = response.id; hearing.cases = this.mapCaseResponseToCaseModel(response.cases); - hearing.hearing_type_name = response.hearing_type_name; - hearing.hearing_type_code = response.hearing_type_code; hearing.case_type = response.case_type_name; hearing.scheduled_date_time = new Date(response.scheduled_date_time); hearing.scheduled_duration = response.scheduled_duration; diff --git a/AdminWebsite/AdminWebsite/ClientApp/src/app/work-allocation/allocate-hearings/allocate-hearings.component.ts b/AdminWebsite/AdminWebsite/ClientApp/src/app/work-allocation/allocate-hearings/allocate-hearings.component.ts index b4998e7a2..ecee8d92b 100644 --- a/AdminWebsite/AdminWebsite/ClientApp/src/app/work-allocation/allocate-hearings/allocate-hearings.component.ts +++ b/AdminWebsite/AdminWebsite/ClientApp/src/app/work-allocation/allocate-hearings/allocate-hearings.component.ts @@ -103,15 +103,6 @@ export class AllocateHearingsComponent implements OnInit { ariaLabel: item.first_name })); }); - - const distinct = (value, index, array) => array.indexOf(value) === index; - this.videoHearingService.getHearingTypes(true).subscribe((data: HearingTypeResponse[]) => { - this.caseTypesSelectOptions = data - .map(item => item.group) - .filter(distinct) - .sort((a, b) => a.localeCompare(b)) - .map(group => ({ entityId: group, label: group })); - }); } searchForHearings(keepExistingMessage: boolean = false) { diff --git a/AdminWebsite/AdminWebsite/Configuration/FeatureToggles.cs b/AdminWebsite/AdminWebsite/Configuration/FeatureToggles.cs index 5346a7102..670c4f039 100644 --- a/AdminWebsite/AdminWebsite/Configuration/FeatureToggles.cs +++ b/AdminWebsite/AdminWebsite/Configuration/FeatureToggles.cs @@ -8,13 +8,7 @@ namespace AdminWebsite.Configuration { public interface IFeatureToggles { - public bool BookAndConfirmToggle(); public bool Dom1Enabled(); - public bool ReferenceDataToggle(); - public bool UseV2Api(); - public bool HrsEnabled(); - public bool AudioSearchEnabled(); - public bool UsePostMay2023Template(); } public class FeatureToggles : IFeatureToggles @@ -22,13 +16,7 @@ public class FeatureToggles : IFeatureToggles private readonly ILdClient _ldClient; private readonly Context _context; private const string LdUser = "vh-admin-web"; - private const string BookAndConfirmToggleKey = "Book_and_Confirm"; private const string Dom1EnabledToggleKey = "dom1"; - private const string ReferenceDataToggleKey = "reference-data"; - private const string UseV2ApiToggleKey = "use-bookings-api-v2"; - private const string HrsFeatureToggleKey = "hrs-integration"; - private const string AudioSearchToggleKey = "hide-audio-search-tile"; - private const string UsePostMay2023TemplateKey = "notify-post-may-2023-templates"; public FeatureToggles(string sdkKey, string environmentName) @@ -39,41 +27,11 @@ public FeatureToggles(string sdkKey, string environmentName) _ldClient = new LdClient(config); } - public bool BookAndConfirmToggle() - { - return GetBoolValueWithKey(BookAndConfirmToggleKey); - } - public bool Dom1Enabled() { return GetBoolValueWithKey(Dom1EnabledToggleKey); } - public bool ReferenceDataToggle() - { - return GetBoolValueWithKey(ReferenceDataToggleKey); - } - - public bool HrsEnabled() - { - return GetBoolValueWithKey(HrsFeatureToggleKey); - } - - public bool AudioSearchEnabled() - { - return GetBoolValueWithKey(AudioSearchToggleKey); - } - - public bool UseV2Api() - { - return GetBoolValueWithKey(UseV2ApiToggleKey); - } - - public bool UsePostMay2023Template() - { - return GetBoolValueWithKey(UsePostMay2023TemplateKey); - } - private bool GetBoolValueWithKey(string key) { if (!_ldClient.Initialized) diff --git a/AdminWebsite/AdminWebsite/Controllers/AudioPlatformController.cs b/AdminWebsite/AdminWebsite/Controllers/AudioPlatformController.cs index 234fe9ff5..17e9d4dc6 100644 --- a/AdminWebsite/AdminWebsite/Controllers/AudioPlatformController.cs +++ b/AdminWebsite/AdminWebsite/Controllers/AudioPlatformController.cs @@ -24,14 +24,12 @@ public class AudioPlatformController : ControllerBase private readonly IVideoApiClient _videoAPiClient; private readonly IBookingsApiClient _bookingsApiClient; private readonly ILogger _logger; - private readonly IFeatureToggles _featureToggles; - public AudioPlatformController(IVideoApiClient videoAPiClient, ILogger logger, IBookingsApiClient bookingsApiClient, IFeatureToggles featureToggles) + public AudioPlatformController(IVideoApiClient videoAPiClient, ILogger logger, IBookingsApiClient bookingsApiClient) { _videoAPiClient = videoAPiClient; _logger = logger; _bookingsApiClient = bookingsApiClient; - _featureToggles = featureToggles; } /// @@ -50,14 +48,7 @@ public async Task GetAudioRecordingLinkAsync(Guid hearingId) try { var requestKey = ""; - if (_featureToggles.HrsEnabled()) - { - requestKey = await GetAudioHrsFileName(hearingId); - } - else - { - requestKey = hearingId.ToString(); - } + requestKey = await GetAudioHrsFileName(hearingId); var response = await _videoAPiClient.GetAudioRecordingLinkAsync(requestKey); return Ok(new HearingAudioRecordingResponse { AudioFileLinks = response.AudioFileLinks }); diff --git a/AdminWebsite/AdminWebsite/Controllers/HearingsController.cs b/AdminWebsite/AdminWebsite/Controllers/HearingsController.cs index 663d5d4fa..f3e3e1343 100644 --- a/AdminWebsite/AdminWebsite/Controllers/HearingsController.cs +++ b/AdminWebsite/AdminWebsite/Controllers/HearingsController.cs @@ -4,7 +4,6 @@ using System.Net; using System.Threading.Tasks; using AdminWebsite.Attributes; -using AdminWebsite.Configuration; using AdminWebsite.Contracts.Enums; using AdminWebsite.Contracts.Requests; using AdminWebsite.Contracts.Responses; @@ -48,7 +47,6 @@ public class HearingsController : ControllerBase private readonly IValidator _editHearingRequestValidator; private readonly IHearingsService _hearingsService; private readonly IConferenceDetailsService _conferenceDetailsService; - private readonly IFeatureToggles _featureToggles; private readonly ILogger _logger; private readonly IUserIdentity _userIdentity; @@ -61,8 +59,7 @@ public HearingsController(IBookingsApiClient bookingsApiClient, IValidator editHearingRequestValidator, ILogger logger, IHearingsService hearingsService, - IConferenceDetailsService conferenceDetailsService, - IFeatureToggles featureToggles) + IConferenceDetailsService conferenceDetailsService) { _bookingsApiClient = bookingsApiClient; _userIdentity = userIdentity; @@ -70,7 +67,6 @@ public HearingsController(IBookingsApiClient bookingsApiClient, _logger = logger; _hearingsService = hearingsService; _conferenceDetailsService = conferenceDetailsService; - _featureToggles = featureToggles; } #pragma warning restore S107 /// @@ -129,27 +125,14 @@ private async Task BookNewHearing(BookingDetailsRequest newBookingReques _logger.LogInformation("BookNewHearing - Attempting to send booking request to Booking API"); - if (_featureToggles.UseV2Api()) - { - var newBookingRequestV2 = newBookingRequest.MapToV2(); - - var hearingDetailsResponse = await _bookingsApiClient.BookNewHearingWithCodeAsync(newBookingRequestV2); - - hearingId = hearingDetailsResponse.Id; - - response = hearingDetailsResponse.Map(); - } - else - { - var newBookingRequestV1 = newBookingRequest.MapToV1(); - - var hearingDetailsResponse = await _bookingsApiClient.BookNewHearingAsync(newBookingRequestV1); - - hearingId = hearingDetailsResponse.Id; - - response = hearingDetailsResponse.Map(); - } + var newBookingRequestV2 = newBookingRequest.MapToV2(); + + var hearingDetailsResponse = await _bookingsApiClient.BookNewHearingWithCodeAsync(newBookingRequestV2); + hearingId = hearingDetailsResponse.Id; + + response = hearingDetailsResponse.Map(); + _logger.LogInformation("BookNewHearing - Successfully booked hearing {Hearing}", hearingId); return response; @@ -411,26 +394,14 @@ public async Task CancelMultiDayHearing(Guid hearingId, CancelMul private async Task GetHearing(Guid hearingId) { - if (_featureToggles.UseV2Api()) - { - var responseV2 = await _bookingsApiClient.GetHearingDetailsByIdV2Async(hearingId); - return responseV2.Map(); - } - - var responseV1 = await _bookingsApiClient.GetHearingDetailsByIdAsync(hearingId); - return responseV1.Map(); + var responseV2 = await _bookingsApiClient.GetHearingDetailsByIdV2Async(hearingId); + return responseV2.Map(); } private async Task MapHearingToUpdate(Guid hearingId) { - if (_featureToggles.UseV2Api()) - { - var updatedHearing2 = await _bookingsApiClient.GetHearingDetailsByIdV2Async(hearingId); - return updatedHearing2.Map(); - } - - var updatedHearing1 = await _bookingsApiClient.GetHearingDetailsByIdAsync(hearingId); - return updatedHearing1.Map(); + var updatedHearing2 = await _bookingsApiClient.GetHearingDetailsByIdV2Async(hearingId); + return updatedHearing2.Map(); } private async Task UpdateHearing(EditHearingRequest request, Guid hearingId, HearingDetailsResponse originalHearing) @@ -451,19 +422,10 @@ private async Task UpdateHearing(EditHearingRequest request, Guid hearingId, Hea request.AudioRecordingRequired = originalHearing.AudioRecordingRequired; } - if (_featureToggles.UseV2Api()) - { - var updateHearingRequestV2 = HearingUpdateRequestMapper.MapToV2(request, _userIdentity.GetUserIdentityName()); - await _bookingsApiClient.UpdateHearingDetails2Async(hearingId, updateHearingRequestV2); - await UpdateParticipantsV2(hearingId, request.Participants, request.Endpoints, originalHearing); - await UpdateJudiciaryParticipants(hearingId, request.JudiciaryParticipants, originalHearing); - } - else - { - var updateHearingRequestV1 = HearingUpdateRequestMapper.MapToV1(request, _userIdentity.GetUserIdentityName()); - await _bookingsApiClient.UpdateHearingDetailsAsync(hearingId, updateHearingRequestV1); - await UpdateParticipantsV1(hearingId, request.Participants, request.Endpoints, originalHearing); - } + var updateHearingRequestV2 = HearingUpdateRequestMapper.MapToV2(request, _userIdentity.GetUserIdentityName()); + await _bookingsApiClient.UpdateHearingDetails2Async(hearingId, updateHearingRequestV2); + await UpdateParticipantsV2(hearingId, request.Participants, request.Endpoints, originalHearing); + await UpdateJudiciaryParticipants(hearingId, request.JudiciaryParticipants, originalHearing); } private async Task UpdateMultiDayHearing(EditMultiDayHearingRequest request, Guid hearingId, Guid groupId) @@ -973,26 +935,14 @@ public async Task GetHearingById(Guid hearingId) try { HearingDetailsResponse hearingResponse; - if (_featureToggles.UseV2Api()) - { - var response = await _bookingsApiClient.GetHearingDetailsByIdV2Async(hearingId); - ICollection groupedHearings = null; - if (response.GroupId != null) - { - groupedHearings = await _bookingsApiClient.GetHearingsByGroupIdV2Async(response.GroupId.Value); - } - hearingResponse = response.Map(groupedHearings); - } - else + var response = await _bookingsApiClient.GetHearingDetailsByIdV2Async(hearingId); + ICollection groupedHearings = null; + if (response.GroupId != null) { - var response = await _bookingsApiClient.GetHearingDetailsByIdAsync(hearingId); - ICollection groupedHearings = null; - if (response.GroupId != null) - { - groupedHearings = await _bookingsApiClient.GetHearingsByGroupIdAsync(response.GroupId.Value); - } - hearingResponse = response.Map(groupedHearings); + groupedHearings = await _bookingsApiClient.GetHearingsByGroupIdV2Async(response.GroupId.Value); } + hearingResponse = response.Map(groupedHearings); + return Ok(hearingResponse); } catch (BookingsApiException e) @@ -1048,8 +998,7 @@ public async Task GetHearingConferenceStatus(Guid hearingId) var participantsNeedVHAccounts = ParticipantsNeedVHAccounts(response.Participants); var accountsStillNeedCreating = participantsNeedVHAccounts.Any(x => x.ContactEmail == x.Username); var isMultiDay = response.GroupId != null; - var isNotifyFlagOn = _featureToggles.UsePostMay2023Template(); - if (isMultiDay && isNotifyFlagOn) + if (isMultiDay) { // Users are created as part of the clone process, so don't wait for them here accountsStillNeedCreating = false; @@ -1195,16 +1144,8 @@ public async Task GetTelephoneConferenceIdById(Guid hearingId) private IEnumerable ParticipantsNeedVHAccounts(List allParticipants) { - IEnumerable participantsNeedVHAccounts; - if (_featureToggles.UseV2Api()) - { - participantsNeedVHAccounts = allParticipants.Where(x => x.UserRoleName == RoleNames.Individual || x.UserRoleName == RoleNames.Representative); - } - else - { - participantsNeedVHAccounts = allParticipants.Where(x => x.UserRoleName != RoleNames.Judge); - } - + var participantsNeedVHAccounts = allParticipants.Where(x => x.UserRoleName == RoleNames.Individual || x.UserRoleName == RoleNames.Representative); + return participantsNeedVHAccounts; } } diff --git a/AdminWebsite/AdminWebsite/Controllers/ReferenceDataController.cs b/AdminWebsite/AdminWebsite/Controllers/ReferenceDataController.cs index 3a2ef521b..b559bc31f 100644 --- a/AdminWebsite/AdminWebsite/Controllers/ReferenceDataController.cs +++ b/AdminWebsite/AdminWebsite/Controllers/ReferenceDataController.cs @@ -4,7 +4,6 @@ using System.Linq; using System.Net; using System.Threading.Tasks; -using AdminWebsite.Configuration; using AdminWebsite.Contracts.Responses; using AdminWebsite.Mappers; using AdminWebsite.Services; @@ -25,19 +24,16 @@ public class ReferenceDataController : ControllerBase { private readonly IBookingsApiClient _bookingsApiClient; private readonly IPublicHolidayRetriever _publicHolidayRetriever; - private readonly IFeatureToggles _featureToggles; /// /// Instantiate the controller /// public ReferenceDataController( IBookingsApiClient bookingsApiClient, - IPublicHolidayRetriever publicHolidayRetriever, - IFeatureToggles featureToggles) + IPublicHolidayRetriever publicHolidayRetriever) { _bookingsApiClient = bookingsApiClient; _publicHolidayRetriever = publicHolidayRetriever; - _featureToggles = featureToggles; } /// @@ -60,13 +56,12 @@ public async Task>> GetHearingTypes([Fro Code = hearingType.Code } )).ToList(); - if (_featureToggles.UseV2Api()) - result.AddRange(caseTypes.Where(ct => !ct.HearingTypes.Any()) - .Select(caseType => new HearingTypeResponse - { - Group = caseType.Name, - ServiceId = caseType.ServiceId - })); + result.AddRange(caseTypes.Where(ct => !ct.HearingTypes.Any()) + .Select(caseType => new HearingTypeResponse + { + Group = caseType.Name, + ServiceId = caseType.ServiceId + })); return Ok(result); } @@ -82,16 +77,9 @@ public async Task>> GetParticipa { var response = new List(); List iCaseRoles; - if (_featureToggles.ReferenceDataToggle()) - { - var caseRoles2 = await _bookingsApiClient.GetCaseRolesForCaseServiceAsync(caseTypeParameter); - iCaseRoles = caseRoles2?.Select(e => (ICaseRoleResponse)e).ToList(); - } - else - { - var caseRoles1 = await _bookingsApiClient.GetCaseRolesForCaseTypeAsync(caseTypeParameter); - iCaseRoles = caseRoles1?.Select(e => (ICaseRoleResponse)e).ToList(); - } + var caseRoles2 = await _bookingsApiClient.GetCaseRolesForCaseServiceAsync(caseTypeParameter); + iCaseRoles = caseRoles2?.Select(e => (ICaseRoleResponse)e).ToList(); + if (iCaseRoles != null && iCaseRoles.Any()) { @@ -99,16 +87,8 @@ public async Task>> GetParticipa { var caseRole = new CaseAndHearingRolesResponse { Name = caseRoleName }; List iHearingRoles; - if (_featureToggles.ReferenceDataToggle()) - { - var hearingRoles1 = await _bookingsApiClient.GetHearingRolesForCaseRoleV2Async(caseTypeParameter, caseRoleName); - iHearingRoles = hearingRoles1.Select(e => (IHearingRoleResponse)e).ToList(); - } - else - { - var hearingRoles2 = await _bookingsApiClient.GetHearingRolesForCaseRoleAsync(caseTypeParameter, caseRoleName); - iHearingRoles = hearingRoles2.Select(e => (IHearingRoleResponse)e).ToList(); - } + var hearingRoles1 = await _bookingsApiClient.GetHearingRolesForCaseRoleV2Async(caseTypeParameter, caseRoleName); + iHearingRoles = hearingRoles1.Select(e => (IHearingRoleResponse)e).ToList(); caseRole.HearingRoles = iHearingRoles.ConvertAll(x => new HearingRole(x.Name, x.UserRole)); diff --git a/AdminWebsite/AdminWebsite/Services/HearingsService.cs b/AdminWebsite/AdminWebsite/Services/HearingsService.cs index 5ab1e0f16..8882f84e0 100644 --- a/AdminWebsite/AdminWebsite/Services/HearingsService.cs +++ b/AdminWebsite/AdminWebsite/Services/HearingsService.cs @@ -7,7 +7,6 @@ using System.Collections.Generic; using System.Linq; using System.Threading.Tasks; -using AdminWebsite.Configuration; using AdminWebsite.Contracts.Responses; using AdminWebsite.Models.EditMultiDayHearing; using BookingsApi.Contract.Interfaces.Requests; @@ -29,14 +28,12 @@ public interface IHearingsService public class HearingsService : IHearingsService { private readonly IBookingsApiClient _bookingsApiClient; - private readonly IFeatureToggles _featureToggles; private readonly ILogger _logger; #pragma warning disable S107 - public HearingsService(IBookingsApiClient bookingsApiClient, ILogger logger, IFeatureToggles featureToggles) + public HearingsService(IBookingsApiClient bookingsApiClient, ILogger logger) { _bookingsApiClient = bookingsApiClient; _logger = logger; - _featureToggles = featureToggles; } public void AssignEndpointDefenceAdvocates(List endpointsWithDa, IReadOnlyCollection participants) @@ -107,7 +104,7 @@ public Task ProcessNewParticipant( { // Add a new participant // Map the request except the username - if (participant.CaseRoleName == RoleNames.Judge || (_featureToggles.UseV2Api() && participant.HearingRoleName is RoleNames.PanelMember or RoleNames.Winger)) + if (participant.CaseRoleName == RoleNames.Judge || (participant.HearingRoleName is RoleNames.PanelMember or RoleNames.Winger)) { if (hearing.Participants != null && hearing.Participants.Exists(p => p.ContactEmail.Equals(participant.ContactEmail) && removedParticipantIds.TrueForAll(removedParticipantId => removedParticipantId != p.Id))) diff --git a/AdminWebsite/docker-compose.yml b/AdminWebsite/docker-compose.yml index f645fb7dc..9022a600c 100644 --- a/AdminWebsite/docker-compose.yml +++ b/AdminWebsite/docker-compose.yml @@ -1,4 +1,3 @@ -version: '3.4' services: adminweb: diff --git a/azure-pipelines.sds.pr-release.yml b/azure-pipelines.sds.pr-release.yml index 4202a984c..f0350d21b 100644 --- a/azure-pipelines.sds.pr-release.yml +++ b/azure-pipelines.sds.pr-release.yml @@ -5,7 +5,7 @@ resources: - repository: azTemplates type: github name: hmcts/azure-devops-templates - ref: master + ref: fixx_upgrade_docker2 endpoint: hmcts pool: