Real-Time Modeling with EF Core 10 InMemory — A Practical Guide to In-Memory Databases and Data Annotations
Cristian Sifuentes

Cristian Sifuentes @cristiansifuentes

About: 🧠 Full-stack dev crafting scalable apps with [NET - Azure], [Angular - React], Git, SQL & extensions. Clean code, dark themes, atomic commits.

Joined:
Apr 15, 2025

Real-Time Modeling with EF Core 10 InMemory — A Practical Guide to In-Memory Databases and Data Annotations

Publish Date: Jun 6
1 1

Real-Time Modeling with EF Core 10 InMemory

Real-Time Modeling with EF Core 10 InMemory — A Practical Guide to In-Memory Databases and Data Annotations

In modern .NET backend development, developers seek simplified database experimentation without complex setup, external dependencies, or long migrations. That’s where the EF Core InMemory provider excels — especially when combined with clean architecture and preview SDK features.

In this article, we will explore how to build a modular and elegant backend with:

  • ✅ EF Core 10.0.0-preview.4
  • ✅ InMemory database for fast prototyping
  • ✅ Data annotations + Fluent API for model validation
  • ✅ Minimal APIs in .NET 10
  • ✅ Rich domain modeling using enums and navigation properties

All through a real-world use case: a jobs catalog system.


Setup and Context

First, let’s scaffold a basic backend using the new minimal API approach introduced in .NET 6 and enhanced through .NET 10.

Project File (.csproj)

<Project Sdk="Microsoft.NET.Sdk.Web">
  <PropertyGroup>
    <TargetFramework>net10.0</TargetFramework>
    <Nullable>enable</Nullable>
    <ImplicitUsings>enable</ImplicitUsings>
  </PropertyGroup>
  <ItemGroup>
    <PackageReference Include="Microsoft.EntityFrameworkCore" Version="10.0.0-preview.4.25258.110" />
    <PackageReference Include="Microsoft.EntityFrameworkCore.InMemory" Version="10.0.0-preview.4.25258.110" />
    <PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="10.0.0-preview.4.25258.110" />
    <PackageReference Include="Npgsql.EntityFrameworkCore.PostgreSQL" Version="10.0.0-preview.3" />
  </ItemGroup>
</Project>
Enter fullscreen mode Exit fullscreen mode

Even though we’re only using InMemory, this setup allows instant provider swapping with SQL Server or PostgreSQL later.


Domain Models: Category and Job

public class Category
{
    [Key]
    public Guid CategoryId { get; set; }

    [Required]
    [MaxLength(150)]
    public string Name { get; set; }

    public string Description { get; set; }
    public virtual ICollection<Job> JobS { get; set; }
}
Enter fullscreen mode Exit fullscreen mode
public class Job
{
    [Key]
    public Guid TaskId { get; set; }

    [ForeignKey(nameof(Category))]
    public Guid CategoryId { get; set; }

    [Required]
    [MaxLength(150)]
    public string Title { get; set; }

    public string Description { get; set; }
    public virtual Priority priority { get; set; }

    public DateTime CreationDate { get; set; }

    public virtual Category Category { get; set; }

    [NotMapped]
    public string Resume { get; set; }
}

public enum Priority
{
    High,
    Medium,
    Low
}
Enter fullscreen mode Exit fullscreen mode

✅ We use data annotations to enforce validation rules and NotMapped for computed values.


DbContext Configuration

public class JobsContext : DbContext
{
    public DbSet<Category> Categories => Set<Category>();
    public DbSet<Job> Jobs => Set<Job>();

    public JobsContext(DbContextOptions options) : base(options) { }
}
Enter fullscreen mode Exit fullscreen mode

We use strongly typed DbSet<T> for clarity and null-safety.


Minimal API with InMemory Provider

var builder = WebApplication.CreateBuilder(args);
builder.Services.AddDbContext<JobsContext>(options =>
    options.UseInMemoryDatabase("JobsDB"));

var app = builder.Build();

app.MapGet("/", () => "Hello World!");

app.MapGet("/dbconextion", async ([FromServices] JobsContext db) =>
{
    db.Database.EnsureCreated();
    return Results.Ok("In memory db: " + db.Database.IsInMemory());
});

app.Run();
Enter fullscreen mode Exit fullscreen mode

Using dependency injection via [FromServices], we gain testability and loose coupling.


Key EF Core Concepts in This Example

Concept Implementation Example
InMemory DB UseInMemoryDatabase("JobsDB")
Minimal API app.MapGet(...)
Enum usage public Priority priority { get; set; }
Navigation properties virtual Category Category { get; set; }
[NotMapped] fields public string Resume { get; set; }
Data Annotations MaxLength, Required, ForeignKey, etc.

Bonus Practice Challenge

To level up:

  • Add endpoint: GET /jobs to list jobs
  • Create POST /job to save a new job entry
  • Add computed property to summarize job title + category name
  • Add logging when jobs with High priority are created

Final Thoughts

The combination of EF Core’s InMemory provider, data annotations, and .NET 10 minimal APIs offers a clean, testable, and lightning-fast way to design and validate your domain.

By working with preview features like EF Core 10.0.0-preview.4, you’ll stay ahead of the curve while mastering robust design principles.


✍️ Written by: Cristian Sifuentes – Full-stack dev crafting scalable apps with [NET - Azure], [Angular - React], Git, SQL & extensions. Clean code, dark themes, atomic commits

💬 What real-time features would you model next with EF Core? Let’s push the limits of schema-free dev.

Comments 1 total

  • davinceleecode
    davinceleecodeJun 20, 2025

    This is a friendly start. Nice content bro. 🤘🔥

Add comment