using MediatR;
using IamService.Domain.AggregatesModel.GroupAggregate;
using IamService.Domain.AggregatesModel.OrganizationAggregate;
using IamService.Domain.Exceptions;

namespace IamService.API.Application.Commands.Groups;

/// <summary>
/// EN: Handler for CreateGroupCommand.
/// VI: Handler cho CreateGroupCommand.
/// </summary>
public class CreateGroupCommandHandler : IRequestHandler<CreateGroupCommand, CreateGroupCommandResult>
{
    private readonly IGroupRepository _groupRepository;
    private readonly IOrganizationRepository _organizationRepository;
    private readonly ILogger<CreateGroupCommandHandler> _logger;

    public CreateGroupCommandHandler(
        IGroupRepository groupRepository,
        IOrganizationRepository organizationRepository,
        ILogger<CreateGroupCommandHandler> logger)
    {
        _groupRepository = groupRepository;
        _organizationRepository = organizationRepository;
        _logger = logger;
    }

    public async Task<CreateGroupCommandResult> Handle(
        CreateGroupCommand request,
        CancellationToken cancellationToken)
    {
        _logger.LogInformation("Creating group: {Name} in organization: {OrganizationId}", 
            request.Name, request.OrganizationId);

        // EN: Validate organization exists
        // VI: Kiểm tra tổ chức tồn tại
        var organization = await _organizationRepository.GetByIdAsync(
            request.OrganizationId, cancellationToken);

        if (organization == null)
        {
            throw new DomainException($"Organization with ID '{request.OrganizationId}' not found.");
        }

        // EN: Create new group (note: organizationId, name, description)
        // VI: Tạo nhóm mới (lưu ý: organizationId, name, description)
        var group = Group.Create(
            request.OrganizationId,
            request.Name,
            request.Description);

        _groupRepository.Add(group);

        await _groupRepository.UnitOfWork.SaveEntitiesAsync(cancellationToken);

        _logger.LogInformation(
            "Group {Name} created successfully with ID {Id}",
            group.Name,
            group.Id);

        return new CreateGroupCommandResult(
            group.Id,
            group.Name,
            group.Description,
            group.OrganizationId,
            group.CreatedAt);
    }
}
