Skip to content

Commit 9ef3d4f

Browse files
committed
Merge branch 'DLS-Release-v1.3.0' into DEV
2 parents c6d5229 + f4b766c commit 9ef3d4f

27 files changed

+975
-73
lines changed
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
namespace DigitalLearningSolutions.Data.Migrations
2+
{
3+
using FluentMigrator;
4+
[Migration(202510021000)]
5+
public class AddIsdeletedSelfAssessmentCollaborators : Migration
6+
{
7+
public override void Up()
8+
{
9+
Alter.Table("SelfAssessmentCollaborators").AddColumn("IsDeleted").AsBoolean().WithDefaultValue(false);
10+
}
11+
public override void Down()
12+
{
13+
Delete.Column("IsDeleted").FromTable("SelfAssessmentCollaborators");
14+
}
15+
}
16+
}

DigitalLearningSolutions.Data/DataServices/CompetencyAssessmentDataService.cs

Lines changed: 205 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
namespace DigitalLearningSolutions.Data.DataServices
22
{
33
using Dapper;
4+
using DigitalLearningSolutions.Data.Extensions;
45
using DigitalLearningSolutions.Data.Models.CompetencyAssessments;
56
using Microsoft.Extensions.Logging;
67
using System;
@@ -57,6 +58,7 @@ int categoryId
5758
bool UpdateSelectCompetenciesTaskStatus(int assessmentId, bool taskStatus, bool? previousStatus);
5859
bool UpdateOptionalCompetenciesTaskStatus(int assessmentId, bool taskStatus, bool? previousStatus);
5960
bool UpdateRoleRequirementsTaskStatus(int assessmentId, bool taskStatus, bool? previousStatus);
61+
bool UpdateWorkingGroupTaskStatus(int assessmentId, bool taskStatus, bool? previousStatus);
6062
void MoveCompetencyInSelfAssessment(int competencyAssessmentId,
6163
int competencyId,
6264
string direction
@@ -68,6 +70,7 @@ string direction
6870
public bool UpdateCompetencyAssessmentFeaturesTaskStatus(int id, bool descriptionStatus, bool providerandCategoryStatus, bool vocabularyStatus,
6971
bool workingGroupStatus, bool AllframeworkCompetenciesStatus);
7072
void UpdateSelfAssessmentFromFramework(int selfAssessmentId, int? frameworkId);
73+
bool UpdatePrimaryFrameworkCompetencies(int assessmentId, int frameworkId);
7174

7275
//INSERT DATA
7376
int InsertCompetencyAssessment(int adminId, int centreId, string competencyAssessmentName);
@@ -77,6 +80,10 @@ public bool UpdateCompetencyAssessmentFeaturesTaskStatus(int id, bool descriptio
7780
//DELETE DATA
7881
bool RemoveFrameworkCompetenciesFromAssessment(int competencyAssessmentId, int frameworkId);
7982
bool RemoveCompetencyFromAssessment(int competencyAssessmentId, int competencyId);
83+
IEnumerable<CompetencyAssessmentCollaboratorDetail> GetCollaboratorsForCompetencyAssessmentId(int competencyAssessmentId);
84+
int AddCollaboratorToCompetencyAssessment(int competencyAssessmentId, string? userEmail, bool canModify, int? centreID);
85+
void RemoveCollaboratorFromCompetencyAssessment(int competencyAssessmentId, int id);
86+
CompetencyAssessmentCollaboratorNotification? GetCollaboratorNotification(int id, int invitedByAdminId);
8087
}
8188

8289
public class CompetencyAssessmentDataService : ICompetencyAssessmentDataService
@@ -646,6 +653,23 @@ public bool UpdateRoleRequirementsTaskStatus(int assessmentId, bool taskStatus,
646653
}
647654
return true;
648655
}
656+
public bool UpdateWorkingGroupTaskStatus(int assessmentId, bool taskStatus, bool? previousStatus)
657+
{
658+
var numberOfAffectedRows = connection.Execute(
659+
@"UPDATE SelfAssessmentTaskStatus SET WorkingGroupTaskStatus = @taskStatus
660+
WHERE SelfAssessmentId = @assessmentId AND (@previousStatus IS NULL OR WorkingGroupTaskStatus = @previousStatus)",
661+
new { assessmentId, taskStatus, previousStatus }
662+
);
663+
if (numberOfAffectedRows < 1)
664+
{
665+
logger.LogWarning(
666+
"Not updating WorkingGroupTaskStatus as db update failed. " +
667+
$"assessmentId: {assessmentId}, taskStatus: {taskStatus}"
668+
);
669+
return false;
670+
}
671+
return true;
672+
}
649673

650674
public IEnumerable<Competency> GetCompetenciesForCompetencyAssessment(int competencyAssessmentId)
651675
{
@@ -747,7 +771,7 @@ public void MoveCompetencyInSelfAssessment(int competencyAssessmentId, int compe
747771
new { SelfAssessmentID = competencyAssessmentId, CompetencyID = competencyId, Direction = direction },
748772
commandType: CommandType.StoredProcedure
749773
);
750-
774+
751775
}
752776

753777
public void MoveCompetencyGroupInSelfAssessment(int competencyAssessmentId, int groupId, string direction)
@@ -811,12 +835,12 @@ FROM SelfAssessments s INNER JOIN
811835
WHERE s.ID = @competencyAssessmentId",
812836
new { competencyAssessmentId }
813837
);
814-
838+
815839
}
816840

817-
public void UpdateSelfAssessmentFromFramework( int selfAssessmentId, int? frameworkId)
841+
public void UpdateSelfAssessmentFromFramework(int selfAssessmentId, int? frameworkId)
818842
{
819-
843+
820844
var numberOfAffectedRows = connection.Execute(
821845
@"UPDATE s
822846
SET
@@ -828,22 +852,22 @@ FROM SelfAssessments s
828852
INNER JOIN AdminUsers AU ON F.OwnerAdminID = AU.AdminID
829853
WHERE s.id = @selfAssessmentId;"
830854
,
831-
new {selfAssessmentId, frameworkId }
855+
new { selfAssessmentId, frameworkId }
832856
);
833857
}
834858
public bool InsertSelfAssessmentStructure(int selfAssessmentId, int? frameworkId)
835859
{
836860

837-
var numberOfAffectedRows = connection.Execute(
838-
@"INSERT INTO SelfAssessmentStructure (SelfAssessmentID, CompetencyID, Ordering, CompetencyGroupID)
861+
var numberOfAffectedRows = connection.Execute(
862+
@"INSERT INTO SelfAssessmentStructure (SelfAssessmentID, CompetencyID, Ordering, CompetencyGroupID)
839863
SELECT s.ID, FC.CompetencyID, ROW_NUMBER() OVER( ORDER BY FCG.Ordering, FC.Ordering ), FCG.CompetencyGroupID
840864
FROM FrameworkCompetencies AS FC
841865
INNER JOIN FrameworkCompetencyGroups AS FCG ON FC.FrameworkCompetencyGroupID = FCG.ID INNER JOIN
842866
SelfAssessments s ON s.id = @selfAssessmentId
843867
WHERE FC.FrameworkID = @frameworkId"
844-
,
845-
new { selfAssessmentId, frameworkId }
846-
);
868+
,
869+
new { selfAssessmentId, frameworkId }
870+
);
847871
if (numberOfAffectedRows < 1)
848872
{
849873
logger.LogWarning(
@@ -855,13 +879,183 @@ FROM FrameworkCompetencies AS FC
855879

856880
return true;
857881
}
882+
883+
public bool UpdatePrimaryFrameworkCompetencies(int assessmentId, int frameworkId)
884+
{
885+
connection.EnsureOpen();
886+
using (var transaction = connection.BeginTransaction())
887+
{
888+
var numberOfAffectedRows = connection.Execute(
889+
@"UPDATE SelfAssessmentFrameworks
890+
SET IsPrimary = 0
891+
WHERE (SelfAssessmentId = @assessmentId)
892+
AND (RemovedDate IS NULL)",
893+
new { assessmentId },
894+
transaction: transaction
895+
);
896+
897+
var numberOfAffectedRow = connection.Execute(
898+
@"UPDATE SelfAssessmentFrameworks
899+
SET IsPrimary = 1
900+
WHERE (SelfAssessmentId = @assessmentId)
901+
AND (FrameworkId = @frameworkId)
902+
AND (RemovedDate IS NULL)",
903+
new { assessmentId, frameworkId },
904+
transaction: transaction
905+
);
906+
907+
if ((numberOfAffectedRow < 1) || (numberOfAffectedRows < 1))
908+
{
909+
logger.LogWarning(
910+
"Not updating SelfAssessmentFrameworks as db update failed. " +
911+
$"assessmentId: {assessmentId}, frameworkId: {frameworkId}"
912+
);
913+
transaction.Rollback();
914+
return false;
915+
}
916+
917+
transaction.Commit();
918+
return true;
919+
}
920+
}
858921
public int? GetSelfAssessmentStructure(int competencyAssessmentId)
859922
{
860923
return connection.QueryFirstOrDefault<int>(
861924
@"SELECT 1 from dbo.SelfAssessmentStructure where selfassessmentid = @competencyAssessmentId",
862925
new { competencyAssessmentId }
863-
);
926+
);
927+
}
928+
public IEnumerable<CompetencyAssessmentCollaboratorDetail> GetCollaboratorsForCompetencyAssessmentId(int competencyAssessmentId)
929+
{
930+
return connection.Query<CompetencyAssessmentCollaboratorDetail>(
931+
@"SELECT
932+
0 AS ID,
933+
sa.ID AS SelfAssessmentID,
934+
au.AdminID AS AdminID,
935+
1 AS CanModify,
936+
au.Email AS UserEmail,
937+
au.Active AS UserActive,
938+
'Owner' AS CompetencyAssessmentRole
939+
FROM SelfAssessments AS sa
940+
INNER JOIN AdminUsers AS au ON sa.CreatedByAdminID = au.AdminID
941+
WHERE (sa.ID = @competencyAssessmentId)
942+
UNION ALL
943+
SELECT
944+
ID,
945+
SelfAssessmentID,
946+
sc.AdminID,
947+
CanModify,
948+
UserEmail,
949+
au.Active AS UserActive,
950+
CASE WHEN CanModify = 1 THEN 'Contributor' ELSE 'Reviewer' END AS CompetencyAssessmentRole
951+
FROM SelfAssessmentCollaborators sc
952+
INNER JOIN AdminUsers AS au ON sc.AdminID = au.AdminID
953+
AND sc.IsDeleted = 0
954+
WHERE (SelfAssessmentID = @competencyAssessmentId)",
955+
new { competencyAssessmentId }
956+
);
957+
}
958+
public int AddCollaboratorToCompetencyAssessment(int competencyAssessmentId, string? userEmail, bool canModify, int? centreID)
959+
{
960+
if (userEmail is null || userEmail.Length == 0)
961+
{
962+
logger.LogWarning(
963+
$"Not adding collaborator to competency assessment as it failed server side valiidation. competencyAssessmentId: {competencyAssessmentId}, userEmail: {userEmail}, canModify:{canModify}"
964+
);
965+
return -3;
966+
}
967+
968+
var existingId = connection.QuerySingle<int>(
969+
@"SELECT COALESCE
970+
((SELECT ID
971+
FROM SelfAssessmentCollaborators
972+
WHERE (SelfAssessmentID = @competencyAssessmentId) AND (UserEmail = @userEmail) AND (IsDeleted=0)), 0) AS ID",
973+
new { competencyAssessmentId, userEmail }
974+
);
975+
if (existingId > 0)
976+
{
977+
return -2;
978+
}
979+
980+
var adminId = (int?)connection.ExecuteScalar(
981+
@"SELECT AdminID FROM AdminUsers WHERE Email = @userEmail AND Active = 1 AND CentreID = @centreID",
982+
new { userEmail, centreID }
983+
);
984+
if (adminId is null)
985+
{
986+
return -4;
987+
}
988+
989+
var ownerEmail = (string?)connection.ExecuteScalar(@"SELECT AU.Email FROM SelfAssessments SA
990+
INNER JOIN AdminUsers AU ON AU.AdminID = SA.CreatedByAdminID
991+
WHERE SA.ID = @competencyAssessmentId", new { competencyAssessmentId });
992+
if (ownerEmail == userEmail)
993+
{
994+
return -5;
995+
}
996+
997+
var numberOfAffectedRows = connection.Execute(
998+
@"INSERT INTO SelfAssessmentCollaborators (SelfAssessmentID, AdminID, UserEmail, CanModify)
999+
VALUES (@competencyAssessmentId, @adminId, @userEmail, @canModify)",
1000+
new { competencyAssessmentId, adminId, userEmail, canModify }
1001+
);
1002+
if (numberOfAffectedRows < 1)
1003+
{
1004+
logger.LogWarning(
1005+
$"Not inserting framework collaborator as db insert failed. AdminId: {adminId}, userEmail: {userEmail}, competencyAssessmentId: {competencyAssessmentId}, canModify: {canModify}"
1006+
);
1007+
return -1;
1008+
}
8641009

1010+
if (adminId > 0)
1011+
{
1012+
connection.Execute(
1013+
@"UPDATE AdminUsers SET IsWorkforceManager = 1 WHERE AdminId = @adminId AND IsWorkforceManager = 0",
1014+
new { adminId }
1015+
);
1016+
}
1017+
1018+
existingId = connection.QuerySingle<int>(
1019+
@"SELECT COALESCE
1020+
((SELECT ID
1021+
FROM SelfAssessmentCollaborators
1022+
WHERE (SelfAssessmentID = @competencyAssessmentId) AND (UserEmail = @userEmail) AND (IsDeleted=0)), 0) AS AdminID",
1023+
new { competencyAssessmentId, adminId, userEmail }
1024+
);
1025+
return existingId;
1026+
}
1027+
1028+
public void RemoveCollaboratorFromCompetencyAssessment(int competencyAssessmentId, int id)
1029+
{
1030+
var adminId = (int?)connection.ExecuteScalar(
1031+
@"SELECT AdminID FROM SelfAssessmentCollaborators WHERE (SelfAssessmentID = @competencyAssessmentId) AND (ID = @id)",
1032+
new { competencyAssessmentId, id }
1033+
);
1034+
connection.Execute(
1035+
@"UPDATE SelfAssessmentCollaborators SET IsDeleted=1 WHERE (SelfAssessmentID = @competencyAssessmentId) AND (ID = @id);
1036+
UPDATE AdminUsers SET IsWorkforceManager = 0 WHERE AdminID = @adminId AND AdminID NOT IN (SELECT DISTINCT AdminID FROM SelfAssessmentCollaborators);",
1037+
new { competencyAssessmentId, id, adminId }
1038+
);
1039+
}
1040+
public CompetencyAssessmentCollaboratorNotification? GetCollaboratorNotification(int id, int invitedByAdminId)
1041+
{
1042+
return connection.Query<CompetencyAssessmentCollaboratorNotification>(
1043+
@"SELECT
1044+
sc.SelfAssessmentID,
1045+
sc.AdminID,
1046+
sc.CanModify,
1047+
sc.UserEmail,
1048+
au.Active AS UserActive,
1049+
CASE WHEN sc.CanModify = 1 THEN 'Contributor' ELSE 'Reviewer' END AS CompetencyAssessmentRole,
1050+
sa.[Name] AS CompetencyAssessmentName,
1051+
(SELECT Forename + ' ' + Surname + (CASE WHEN Active = 1 THEN '' ELSE ' (Inactive)' END) AS Expr1 FROM AdminUsers AS au1 WHERE (AdminID = @invitedByAdminId)) AS InvitedByName,
1052+
(SELECT Email FROM AdminUsers AS au2 WHERE (AdminID = @invitedByAdminId)) AS InvitedByEmail
1053+
FROM SelfAssessmentCollaborators AS sc
1054+
INNER JOIN SelfAssessments AS sa ON sc.SelfAssessmentID = sa.ID
1055+
INNER JOIN AdminUsers AS au ON sc.AdminID = au.AdminID
1056+
WHERE (sc.ID = @id) AND (sc.IsDeleted=0)",
1057+
new { invitedByAdminId, id }
1058+
).FirstOrDefault();
8651059
}
8661060
}
8671061
}

DigitalLearningSolutions.Data/DataServices/CourseDataService.cs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -514,7 +514,8 @@ INNER JOIN Users AS U
514514
LEFT OUTER JOIN UserCentreDetails AS UCD ON
515515
DA.UserID = UCD.UserID AND
516516
DA.CentreID = UCD.CentreID
517-
WHERE (DA.UserID = @delegateUserId)", new { supervisorId, delegateUserId, adminEmail });
517+
WHERE (DA.UserID = @delegateUserId AND DA.CentreID = @centreId)",
518+
new { supervisorId, delegateUserId, adminEmail, centreId });
518519
}
519520

520521
if (candidateAssessmentId > 0 && supervisorDelegateId > 0 && selfAssessmentSupervisorRoleId > 0)

DigitalLearningSolutions.Data/DataServices/SelfAssessmentDataService/SelfAssessmentDataService.cs

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -296,7 +296,12 @@ FROM SelfAssessments
296296
COALESCE(ucd.Email, u.PrimaryEmail) AS DelegateEmail,
297297
da.Active AS IsDelegateActive,
298298
sa.Name AS [Name],
299-
MAX(casv.Verified) as SignedOff,
299+
CASE
300+
WHEN MAX(sar.[DateTime]) >= MAX(casv.Verified) THEN NULL
301+
ELSE (
302+
MAX(casv.Verified)
303+
)
304+
END AS SignedOff,
300305
sa.SupervisorSelfAssessmentReview,
301306
sa.SupervisorResultsReview";
302307

@@ -311,6 +316,8 @@ LEFT OUTER JOIN Users AS uEnrolledBy WITH (NOLOCK) ON uEnrolledBy.ID = aaEnrolle
311316
LEFT JOIN dbo.CandidateAssessmentSupervisors AS cas WITH (NOLOCK) ON ca.ID = cas.CandidateAssessmentID
312317
LEFT JOIN dbo.CandidateAssessmentSupervisorVerifications AS casv WITH (NOLOCK) ON cas.ID = casv.CandidateAssessmentSupervisorID AND
313318
(casv.Verified IS NOT NULL AND casv.SignedOff = 1)
319+
LEFT JOIN SelfAssessmentResults AS sar ON ca.SelfAssessmentID = sar.SelfAssessmentID AND
320+
ca.DelegateUserID = sar.DelegateUserID
314321
315322
WHERE sa.ID = @selfAssessmentId
316323
AND da.CentreID = @centreID AND csa.CentreID = @centreID
@@ -349,7 +356,8 @@ LEFT JOIN dbo.CandidateAssessmentSupervisorVerifications AS casv WITH (NOLOCK) O
349356

350357
if (signedOff != null)
351358
{
352-
groupBy += (bool)signedOff ? " HAVING MAX(casv.Verified) IS NOT NULL " : " HAVING MAX(casv.Verified) IS NULL ";
359+
groupBy += (bool)signedOff ? " HAVING MAX(sar.[DateTime]) < MAX(casv.Verified) AND MAX(casv.Verified) IS NOT NULL " :
360+
" HAVING MAX(sar.[DateTime]) >= MAX(casv.Verified) OR MAX(casv.Verified) IS NULL ";
353361
}
354362

355363
string orderBy;

0 commit comments

Comments
 (0)