From 3f739daba954c888914816c1d6c75b36fb60e024 Mon Sep 17 00:00:00 2001 From: Aleksander Lund Date: Sun, 17 Dec 2023 23:33:51 +0100 Subject: [PATCH] Fixing text for Average time to handle request + Change the way we calculate workload --- .../AdaptiveCards/AdaptiveCardBuilder.cs | 21 +++-- .../ResourceOwnerAdaptiveCardData.cs | 2 +- .../Notifications/Models/PersonnelContent.cs | 1 - .../ScheduledReportContentBuilderFunction.cs | 77 ++++++++++--------- 4 files changed, 57 insertions(+), 44 deletions(-) diff --git a/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/Models/AdaptiveCards/AdaptiveCardBuilder.cs b/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/Models/AdaptiveCards/AdaptiveCardBuilder.cs index fd3eae07b..83be96ab7 100644 --- a/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/Models/AdaptiveCards/AdaptiveCardBuilder.cs +++ b/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/Models/AdaptiveCards/AdaptiveCardBuilder.cs @@ -78,14 +78,25 @@ public AdaptiveCardBuilder AddListContainer(string headerText, IEnumerable + { new AdaptiveActionSet() { + Actions = new List + { + new AdaptiveOpenUrlAction() + { + Title = title, + Url = new Uri(url) + } + } + } + } }; - _adaptiveCard.Actions.Add(actionButton); + _adaptiveCard.Body.Add(listContainer); + return this; } public AdaptiveCard Build() diff --git a/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/Models/AdaptiveCards/ResourceOwnerAdaptiveCardData.cs b/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/Models/AdaptiveCards/ResourceOwnerAdaptiveCardData.cs index 00178fa00..890d4a1c4 100644 --- a/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/Models/AdaptiveCards/ResourceOwnerAdaptiveCardData.cs +++ b/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/Models/AdaptiveCards/ResourceOwnerAdaptiveCardData.cs @@ -10,7 +10,7 @@ public class ResourceOwnerAdaptiveCardData public int NumberOfOpenRequests { get; set; } public int NumberOfRequestsStartingInMoreThanThreeMonths { get; set; } public int NumberOfRequestsStartingInLessThanThreeMonths { get; set; } - public double AverageTimeToHandleRequests { get; set; } + public string AverageTimeToHandleRequests { get; set; } public int AllocationChangesAwaitingTaskOwnerAction { get; set; } public int ProjectChangesAffectingNextThreeMonths { get; set; } internal IEnumerable PersonnelPositionsEndingWithNoFutureAllocation { get; set; } diff --git a/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/Models/PersonnelContent.cs b/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/Models/PersonnelContent.cs index 5592c2c8b..51a26eab5 100644 --- a/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/Models/PersonnelContent.cs +++ b/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/Models/PersonnelContent.cs @@ -10,7 +10,6 @@ public class PersonnelContent public string? ProjectName { get; set; } public string? PositionName { get; set; } public double? TotalWorkload { get; set; } - public int? NumberOfPositionInstances { get; set; } public PersonnelPosition? EndingPosition { get; set; } public PersonnelContent() { } diff --git a/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/ScheduledReportContentBuilderFunction.cs b/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/ScheduledReportContentBuilderFunction.cs index a1c941338..3546516ff 100644 --- a/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/ScheduledReportContentBuilderFunction.cs +++ b/src/backend/function/Fusion.Resources.Functions/Functions/Notifications/ScheduledReportContentBuilderFunction.cs @@ -20,6 +20,7 @@ using Fusion.Integration.Configuration; using Fusion.Integration.ServiceDiscovery; using Microsoft.Extensions.Configuration; +using System.Data; namespace Fusion.Resources.Functions.Functions.Notifications; @@ -147,40 +148,36 @@ private async Task BuildContentForResourceOwner(Guid azureUniqueId, string fullD var averageTimeToHandleRequest = CalculateAverageTimeToHandleRequests(departmentRequests); //8.Allocation changes awaiting task owner action: - //number of allocation changes made by resource owner awaiting task owner action - //M� hente ut alle posisjoner som har ressurser for en gitt avdeling og sjekke p� om det er gjort endringer her den siste tiden var numberOfAllocationchangesAwaitingTaskOwnerAction = GetchangesAwaitingTaskOwnerAction(departmentRequests); //9.Project changes affecting next 3 months - //number of project changes(changes initiated by project / task) with a change affecting the next 3 months var numberOfChangesAffectingNextThreeMonths = GetAllChangesForResourceDepartment(personnelForDepartment); //10.Allocations ending soon with no future allocation var listOfPersonnelWithoutFutureAllocations = FilterPersonnelWithoutFutureAllocations(personnelForDepartment); //11.Personnel with more than 100 % workload - var listOfPersonnelsWithMoreThan100Percent = personnelForDepartment.Where(p => - p.PositionInstances.Where(pos => pos.IsActive).Select(pos => pos.Workload).Sum() > 100); - var listOfPersonnelForDepartmentWithMoreThan100Percent = - listOfPersonnelsWithMoreThan100Percent.Select(p => CreatePersonnelWithTBEContent(p)); + var listOfPersonnelWithTBEContent = + personnelForDepartment.Select(p => CreatePersonnelWithTBEContent(p)); + var listOfPersonnelWithTBEContentOnlyMoreThan100PercentWorkload = listOfPersonnelWithTBEContent.Where(p => p.TotalWorkload > 100); var card = ResourceOwnerAdaptiveCardBuilder(new ResourceOwnerAdaptiveCardData - { - TotalNumberOfPersonnel = numberOfPersonnel, - TotalCapacityInUsePercentage = percentageOfTotalCapacity, - NumberOfRequestsLastWeek = numberOfRequestsLastWeek, - NumberOfOpenRequests = totalNumberOfOpenRequests, - NumberOfRequestsStartingInMoreThanThreeMonths = + { + TotalNumberOfPersonnel = numberOfPersonnel, + TotalCapacityInUsePercentage = percentageOfTotalCapacity, + NumberOfRequestsLastWeek = numberOfRequestsLastWeek, + NumberOfOpenRequests = totalNumberOfOpenRequests, + NumberOfRequestsStartingInMoreThanThreeMonths = numberOfDepartmentRequestWithMoreThanThreeMonthsBeforeStart, - NumberOfRequestsStartingInLessThanThreeMonths = + NumberOfRequestsStartingInLessThanThreeMonths = numberOfDepartmentRequestWithLessThanThreeMonthsBeforeStartAndNoNomination, - AverageTimeToHandleRequests = averageTimeToHandleRequest, - AllocationChangesAwaitingTaskOwnerAction = numberOfAllocationchangesAwaitingTaskOwnerAction, - ProjectChangesAffectingNextThreeMonths = numberOfChangesAffectingNextThreeMonths, - PersonnelPositionsEndingWithNoFutureAllocation = listOfPersonnelWithoutFutureAllocations, - PersonnelAllocatedMoreThan100Percent = listOfPersonnelForDepartmentWithMoreThan100Percent - }, + AverageTimeToHandleRequests = averageTimeToHandleRequest, + AllocationChangesAwaitingTaskOwnerAction = numberOfAllocationchangesAwaitingTaskOwnerAction, + ProjectChangesAffectingNextThreeMonths = numberOfChangesAffectingNextThreeMonths, + PersonnelPositionsEndingWithNoFutureAllocation = listOfPersonnelWithoutFutureAllocations, + PersonnelAllocatedMoreThan100Percent = listOfPersonnelWithTBEContentOnlyMoreThan100PercentWorkload + }, fullDepartment, departmentSapId); var sendNotification = await _notificationsClient.SendNotification( @@ -205,9 +202,8 @@ private IEnumerable FilterPersonnelWithoutFutureAllocations( IEnumerable personnelForDepartment) { var threeMonthsFuture = DateTime.UtcNow.AddMonths(3); - var personnelWithPositionsEndingInThreeMonths = personnelForDepartment.Where(x => - x.PositionInstances.Where(pos => pos.IsActive && pos.AppliesTo <= threeMonthsFuture).Any()); + x.PositionInstances.Where(pos => pos.IsActive && pos.AppliesTo <= threeMonthsFuture).Any()); var personnelWithoutFutureAllocations = personnelWithPositionsEndingInThreeMonths.Where(person => person.PositionInstances.All(pos => pos.AppliesTo < threeMonthsFuture)); return personnelWithoutFutureAllocations.Select(p => CreatePersonnelContent(p)); @@ -293,19 +289,20 @@ private int GetchangesAwaitingTaskOwnerAction(IEnumerable listOfRequests) + private string CalculateAverageTimeToHandleRequests(IEnumerable listOfRequests) { - /* How to calculate: - * + /* + * How to calculate: * Find the workflow "created" and then find the date * This should mean that task owner have created and sent the request to resource owner * Find the workflow "proposal" and then find the date * This should mean that the resource owner have done their bit - * TODO: Maybe we need to consider other states - */ + */ + var requestsHandledByResourceOwner = 0; var totalNumberOfDays = 0.0; + var averageTimeUsedToHandleRequest = "NA"; var threeMonthsAgo = DateTime.UtcNow.AddMonths(-3); @@ -333,10 +330,15 @@ private double CalculateAverageTimeToHandleRequests(IEnumerable 0)) - return 0; + if (totalNumberOfDays > 0) + { + var averageAmountOfTimeDouble = totalNumberOfDays / requestsHandledByResourceOwner; + // To get whole number + int averageAmountOfTimeInt = Convert.ToInt32(averageAmountOfTimeDouble); - return totalNumberOfDays / requestsHandledByResourceOwner; + averageTimeUsedToHandleRequest = averageAmountOfTimeInt >= 1 ? averageAmountOfTimeInt.ToString() + " day(s)" : "Less than a day"; + } + return averageTimeUsedToHandleRequest; } private PersonnelContent CreatePersonnelContent(InternalPersonnelPerson person) @@ -359,15 +361,16 @@ private PersonnelContent CreatePersonnelContent(InternalPersonnelPerson person) private PersonnelContent CreatePersonnelWithTBEContent(InternalPersonnelPerson person) { - var positionInstances = person.PositionInstances.Where(pos => pos.IsActive); - var sumWorkload = positionInstances.Select(pos => pos.Workload).Sum(); - var numberOfPositionInstances = positionInstances.Count(); + var totalWorkLoad = person.ApiPersonAbsences? + .Where(ab => ab.Type != ApiAbsenceType.Absence && ab.IsActive).Select(ab => ab.AbsencePercentage).Sum(); + totalWorkLoad += person.PositionInstances?.Where(pos => pos.IsActive).Select(pos => pos.Workload).Sum(); + var personnelContent = new PersonnelContent() { FullName = person.Name, - TotalWorkload = sumWorkload, - NumberOfPositionInstances = numberOfPositionInstances, + TotalWorkload = totalWorkLoad, }; + return personnelContent; } @@ -388,8 +391,8 @@ private async Task ResourceOwnerAdaptiveCardBuilder(ResourceOwnerA .AddColumnSet(new AdaptiveCardColumn(cardData.NumberOfRequestsStartingInMoreThanThreeMonths.ToString(), "Requests with start date > 3 months")) .AddColumnSet(new AdaptiveCardColumn( - cardData.AverageTimeToHandleRequests.ToString(FormatDoubleToHaveOneDecimal), - "Average time to handle request", "days")) + cardData.AverageTimeToHandleRequests, + "Average time to handle request")) .AddColumnSet(new AdaptiveCardColumn(cardData.AllocationChangesAwaitingTaskOwnerAction.ToString(), "Allocation changes awaiting task owner action")) .AddColumnSet(new AdaptiveCardColumn(cardData.ProjectChangesAffectingNextThreeMonths.ToString(),