Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .editorconfig
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ trim_trailing_whitespace = true
encoding = utf-8-bom

# ReSharper properties
resharper_csharp_blank_lines_around_single_line_invocable = 1
resharper_csharp_wrap_after_declaration_lpar = true
resharper_csharp_wrap_after_invocation_lpar = true
resharper_csharp_wrap_arguments_style = chop_if_long
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -451,5 +451,111 @@ public void UpdateLearningPathwayDefaultsForCourse_correctly_updates_learning_pa
transaction.Dispose();
}
}

[Test]
public void UpdateCourseOptions_updates_course_options_successfully()
{
using var transaction = new TransactionScope();

// Given
const int customisationId = 100;
const int centreId = 101;
const int categoryId = 0;

var defaultCourseOptions = new CourseOptions()
{
Active = true,
DiagObjSelect = true,
SelfRegister = false,
HideInLearnerPortal = false,
};

try
{
// When
courseDataService.UpdateCourseOptions(defaultCourseOptions, customisationId);
var updatedCourseOptions = courseDataService.GetCourseOptionsForAdminCategoryId(
customisationId,
centreId,
categoryId
);

// Then
using (new AssertionScope())
{
updatedCourseOptions?.Active.Should().BeTrue();
updatedCourseOptions?.DiagObjSelect.Should().BeTrue();
updatedCourseOptions?.SelfRegister.Should().BeFalse();
updatedCourseOptions?.HideInLearnerPortal.Should().BeFalse();
}
}
finally
{
transaction.Dispose();
}
}

[Test]
public void GetCourseOptionsForAdminCategoryId_gets_correct_data_for_valid_centre_and_category_Id()
{
// Given
const int customisationId = 1379;
const int centreId = 101;
const int categoryId = 0;

// When
var updatedCourseOptions = courseDataService.GetCourseOptionsForAdminCategoryId(
customisationId,
centreId,
categoryId
);

// Then
using (new AssertionScope())
{
updatedCourseOptions?.Active.Should().BeTrue();
updatedCourseOptions?.DiagObjSelect.Should().BeTrue();
updatedCourseOptions?.SelfRegister.Should().BeTrue();
updatedCourseOptions?.HideInLearnerPortal.Should().BeTrue();
}
}

[Test]
public void GetCourseOptionsForAdminCategoryId_with_incorrect_centerId_and_correct_customisationId_and_categoryId_returns_null()
{
// Given
const int customisationId = 1379;
const int centreId = 5;
const int categoryId = 0;

// When
var updatedCourseOptions = courseDataService.GetCourseOptionsForAdminCategoryId(
customisationId,
centreId,
categoryId
);

// Then
updatedCourseOptions.Should().BeNull();
}

[Test]
public void GetCourseOptionsForAdminCategoryId_with_incorrect_categoryId_and_correct_customisationId_and_centerId_returns_null()
{
// Given
const int customisationId = 1379;
const int centreId = 101;
const int categoryId = 10;

// When
var updatedCourseOptions = courseDataService.GetCourseOptionsForAdminCategoryId(
customisationId,
centreId,
categoryId
);

// Then
updatedCourseOptions.Should().BeNull();
}
}
}
46 changes: 46 additions & 0 deletions DigitalLearningSolutions.Data/DataServices/CourseDataService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,9 @@ void UpdateLearningPathwayDefaultsForCourse(
bool mandatory,
bool autoRefresh
);

void UpdateCourseOptions(CourseOptions courseOptions, int customisationId);
CourseOptions? GetCourseOptionsForAdminCategoryId(int customisationId, int centreId, int categoryId);
}

public class CourseDataService : ICourseDataService
Expand Down Expand Up @@ -423,5 +426,48 @@ bool autoRefresh
new { completeWithinMonths, validityMonths, mandatory, autoRefresh, customisationId }
);
}

public void UpdateCourseOptions(CourseOptions courseOptions, int customisationId)
{
connection.Execute(
@"UPDATE cu
SET Active = @Active,
SelfRegister = @SelfRegister,
HideInLearnerPortal = @HideInLearnerPortal,
DiagObjSelect = @DiagObjSelect
FROM dbo.Customisations AS cu
WHERE
cu.CustomisationID = @customisationId",
new
{
courseOptions.Active,
courseOptions.SelfRegister,
courseOptions.HideInLearnerPortal,
courseOptions.DiagObjSelect,
customisationId,
});
}

public CourseOptions? GetCourseOptionsForAdminCategoryId(int customisationId, int centreId, int categoryId)
{
return connection.Query<CourseOptions>(
@"SELECT
cu.Active,
cu.SelfRegister,
cu.HideInLearnerPortal,
cu.DiagObjSelect,
ap.DiagAssess
FROM dbo.Customisations AS cu
INNER JOIN dbo.Applications AS ap ON ap.ApplicationID = cu.ApplicationID
LEFT JOIN dbo.Customisations AS refreshToCu ON refreshToCu.CustomisationID = cu.RefreshToCustomisationId
LEFT JOIN dbo.Applications AS refreshToAp ON refreshToAp.ApplicationID = refreshToCu.ApplicationID
WHERE
(ap.CourseCategoryID = @categoryId OR @categoryId = 0)
AND cu.CentreID = @centreId
AND ap.ArchivedDate IS NULL
AND cu.CustomisationID = @customisationId",
new { customisationId, centreId, categoryId }
).FirstOrDefault();
}
}
}
11 changes: 11 additions & 0 deletions DigitalLearningSolutions.Data/Models/Courses/CourseOptions.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
namespace DigitalLearningSolutions.Data.Models.Courses
{
public class CourseOptions
{
public bool Active { get; set; }
public bool SelfRegister { get; set; }
public bool HideInLearnerPortal { get; set; }
public bool DiagObjSelect { get; set; }
public bool DiagAssess { get; set; }
}
}
20 changes: 20 additions & 0 deletions DigitalLearningSolutions.Data/Services/CourseService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,9 @@ public void UpdateLearningPathwayDefaultsForCourse(
bool mandatory,
bool autoRefresh
);

void UpdateCourseOptions(CourseOptions courseOptions, int customisationId);
CourseOptions? GetCourseOptionsForAdminCategoryId(int customisationId, int centreId, int categoryId);
}

public class CourseService : ICourseService
Expand Down Expand Up @@ -106,5 +109,22 @@ bool autoRefresh
autoRefresh
);
}

public void UpdateCourseOptions(CourseOptions courseOptions, int customisationId)
{
courseDataService.UpdateCourseOptions(
courseOptions,
customisationId
);
}

public CourseOptions? GetCourseOptionsForAdminCategoryId(int customisationId, int centreId, int categoryId)
{
return courseDataService.GetCourseOptionsForAdminCategoryId(
customisationId,
centreId,
categoryId
);
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ public BasicAuthenticatedAccessibilityTests(AuthenticatedAccessibilityTestsFixtu
"/TrackingSystem/CourseSetup/10716/Manage/LearningPathwayDefaults",
"Edit Learning Pathway defaults"
)]
[InlineData("/TrackingSystem/CourseSetup/10716/Manage/EditCourseOptions", "Edit course options")]
[InlineData("/TrackingSystem/Delegates/All", "Delegates")]
[InlineData("/TrackingSystem/Delegates/Groups", "Groups")]
[InlineData("/TrackingSystem/Delegates/Groups/5/Delegates", "Group delegates")]
Expand Down
Original file line number Diff line number Diff line change
@@ -1,14 +1,20 @@
namespace DigitalLearningSolutions.Web.Tests.Controllers.TrackingSystem.CourseSetup
{
using DigitalLearningSolutions.Data.DataServices;
using DigitalLearningSolutions.Data.Models.Courses;
using DigitalLearningSolutions.Data.Services;
using DigitalLearningSolutions.Web.Controllers.TrackingSystem.CourseSetup;
using DigitalLearningSolutions.Web.ServiceFilter;
using DigitalLearningSolutions.Web.Tests.ControllerHelpers;
using DigitalLearningSolutions.Web.ViewModels.TrackingSystem.CourseSetup.CourseDetails;
using FakeItEasy;
using FluentAssertions.AspNetCore.Mvc;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Mvc.Abstractions;
using Microsoft.AspNetCore.Mvc.Filters;
using Microsoft.AspNetCore.Routing;
using NUnit.Framework;
using System.Collections.Generic;

internal class ManageCourseControllerTests
{
Expand Down Expand Up @@ -115,5 +121,70 @@ public void
result.Should().BeViewResult().ModelAs<EditLearningPathwayDefaultsViewModel>();
Assert.IsFalse(controller.ModelState.IsValid);
}

[Test]
public void Edit_Course_Options_page_opens_up_with_course_options()
{
// Given
const int customisationId = 1;
A.CallTo(
() => courseService.VerifyAdminUserCanAccessCourse(
customisationId,
A<int>._,
A<int>._
)
).Returns(true);

A.CallTo(
() => courseService.GetCourseOptionsForAdminCategoryId(
customisationId,
A<int>._,
A<int>._
)
).Returns(new CourseOptions());


// When
var result = controller.EditCourseOptions(customisationId);

// Then
result.Should().BeViewResult().WithDefaultViewName().ModelAs<EditCourseOptionsViewModel>();
}

[Test]
public void Edit_Course_Options_page_redirects_to_Index_when_course_details_are_updated()
{
// Given
const int customisationId = 1;
var courseOptions = new CourseOptions()
{
Active = true,
DiagObjSelect = true,
HideInLearnerPortal = true,
SelfRegister = true
};

A.CallTo(
() => courseService.UpdateCourseOptions(
A<CourseOptions>._,
customisationId
)
).DoesNothing();

var editCourseOptionsViewModel = new EditCourseOptionsViewModel(courseOptions, customisationId);

// When
var result = controller.EditCourseOptions(customisationId, editCourseOptionsViewModel);

// Then
A.CallTo(
() => courseService.UpdateCourseOptions(
A<CourseOptions>._,
customisationId
)
).MustHaveHappened();

result.Should().BeRedirectToActionResult().WithControllerName("ManageCourse").WithActionName("Index");
}
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
namespace DigitalLearningSolutions.Web.Controllers.TrackingSystem.CourseSetup
{
using DigitalLearningSolutions.Data.Enums;
using DigitalLearningSolutions.Data.Models.Courses;
using DigitalLearningSolutions.Data.Services;
using DigitalLearningSolutions.Web.Attributes;
using DigitalLearningSolutions.Web.Helpers;
Expand Down Expand Up @@ -99,5 +100,41 @@ EditLearningPathwayDefaultsViewModel model

return RedirectToAction("Index", new { customisationId = model.CustomisationId });
}

[HttpGet]
[Route("EditCourseOptions")]
public IActionResult EditCourseOptions(int customisationId)
{
var centreId = User.GetCentreId();
var categoryId = User.GetAdminCategoryId()!;

var courseOptions = courseService.GetCourseOptionsForAdminCategoryId(
customisationId,
centreId,
categoryId.GetValueOrDefault()
);

var model = new EditCourseOptionsViewModel(courseOptions!, customisationId);
return View(model);
}

[HttpPost]
[Route("EditCourseOptions")]
public IActionResult EditCourseOptions(
int customisationId,
EditCourseOptionsViewModel editCourseOptionsViewModel
)
{
var courseOptions = new CourseOptions
{
Active = editCourseOptionsViewModel.Active,
SelfRegister = editCourseOptionsViewModel.AllowSelfEnrolment,
HideInLearnerPortal = editCourseOptionsViewModel.HideInLearningPortal,
DiagObjSelect = editCourseOptionsViewModel.DiagnosticObjectiveSelection,
};

courseService.UpdateCourseOptions(courseOptions, customisationId);
return RedirectToAction("Index", "ManageCourse", new { customisationId });
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,10 @@ public CourseOptionsViewModel(CourseDetails courseDetails)
AllowSelfEnrolment = courseDetails.SelfRegister;
DiagnosticObjectiveSelection = courseDetails.DiagObjSelect;
HideInLearningPortal = courseDetails.HideInLearnerPortal;
CustomisationId = courseDetails.CustomisationId;
}

public int CustomisationId { get; set; }
public bool Active { get; set; }
public bool AllowSelfEnrolment { get; set; }
public bool DiagnosticObjectiveSelection { get; set; }
Expand Down
Loading