Imagile.EntityFrameworkCore.Tests
1.0.0
dotnet add package Imagile.EntityFrameworkCore.Tests --version 1.0.0
NuGet\Install-Package Imagile.EntityFrameworkCore.Tests -Version 1.0.0
<PackageReference Include="Imagile.EntityFrameworkCore.Tests" Version="1.0.0" />
<PackageVersion Include="Imagile.EntityFrameworkCore.Tests" Version="1.0.0" />
<PackageReference Include="Imagile.EntityFrameworkCore.Tests" />
paket add Imagile.EntityFrameworkCore.Tests --version 1.0.0
#r "nuget: Imagile.EntityFrameworkCore.Tests, 1.0.0"
#:package Imagile.EntityFrameworkCore.Tests@1.0.0
#addin nuget:?package=Imagile.EntityFrameworkCore.Tests&version=1.0.0
#tool nuget:?package=Imagile.EntityFrameworkCore.Tests&version=1.0.0
Imagile.EntityFrameworkCore.Tests
Opinionated convention tests for Entity Framework Core DbContexts with fluent exclusion configuration.
Features
- Convention Testing: Automated tests to enforce database design conventions
- Fluent Configuration: Easy-to-use fluent API for excluding entities and properties from rules
- Multiple DbContext Support: Test multiple DbContexts in a single test class
- In-Memory Testing: Includes a base class for easy in-memory SQLite database testing
Requirements
- .NET 10.0 or higher
Installation
dotnet add package Imagile.EntityFrameworkCore.Tests
Built-in Convention Rules
Design Rules
PrimaryKeysMustBeIntsRule
Validates that single-property primary keys are of type int or long. Skips owned entities and composite keys.
ProhibitGuidPrimaryKeysRule
Validates that single-property primary keys are not of type Guid. Skips owned entities and composite keys.
ProhibitNullableBooleansRule
Validates that no properties have type bool? (nullable boolean).
ProhibitNullableStringsRule
Validates that string properties are not nullable unless explicitly configured as required.
StringsMustHaveMaxLengthRule
Validates that all string properties have a maximum length configured via GetMaxLength().
Naming Rules
TableNamesMustBePluralRule
Validates that table names are plural (e.g., "Users", not "User").
TableNamesMustBePascalCaseRule
Validates that table names are PascalCase.
PropertyNamesMustBePascalCaseRule
Validates that property names are PascalCase.
ForeignKeysMustEndWithIdRule
Validates that foreign key properties end with "Id".
PrimaryKeyMustBeEntityNameIdRule
Validates that single-property primary keys follow the format EntityNameId (e.g., UserId for a User entity).
DateTimesMustEndWithDateRule
Validates that DateTime and DateTimeOffset properties end with "Date" (e.g., CreatedDate, ModifiedDate).
BooleansMustStartWithPrefixRule
Validates that Boolean properties start with "Is", "Has", "Are", or "Does" (e.g., IsActive, HasChildren).
GuidsMustEndWithUniqueRule
Validates that Guid properties (except primary and foreign keys) end with "Unique" (e.g., UserUnique).
EnumsMustEndWithTypeRule
Validates that Enum properties (except primary and foreign keys) end with "Type" (e.g., StatusType, RoleType).
Usage
Basic Usage
Create a test class that inherits from DbContextConventionTests:
using Imagile.EntityFrameworkCore.Tests;
using Microsoft.Data.Sqlite;
using Microsoft.EntityFrameworkCore;
public class MyDesignTests : DbContextConventionTests
{
protected override IEnumerable<DbContext> CreateContexts()
{
var connection = new SqliteConnection("DataSource=:memory:");
connection.Open();
var options = new DbContextOptionsBuilder<MyDbContext>()
.UseSqlite(connection)
.Options;
var context = new MyDbContext(options);
context.Database.EnsureCreated();
yield return context;
}
}
Configuring Exclusions
You can exclude entities or properties from specific rules or all rules:
public class MyDesignTests : DbContextConventionTests
{
protected override IEnumerable<DbContext> CreateContexts()
{
// ... create contexts
}
protected override void Configure(ConventionTestOptionsBuilder builder)
{
builder
// Exclude specific properties from a rule
.ForRule<ProhibitNullableStringsRule>(rule => rule
.ExcludeProperty<Employee, string?>(e => e.Department)
.ExcludeProperty<Employee, string?>(e => e.JobTitle))
// Exclude entire entities from a rule
.ForRule<StringsMustHaveMaxLengthRule>(rule => rule
.ExcludeEntity<AuditLog>())
// Exclude an entity from ALL rules
.ExcludeEntityFromAllRules<__EFMigrationsHistory>();
}
}
String-based Exclusions
You can also use string-based exclusions if you don't have compile-time access to the entity types:
protected override void Configure(ConventionTestOptionsBuilder builder)
{
builder
.ForRule<ProhibitNullableStringsRule>(rule => rule
.ExcludeProperty("Employee", "Department")
.ExcludeEntity("AuditLog"))
.ExcludeEntityFromAllRules("__EFMigrationsHistory");
}
Multiple DbContexts
Test multiple DbContexts in a single test class:
protected override IEnumerable<DbContext> CreateContexts()
{
// First context
var connection1 = new SqliteConnection("DataSource=:memory:");
connection1.Open();
var context1 = new CompanyDbContext(
new DbContextOptionsBuilder<CompanyDbContext>()
.UseSqlite(connection1)
.Options);
context1.Database.EnsureCreated();
yield return context1;
// Second context
var connection2 = new SqliteConnection("DataSource=:memory:");
connection2.Open();
var context2 = new SharedDbContext(
new DbContextOptionsBuilder<SharedDbContext>()
.UseSqlite(connection2)
.Options);
context2.Database.EnsureCreated();
yield return context2;
}
In-Memory Database Testing
The package includes an InMemoryDatabaseTest<TContext> base class for easy in-memory SQLite testing:
using Imagile.EntityFrameworkCore.Tests.Infrastructure;
using Microsoft.EntityFrameworkCore;
public class MyRepositoryTests : InMemoryDatabaseTest<MyDbContext>
{
protected override MyDbContext CreateContext(DbContextOptions<MyDbContext> options)
{
return new MyDbContext(options);
}
[Fact]
public async Task MyTest()
{
// Context is already initialized and ready to use
var entity = new MyEntity { Name = "Test" };
Context.MyEntities.Add(entity);
await Context.SaveChangesAsync();
// Assertions...
}
}
License
MIT
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net10.0 is compatible. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
-
net10.0
- FluentAssertions (>= 6.12.0)
- Humanizer.Core (>= 3.0.1)
- Microsoft.Data.Sqlite (>= 10.0.0)
- Microsoft.EntityFrameworkCore (>= 10.0.0)
- Microsoft.EntityFrameworkCore.Sqlite (>= 10.0.0)
- xunit (>= 2.9.3)
NuGet packages
This package is not used by any NuGet packages.
GitHub repositories
This package is not used by any popular GitHub repositories.
| Version | Downloads | Last Updated |
|---|---|---|
| 1.0.0 | 103 | 1/24/2026 |