// EN: Handler for CreateAppointmentCommand.
// VI: Handler cho CreateAppointmentCommand.

using BookingService.API.Application.DTOs;
using BookingService.Domain.AggregatesModel.AppointmentAggregate;
using BookingService.Infrastructure.Repositories;
using MediatR;

namespace BookingService.API.Application.Commands;

/// <summary>
/// EN: Handler for creating new appointments.
/// VI: Handler để tạo cuộc hẹn mới.
/// </summary>
public class CreateAppointmentCommandHandler : IRequestHandler<CreateAppointmentCommand, AppointmentDto>
{
    private readonly IAppointmentRepository _appointmentRepository;
    private readonly ILogger<CreateAppointmentCommandHandler> _logger;

    public CreateAppointmentCommandHandler(
        IAppointmentRepository appointmentRepository,
        ILogger<CreateAppointmentCommandHandler> logger)
    {
        _appointmentRepository = appointmentRepository ?? throw new ArgumentNullException(nameof(appointmentRepository));
        _logger = logger ?? throw new ArgumentNullException(nameof(logger));
    }

    public async Task<AppointmentDto> Handle(CreateAppointmentCommand request, CancellationToken cancellationToken)
    {
        _logger.LogInformation(
            "Creating appointment for shop {ShopId}, service {ServiceId}, time {StartTime}-{EndTime}",
            request.ShopId, request.ServiceId, request.StartTime, request.EndTime);

        // EN: Create appointment via domain aggregate
        // VI: Tạo appointment qua domain aggregate
        var appointment = new Appointment(
            request.ShopId,
            request.ServiceId,
            request.StartTime,
            request.EndTime,
            request.CustomerId,
            request.StaffId,
            request.ResourceId
        );

        // EN: Save to repository
        // VI: Lưu vào repository
        _appointmentRepository.Add(appointment);
        await _appointmentRepository.UnitOfWork.SaveEntitiesAsync(cancellationToken);

        _logger.LogInformation("Created appointment {AppointmentId}", appointment.Id);

        // EN: Return DTO
        // VI: Trả về DTO
        return new AppointmentDto
        {
            Id = appointment.Id,
            ShopId = appointment.ShopId,
            CustomerId = appointment.CustomerId,
            StaffId = appointment.StaffId,
            ResourceId = appointment.ResourceId,
            ServiceId = appointment.ServiceId,
            StartTime = appointment.StartTime,
            EndTime = appointment.EndTime,
            Status = appointment.Status,
            CreatedAt = appointment.CreatedAt
        };
    }
}
