Introdução ao Entity Framework Core (EF Core)
Se você trabalha com .NET e lida com dados relacionais, o Entity Framework Core (EF Core) é, sem dúvida, uma das ferramentas mais cruciais que você precisa dominar. Ele atua como uma ponte robusta entre o mundo orientado a objetos do C# e o mundo relacional dos seus bancos de dados (como SQL Server, MySQL ou PostgreSQL).
Neste guia detalhado, vamos desvendar o EF Core, desde o conceito de ORM até a execução das operações mais fundamentais, o famoso CRUD.
O Que é um ORM e Por Que Você Precisa Dele?
O EF Core é um Object-Relational Mapper (ORM), ou Mapeador Objeto-Relacional. Mas o que isso significa na prática?
Imagine que sua aplicação é escrita em C#, uma linguagem orientada a objetos que usa classes, objetos e propriedades. Seu banco de dados, por outro lado, usa tabelas, linhas e colunas e é acessado via comandos SQL. Sem um ORM, você precisaria:
Escrever comandos SQL complexos (
SELECT,INSERT,UPDATE,DELETE) como strings.Executar esses comandos através de drivers de banco de dados.
Pegar o resultado (um
DataReaderouDataTable).Mapear manualmente cada coluna do resultado para as propriedades do seu objeto C#.
Essa tarefa é repetitiva, propensa a erros de digitação (e, consequentemente, falhas em tempo de execução) e consome tempo valioso de desenvolvimento.
É aí que o EF Core entra:
O EF Core permite que você manipule dados diretamente usando seus objetos C# fortemente tipados. Ele se encarrega de traduzir as operações em objetos para os comandos SQL apropriados e vice-versa, eliminando a maior parte do código de acesso a dados manual.
Vantagens Chave do EF Core
| Vantagem | Descrição |
| Redução de Código Repetitivo | Você escreve menos código para acessar, inserir e atualizar dados. |
| Segurança de Tipo | Você trabalha com objetos C# (ex: List<Produto>), o que permite que o compilador detecte erros de consulta em tempo de compilação, e não apenas em tempo de execução. |
| Multiplataforma | Sendo parte do .NET Core, ele funciona em Windows, Mac e Linux. |
| Suporte a Múltiplos Bancos | Através de provedores de dados (NuGet Packages), ele suporta SQL Server, MySQL, PostgreSQL, SQLite, Cosmos DB, e até mesmo um banco de dados em memória para testes. |
| LINQ (Language Integrated Query) | Permite que você escreva consultas ricas e expressivas em C#, que são convertidas em SQL nativo de forma otimizada. |
Os Três Pilares do EF Core
Para usar o EF Core, você precisa entender três conceitos centrais.
1. Entidades (Models)
Uma Entidade é simplesmente uma classe C# que mapeia para uma tabela no banco de dados.
public class Produto
{
// Mapeado para a chave primária (convenção)
public int Id { get; set; }
public string Nome { get; set; }
public decimal Preco { get; set; }
// Propriedade de Navegação (Relacionamento)
public Categoria Categoria { get; set; }
}
2. DbContext (O Gerente da Sessão)
O DbContext é o coração do EF Core. Ele representa uma sessão com o banco de dados.
É a classe central que:
Gerencia a Conexão: Sabe como se conectar ao seu banco de dados.
Rastreia as Entidades: Monitora as alterações feitas nos objetos que foram carregados. Se você mudar a propriedade
Nomede umProduto, oDbContextsabe disso.Expõe Coleções: Define as propriedades do tipo
DbSet<TEntity>, que representam as coleções (tabelas) em seu banco de dados.
using Microsoft.EntityFrameworkCore;
public class MeuContexto : DbContext
{
// Estas propriedades mapeiam para as tabelas no seu banco
public DbSet<Produto> Produtos { get; set; }
public DbSet<Categoria> Categorias { get; set; }
// Usado para configurar o provedor e a string de conexão
protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
{
optionsBuilder.UseSqlServer("SuaStringDeConexaoAqui");
}
}
3. Migrations (O Evolucionista do Schema)
No desenvolvimento moderno, a abordagem mais comum é o Code First (Código Primeiro), onde você define suas classes C# e, a partir delas, o EF Core gera o banco de dados.
Migrations é o recurso que permite que você:
Crie o banco de dados inicial com base nas suas entidades.
Evolua o schema do banco de dados (adicionar colunas, renomear tabelas, etc.) à medida que suas classes C# mudam, de forma controlada e rastreável.
O fluxo de trabalho é simples:
Você altera uma classe C# (
Produto.AdicionarPropriedadeEntrega).Você executa o comando:
Add-Migration AdicionarCampoEntrega(no Package Manager Console).O EF Core gera uma classe de migração (código C#) com as instruções SQL para fazer a alteração.
Você aplica as alterações no banco de dados com:
Update-Database.
Dominando o CRUD com LINQ
O verdadeiro poder do EF Core reside na sua integração com o LINQ. Você não escreve SQL; você escreve consultas em C# que parecem inglês.
Vamos usar nosso MeuContexto para realizar as operações fundamentais (CRUD).
C: Create (Inserir Dados)
Para adicionar um novo registro, você cria o objeto C# e diz ao DbContext para rastreá-lo.
using (var db = new MeuContexto())
{
var novoProduto = new Produto { Nome = "Notebook Gamer", Preco = 5999.99m };
// 1. Adiciona o objeto ao rastreamento do contexto
db.Produtos.Add(novoProduto);
// 2. Persiste todas as alterações pendentes no banco de dados
await db.SaveChangesAsync();
}
// O DbContext é descartado aqui, liberando recursos
R: Read (Consultar Dados)
A consulta é feita usando LINQ. O EF Core converte sua expressão LINQ em um comando SELECT otimizado.
| Operação | Exemplo com LINQ (e SQL Gerado) |
| Buscar Todos | var todos = await db.Produtos.ToListAsync(); |
| Buscar por ID (Único) | var p = await db.Produtos.FindAsync(10); |
| Filtrar (WHERE) | var caros = db.Produtos.Where(p => p.Preco > 1000).ToList(); |
| Ordenar (ORDER BY) | var ordenados = db.Produtos.OrderBy(p => p.Nome).ToList(); |
| Relacionamentos (JOIN) | var blogs = db.Blogs.Include(b => b.Posts).ToList(); |
Nota sobre ToListAsync(): A consulta só é enviada ao banco de dados quando você chama um método de execução (como ToList(), FirstOrDefault(), Count() ou ToArray()). Isso é conhecido como Execução Adiável.
U: Update (Atualizar Dados)
A atualização é incrivelmente simples porque o DbContext está rastreando os objetos.
using (var db = new MeuContexto())
{
// 1. Encontra e carrega o objeto (o DbContext começa a rastreá-lo)
var produtoParaAtualizar = await db.Produtos.FirstOrDefaultAsync(p => p.Nome == "Notebook Gamer");
if (produtoParaAtualizar != null)
{
// 2. Altera a propriedade do objeto C#
produtoParaAtualizar.Preco = 4999.00m;
// 3. O DbContext detecta a mudança e gera um comando UPDATE
await db.SaveChangesAsync();
}
}
D: Delete (Excluir Dados)
Para excluir, você remove o objeto da coleção e salva as alterações.
using (var db = new MeuContexto())
{
// 1. Carrega (ou anexa) o objeto
var produtoParaExcluir = await db.Produtos.FindAsync(10);
if (produtoParaExcluir != null)
{
// 2. Marca o objeto como "Deletado"
db.Produtos.Remove(produtoParaExcluir);
// 3. O DbContext gera um comando DELETE
await db.SaveChangesAsync();
}
}
Considerações sobre Performance (A Faca de Dois Gumes do ORM)
O EF Core é uma ferramenta fantástica, mas como todo ORM, ele tem seu "preço":
⚠️ Desvantagens e Como Mitigá-las
| Desvantagem | Impacto | Como Resolver |
| Queries Subótimas | Em consultas muito complexas, o SQL gerado pelo EF Core pode não ser tão eficiente quanto um SQL escrito manualmente. | Use AsNoTracking() para leituras onde você não vai modificar o objeto. |
| Overhead de Tracking | O rastreamento de entidades (Change Tracker) consome tempo e memória, especialmente ao carregar milhares de registros. | Para consultas de leitura (sem atualização), use AsNoTracking() para desabilitar o rastreamento. |
| Curva de Aprendizado (LINQ) | Para consultas avançadas, dominar o LINQ pode ser desafiador. | Para consultas extremamente complexas e otimizadas, use SQL Bruto com FromSqlRaw() ou mude para um micro-ORM (como Dapper) em pontos críticos de performance. |
Dicas de Performance Profissional
Use
Selectpara Projeção: Em vez de carregar a entidade completa, use.Select()para carregar apenas as colunas que você realmente precisa. Isso reduz a carga de dados e o tempo de mapeamento.C#// Ruim: Carrega todas as 10 colunas // var produtos = db.Produtos.ToList(); // Bom: Carrega apenas 2 colunas var nomes = db.Produtos.Select(p => p.Nome).ToList();AsNoTracking(): Use-o sempre em consultas que apenas lerão dados. Ele impede que oDbContextmonitore os objetos, resultando em um ganho de velocidade significativo.Consultas Assíncronas: No .NET moderno, use a versão assíncrona dos métodos (
ToListAsync(),FirstOrDefaultAsync(),SaveChangesAsync()) para evitar o bloqueio da thread principal.
Próximos Passos na Sua Jornada com EF Core
O Entity Framework Core é o padrão da indústria para acesso a dados no .NET. Sua curva de aprendizado vale o investimento, pois ele proporciona clareza, segurança e agilidade no desenvolvimento.
Para continuar sua jornada, procure tutoriais práticos sobre:
Relacionamentos (1:N, N:N): Como configurar relacionamentos complexos entre entidades.
Provedores de Banco de Dados: Como configurar o EF Core para usar diferentes provedores (ex:
UseNpgsqlpara PostgreSQL).Injeção de Dependência: Como usar o
DbContextem ambientes ASP.NET Core de forma eficiente.
Comece hoje mesmo a trocar seu código SQL por expressões LINQ elegantes e veja como seu tempo de desenvolvimento diminui drasticamente!

Comentários
Postar um comentário