ASP.NET Tutorial menu

ASP.NET Database with EF Core

Entity Framework Core (EF Core) lets you work with a database using C# classes instead of writing SQL by hand.

What is EF Core?

EF Core is an ORM (Object-Relational Mapper). It maps:

C#Database
A classA table
A propertyA column
An objectA row
A DbSet<T>A table you can query

It works with SQL Server, SQLite, PostgreSQL, MySQL and more. This lesson uses SQLite because it needs no installation: the whole database is one file.

Install the Packages

Run these in your project folder:

Example

bash
dotnet add package Microsoft.EntityFrameworkCore.Sqlite
dotnet add package Microsoft.EntityFrameworkCore.Design
dotnet tool install --global dotnet-ef

The Entity and the DbContext

Create a new file Data.cs in the project folder and add these two classes:

Example

csharp
using Microsoft.EntityFrameworkCore;

public class Student
{
    public int Id { get; set; }
    public string Name { get; set; } = "";
    public string Course { get; set; } = "";
    public bool FeePaid { get; set; }
}

public class SchoolDb : DbContext
{
    public SchoolDb(DbContextOptions<SchoolDb> options) : base(options) { }

    public DbSet<Student> Students => Set<Student>();
}

A property named Id automatically becomes the primary key.

Register It in Program.cs

Example

csharp
using Microsoft.EntityFrameworkCore;

var builder = WebApplication.CreateBuilder(args);

builder.Services.AddDbContext<SchoolDb>(options =>
    options.UseSqlite("Data Source=school.db"));

var app = builder.Build();

This is dependency injection: ASP.NET Core creates a SchoolDb for each request and gives it to any page or endpoint that asks for it.

Create the Database with Migrations

A migration is a saved set of changes to the database structure.

Example

bash
dotnet ef migrations add InitialCreate
dotnet ef database update
Output
Build started...
Build succeeded.
Applying migration '20261015093000_InitialCreate'.
Done.

Now school.db exists with a Students table. When you change your classes later, add a new migration and run database update again.

Using It in Minimal APIs

Example

csharp
app.MapGet("/students", async (SchoolDb db) =>
    await db.Students.OrderBy(s => s.Name).ToListAsync());

app.MapPost("/students", async (Student s, SchoolDb db) =>
{
    db.Students.Add(s);
    await db.SaveChangesAsync();
    return Results.Created($"/students/{s.Id}", s);
});

app.MapPut("/students/{id:int}/paid", async (int id, SchoolDb db) =>
{
    var student = await db.Students.FindAsync(id);
    if (student is null) return Results.NotFound();
    student.FeePaid = true;
    await db.SaveChangesAsync();
    return Results.NoContent();
});

app.Run();

After posting two students, /students returns:

Output
[{"id":2,"name":"Ali","course":"SEO","feePaid":false},{"id":1,"name":"Ayesha","course":"Web Development","feePaid":true}]

Using It in a Razor Page

Ask for the SchoolDb in the PageModel's constructor:

Example

csharp
using Microsoft.AspNetCore.Mvc.RazorPages;
using Microsoft.EntityFrameworkCore;

public class StudentsModel : PageModel
{
    private readonly SchoolDb _db;
    public StudentsModel(SchoolDb db) => _db = db;

    public List<Student> Unpaid { get; private set; } = new();

    public async Task OnGetAsync()
    {
        Unpaid = await _db.Students
            .Where(s => !s.FeePaid)
            .ToListAsync();
    }
}

Useful LINQ Queries

CodeMeaning
db.Students.ToListAsync()All rows
.Where(s => s.Course == "SEO")Filter rows
.OrderBy(s => s.Name)Sort
.FirstOrDefaultAsync(s => s.Id == 5)One row or null
.CountAsync()Number of rows
db.Remove(student)Delete (then call SaveChangesAsync)

EF Core always uses parameters when it sends your values to the database, so LINQ queries are safe from SQL injection.

Exercise

Exercise

Which method actually writes your added or changed objects to the database?

Learn ASP.NET with a teacher

Join the Full Stack Development course at Workownix, online or in Orangi Town, Karachi, and get a certificate.

See the course Ask on WhatsApp