/// <summary> /// Get an Owner record /// </summary> /// <param name="id"></param> /// <param name="context"></param> /// <param name="configuration"></param> /// <returns></returns> public static HetOwner GetRecord(int id, DbAppContext context, IConfiguration configuration) { // get equipment status types int?statusIdArchived = StatusHelper.GetStatusId(HetEquipment.StatusArchived, "equipmentStatus", context); if (statusIdArchived == null) { throw new ArgumentException("Status Code not found"); } // get owner record HetOwner owner = context.HetOwner.AsNoTracking() .Include(x => x.OwnerStatusType) .Include(x => x.LocalArea.ServiceArea.District.Region) .Include(x => x.HetEquipment) .ThenInclude(y => y.LocalArea.ServiceArea.District.Region) .Include(x => x.HetEquipment) .ThenInclude(y => y.DistrictEquipmentType) .ThenInclude(z => z.EquipmentType) .Include(x => x.HetEquipment) .ThenInclude(y => y.Owner) .ThenInclude(c => c.PrimaryContact) .Include(x => x.HetEquipment) .ThenInclude(y => y.EquipmentStatusType) .Include(x => x.HetEquipment) .ThenInclude(y => y.HetEquipmentAttachment) .Include(x => x.HetContact) .Include(x => x.PrimaryContact) .FirstOrDefault(a => a.OwnerId == id); if (owner != null) { // remove any archived equipment owner.HetEquipment = owner.HetEquipment.Where(e => e.EquipmentStatusTypeId != statusIdArchived).ToList(); // populate the "Status" description owner.Status = owner.OwnerStatusType.OwnerStatusTypeCode; foreach (HetEquipment equipment in owner.HetEquipment) { equipment.IsHired = EquipmentHelper.IsHired(id, context); equipment.NumberOfBlocks = EquipmentHelper.GetNumberOfBlocks(equipment, configuration); equipment.HoursYtd = EquipmentHelper.GetYtdServiceHours(id, context); equipment.Status = equipment.EquipmentStatusType.EquipmentStatusTypeCode; equipment.EquipmentNumber = int.Parse(Regex.Match(equipment.EquipmentCode, @"\d+").Value); } // HETS-1115 - Do not allow changing seniority affecting entities if an active request exists owner.ActiveRentalRequest = RentalRequestStatus(id, context); } return(owner); }
public static TimeRecordLite GetTimeRecords(int id, DbAppContext context, IConfiguration configuration) { HetRentalAgreement agreement = context.HetRentalAgreement.AsNoTracking() .Include(x => x.Equipment) .ThenInclude(y => y.DistrictEquipmentType) .ThenInclude(z => z.EquipmentType) .Include(x => x.Project) .Include(x => x.HetTimeRecord) .First(x => x.RentalAgreementId == id); // get the max hours for this equipment type float? hoursYtd = 0.0F; int maxHours = 0; string equipmentCode = ""; if (agreement.Equipment?.EquipmentId != null && agreement.Equipment.DistrictEquipmentType?.EquipmentType != null) { maxHours = Convert.ToInt32(agreement.Equipment.DistrictEquipmentType.EquipmentType.IsDumpTruck ? configuration.GetSection("MaximumHours:DumpTruck").Value : configuration.GetSection("MaximumHours:Default").Value); int equipmentId = agreement.Equipment.EquipmentId; hoursYtd = EquipmentHelper.GetYtdServiceHours(equipmentId, context); equipmentCode = agreement.Equipment.EquipmentCode; } // get the project info string projectName = ""; string projectNumber = ""; if (agreement.Project != null) { projectName = agreement.Project.Name; projectNumber = agreement.Project.ProvincialProjectNumber; } TimeRecordLite timeRecord = new TimeRecordLite { TimeRecords = new List <HetTimeRecord>() }; timeRecord.TimeRecords.AddRange(agreement.HetTimeRecord); timeRecord.EquipmentCode = equipmentCode; timeRecord.ProjectName = projectName; timeRecord.ProvincialProjectNumber = projectNumber; timeRecord.HoursYtd = hoursYtd; timeRecord.MaximumHours = maxHours; return(timeRecord); }
/// <summary> /// Get an Owner record /// </summary> /// <param name="id"></param> /// <param name="context"></param> /// <param name="configuration"></param> /// <returns></returns> public static HetOwner GetRecord(int id, DbAppContext context, IConfiguration configuration) { HetOwner owner = context.HetOwner.AsNoTracking() .Include(x => x.OwnerStatusType) .Include(x => x.LocalArea.ServiceArea.District.Region) .Include(x => x.HetEquipment) .ThenInclude(y => y.LocalArea.ServiceArea.District.Region) .Include(x => x.HetEquipment) .ThenInclude(y => y.DistrictEquipmentType) .ThenInclude(z => z.EquipmentType) .Include(x => x.HetEquipment) .ThenInclude(y => y.Owner) .ThenInclude(c => c.PrimaryContact) .Include(x => x.HetEquipment) .ThenInclude(y => y.EquipmentStatusType) .Include(x => x.HetEquipment) .ThenInclude(y => y.HetEquipmentAttachment) .Include(x => x.HetContact) .Include(x => x.PrimaryContact) .FirstOrDefault(a => a.OwnerId == id); if (owner != null) { // remove any archived equipment owner.HetEquipment = owner.HetEquipment.Where(e => e.EquipmentStatusType.EquipmentStatusTypeCode != HetEquipment.StatusArchived).ToList(); // populate the "Status" description owner.Status = owner.OwnerStatusType.OwnerStatusTypeCode; foreach (HetEquipment equipment in owner.HetEquipment) { equipment.IsHired = EquipmentHelper.IsHired(id, context); equipment.NumberOfBlocks = EquipmentHelper.GetNumberOfBlocks(equipment, configuration); equipment.HoursYtd = EquipmentHelper.GetYtdServiceHours(id, context); equipment.Status = equipment.EquipmentStatusType.EquipmentStatusTypeCode; equipment.EquipmentNumber = int.Parse(Regex.Match(equipment.EquipmentCode, @"\d+").Value); } } return(owner); }
/// <summary> /// Get rental request record /// </summary> /// <param name="id"></param> /// <param name="context"></param> public static HetRentalRequest GetRecord(int id, DbAppContext context) { HetRentalRequest request = context.HetRentalRequest.AsNoTracking() .Include(x => x.RentalRequestStatusType) .Include(x => x.LocalArea.ServiceArea.District.Region) .Include(x => x.Project) .ThenInclude(c => c.PrimaryContact) .Include(x => x.Project) .ThenInclude(c => c.ProjectStatusType) .Include(x => x.HetRentalRequestAttachment) .Include(x => x.DistrictEquipmentType) .Include(x => x.HetRentalRequestRotationList) .ThenInclude(y => y.Equipment) .ThenInclude(z => z.EquipmentStatusType) .FirstOrDefault(a => a.RentalRequestId == id); if (request != null) { request.Status = request.RentalRequestStatusType.RentalRequestStatusTypeCode; // calculate the Yes Count based on the RentalRequestList request.YesCount = CalculateYesCount(request); // calculate YTD hours for the equipment records if (request.HetRentalRequestRotationList != null) { foreach (HetRentalRequestRotationList rotationList in request.HetRentalRequestRotationList) { if (rotationList.Equipment != null) { rotationList.Equipment.HoursYtd = EquipmentHelper.GetYtdServiceHours(rotationList.Equipment.EquipmentId, context); } } } } return(request); }
public static TimeRecordLite GetTimeRecords(int id, int?districtId, DbAppContext context, IConfiguration configuration) { // get fiscal year HetDistrictStatus status = context.HetDistrictStatus.AsNoTracking() .First(x => x.DistrictId == districtId); int?fiscalYear = status.CurrentFiscalYear; // get agreement and time records HetRentalAgreement agreement = context.HetRentalAgreement.AsNoTracking() .Include(x => x.Equipment) .ThenInclude(y => y.DistrictEquipmentType) .ThenInclude(z => z.EquipmentType) .Include(x => x.Project) .Include(x => x.HetTimeRecord) .First(x => x.RentalAgreementId == id); // get the max hours for this equipment type float? hoursYtd = 0.0F; int maxHours = 0; string equipmentCode = ""; if (agreement.Equipment?.EquipmentId != null && agreement.Equipment.DistrictEquipmentType?.EquipmentType != null) { maxHours = Convert.ToInt32(agreement.Equipment.DistrictEquipmentType.EquipmentType.IsDumpTruck ? configuration.GetSection("MaximumHours:DumpTruck").Value : configuration.GetSection("MaximumHours:Default").Value); int equipmentId = agreement.Equipment.EquipmentId; hoursYtd = EquipmentHelper.GetYtdServiceHours(equipmentId, context); equipmentCode = agreement.Equipment.EquipmentCode; } // get the project info string projectName = ""; string projectNumber = ""; if (agreement.Project != null) { projectName = agreement.Project.Name; projectNumber = agreement.Project.ProvincialProjectNumber; } // fiscal year in the status table stores the "start" of the year TimeRecordLite timeRecord = new TimeRecordLite(); if (fiscalYear != null) { DateTime fiscalYearStart = new DateTime((int)fiscalYear, 4, 1); timeRecord.TimeRecords = new List <HetTimeRecord>(); timeRecord.TimeRecords.AddRange(agreement.HetTimeRecord.Where(x => x.WorkedDate >= fiscalYearStart)); } timeRecord.EquipmentCode = equipmentCode; timeRecord.ProjectName = projectName; timeRecord.ProvincialProjectNumber = projectNumber; timeRecord.HoursYtd = hoursYtd; timeRecord.MaximumHours = maxHours; return(timeRecord); }
/// <summary> /// Seniority List view model /// </summary> /// <param name="model"></param> /// <param name="scoringRules"></param> /// <param name="rotationList"></param> /// <param name="context"></param> /// <returns></returns> public static SeniorityViewModel ToSeniorityViewModel(HetEquipment model, SeniorityScoringRules scoringRules, HetRentalRequestRotationList rotationList, DbAppContext context) { SeniorityViewModel seniorityViewModel = new SeniorityViewModel(); if (model == null) { return(seniorityViewModel); } int numberOfBlocks = 0; // get number of blocks for this equipment type if (model.DistrictEquipmentType != null) { numberOfBlocks = model.DistrictEquipmentType.EquipmentType.IsDumpTruck ? scoringRules.GetTotalBlocks("DumpTruck") + 1 : scoringRules.GetTotalBlocks() + 1; } // get equipment block number int blockNumber = 0; if (model.BlockNumber != null) { blockNumber = (int)model.BlockNumber; } // get equipment block number int numberInBlock = 0; if (model.NumberInBlock != null) { numberInBlock = (int)model.NumberInBlock; } // ************************************************************* // check if this record/owner was called last // ************************************************************* bool callLast = rotationList != null && rotationList.EquipmentId == model.EquipmentId; seniorityViewModel.LastCalled = callLast ? "Y" : " "; // ************************************************************* // map data to view model // ************************************************************* seniorityViewModel.Id = model.EquipmentId; if (model.DistrictEquipmentType != null) { seniorityViewModel.EquipmentType = model.DistrictEquipmentType.DistrictEquipmentName; } if (model.Owner != null) { seniorityViewModel.OwnerName = model.Owner.OrganizationName; seniorityViewModel.OwnerId = model.OwnerId; } // replacing Open with 3 (HETS-968 Rotation list -Wrong Block number for Open block) seniorityViewModel.Block = blockNumber == numberOfBlocks ? "3" : blockNumber.ToString(); // format the seniority value seniorityViewModel.Seniority = $"{model.Seniority:0.###}"; // format year / make / model / size seniorityViewModel.YearMakeModelSize = $"{model.Year}/{model.Make}/{model.Model}/{model.Size}"; seniorityViewModel.EquipmentCode = model.EquipmentCode; seniorityViewModel.YearsRegistered = model.YearsOfService.ToString(); // Determine if this equipment is currently hired seniorityViewModel.IsHired = EquipmentHelper.IsHired(model.EquipmentId, context) ? "Y" : "N"; // calculate and format the ytd hours float tempHours = EquipmentHelper.GetYtdServiceHours(model.EquipmentId, context); seniorityViewModel.YtdHours = string.Format("{0:0.###}", tempHours); // format the hours seniorityViewModel.HoursYearMinus1 = string.Format("{0:0.###}", model.ServiceHoursLastYear); seniorityViewModel.HoursYearMinus2 = string.Format("{0:0.###}", model.ServiceHoursTwoYearsAgo); seniorityViewModel.HoursYearMinus3 = string.Format("{0:0.###}", model.ServiceHoursThreeYearsAgo); // add the correct sorting order (numeric) seniorityViewModel.SenioritySortOrder = EquipmentHelper.CalculateSenioritySortOrder(blockNumber, numberInBlock); return(seniorityViewModel); }
/// <summary> /// Get rental request record /// </summary> /// <param name="id"></param> /// <param name="scoringRules"></param> /// <param name="context"></param> public static HetRentalRequest GetRecordWithRotationList(int id, SeniorityScoringRules scoringRules, DbAppContext context) { HetRentalRequest request = context.HetRentalRequest.AsNoTracking() .Include(x => x.DistrictEquipmentType) .ThenInclude(y => y.EquipmentType) .Include(x => x.FirstOnRotationList) .Include(x => x.HetRentalRequestAttachment) .Include(x => x.HetRentalRequestRotationList) .ThenInclude(y => y.Equipment) .ThenInclude(r => r.HetEquipmentAttachment) .Include(x => x.HetRentalRequestRotationList) .ThenInclude(y => y.Equipment) .ThenInclude(r => r.LocalArea) .Include(x => x.HetRentalRequestRotationList) .ThenInclude(y => y.Equipment) .ThenInclude(r => r.DistrictEquipmentType) .Include(x => x.HetRentalRequestRotationList) .ThenInclude(y => y.Equipment) .ThenInclude(e => e.Owner) .ThenInclude(c => c.PrimaryContact) .FirstOrDefault(a => a.RentalRequestId == id); if (request != null) { // re-sort list using: LocalArea / District Equipment Type and SenioritySortOrder (desc) request.HetRentalRequestRotationList = request.HetRentalRequestRotationList .OrderBy(e => e.RotationListSortOrder) .ToList(); // calculate the Yes Count based on the RentalRequestList request.YesCount = CalculateYesCount(request); // calculate YTD hours for the equipment records if (request.HetRentalRequestRotationList != null) { foreach (HetRentalRequestRotationList rotationList in request.HetRentalRequestRotationList) { if (rotationList.Equipment != null) { int numberOfBlocks = 0; // get number of blocks for this equipment type if (rotationList.Equipment.DistrictEquipmentType != null) { numberOfBlocks = rotationList.Equipment.DistrictEquipmentType.EquipmentType.IsDumpTruck ? scoringRules.GetTotalBlocks("DumpTruck") + 1 : scoringRules.GetTotalBlocks() + 1; } // get equipment seniority float seniority = 0F; if (rotationList.Equipment.Seniority != null) { seniority = (float)rotationList.Equipment.Seniority; } // get equipment block number int blockNumber = 0; if (rotationList.Equipment.BlockNumber != null) { blockNumber = (int)rotationList.Equipment.BlockNumber; //HETS-968 - Rotation list -Wrong Block number for Open block if (blockNumber == numberOfBlocks) { blockNumber = 3; rotationList.Equipment.BlockNumber = blockNumber; } } rotationList.Equipment.HoursYtd = EquipmentHelper.GetYtdServiceHours(rotationList.Equipment.EquipmentId, context); rotationList.Equipment.SeniorityString = EquipmentHelper.FormatSeniorityString(seniority, blockNumber, numberOfBlocks); } } } } return(request); }
/// <summary> /// Annual Rollover /// </summary> /// <param name="context"></param> /// <param name="districtId"></param> /// <param name="seniorityScoringRules"></param> /// <param name="connectionString"></param> public static void AnnualRolloverJob(PerformContext context, int districtId, string seniorityScoringRules, string connectionString) { try { // open a connection to the database DbAppContext dbContext = new DbAppContext(connectionString); // get processing rules SeniorityScoringRules scoringRules = new SeniorityScoringRules(seniorityScoringRules); // update progress bar IProgressBar progress = context.WriteProgressBar(); context.WriteLine("Starting Annual Rollover Job - District #" + districtId); progress.SetValue(0); // validate district id HetDistrict district = dbContext.HetDistrict.AsNoTracking() .FirstOrDefault(x => x.DistrictId == districtId); if (district == null) { context.WriteLine("District not found"); progress.SetValue(100); return; } // get status record - and ensure we're active HetDistrictStatus status = GetRecord(districtId, dbContext); if (status == null) { context.WriteLine("District Status not found"); progress.SetValue(100); return; } // get equipment status int?statusId = StatusHelper.GetStatusId(HetEquipment.StatusApproved, "equipmentStatus", dbContext); if (statusId == null) { context.WriteLine("Equipment Status not found"); progress.SetValue(100); return; } // determine the "Rollover Date" (required for testing) DateTime rolloverDate; if (DateTime.UtcNow.Month == 1 || DateTime.UtcNow.Month == 2 || DateTime.UtcNow.Month == 3) { if (status.NextFiscalYear == null) { status.NextFiscalYear = DateTime.UtcNow.Year; } rolloverDate = new DateTime((int)status.NextFiscalYear, DateTime.UtcNow.Month, DateTime.UtcNow.Day); } else { if (status.CurrentFiscalYear == null) { status.CurrentFiscalYear = DateTime.UtcNow.Year; } rolloverDate = new DateTime((int)status.CurrentFiscalYear, DateTime.UtcNow.Month, DateTime.UtcNow.Day); } // get all district equipment types List <HetDistrictEquipmentType> equipmentTypes = dbContext.HetDistrictEquipmentType.AsNoTracking() .Include(x => x.EquipmentType) .Where(x => x.DistrictId == districtId).ToList(); // get all local areas List <HetLocalArea> localAreas = dbContext.HetLocalArea.AsNoTracking() .Where(a => a.ServiceArea.DistrictId == districtId).ToList(); // update status - job is kicked off int localAreaCompleteCount = 0; int equipmentCompleteCount = 0; UpdateStatusKickoff(dbContext, status, localAreaCompleteCount, equipmentCompleteCount); // process all local areas and equipment types foreach (HetLocalArea localArea in localAreas.WithProgress(progress)) { // re-open the connection dbContext = new DbAppContext(connectionString); if (localArea.Name != null) { context.WriteLine("Local Area: " + localArea.Name); } else { context.WriteLine("Local Area ID: " + localArea.LocalAreaId); } // reset equipment counter equipmentCompleteCount = 0; foreach (HetDistrictEquipmentType equipmentType in equipmentTypes) { // it this a dump truck? bool isDumpTruck = equipmentType.EquipmentType.IsDumpTruck; // get rules for scoring and seniority block int seniorityScoring = isDumpTruck ? scoringRules.GetEquipmentScore("DumpTruck") : scoringRules.GetEquipmentScore(); int blockSize = isDumpTruck ? scoringRules.GetBlockSize("DumpTruck") : scoringRules.GetBlockSize(); int totalBlocks = isDumpTruck ? scoringRules.GetTotalBlocks("DumpTruck") : scoringRules.GetTotalBlocks(); using (DbAppContext etContext = new DbAppContext(connectionString)) { List <HetEquipment> data = etContext.HetEquipment .Include(x => x.LocalArea) .Include(x => x.DistrictEquipmentType.EquipmentType) .Where(x => x.EquipmentStatusTypeId == statusId && x.LocalAreaId == localArea.LocalAreaId && x.DistrictEquipmentTypeId == equipmentType.DistrictEquipmentTypeId) .ToList(); foreach (HetEquipment equipment in data) { // rollover the year equipment.ServiceHoursThreeYearsAgo = equipment.ServiceHoursTwoYearsAgo; equipment.ServiceHoursTwoYearsAgo = equipment.ServiceHoursLastYear; equipment.ServiceHoursLastYear = EquipmentHelper.GetYtdServiceHours(equipment.EquipmentId, dbContext, rolloverDate); equipment.CalculateYearsOfService(DateTime.UtcNow); // blank out the override reason equipment.SeniorityOverrideReason = ""; // update the seniority score equipment.CalculateSeniority(seniorityScoring); etContext.HetEquipment.Update(equipment); etContext.SaveChanges(); } } // now update the rotation list using (DbAppContext abContext = new DbAppContext(connectionString)) { int localAreaId = localArea.LocalAreaId; int equipmentTypeId = equipmentType.DistrictEquipmentTypeId; SeniorityListHelper.AssignBlocks(localAreaId, equipmentTypeId, blockSize, totalBlocks, abContext); } // increment counters and update status equipmentCompleteCount++; UpdateStatus(dbContext, status, localAreaCompleteCount, equipmentCompleteCount); } // increment counters and update status localAreaCompleteCount++; UpdateStatus(dbContext, status, localAreaCompleteCount, equipmentCompleteCount); if (status.ProgressPercentage != null) { progress.SetValue((int)status.ProgressPercentage); } } // done! UpdateStatusComplete(dbContext, status, localAreaCompleteCount, equipmentCompleteCount); progress.SetValue(100); // ********************************************************** // regenerate Owner Secret Keys for this district // ********************************************************** dbContext = new DbAppContext(connectionString); context.WriteLine(""); context.WriteLine("Generate New Secret Keys - District #" + districtId); progress = context.WriteProgressBar(); progress.SetValue(0); // get records List <HetOwner> owners = dbContext.HetOwner.AsNoTracking() .Where(x => x.BusinessId == null && x.LocalArea.ServiceArea.DistrictId == districtId) .ToList(); int i = 0; int ownerCount = owners.Count; foreach (HetOwner owner in owners) { i++; string key = SecretKeyHelper.RandomString(8, owner.OwnerId); string temp = owner.OwnerCode; if (string.IsNullOrEmpty(temp)) { temp = SecretKeyHelper.RandomString(4, owner.OwnerId); } key = temp + "-" + (rolloverDate.Year + 1) + "-" + key; // get owner and update HetOwner ownerRecord = dbContext.HetOwner.First(x => x.OwnerId == owner.OwnerId); ownerRecord.SharedKey = key; dbContext.HetOwner.Update(ownerRecord); decimal tempProgress = Convert.ToDecimal(i) / Convert.ToDecimal(ownerCount); tempProgress = tempProgress * 100; int percentComplete = Convert.ToInt32(tempProgress); if (percentComplete < 1) { percentComplete = 1; } if (percentComplete > 99) { percentComplete = 100; } progress.SetValue(percentComplete); } // save remaining updates - done! dbContext.SaveChangesForImport(); progress.SetValue(100); context.WriteLine("Generate New Secret Keys - Done"); } catch (Exception e) { Console.WriteLine(e); throw; } }