using MediatR;
using Microsoft.Extensions.Logging;
using MktZaloService.Domain.AggregatesModel.CustomerAggregate;

namespace MktZaloService.API.Application.Commands.Customers;

/// <summary>
/// EN: Handler for UpdateCustomerCommand.
/// VI: Handler cho UpdateCustomerCommand.
/// </summary>
public class UpdateCustomerCommandHandler : IRequestHandler<UpdateCustomerCommand, UpdateCustomerResult>
{
    private readonly ICustomerRepository _customerRepository;
    private readonly ILogger<UpdateCustomerCommandHandler> _logger;

    public UpdateCustomerCommandHandler(
        ICustomerRepository customerRepository,
        ILogger<UpdateCustomerCommandHandler> logger)
    {
        _customerRepository = customerRepository;
        _logger = logger;
    }

    public async Task<UpdateCustomerResult> Handle(
        UpdateCustomerCommand request,
        CancellationToken cancellationToken)
    {
        var customer = await _customerRepository.GetByIdAsync(request.CustomerId, cancellationToken);

        if (customer == null)
        {
            return new UpdateCustomerResult(false, Error: "Customer not found");
        }

        try
        {
            // EN: Update profile if any field provided / VI: Cập nhật profile nếu có field nào được cung cấp
            if (!string.IsNullOrEmpty(request.DisplayName) ||
                !string.IsNullOrEmpty(request.AvatarUrl) ||
                !string.IsNullOrEmpty(request.PhoneNumber) ||
                !string.IsNullOrEmpty(request.Email))
            {
                customer.UpdateProfile(
                    request.DisplayName ?? customer.Profile.DisplayName,
                    request.AvatarUrl ?? customer.Profile.AvatarUrl,
                    request.PhoneNumber ?? customer.Profile.PhoneNumber,
                    request.Email ?? customer.Profile.Email);
            }

            // EN: Add tags / VI: Thêm tags
            if (request.TagsToAdd?.Any() == true)
            {
                foreach (var tagName in request.TagsToAdd)
                {
                    customer.AddTag(tagName);
                }
            }

            // EN: Remove tags / VI: Xóa tags
            if (request.TagsToRemove?.Any() == true)
            {
                foreach (var tagName in request.TagsToRemove)
                {
                    customer.RemoveTag(tagName);
                }
            }

            _customerRepository.Update(customer);
            await _customerRepository.UnitOfWork.SaveEntitiesAsync(cancellationToken);

            _logger.LogInformation(
                "EN: Updated customer {CustomerId}. VI: Đã cập nhật khách hàng {CustomerId}",
                customer.Id);

            return new UpdateCustomerResult(true);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex,
                "EN: Error updating customer. VI: Lỗi cập nhật khách hàng");
            return new UpdateCustomerResult(false, Error: ex.Message);
        }
    }
}
