brunobritodev / AspNetCore.IQueryable.Extensions

LINQ extensions to help build IQueryAble Expressions
MIT License
159 stars 29 forks source link

É possivel usar em consultas com include e theninclude ? E como fazer se possivel ? #19

Closed michelmicheloti closed 2 years ago

michelmicheloti commented 2 years ago

Gostaria de usar em uma consulta do tipo

await _context.Report.AsNoTracking() .Include(x => x.Area) .Include(x => x.Customer) .Include(x => x.ReportSerialNumbers) .ThenInclude(y => y.SerialNumber) .Include(x => x.ApprovalRequest) .ToListAsync();

Ultilizando uma classe do tipo:

  public class ReportQueryableDto : ICustomQueryable, IQueryPaging, IQuerySort
{
    public string AreaDescripton { get; set; }
    public DateTime? CreateDate { get; set; }
    public string CustomerDescripton { get; set; }
    public string FullName { get; set; }
    [QueryOperator(Operator = WhereOperator.Equals, HasName = "RequestCode")]
    public string ReportNumber { get; set; }
    public string UserName { get; set; }
    public int? Limit { get; set; } = 100;
    public int? Offset { get; set; }
    public string Sort { get; set; }
}

Onde as propriedades que tem o Description no nome, precisa buscar as informações dentro das tabelas corespondentes

michelmicheloti commented 2 years ago

A abordagem mencionado pelo @GedanMagal na issue #16 funciona!

No meu caso utilizo um ThenInclude e a solução que achei foi por um if nesse caso (Se alguém souber de uma abordagem melhor agradeço o compartilhamento)

Compartilho um cenario semelhante ao que apliquei a seguir

[The approach mentioned by @GedanMagal on issue #16 works! In my case I use a ThenInclude and the solution I found was an if in this case (If anyone knows of a better approach I'd appreciate the sharing) I share a scenario similar to the one I applied below]

// Main Table
public class ReportEntity
{
    public int AreaId { get; set; }
    public AreaEntity Area { get; set; }
    public int CustomerId { get; set; }
    public CustomerEntity Customer { get; set; }

    public ICollection<ReportSerialNumberEntity> ReportSerialNumbers { get; set; }
}

public class AreaEntity
{
    public string Description { get; set; }
    public ICollection<ReportEntity> Reports { get; set; }
}

public class CustomerEntity
{
    public string Description { get; set; }
    public ICollection<ReportEntity> Reports { get; set; }
}

public class SerialNumberEntity
{
    public string Serial { get; set; }
    public ICollection<ReportSerialNumberEntity> ReportSerialNumbers { get; set; }
}

// Join Table -> Report x SerialNumber
public class ReportSerialNumberEntity
{
    public int ReportId { get; set; }
    public ReportEntity Report { get; set; }

    public int SerialNumberId { get; set; }
    public SerialNumberEntity SerialNumber { get; set; }
}

public class ReportQueryableDto : ICustomQueryable, IQueryPaging, IQuerySort
{
    [QueryOperator(Operator = WhereOperator.Contains, HasName = **"Area.Description"**)]
    public string Area { get; set; }

    [QueryOperator(Operator = WhereOperator.Contains, HasName = **"Customer.Description"**)]
    public string Customer { get; set; }

    public string SerialNumber { get; set; }

    public int? Limit { get; set; } = 10;
    public int? Offset { get; set; }
    public string Sort { get; set; }
}

public async Task<IEnumerable<ReportEntity>> SelectByQueryable(ReportQueryableDto queryableDto)
{
    IQueryable<ReportEntity> query =  _dataset.AsNoTracking()
                                                .Include(x => x.Area)
                                                .Include(x => x.Customer)
                                                .Include(x => x.ReportSerialNumbers)
                                                    .ThenInclude(y => y.SerialNumber)                            
                                                .Include(x => x.SmartApprovalRequest)
                                                .AsQueryable();                            

    if(queryableDto.SerialNumber.IsPresent())
    {
        query = query.Where(x => x.ReportSerialNumbers.Any(y => y.SerialNumber.Serial.Equals(queryableDto.SerialNumber)));
    }

    return await query.Apply(queryableDto).ToListAsync();
}