Entity Framework Core Audit Trail With Audit.Net
Hirusha Fernando
Posted on March 19, 2024
What is Audit Trail?
Audit trail is a record of all user activities within an application. It captures details like who accessed the application, what changes were made, and when they occurred. By maintaining an audit trail, developers can track data modifications, identify unauthorized access, and ensure compliance with industry regulations.
Audit.Net
Audit.NET is Nuget package that can use to implement Audit Trail in dotnet applications. Instead of implement an audit trial manually, we can use this to easily add audit trial to our application.
For Entity Framework Core, they have provided a package called Audit.EntityFramework.Core. In this blog post, let's see how to use this package to implement audit trial in ASP.Net Core application with Entity Framework Core.
Let's Start
First clone this github repository and open project in Visual Studio. I will implement audit trial to this blazor project. In this article I use Blazor Server App using dotnet 6.0.
git clone git@github.com:HRS0986/AuditTrialDemo.git
After opened, you can see folder structure like this
Now let's install Audit.EntityFramework.Core package
They have provided more than one ways to implement audit trial with this package. I will do this in the most easiest way. After installing, go to ApplicationDbContext.
// Data.ApplicationDbContext.cs - Before
public class ApplicationDbContext : DbContext
{
public virtual DbSet<Book> Books { get; set; }
public ApplicationDbContext(DbContextOptions<ApplicationDbContext> options) : base(options) { }
protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder) { }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Book>(entity =>
{
entity.Property(e => e.Id).IsRequired().UseIdentityColumn();
entity.Property(e => e.Title).IsRequired();
entity.Property(e => e.Description).IsRequired();
entity.Property(e => e.Author).IsRequired();
});
}
}
We have to inerit our ApplicationDbContext class from the AuditDbContext instead of DbContext.
// Data.ApplicationDbContext.cs - After
public class ApplicationDbContext : AuditDbContext
{
public virtual DbSet<Book> Books { get; set; }
public ApplicationDbContext(DbContextOptions<ApplicationDbContext> options) : base(options) { }
protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder) { }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Book>(entity =>
{
entity.Property(e => e.Id).IsRequired().UseIdentityColumn();
entity.Property(e => e.Title).IsRequired();
entity.Property(e => e.Description).IsRequired();
entity.Property(e => e.Author).IsRequired();
});
}
}
Then run the project. Do some action. Delete book, Add new book or Update book. You can see a json file in the project root. If you open that file, you can see a json object like this.
Now let's create separete folder for audit logs and add configurations to write audit logs in that folder. Add this configuration to program.cs Replace YOUR_FOLDER_PATH with your foder path where you want to save your audit logs. If you want to chage the file name of the json. change {auditEvent.Environment.UserName}_{DateTime.Now.Ticks}.json to you file name
// Program.cs
Audit.Core.Configuration.Setup()
.UseFileLogProvider(config => config
.DirectoryBuilder(_ => $@"YOUR_FOLDER_PATH\")
.FilenameBuilder(auditEvent => $"{auditEvent.Environment.UserName}_{DateTime.Now.Ticks}.json"));
Now our audit trial is working. But some times when your perform update action, the OriginalValue and the NewValue properties can contain same NewValue. This is not what we want. To fix this simple put [AuditDbContext(ReloadDatabaseValues = true)] attribute on the ApplicationDbContext Class like this.
[AuditDbContext(ReloadDatabaseValues = true)]
public class ApplicationDbContext : AuditDbContext
{
public virtual DbSet<Book> Books { get; set; }
...
This is the easiest way to use Audit.EntityFramework.Core package. You can customize this as you want. They have provided many options with this. If you read their documentation, you can find more details. That's all for now. Happy Coding !
If this blog is helpful to you, don't forget to give a like
You can reach me on
Posted on March 19, 2024
Join Our Newsletter. No Spam, Only the good stuff.
Sign up to receive the latest update from our blog.