Entity Framework Core with PostgreSQL
Build scalable applications with EF Core and PostgreSQL.
By EMEPublished: February 20, 2025
entity frameworkpostgresqlormrelational
A Simple Analogy
EF Core is like a translator between C# and SQL. You write C# queries that become SQL automatically.
Why EF Core + PostgreSQL?
- Type-safe: Compile-time query checking
- LINQ: Natural query syntax
- Relationships: Handle foreign keys automatically
- Migrations: Version control for schema
- Performance: Lazy loading and optimization
Setup & Configuration
public class AppDbContext : DbContext
{
public DbSet<Product> Products { get; set; }
public DbSet<Category> Categories { get; set; }
protected override void OnConfiguring(DbContextOptionsBuilder options)
{
options.UseNpgsql("Host=localhost;Database=myapp;Username=user;Password=pass");
}
}
// Register in DI
services.AddDbContext<AppDbContext>(options =>
options.UseNpgsql(configuration.GetConnectionString("Default")));
Entity Configuration
public class Product
{
public int Id { get; set; }
public string Name { get; set; }
public decimal Price { get; set; }
public int CategoryId { get; set; }
public Category Category { get; set; }
}
public class Category
{
public int Id { get; set; }
public string Name { get; set; }
public List<Product> Products { get; set; }
}
// Fluent API configuration
public class ProductEntityConfiguration : IEntityTypeConfiguration<Product>
{
public void Configure(EntityTypeBuilder<Product> builder)
{
builder.HasKey(p => p.Id);
builder.Property(p => p.Name).HasMaxLength(200).IsRequired();
builder.Property(p => p.Price).HasPrecision(10, 2);
builder.HasIndex(p => p.Name).IsUnique();
}
}
LINQ Queries
// Select
var products = await _context.Products.ToListAsync();
// Filter
var expensive = await _context.Products
.Where(p => p.Price > 100)
.ToListAsync();
// Join
var withCategory = await _context.Products
.Include(p => p.Category)
.ToListAsync();
// Pagination
var page = await _context.Products
.OrderBy(p => p.Name)
.Skip((pageNumber - 1) * pageSize)
.Take(pageSize)
.ToListAsync();
// Aggregate
var count = await _context.Products.CountAsync();
var total = await _context.Products.SumAsync(p => p.Price);
Migrations
# Create migration
dotnet ef migrations add AddProductTable
# Update database
dotnet ef database update
# Rollback
dotnet ef database update PreviousMigration
# Generate SQL script
dotnet ef migrations script
Best Practices
- Async: Always use async methods
- Projection: Select only needed fields
- Eager loading: Use Include for relationships
- Indexes: Add for frequently queried columns
- Transactions: Group related operations
Related Concepts
- Dapper
- Prisma
- Sequelize
- Raw SQL
Summary
EF Core with PostgreSQL provides type-safe, LINQ-based data access with automatic schema migration and relationship management.