From 51ca74ba9c9937dd8f7f7978e22d0425e745fd24 Mon Sep 17 00:00:00 2001 From: Ryan Maffit Date: Tue, 11 Jun 2024 16:31:40 +0000 Subject: [PATCH] PSR list updates --- .../hq/src/app/models/PSR/get-PSR-v1.ts | 8 +- .../app/psr/psrlist/psrlist.component.html | 91 +++++++++---------- .../src/app/psr/psrlist/psrlist.component.ts | 1 + .../GetProjectStatusReportsV1.cs | 12 ++- .../20240611024751_AddedProjectStatus.cs | 1 + .../Services/ProjectStatusReportServiceV1.cs | 58 ++++++++++-- 6 files changed, 113 insertions(+), 58 deletions(-) diff --git a/src/angular/hq/src/app/models/PSR/get-PSR-v1.ts b/src/angular/hq/src/app/models/PSR/get-PSR-v1.ts index 8a5b87fd..17d768e1 100644 --- a/src/angular/hq/src/app/models/PSR/get-PSR-v1.ts +++ b/src/angular/hq/src/app/models/PSR/get-PSR-v1.ts @@ -36,7 +36,10 @@ export enum SortColumn { BookingHours = 16, BookingAvailableHours = 17, TotalPercentComplete = 18, - BookingPercentComplete = 19 + BookingPercentComplete = 19, + SummaryHoursTotal = 20, + SummaryHoursAvailable = 21, + SummaryPercentComplete = 22 } export interface GetPSRRecordV1 { @@ -68,6 +71,9 @@ export interface GetPSRRecordV1 { lastHours?: number; submittedAt?: Date | null; isLate: boolean; + summaryHoursTotal: number; + summaryHoursAvailable: number; + summaryPercentComplete: number; } export interface GetPSRRecordsV1 { diff --git a/src/angular/hq/src/app/psr/psrlist/psrlist.component.html b/src/angular/hq/src/app/psr/psrlist/psrlist.component.html index 74975535..fc334ce4 100644 --- a/src/angular/hq/src/app/psr/psrlist/psrlist.component.html +++ b/src/angular/hq/src/app/psr/psrlist/psrlist.component.html @@ -49,26 +49,18 @@

PSR

PM - Hrs This + Hrs This - Hrs Book - + Hrs Total + - Hrs Avl Book - + Hrs Available + - Hrs Total - - - Hrs Avl Total - - - Booking % - - - Total % - + Status + Complete % + @@ -80,7 +72,7 @@

No matching records found

} @for((report of projectStatusReports$ | async); track report.id) { - + {{report.chargeCode}} {{report.startDate}} {{report.endDate}} @@ -88,41 +80,44 @@

No matching records found

{{report.projectName}} {{report.projectManagerName}} {{report.thisHours | number: '0.2-2'}} - {{report.bookingHours | number: '0.2-2'}} - {{report.bookingAvailableHours | number: '0.2-2'}} - {{report.totalHours | number: '0.2-2'}} - {{report.totalAvailableHours | number: '0.2-2'}} + {{report.summaryHoursTotal | number: '0.2-2'}} + {{report.summaryHoursAvailable | number: '0.2-2'}} + {{getProjectSatusString(report.status)}} - @if(report.bookingPercentComplete && report.bookingPercentComplete > 1) { -
-
-
- } @else { -
-
-
+ @if(report.status == ProjectStatus.Ongoing) + { + @if(report.bookingPercentComplete && report.bookingPercentComplete > 1) { +
+
+
+ } @else { +
+
+
+ } +
+ {{ report.bookingHours | number: '0.2-2' }} hrs this {{ getPeriodName(report.bookingPeriod) }} to date + {{ report.bookingPercentComplete | percent }} +
} -
- {{ report.bookingHours | number: '0.2-2' }} hrs this {{ getPeriodName(report.bookingPeriod) }} to date - {{ report.bookingPercentComplete | percent }} -
- - - @if(report.totalPercentComplete && report.totalPercentComplete > 1) { -
-
-
- } @else { -
-
-
+ @if(report.status == ProjectStatus.InProduction) + { + @if(report.totalPercentComplete && report.totalPercentComplete > 1) { +
+
+
+ } @else { +
+
+
+ } +
+ {{ report.totalHours | number: '0.2-2' }} hrs total + {{ report.totalPercentComplete != null ? (report.totalPercentComplete | percent) : '-' }} +
} -
- {{ report.totalHours | number: '0.2-2' }} hrs total - {{ report.totalPercentComplete != null ? (report.totalPercentComplete | percent) : '-' }} -
- VIEW + VIEW } diff --git a/src/angular/hq/src/app/psr/psrlist/psrlist.component.ts b/src/angular/hq/src/app/psr/psrlist/psrlist.component.ts index f7cf4f1c..cc54e680 100644 --- a/src/angular/hq/src/app/psr/psrlist/psrlist.component.ts +++ b/src/angular/hq/src/app/psr/psrlist/psrlist.component.ts @@ -56,6 +56,7 @@ export class PSRListComponent implements OnInit, OnDestroy { Math = Math; sortColumn = SortColumn; sortDirection = SortDirection; + ProjectStatus = ProjectStatus; async ngOnInit() { this.psrListService.showSearch(); diff --git a/src/dotnet/HQ.Abstractions/ProjectStatusReports/GetProjectStatusReportsV1.cs b/src/dotnet/HQ.Abstractions/ProjectStatusReports/GetProjectStatusReportsV1.cs index 64050507..51a7b276 100644 --- a/src/dotnet/HQ.Abstractions/ProjectStatusReports/GetProjectStatusReportsV1.cs +++ b/src/dotnet/HQ.Abstractions/ProjectStatusReports/GetProjectStatusReportsV1.cs @@ -46,6 +46,9 @@ public enum SortColumn BookingAvailableHours = 17, TotalPercentComplete = 18, BookingPercentComplete = 19, + SummaryHoursTotal = 20, + SummaryHoursAvailable = 21, + SummaryPercentComplete = 22, } public class Response : PagedResponseV1 @@ -98,11 +101,16 @@ public class Record public DateOnly? TotalEndDate { get; set; } public DateOnly StartDate { get; set; } public DateOnly EndDate { get; set; } - public DateOnly BookingStartDate { get; set; } - public DateOnly BookingEndDate { get; set; } + public DateOnly? BookingStartDate { get; set; } + public DateOnly? BookingEndDate { get; set; } public Period BookingPeriod { get; set; } public Guid? LastId { get; set; } public decimal? LastHours { get; set; } public bool IsLate { get; set; } + + public decimal? SummaryHoursTotal { get; set; } + public decimal? SummaryHoursAvailable { get; set; } + public decimal? SummaryPercentComplete { get; set; } + public decimal? SummaryPercentCompleteSort { get; set; } } } diff --git a/src/dotnet/HQ.Server/Data/Migrations/20240611024751_AddedProjectStatus.cs b/src/dotnet/HQ.Server/Data/Migrations/20240611024751_AddedProjectStatus.cs index 195ed71f..4ad23d3b 100644 --- a/src/dotnet/HQ.Server/Data/Migrations/20240611024751_AddedProjectStatus.cs +++ b/src/dotnet/HQ.Server/Data/Migrations/20240611024751_AddedProjectStatus.cs @@ -20,6 +20,7 @@ protected override void Up(MigrationBuilder migrationBuilder) migrationBuilder.Sql("UPDATE projects p SET status = 5 FROM charge_codes c WHERE p.id = c.project_id AND c.code LIKE 'Q%'"); migrationBuilder.Sql("UPDATE projects p SET status = 6 FROM charge_codes c WHERE p.id = c.project_id AND c.code LIKE 'P%'"); migrationBuilder.Sql("UPDATE projects p SET status = 6 FROM charge_codes c WHERE p.id = c.project_id AND c.code LIKE 'S%'"); + migrationBuilder.Sql("UPDATE project_status_reports psr SET status = p.status FROM projects p WHERE p.id = psr.project_id"); } /// diff --git a/src/dotnet/HQ.Server/Services/ProjectStatusReportServiceV1.cs b/src/dotnet/HQ.Server/Services/ProjectStatusReportServiceV1.cs index f8983cf5..e4580fac 100644 --- a/src/dotnet/HQ.Server/Services/ProjectStatusReportServiceV1.cs +++ b/src/dotnet/HQ.Server/Services/ProjectStatusReportServiceV1.cs @@ -29,7 +29,7 @@ public ProjectStatusReportServiceV1(HQDbContext context) int createdCount = 0; int skippedCount = 0; - var projects = await _context.Projects.Where(t => t.ChargeCode != null && t.ChargeCode.Active) + var projects = await _context.Projects.Where(t => t.ChargeCode != null && t.ChargeCode.Active && (t.Status == ProjectStatus.InProduction || t.Status == ProjectStatus.Ongoing)) .ToListAsync(ct); DateOnly startDate = request.ForWeek.Value.AddDays(DayOfWeek.Monday - request.ForWeek.Value.DayOfWeek); @@ -164,8 +164,7 @@ public ProjectStatusReportServiceV1(HQDbContext context) .Select(t => new { Row = t, - Previous = _context.ProjectStatusReports.Where(x => x.ProjectId == t.ProjectId && x.StartDate < t.StartDate).OrderByDescending(x => x.StartDate).FirstOrDefault(), - Next = _context.ProjectStatusReports.Where(x => x.ProjectId == t.ProjectId && x.StartDate > t.EndDate).OrderBy(x => x.StartDate).FirstOrDefault() + Previous = _context.ProjectStatusReports.Where(x => x.ProjectId == t.ProjectId && x.StartDate < t.StartDate).OrderByDescending(x => x.StartDate).FirstOrDefault() }) .Select(t => new GetProjectStatusReportsV1.Record() { @@ -180,16 +179,18 @@ public ProjectStatusReportServiceV1(HQDbContext context) ClientId = t.Row.Project.Client.Id, ClientName = t.Row.Project.Client.Name, ProjectManagerName = t.Row.Project.ProjectManager != null ? t.Row.Project.ProjectManager.Name : null, - Status = t.Row.Project.Status, + Status = t.Row.Status, + IsLate = t.Row.SubmittedAt == null, + ThisHours = t.Row.Project.ChargeCode!.Times.Where(x => x.Date >= t.Row.StartDate && x.Date <= t.Row.EndDate).Sum(x => x.Hours), ThisPendingHours = t.Row.Project.ChargeCode!.Times.Where(x => x.Status != TimeStatus.Accepted && x.Date >= t.Row.StartDate && x.Date <= t.Row.EndDate).Sum(x => x.Hours), + LastId = t.Previous != null ? t.Previous.Id : null, LastHours = t.Previous != null && t.Previous.Project.ChargeCode != null ? t.Previous.Project.ChargeCode.Times.Where(x => x.Date >= t.Previous.StartDate && x.Date <= t.Previous.EndDate).Sum(x => x.Hours) : null, - IsLate = t.Next != null && t.Row.SubmittedAt == null, BookingPeriod = t.Row.BookingPeriod, - BookingStartDate = t.Row.BookingStartDate, - BookingEndDate = t.Row.BookingEndDate, + BookingStartDate = t.Row.Project.ChargeCode!.Times.Where(x => x.Date >= t.Row.BookingStartDate && x.Date <= t.Row.BookingEndDate && x.Date <= t.Row.EndDate).Min(x => x.Date), + BookingEndDate = t.Row.Project.ChargeCode!.Times.Where(x => x.Date >= t.Row.BookingStartDate && x.Date <= t.Row.BookingEndDate && x.Date <= t.Row.EndDate).Max(x => x.Date), BookingHours = t.Row.Project.ChargeCode!.Times.Where(x => x.Date >= t.Row.BookingStartDate && x.Date <= t.Row.BookingEndDate && x.Date <= t.Row.EndDate).Sum(x => x.Hours), BookingAvailableHours = t.Row.Project.BookingHours - t.Row.Project.ChargeCode!.Times.Where(x => x.Date >= t.Row.BookingStartDate && x.Date <= t.Row.BookingEndDate && x.Date <= t.Row.EndDate).Sum(x => x.Hours), BookingPercentComplete = t.Row.Project.BookingHours == 0 ? 0 : t.Row.Project.ChargeCode!.Times.Where(x => x.Date >= t.Row.BookingStartDate && x.Date <= t.Row.BookingEndDate && x.Date <= t.Row.EndDate).Sum(x => x.Hours) / t.Row.Project.BookingHours, @@ -200,6 +201,46 @@ public ProjectStatusReportServiceV1(HQDbContext context) TotalPercentCompleteSort = !t.Row.Project.TotalHours.HasValue || t.Row.Project.TotalHours == 0 ? -1 : t.Row.Project.ChargeCode!.Times.Where(x => x.Date <= t.Row.EndDate).Sum(x => x.Hours) / t.Row.Project.TotalHours.Value, TotalStartDate = t.Row.Project.ChargeCode.Times.Where(x => x.Date <= t.Row.EndDate).Min(t => t.Date), TotalEndDate = t.Row.Project.ChargeCode.Times.Where(x => x.Date <= t.Row.EndDate).Max(t => t.Date), + }) + .Select(t => new GetProjectStatusReportsV1.Record() { + Id = t.Id, + Report = t.Report, + SubmittedAt = t.SubmittedAt, + StartDate = t.StartDate, + EndDate = t.EndDate, + ChargeCode = t.ChargeCode, + ProjectName = t.ProjectName, + ProjectId = t.ProjectId, + ClientId = t.ClientId, + ClientName = t.ClientName, + ProjectManagerName = t.ProjectManagerName, + Status = t.Status, + IsLate = t.IsLate, + + ThisHours = t.ThisHours, + ThisPendingHours = t.ThisPendingHours, + + LastId = t.LastId, + LastHours = t.LastHours, + + BookingPeriod = t.BookingPeriod, + BookingStartDate = t.BookingStartDate, + BookingEndDate = t.BookingEndDate, + BookingHours = t.BookingHours, + BookingAvailableHours = t.BookingAvailableHours, + BookingPercentComplete = t.BookingPercentComplete, + + TotalHours = t.TotalHours, + TotalAvailableHours = t.TotalAvailableHours, + TotalPercentComplete = t.TotalPercentComplete, + TotalPercentCompleteSort = t.TotalPercentCompleteSort, + TotalStartDate = t.TotalStartDate, + TotalEndDate = t.TotalEndDate, + + SummaryHoursTotal = t.Status == ProjectStatus.Ongoing ? t.BookingHours : t.TotalHours, + SummaryHoursAvailable = t.Status == ProjectStatus.Ongoing ? t.BookingAvailableHours : t.TotalAvailableHours, + SummaryPercentComplete = t.Status == ProjectStatus.Ongoing ? t.BookingPercentComplete : t.TotalPercentComplete, + SummaryPercentCompleteSort = t.Status == ProjectStatus.Ongoing ? t.BookingPercentComplete : t.TotalPercentCompleteSort }); var totalHours = await mapped.SumAsync(t => t.TotalHours, ct); @@ -226,6 +267,9 @@ public ProjectStatusReportServiceV1(HQDbContext context) { Abstractions.ProjectStatusReports.GetProjectStatusReportsV1.SortColumn.BookingAvailableHours, "BookingAvailableHours" }, { Abstractions.ProjectStatusReports.GetProjectStatusReportsV1.SortColumn.TotalPercentComplete, "TotalPercentCompleteSort" }, { Abstractions.ProjectStatusReports.GetProjectStatusReportsV1.SortColumn.BookingPercentComplete, "BookingPercentComplete" }, + { Abstractions.ProjectStatusReports.GetProjectStatusReportsV1.SortColumn.SummaryHoursTotal, "SummaryHoursTotal" }, + { Abstractions.ProjectStatusReports.GetProjectStatusReportsV1.SortColumn.SummaryHoursAvailable, "SummaryHoursAvailable" }, + { Abstractions.ProjectStatusReports.GetProjectStatusReportsV1.SortColumn.SummaryPercentComplete, "SummaryPercentCompleteSort" }, }; var sortProperty = sortMap[request.SortBy];