// EN: MerchantStaff repository interface.
// VI: Interface repository cho MerchantStaff.

using MerchantService.Domain.SeedWork;

namespace MerchantService.Domain.AggregatesModel.MerchantStaffAggregate;

/// <summary>
/// EN: Repository interface for MerchantStaff aggregate.
/// VI: Interface repository cho MerchantStaff aggregate.
/// </summary>
public interface IMerchantStaffRepository : IRepository<MerchantStaff>
{
    /// <summary>
    /// EN: Get staff by ID.
    /// VI: Lấy nhân viên theo ID.
    /// </summary>
    Task<MerchantStaff?> GetByIdAsync(Guid id, CancellationToken cancellationToken = default);
    
    /// <summary>
    /// EN: Get staff by user ID (IAM User).
    /// VI: Lấy nhân viên theo user ID (IAM User).
    /// </summary>
    Task<MerchantStaff?> GetByUserIdAsync(Guid userId, CancellationToken cancellationToken = default);
    
    /// <summary>
    /// EN: Get staff by user ID and merchant ID.
    /// VI: Lấy nhân viên theo user ID và merchant ID.
    /// </summary>
    Task<MerchantStaff?> GetByUserIdAndMerchantIdAsync(Guid userId, Guid merchantId, CancellationToken cancellationToken = default);
    
    /// <summary>
    /// EN: Get all staff by merchant ID.
    /// VI: Lấy tất cả nhân viên theo merchant ID.
    /// </summary>
    Task<IReadOnlyList<MerchantStaff>> GetByMerchantIdAsync(Guid merchantId, CancellationToken cancellationToken = default);
    
    /// <summary>
    /// EN: Get staff by shop ID (through ShopMember).
    /// VI: Lấy nhân viên theo shop ID (thông qua ShopMember).
    /// </summary>
    Task<IReadOnlyList<MerchantStaff>> GetByShopIdAsync(Guid shopId, CancellationToken cancellationToken = default);
    
    /// <summary>
    /// EN: Check if user is already staff of merchant.
    /// VI: Kiểm tra user đã là nhân viên của merchant chưa.
    /// </summary>
    Task<bool> ExistsByUserIdAndMerchantIdAsync(Guid userId, Guid merchantId, CancellationToken cancellationToken = default);
    
    /// <summary>
    /// EN: Get staff by email.
    /// VI: Lấy nhân viên theo email.
    /// </summary>
    Task<MerchantStaff?> GetByEmailAsync(string email, CancellationToken cancellationToken = default);

    /// <summary>
    /// EN: Get multiple staff members by their IDs (batch lookup).
    /// VI: Lấy nhiều nhân viên theo danh sách ID (batch lookup).
    /// </summary>
    Task<IReadOnlyList<MerchantStaff>> GetByIdsAsync(IEnumerable<Guid> ids, CancellationToken cancellationToken = default);

    /// <summary>
    /// EN: Add a new staff member.
    /// VI: Thêm nhân viên mới.
    /// </summary>
    MerchantStaff Add(MerchantStaff staff);
    
    /// <summary>
    /// EN: Update a staff member.
    /// VI: Cập nhật nhân viên.
    /// </summary>
    void Update(MerchantStaff staff);
}
