Performance de código Entity Framework Core – Parte 3

This post has been republished via RSS; it originally appeared at: Microsoft Tech Community - Latest Blogs - .

Será que eu preciso de tracking?

 

Tracking no EF Core

Tracking ou rastreamento no Entity Framework serve para determinar se um objeto recebido do banco de dados foi excluído, modificado ou criado pela aplicação para que os comandos SQL correspondentes sejam gerados e executados através do método SaveChanges.

 

Por padrão todas as consultas que retornem entidades definidas no DbContext irão gerar estruturas de dados necessárias para verificar os objetos que estão no contexto e manter tanto a versão original quanto a modificada dos dados.

 

Quando não se deseja que alterações sejam rastreadas, utiliza-se o método AsNoTracking:

 

    var blogs = context.Blogs
        .AsNoTracking()
        .ToList();

Também é possível alterar o comportamento para um DbContext:

 

    context.ChangeTracker.QueryTrackingBehavior = QueryTrackingBehavior.NoTracking;

    var blogs = context.Blogs.ToList();

Ou alterar a configuração padrão no método OnConfiguring do DbContext

 

    protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
    {
        if (!optionsBuilder.IsConfigured)
        {
            optionsBuilder.UseSqlServer(AdvWorksDbContext.connectionString)
                .UseQueryTrackingBehavior(QueryTrackingBehavior.NoTracking);
        }
    }

Quando desativar o tracking

Se a aplicação for uma aplicação Web o tracking deveria ser desativado por padrão. Aplicações Web por definição são aplicações onde não existe estado, para cada requisição se obtém os dados necessários para gerar uma resposta (HTML, XML ou JSON normalmente) e ao final se descarta esses dados. Se o usuário faz qualquer alteração dos dados no browser essas alterações serão submetidas em uma nova requisição que pode inclusive ser processada em outro servidor e tanto os resultados quanto os dados de tracking da requisição anterior já não estão mais acessíveis.

 

Sempre é possível manter esses dados no servidor aguardando a próxima requisição, mas não é uma prática recomendada manter estado no servidor para que seja manipulado pelos usuários visto que isso tem impactos na escalabilidade e desempenho da solução.

 

O tracking faz sentido para aplicações do tipo cliente/servidor onde os dados são baixados para uma aplicação desktop, manipulados pelos usuários e depois salvos para o servidor.

 

A diferença entre trazer os dados com tracking ligado e desligado pode ser vista em um benchmark:

 

...

    [Benchmark(Baseline = true)]
    public List<Customer> AsTracking() {
        using  AdvWorksDbContext context = new AdvWorksDbContext();
        return context.Customers.AsTracking().ToList();
    }
    
    [Benchmark()]
    public List<Customer> AsNoTracking() {
        using AdvWorksDbContext context = new AdvWorksDbContext();
        return context.Customers.AsNoTracking().ToList();
    }
|       Method |     Mean |     Error |   StdDev |   Median | Ratio | RatioSD | Allocated |
|------------- |---------:|----------:|---------:|---------:|------:|--------:|----------:|
|   AsTracking | 9.678 ms | 0.6053 ms | 1.727 ms | 8.884 ms |  1.00 |    0.00 |  1,998 KB |
| AsNoTracking | 7.233 ms | 0.9377 ms | 2.551 ms | 6.767 ms |  0.77 |    0.32 |    964 KB |

Nesse exemplo simples pode se ver que, além do tempo menor para trazer os dados, um pouco mais do dobro de memória foi alocado para o rastreamento de alterações, em aplicações Web esses dados são descartados sem qualquer uso na maioria das vezes.

 

Conclusões

Em cenários stateless, leia-se aplicações Web em geral, use AsNoTracking nas consultas ou configure o comportamento padrão como NoTracking. Além do ganho em desempenho não faz sentido consumir recursos com algo que não será usado pela aplicação.

 

Referências

Artigos anteriores

Leave a Reply

Your email address will not be published. Required fields are marked *

*

This site uses Akismet to reduce spam. Learn how your comment data is processed.