Files
PowderCoatingLogix/src/PowderCoating.Application/Mappings/AppointmentProfile.cs
T
2026-04-23 21:38:24 -04:00

144 lines
8.7 KiB
C#

using AutoMapper;
using PowderCoating.Core.Entities;
using PowderCoating.Application.DTOs.Appointment;
namespace PowderCoating.Application.Mappings;
public class AppointmentProfile : Profile
{
public AppointmentProfile()
{
// Appointment to AppointmentDto - Map all lookup properties from navigation
CreateMap<Appointment, AppointmentDto>()
// Customer mappings (nullable for internal appointments)
.ForMember(dest => dest.CustomerName,
opt => opt.MapFrom(src => src.Customer != null
? (!string.IsNullOrWhiteSpace(src.Customer.CompanyName)
? src.Customer.CompanyName
: $"{src.Customer.ContactFirstName} {src.Customer.ContactLastName}".Trim())
: null))
.ForMember(dest => dest.CustomerPhone,
opt => opt.MapFrom(src => src.Customer != null ? src.Customer.Phone : null))
.ForMember(dest => dest.CustomerEmail,
opt => opt.MapFrom(src => src.Customer != null ? src.Customer.Email : null))
// Job mappings (optional)
.ForMember(dest => dest.JobNumber,
opt => opt.MapFrom(src => src.Job != null ? src.Job.JobNumber : null))
// Worker assignment
.ForMember(dest => dest.AssignedWorkerName,
opt => opt.MapFrom(src => src.AssignedUser != null ? src.AssignedUser.FullName : null))
// Appointment Type lookup mappings
.ForMember(dest => dest.AppointmentTypeId, opt => opt.MapFrom(src => src.AppointmentTypeId))
.ForMember(dest => dest.TypeCode, opt => opt.MapFrom(src => src.AppointmentType.TypeCode))
.ForMember(dest => dest.TypeDisplayName, opt => opt.MapFrom(src => src.AppointmentType.DisplayName))
.ForMember(dest => dest.TypeColorClass, opt => opt.MapFrom(src => src.AppointmentType.ColorClass))
.ForMember(dest => dest.TypeIconClass, opt => opt.MapFrom(src => src.AppointmentType.IconClass))
.ForMember(dest => dest.TypeRequiresJobLink, opt => opt.MapFrom(src => src.AppointmentType.RequiresJobLink))
// Appointment Status lookup mappings
.ForMember(dest => dest.AppointmentStatusId, opt => opt.MapFrom(src => src.AppointmentStatusId))
.ForMember(dest => dest.StatusCode, opt => opt.MapFrom(src => src.AppointmentStatus.StatusCode))
.ForMember(dest => dest.StatusDisplayName, opt => opt.MapFrom(src => src.AppointmentStatus.DisplayName))
.ForMember(dest => dest.StatusColorClass, opt => opt.MapFrom(src => src.AppointmentStatus.ColorClass))
.ForMember(dest => dest.StatusIconClass, opt => opt.MapFrom(src => src.AppointmentStatus.IconClass))
.ForMember(dest => dest.StatusIsTerminal, opt => opt.MapFrom(src => src.AppointmentStatus.IsTerminalStatus));
// Appointment to AppointmentListDto - Lightweight for grid views
CreateMap<Appointment, AppointmentListDto>()
.ForMember(dest => dest.CustomerName,
opt => opt.MapFrom(src => src.Customer != null
? (!string.IsNullOrWhiteSpace(src.Customer.CompanyName)
? src.Customer.CompanyName
: $"{src.Customer.ContactFirstName} {src.Customer.ContactLastName}".Trim())
: null))
.ForMember(dest => dest.AssignedWorkerName,
opt => opt.MapFrom(src => src.AssignedUser != null ? src.AssignedUser.FullName : null))
// Type lookup mappings
.ForMember(dest => dest.TypeDisplayName, opt => opt.MapFrom(src => src.AppointmentType.DisplayName))
.ForMember(dest => dest.TypeColorClass, opt => opt.MapFrom(src => src.AppointmentType.ColorClass))
// Status lookup mappings
.ForMember(dest => dest.StatusDisplayName, opt => opt.MapFrom(src => src.AppointmentStatus.DisplayName))
.ForMember(dest => dest.StatusColorClass, opt => opt.MapFrom(src => src.AppointmentStatus.ColorClass));
// Appointment to CalendarEventDto - For calendar JSON API
CreateMap<Appointment, CalendarEventDto>()
.ForMember(dest => dest.Start,
opt => opt.MapFrom(src => src.ScheduledStartTime.ToString("yyyy-MM-ddTHH:mm:ss")))
.ForMember(dest => dest.End,
opt => opt.MapFrom(src => src.ScheduledEndTime.ToString("yyyy-MM-ddTHH:mm:ss")))
.ForMember(dest => dest.AllDay, opt => opt.MapFrom(src => src.IsAllDay))
.ForMember(dest => dest.CustomerName,
opt => opt.MapFrom(src => src.Customer != null
? (!string.IsNullOrWhiteSpace(src.Customer.CompanyName)
? src.Customer.CompanyName
: $"{src.Customer.ContactFirstName} {src.Customer.ContactLastName}".Trim())
: "Internal"))
.ForMember(dest => dest.TypeDisplayName, opt => opt.MapFrom(src => src.AppointmentType.DisplayName))
.ForMember(dest => dest.StatusCode, opt => opt.MapFrom(src => src.AppointmentStatus.StatusCode))
// Calendar colors based on appointment type color class
.ForMember(dest => dest.BackgroundColor,
opt => opt.MapFrom(src => GetBootstrapColor(src.AppointmentType.ColorClass)))
.ForMember(dest => dest.BorderColor,
opt => opt.MapFrom(src => GetBootstrapColor(src.AppointmentType.ColorClass)))
.ForMember(dest => dest.TextColor, opt => opt.MapFrom(src => "#ffffff"));
// CreateAppointmentDto to Appointment
CreateMap<CreateAppointmentDto, Appointment>()
.ForMember(dest => dest.AppointmentNumber, opt => opt.Ignore()) // Generated by system
.ForMember(dest => dest.AppointmentStatusId, opt => opt.Ignore()) // Set to default "SCHEDULED" by controller
.ForMember(dest => dest.AppointmentStatus, opt => opt.Ignore()) // Will be set by FK
.ForMember(dest => dest.AppointmentType, opt => opt.Ignore()); // Will be set by FK
// QuickCreateAppointmentDto to Appointment (for calendar quick create)
CreateMap<QuickCreateAppointmentDto, Appointment>()
.ForMember(dest => dest.AppointmentNumber, opt => opt.Ignore())
.ForMember(dest => dest.AppointmentStatusId, opt => opt.Ignore())
.ForMember(dest => dest.AppointmentStatus, opt => opt.Ignore())
.ForMember(dest => dest.AppointmentType, opt => opt.Ignore())
.ForMember(dest => dest.Description, opt => opt.MapFrom(src => (string?)null))
.ForMember(dest => dest.Location, opt => opt.MapFrom(src => (string?)null))
.ForMember(dest => dest.Notes, opt => opt.MapFrom(src => (string?)null))
.ForMember(dest => dest.IsReminderEnabled, opt => opt.MapFrom(src => true))
.ForMember(dest => dest.ReminderMinutesBefore, opt => opt.MapFrom(src => 30));
// UpdateAppointmentDto to Appointment
CreateMap<UpdateAppointmentDto, Appointment>()
.ForMember(dest => dest.AppointmentNumber, opt => opt.Ignore()) // Cannot be changed
.ForMember(dest => dest.AppointmentStatus, opt => opt.Ignore()) // Will be set by FK
.ForMember(dest => dest.AppointmentType, opt => opt.Ignore()); // Will be set by FK
// Appointment to UpdateAppointmentDto (needed for Edit GET action)
CreateMap<Appointment, UpdateAppointmentDto>()
.ForMember(dest => dest.AppointmentStatusId, opt => opt.MapFrom(src => src.AppointmentStatusId))
.ForMember(dest => dest.AppointmentTypeId, opt => opt.MapFrom(src => src.AppointmentTypeId));
}
/// <summary>
/// Maps Bootstrap color class names to hex color codes for calendar events
/// </summary>
private static string GetBootstrapColor(string colorClass)
{
return colorClass.ToLower() switch
{
"primary" => "#0d6efd",
"secondary" => "#6c757d",
"success" => "#198754",
"danger" => "#dc3545",
"warning" => "#ffc107",
"info" => "#0dcaf0",
"light" => "#f8f9fa",
"dark" => "#212529",
// Custom color names for appointment types
"purple" => "#6f42c1",
"green" => "#198754",
"blue" => "#0d6efd",
"orange" => "#fd7e14",
"red" => "#dc3545",
"yellow" => "#ffc107",
"cyan" => "#0dcaf0",
"pink" => "#d63384",
"gray" => "#6c757d",
_ => "#0d6efd" // Default to primary blue
};
}
}