Entity Framework Plus EF Core Interceptors with EF Plus
EF Plus provides its own interceptors that allow you to intercept commands, connections, and transactions executed by Entity Framework Core.
- DbCommandInterceptor: intercepts commands.
- DbConnectionInterceptor: intercepts connection events.
- DbTransactionInterceptor: intercepts transaction events.
If you are already familiar with EF Core interceptors, you might wonder why EF Plus provides its own implementation. After all, EF Core already includes official interceptors. See EF Core Interceptors.
There are three main reasons:
- EF Plus introduced interceptors before they were available in EF Core 3.
- They use the same syntax for adding them as EF6 Interceptors, making migration easier.
- They can be added after a
DbContexthas been created.
In most cases, we recommend using the official interceptors provided by EF Core.
However, some EF Plus features such as Query Hint and WhereBulkContains rely on EF Plus interceptors because they need to add an interceptor to an existing context after it has already been created.
For example, the QueryHint feature uses an interceptor to modify the SQL command generated by EF Core and append a query hint before the command is executed. To achieve this, EF Plus needs to be able to add an interceptor to a DbContext after it has already been created.
Interceptor Examples
The following examples show how to create an interceptor and how to register it globally or for a specific DbContext instance.
Create an Interceptor
To create an interceptor, simply create a class that inherits from either DbCommandInterceptor, DbConnectionInterceptor, or DbTransactionInterceptor, and override the methods you want to intercept.
For example:
// @nuget: Z.EntityFramework.Plus.EFCore using System.Data.Common; using Z.EntityFramework.Extensions; public class EFCommandInterceptor : DbCommandInterceptor { public override void NonQueryExecuting( DbCommand command, DbCommandInterceptionContext<int> interceptionContext) { base.NonQueryExecuting(command, interceptionContext); Console.WriteLine(command.CommandText); } }
You can override the following methods:
DbCommandInterceptorNonQueryExecutedNonQueryExecutingReaderExecutedReaderExecutingScalarExecutedScalarExecutingNonQueryErrorReaderErrorScalarError
DbConnectionInterceptorOpeningOpenedErrorClosingClosed
DbTransactionInterceptorCommittedDisposedErrorRolledBackStartedUsed
In the later examples, we provide complete runnable examples for each interceptor type and demonstrate all available methods in action.
Add an Interceptor Globally with DbInterception.Add
Once you have created your interceptor class, you can register it globally using the DbInterception.Add(interceptor) method, just like in EF6.
For example:
// @nuget: Z.EntityFramework.Plus.EFCore using System.Data.Common; using Z.EntityFramework.Extensions; DbInterception.Add(new EFCommandInterceptor()); DbInterception.Add(new EFConnectionInterceptor()); DbInterception.Add(new EFTransactionInterceptor());
Once registered, the interceptor logic will be applied to all existing and newly created DbContext instances.
Intercept Commands with DbCommandInterceptor
The DbCommandInterceptor allows you to intercept database commands executed by Entity Framework.
In this example, we log the SQL command text before it is executed:
// @nuget: Z.EntityFramework.Plus.EFCore using System.Data.Common; using Z.EntityFramework.Extensions; DbInterception.Add(new EFCommandInterceptor()); using var context = new AppDbContext(); var customers = context.Customers.ToList();
public class EFCommandInterceptor : DbCommandInterceptor { public override void ReaderExecuting( DbCommand command, DbCommandInterceptionContext<DbDataReader> interceptionContext) { Console.WriteLine(command.CommandText); base.ReaderExecuting(command, interceptionContext); } }
Output:
SELECT [c].[Id], [c].[Name] FROM [Customers] AS [c]
The DbCommandInterceptor also provides methods for intercepting non-query commands, scalar commands, and errors.
The online example contains a complete runnable example that overrides all available methods and shows the output generated for each intercepted event.
Intercept Connections with DbConnectionInterceptor
The DbConnectionInterceptor allows you to intercept connection events such as opening, closing, and connection errors.
In this example, we log a message when the database connection is opened:
// @nuget: Z.EntityFramework.Plus.EFCore using System.Data.Common; using Z.EntityFramework.Extensions; DbInterception.Add(new EFConnectionInterceptor()); using var context = new AppDbContext(); var customers = context.Customers.ToList();
public class EFConnectionInterceptor : DbConnectionInterceptor { public override void Opened( DbConnection connection, DbConnectionInterceptionContext interceptionContext) { Console.WriteLine("Connection opened."); base.Opened(connection, interceptionContext); } }
Output:
Connection opened.
The DbConnectionInterceptor also provides methods for intercepting connection opening, closing, closed, and error events.
The online example contains a complete runnable example that overrides all available methods and shows the output generated for each intercepted event.
Intercept Transactions with DbTransactionInterceptor
The DbTransactionInterceptor allows you to intercept transaction events such as transaction start, commit, rollback, and errors.
In this example, we log a message when a transaction is committed:
// @nuget: Z.EntityFramework.Plus.EFCore using System.Data.Common; using Z.EntityFramework.Extensions; DbInterception.Add(new EFTransactionInterceptor()); using var context = new AppDbContext(); using var transaction = context.Database.BeginTransaction(); context.Customers.Add(new Customer { Name = "Customer A" }); context.SaveChanges(); transaction.Commit();
public class EFTransactionInterceptor : DbTransactionInterceptor { public override void Committed( DbTransaction transaction, DbTransactionInterceptionContext interceptionContext) { Console.WriteLine("Transaction committed."); base.Committed(transaction, interceptionContext); } }
Output:
Transaction committed.
The DbTransactionInterceptor also provides methods for intercepting transaction start, rollback, disposal, usage, and error events.
The online example contains a complete runnable example that overrides all available methods and shows the output generated for each intercepted event.
Summary
In this article, you learned how to use EF Plus interceptors to intercept commands, connections, and transactions executed by Entity Framework Core.
You also learned how to:
- Create a custom interceptor by inheriting from
DbCommandInterceptor,DbConnectionInterceptor, orDbTransactionInterceptor. - Register an interceptor globally with
DbInterception.Add. - Intercept command, connection, and transaction events.
In most cases, we recommend using the official interceptors provided by EF Core. However, EF Plus interceptors remain useful for scenarios where an interceptor needs to be added after a DbContext has already been created, which is required by some EF Plus features such as QueryHint and WhereBulkContains.
ZZZ Projects